Listbox
ImplementedInline ARIA selection widget with full keyboard support (WAI-ARIA Listbox pattern 1.2). Single and multiple selection modes, option groups, and custom option rendering.
components/molecules/Listbox/Listbox.tsxAlways-visible ARIA listbox (WAI-ARIA 1.2 pattern) for single and multiple selection. Full keyboard navigation, option groups, and custom option rendering. Use Select or SearchSelect when you need a collapsed trigger + popup instead.
Listbox
Form selection molecule
An inline selection list with role="listbox", aria-activedescendant tracking, wrap-around arrow navigation, and per-option disabled state. Controlled via value/onChange; ariaLabel is required for the accessible name.
- General admission
- VIPBackstage access
- Early bird
- Press
- Friday
- Saturday
- Sunday
Props
Listbox
optionsListboxOption[]—Array of options with value, label, disabled, group, description
mode'single' | 'multiple''single'Single or multi-select mode
valuestring | string[]—Selected value(s)
defaultValuestring | string[]—Initial uncontrolled value
onChange(value: string | string[]) => void—Callback when selection changes
size'sm' | 'md' | 'lg''md'Size variant
variant'default' | 'bordered' | 'flush''default'Visual style variant
emptyMessagestring'No options'Message shown when options array is empty
labelsListboxLabels—i18n label overrides object (step-6 source fixes). labels.empty replaces the English-default emptyMessage ('No options') on localized surfaces — prefer it over overriding emptyMessage directly on /fr routes.
disabledbooleanfalseDisable the entire listbox
ariaLabelstring—Accessible label for the listbox
ariaLabelledBystring—ID of element that labels this listbox
maxHeightnumber240Max height in pixels before scrolling
groupsArray<{ id: string; label: string }>—Option group headers
autoFocusFirstOptionbooleanfalseAuto-focus first option on mount
renderOption(option, state) => ReactNode—Custom option renderer
localestring—lang attribute for per-option language annotation
classNamestring—Additional CSS classes
idstring—DOM id
<Listbox />Accessibility
Keyboard
1 ruleARIA
1 ruleUsage
Import
import { Listbox } from "@epasslive/design-system"Example 1
<Listbox options={options} value={selected} onChange={setSelected} ariaLabel="Ticket type" />Example 2
<Listbox options={days} mode="multiple" value={picked} onChange={setPicked} ariaLabel="Event days" />Anti-patterns
— Do not use for collapsed trigger+popup selection — Select or SearchSelect own that pattern
— Never omit value, onChange, or ariaLabel — the component is controlled and requires an accessible name