Skip to main content
BEEQ Option List component overview
bq-option-list is the required wrapper for bq-option and bq-option-group elements. It sets the role="listbox" context, handles keyboard and click events from child options, and emits a single bqSelect event with the selected item’s value back to the parent component.
bq-option-list is a structural container — it does not render any visible UI of its own. It is used internally by higher-level components such as bq-select and bq-dropdown. Use it directly only when you are building a custom listbox-based control.

When to use

Use option list when
  • You are composing a custom dropdown, command palette, or navigation menu from bq-option items
  • You need a role="listbox" container that bubbles selection events from child options to your component logic
  • You want to combine flat options with bq-option-group sections in the same list

Do not use option list when
  • You are using bq-select or bq-dropdown — these components manage bq-option-list internally
  • You need a multi-select list with checkboxes — use form controls such as bq-checkbox directly
  • The items are primarily navigational links rather than discrete selectable choices

Option List patterns

Flat list

A plain sequence of bq-option items. Use when all choices belong to the same category and no visual separation is needed.

Grouped list

One or more bq-option-group containers inside the list. Use when choices fall into distinct named categories that help users scan faster.

Mixed list

Ungrouped options above or below grouped sections. Use when a “pinned” set of common choices (for example, “Recently used”) should appear before the full categorized list.

Anatomy

BEEQ Option List component anatomy
bq-option-list is a single flex column container that holds slotted option items or option groups. It has no visual chrome of its own — the border, shadow, and background typically come from the enclosing panel or dropdown trigger.
PartElementDescription
1BaseThe internal <div> that stacks slotted options vertically with consistent gap
2Option itemsbq-option or bq-option-group elements placed in the default slot

Design guidelines

Use with a containing surface

bq-option-list provides layout and interaction semantics but no background or border. Wrap it in a surface element — typically a panel, popover, or card — that provides the visual boundary users associate with a dropdown or list.
When used inside bq-select or bq-dropdown, the containing surface is handled automatically. The guidelines here apply when you are building a custom container from scratch.

Vertical rhythm

The gap between items is controlled by the --bq-option-group--gapY-list CSS custom property. The default is tight (var(--bq-spacing-xs)) to keep the list compact. Increase it only when items are taller than a single text line or when the list is used in a context with generous surrounding whitespace.

Accessible label

The ariaLabel prop (rendered as aria-label on the host element) names the listbox for screen readers. The default value is "Options". Override it with a more specific label when the context makes the default ambiguous — for example, "Navigation links" or "Assignees".

Usage

Flat list

A simple list with no groups. Each bq-option carries a value so the parent can identify the selection via the bqSelect event.
To use grouped sections, place bq-option-group elements inside bq-option-list. The bqSelect event still bubbles from whichever bq-option the user activates. See the Option Group page for full grouped list examples including header prefix and suffix slots.

Options

Custom accessible label

Override aria-label when the default "Options" is too generic for the context. A specific label helps screen reader users understand the purpose of the list before navigating into it.

Best practices

DoAlways place bq-option and bq-option-group directly inside bq-option-list — the component listens for bqClick and bqEnter events from child options and will not receive them if additional wrapper elements break the event path.

Don’tWrap options in arbitrary <div> or <span> elements inside the list. Non-option wrappers break the bqClick/bqEnter event delegation that bq-option-list relies on to emit bqSelect.

DoOverride aria-label with a descriptive phrase when the list is not the only role="listbox" on the page or when the default "Options" does not communicate the list’s purpose.

Don’tLeave the default aria-label="Options" on multiple lists within the same view without making each one contextually unique — screen reader users navigating by landmark will see identical labels and cannot tell the lists apart.

DoListen to the bqSelect event on bq-option-list rather than individual bqClick events on each bq-option. The list normalises both click and Enter-key activations into a single bqSelect event with a consistent { value, item } payload.

Don’tAttach separate bqClick listeners to every bq-option when you only need the selected value — bq-option-list already aggregates these and emitting redundant handlers increases the chance of inconsistent state.

DoUse bq-option-group to divide a long list into named sections when the number of items makes scanning difficult.

Don’tRender dozens of flat options without any grouping. An ungrouped list longer than around eight items becomes hard to scan — users have to read every item individually rather than jumping to the relevant category.

Accessibility

bq-option-list sets role="listbox" on its host element during componentDidLoad. This establishes the ARIA container that child bq-option elements (which carry role="option") require in order to form a valid accessible list. The ariaLabel prop is reflected as aria-label on the host and defaults to "Options". It names the listbox for assistive technologies. As a developer, you are responsible for:
  • Providing a meaningful ariaLabel when the default is ambiguous. Screen readers announce the listbox name before a user navigates into it, so a specific label (“Assignees”, “Color palette”) is more useful than the generic default.
  • Placing only bq-option and bq-option-group elements inside the list — inserting non-option elements breaks the role="listbox" / role="option" relationship that assistive technologies expect.
  • Managing focus when the list is shown or hidden — bq-option-list does not manage focus automatically. If you are building a custom dropdown, move focus to the first option when the list opens and return it to the trigger when it closes.

API reference

Properties

PropertyAttributeDescriptionTypeDefault
ariaLabelaria-labelAccessible label for the listboxstring'Options'

Events

EventDescriptionType
bqSelectEmitted when an option is selected via click or Enter keyCustomEvent<{ value: string; item: HTMLBqOptionElement }>

Slots

SlotDescription
(default)bq-option and bq-option-group items

Shadow parts

PartDescription
baseThe internal <div> wrapper that stacks slotted items vertically

CSS custom properties

VariableDescriptionDefault
--bq-option-group--gapY-listVertical gap between items in the listvar(--bq-spacing-xs)

Resources

Interactive playground

Explore option list variants and states in Storybook

Source code

View the component source on GitHub