Combobox
A composable, accessible Combobox component for modern React applications.
tsx
import { Combobox } from '@nofinite/nui';Interactive Preview
Loading preview...
A searchable dropdown input component that allows users to filter and select options from a list. Supports controlled/uncontrolled usage, keyboard navigation, icons, custom rendering, filtering, and accessibility-compliant listbox behavior.
Usage
Basic Combobox
tsx
import { Combobox } from '@nofinite/nui';
<Combobox
options={[
{ label: "React", value: "react" },
{ label: "Vue", value: "vue" },
{ label: "Angular", value: "angular" }
]}
/>Controlled Combobox
tsx
const [value, setValue] = useState("");
<Combobox
value={value}
onChange={setValue}
options={options}
/>Combobox with Icons
tsx
<Combobox
leftIcon={<Icon />}
rightIcon={<Icon />}
options={options}
/>Custom Option Rendering
tsx
<Combobox
options={options}
renderOption={(opt, active) => (
<span style={{ fontWeight: active ? 600 : 400 }}>
{opt.label}
</span>
)}
/>Custom Filter
tsx
<Combobox
options={options}
filter={(input, option) =>
option.label.toLowerCase().startsWith(input.toLowerCase())
}
/>Variants
Combobox supports interaction-based variants.
tsx
<Combobox options={options} /> // Default combobox
<Combobox disabled options={options} /> // Disabled combobox
<Combobox leftIcon={<Icon />} /> // With icons
<Combobox renderOption={() => {}} /> // Custom rendered optionsAvailable variants:
default– Standard searchable comboboxdisabled– Non-interactive comboboxicon– Combobox with input iconscustom-render– Combobox with custom option rendering
Guidelines:
- Use
defaultfor general dropdown selection. - Use
disabledto prevent interaction when unavailable. - Use
iconfor contextual affordances. - Use
custom-renderfor complex option UI.
States
| State | Description |
|---|---|
default | Closed combobox |
open | Dropdown visible |
active | Keyboard-highlighted option |
selected | Currently selected option |
empty | No results state |
Accessibility
-
Uses ARIA combobox + listbox pattern
-
Supports full keyboard navigation
- Arrow keys for navigation
- Enter for selection
- Escape to close
-
aria-expanded,aria-controls, andaria-activedescendantensure screen reader support -
Click-outside handling prevents accidental focus loss
-
Option selection correctly updates
aria-selected
Best Practices
Do
- Use combobox for searchable selections
- Provide meaningful empty state message
- Use custom filter for large datasets
- Keep option labels concise
- Use icons for recognition
Don’t
- Use combobox for very small lists without search need
- Hide essential information inside custom renderers
- Disable keyboard navigation
- Overload options with long content
API Reference
| Prop | Type | Default | Description |
|---|---|---|---|
data* | ComboboxOption[] | — | — |
value | string | — | Controlled value of the combobox |
defaultValue | string | — | Initial uncontrolled value |
onChange | ((value: string) => void) | — | Callback fired when an option is selected |
placeholder | string | Select... | — |
disabled | boolean | false | — |
emptyMessage | string | No results found | Message displayed when filtering returns zero results |
filter | ((input: string, option: ComboboxOption) => boolean) | — | Custom filter function. Defaults to simple substring matching on the label. |
leftIcon | ReactNode | — | — |
rightIcon | ReactNode | — | — |
renderOption | ((option: ComboboxOption, active: boolean) => ReactNode) | — | Custom renderer for the entire option row |
renderOptionIcon | ((option: ComboboxOption) => ReactNode) | — | Custom renderer strictly for the option's icon |