{"slug":"select","title":"Select","description":"Using the select machine in your project.","contentType":"component","framework":"react","content":"A Select component allows users pick a value from predefined options.\n\n## Resources\n\n\n[Latest version: v1.31.0](https://www.npmjs.com/package/@zag-js/select)\n[Logic Visualizer](https://zag-visualizer.vercel.app/select)\n[Source Code](https://github.com/chakra-ui/zag/tree/main/packages/machines/select)\n\n\n\n**Features**\n\n- Support for selecting a single or multiple option\n- Keyboard support for opening the listbox using the arrow keys, including\n  automatically focusing the first or last item.\n- Support for looping keyboard navigation.\n- Support for selecting an item on blur.\n- Typeahead to allow selecting options by typing text, even without opening the\n  listbox\n- Support for Right to Left direction.\n\n## Installation\n\nTo use the select machine in your project, run the following command in your\ncommand line:\n\n```bash\nnpm install @zag-js/select @zag-js/react\n# or\nyarn add @zag-js/select @zag-js/react\n```\n\n## Anatomy\n\nTo set up the select correctly, you'll need to understand its anatomy and how we\nname its parts.\n\n> Each part includes a `data-part` attribute to help identify them in the DOM.\n\n\n\n## Usage\n\nFirst, import the select package into your project\n\n```jsx\nimport * as select from \"@zag-js/select\"\n```\n\nThe select package exports these functions:\n\n- `machine` — The state machine logic for the select.\n- `connect` — The function that translates the machine's state to JSX attributes\n  and event handlers.\n- `collection` - The function that creates a\n  [collection interface](/overview/collection) from an array of items.\n\n> You'll need to provide a unique `id` to the `useMachine` hook. This is used to\n> ensure that every part has a unique identifier.\n\nNext, import the required hooks and functions for your framework and use the\nselect machine in your project 🔥\n\n```jsx\nimport * as select from \"@zag-js/select\"\nimport { useMachine, normalizeProps, Portal } from \"@zag-js/react\"\nimport { useId, useRef } from \"react\"\n\nconst selectData = [\n  { label: \"Nigeria\", value: \"NG\" },\n  { label: \"Japan\", value: \"JP\" },\n  { label: \"Korea\", value: \"KO\" },\n  { label: \"Kenya\", value: \"KE\" },\n  { label: \"United Kingdom\", value: \"UK\" },\n  { label: \"Ghana\", value: \"GH\" },\n  { label: \"Uganda\", value: \"UG\" },\n]\n\nexport function Select() {\n  const collection = select.collection({\n    items: selectData,\n    itemToString: (item) => item.label,\n    itemToValue: (item) => item.value,\n  })\n\n  const service = useMachine(select.machine, {\n    id: useId(),\n    collection,\n  })\n\n  const api = select.connect(service, normalizeProps)\n\n  return (\n    <div {...api.getRootProps()}>\n      <div {...api.getControlProps()}>\n        <label {...api.getLabelProps()}>Label</label>\n        <button {...api.getTriggerProps()}>\n          {api.valueAsString || \"Select option\"}\n        </button>\n      </div>\n\n      <Portal>\n        <div {...api.getPositionerProps()}>\n          <ul {...api.getContentProps()}>\n            {selectData.map((item) => (\n              <li key={item.value} {...api.getItemProps({ item })}>\n                <span>{item.label}</span>\n                <span {...api.getItemIndicatorProps({ item })}>✓</span>\n              </li>\n            ))}\n          </ul>\n        </div>\n      </Portal>\n    </div>\n  )\n}\n```\n\n### Setting the initial value\n\nUse the `defaultValue` property to set the initial value of the select.\n\n> The `value` property must be an array of strings. If selecting a single value,\n> pass an array with a single string.\n\n```jsx {13}\nconst collection = select.collection({\n  items: [\n    { label: \"Nigeria\", value: \"ng\" },\n    { label: \"Ghana\", value: \"gh\" },\n    { label: \"Kenya\", value: \"ke\" },\n    //...\n  ],\n})\n\nconst service = useMachine(select.machine, {\n  id: useId(),\n  collection,\n  defaultValue: [\"ng\"],\n})\n```\n\n### Selecting multiple values\n\nTo allow selecting multiple values, set the `multiple` property to `true`.\n\n```jsx {5}\nconst service = useMachine(select.machine, {\n  id: useId(),\n  collection,\n  multiple: true,\n})\n```\n\n### Using a custom object format\n\nBy default, the select collection expects an array of items with `label` and\n`value` properties. To use a custom object format, pass the `itemToString` and\n`itemToValue` properties to the collection function.\n\n- `itemToString` — A function that returns the string representation of an item.\n  Used to compare items when filtering.\n- `itemToValue` — A function that returns the unique value of an item.\n- `itemToDisabled` — A function that returns the disabled state of an item.\n- `groupBy` — A function that returns the group of an item.\n- `groupSort` — An array or function to sort the groups.\n\n```jsx\nconst collection = select.collection({\n  // custom object format\n  items: [\n    { id: 1, fruit: \"Banana\", available: true, quantity: 10 },\n    { id: 2, fruit: \"Apple\", available: false, quantity: 5 },\n    { id: 3, fruit: \"Orange\", available: true, quantity: 3 },\n    //...\n  ],\n  // convert item to string\n  itemToString(item) {\n    return item.fruit\n  },\n  // convert item to value\n  itemToValue(item) {\n    return item.id\n  },\n  // convert item to disabled state\n  itemToDisabled(item) {\n    return !item.available || item.quantity === 0\n  },\n  groupBy(item) {\n    return item.available ? \"available\" : \"unavailable\"\n  },\n  groupSort: [\"available\", \"unavailable\"],\n})\n\n// use the collection\nconst service = useMachine(select.machine, {\n  id: useId(),\n  collection,\n})\n```\n\n### Usage within a form\n\nTo use select within a form, you'll need to:\n\n- Pass the `name` property to the select machine's context\n- Render a hidden `select` element using `api.getSelectProps()`\n\n```jsx\nimport * as select from \"@zag-js/select\"\nimport { useMachine, normalizeProps, Portal } from \"@zag-js/react\"\nimport { useId } from \"react\"\n\nconst selectData = [\n  { label: \"Nigeria\", value: \"NG\" },\n  { label: \"Japan\", value: \"JP\" },\n  { label: \"Korea\", value: \"KO\" },\n  { label: \"Kenya\", value: \"KE\" },\n  { label: \"United Kingdom\", value: \"UK\" },\n  { label: \"Ghana\", value: \"GH\" },\n  { label: \"Uganda\", value: \"UG\" },\n]\n\nexport function SelectWithForm() {\n  const service = useMachine(select.machine, {\n    id: useId(),\n    collection: select.collection({ items: selectData }),\n    name: \"country\",\n  })\n\n  const api = select.connect(service, normalizeProps)\n\n  return (\n    <form>\n      {/* Hidden select */}\n      <select {...api.getHiddenSelectProps()}>\n        {selectData.map((option) => (\n          <option key={option.value} value={option.value}>\n            {option.label}\n          </option>\n        ))}\n      </select>\n\n      {/* Custom Select */}\n      <div {...api.getControlProps()}>\n        <label {...api.getLabelProps()}>Label</label>\n        <button type=\"button\" {...api.getTriggerProps()}>\n          <span>{api.valueAsString || \"Select option\"}</span>\n          <CaretIcon />\n        </button>\n      </div>\n\n      <Portal>\n        <div {...api.getPositionerProps()}>\n          <ul {...api.getContentProps()}>\n            {selectData.map((item) => (\n              <li key={item.value} {...api.getItemProps({ item })}>\n                <span>{item.label}</span>\n                <span {...api.getItemIndicatorProps({ item })}>✓</span>\n              </li>\n            ))}\n          </ul>\n        </div>\n      </Portal>\n    </form>\n  )\n}\n```\n\n### Disabling the select\n\nTo disable the select, set the `disabled` property in the machine's context to\n`true`.\n\n```jsx {4}\nconst service = useMachine(select.machine, {\n  id: useId(),\n  collection,\n  disabled: true,\n})\n```\n\n### Disabling an item\n\nTo make a combobox option disabled, pass the `isItemDisabled` property to the\ncollection function.\n\n```jsx {3-4}\nconst collection = select.collection({\n  items: countries,\n  isItemDisabled(item) {\n    return item.disabled\n  },\n})\n\nconst service = useMachine(select.machine, {\n  id: useId(),\n  collection,\n})\n```\n\n### Close on select\n\nThis behaviour ensures that the menu is closed when an item is selected and is\n`true` by default. It's only concerned with when an item is selected with\npointer, space key or enter key.\n\nTo disable the behaviour, set the `closeOnSelect` property in the machine's\ncontext to `false`.\n\n```jsx {4}\nconst service = useMachine(select.machine, {\n  id: useId(),\n  collection,\n  closeOnSelect: false,\n})\n```\n\n### Looping the keyboard navigation\n\nWhen navigating with the select using the arrow down and up keys, the select\nstops at the first and last options. If you need want the navigation to loop\nback to the first or last option, set the `loop: true` in the machine's context.\n\n```jsx {4}\nconst service = useMachine(select.machine, {\n  id: useId(),\n  collection,\n  loop: true,\n})\n```\n\n### Listening for highlight changes\n\nWhen an item is highlighted with the pointer or keyboard, use the\n`onHighlightChange` to listen for the change and do something with it.\n\n```jsx {3-6}\nconst service = useMachine(select.machine, {\n  id: useId(),\n  onHighlightChange(details) {\n    // details => { highlightedValue: string | null, highlightedItem: CollectionItem | null }\n    console.log(details)\n  },\n})\n```\n\n### Listening for selection changes\n\nWhen an item is selected, use the `onValueChange` property to listen for the\nchange and do something with it.\n\n```jsx {4-6}\nconst service = useMachine(select.machine, {\n  id: useId(),\n  collection,\n  onValueChange(details) {\n    // details => { value: string[], items: Item[] }\n    console.log(details)\n  },\n})\n```\n\n### Listening for open and close events\n\nWhen the select is opened or closed, the `onOpenChange` callback is called. You\ncan listen for these events and do something with it.\n\n```jsx {4-7}\nconst service = useMachine(select.machine, {\n  id: useId(),\n  collection,\n  onOpenChange(details) {\n    // details => { open: boolean }\n    console.log(\"Select opened\")\n  },\n})\n```\n\n### Grouping items\n\nThe select component relies explicitly on the collection. This means the\nrendered items much match the items in the collection.\n\nTo ensure this, you need to pass the `groupBy` option to the collection\nfunction.\n\n```tsx\nconst collection = select.collection({\n  items: [],\n  itemToValue: (item) => item.value,\n  itemToString: (item) => item.label,\n  groupBy: (item) => item.group || \"default\",\n})\n```\n\nThen, use the `collection.group()` method to render the grouped items.\n\n```tsx\n{\n  collection.group().map(([group, items], index) => (\n    <div key={`${group}-${index}`}>\n      <div {...api.getItemGroupProps({ id: group })}>{group}</div>\n      {items.map((item, index) => (\n        <div key={`${item.value}-${index}`} {...api.getItemProps({ item })}>\n          <span {...api.getItemTextProps({ item })}>{item.label}</span>\n          <span {...api.getItemIndicatorProps({ item })}>✓</span>\n        </div>\n      ))}\n    </div>\n  ))\n}\n```\n\n### Usage with large data\n\nCombine the select machine with the virtualization library like `react-window`\nor `@tanstack/react-virtual` to handle large data.\n\nHere's an example using `@tanstack/react-virtual`:\n\n```jsx\nfunction Demo() {\n  const selectData = []\n\n  const contentRef = useRef(null)\n\n  const rowVirtualizer = useVirtualizer({\n    count: selectData.length,\n    getScrollElement: () => contentRef.current,\n    estimateSize: () => 32,\n  })\n\n  const service = useMachine(select.machine, {\n    id: useId(),\n    collection,\n    scrollToIndexFn(details) {\n      rowVirtualizer.scrollToIndex(details.index, {\n        align: \"center\",\n        behavior: \"auto\",\n      })\n    },\n  })\n\n  const api = select.connect(service, normalizeProps)\n\n  return (\n    <div {...api.getRootProps()}>\n      {/* ... */}\n      <Portal>\n        <div {...api.getPositionerProps()}>\n          <div ref={contentRef} {...api.getContentProps()}>\n            <div\n              style={{\n                height: `${rowVirtualizer.getTotalSize()}px`,\n                width: \"100%\",\n                position: \"relative\",\n              }}\n            >\n              {rowVirtualizer.getVirtualItems().map((virtualItem) => {\n                const item = selectData[virtualItem.index]\n                return (\n                  <div\n                    key={item.value}\n                    {...api.getItemProps({ item })}\n                    style={{\n                      position: \"absolute\",\n                      top: 0,\n                      left: 0,\n                      width: \"100%\",\n                      height: `${virtualItem.size}px`,\n                      transform: `translateY(${virtualItem.start}px)`,\n                      whiteSpace: \"nowrap\",\n                      overflow: \"hidden\",\n                      textOverflow: \"ellipsis\",\n                    }}\n                  >\n                    <span>{item.label}</span>\n                    <span {...api.getItemIndicatorProps({ item })}>✓</span>\n                  </div>\n                )\n              })}\n            </div>\n          </div>\n        </div>\n      </Portal>\n    </div>\n  )\n}\n```\n\n### Usage within dialog\n\nWhen using the select within a dialog, avoid rendering the select in a `Portal`\nor `Teleport`. This is because the dialog will trap focus within it, and the\nselect will be rendered outside the dialog.\n\n## Styling guide\n\nEarlier, we mentioned that each select part has a `data-part` attribute added to\nthem to select and style them in the DOM.\n\n### Open and closed state\n\nWhen the select is open, the trigger and content is given a `data-state`\nattribute.\n\n```css\n[data-part=\"trigger\"][data-state=\"open|closed\"] {\n  /* styles for open or closed state */\n}\n\n[data-part=\"content\"][data-state=\"open|closed\"] {\n  /* styles for open or closed state */\n}\n```\n\n### Selected state\n\nItems are given a `data-state` attribute, indicating whether they are selected.\n\n```css\n[data-part=\"item\"][data-state=\"checked|unchecked\"] {\n  /* styles for selected or unselected state */\n}\n```\n\n### Highlighted state\n\nWhen an item is highlighted, via keyboard navigation or pointer, it is given a\n`data-highlighted` attribute.\n\n```css\n[data-part=\"item\"][data-highlighted] {\n  /* styles for highlighted state */\n}\n```\n\n### Invalid state\n\nWhen the select is invalid, the label and trigger is given a `data-invalid`\nattribute.\n\n```css\n[data-part=\"label\"][data-invalid] {\n  /* styles for invalid state */\n}\n\n[data-part=\"trigger\"][data-invalid] {\n  /* styles for invalid state */\n}\n```\n\n### Disabled state\n\nWhen the select is disabled, the trigger and label is given a `data-disabled`\nattribute.\n\n```css\n[data-part=\"trigger\"][data-disabled] {\n  /* styles for disabled select state */\n}\n\n[data-part=\"label\"][data-disabled] {\n  /* styles for disabled label state */\n}\n\n[data-part=\"item\"][data-disabled] {\n  /* styles for disabled option state */\n}\n```\n\n> Optionally, when an item is disabled, it is given a `data-disabled` attribute.\n\n### Empty state\n\nWhen no option is selected, the trigger is given a `data-placeholder-shown`\nattribute.\n\n```css\n[data-part=\"trigger\"][data-placeholder-shown] {\n  /* styles for empty select state */\n}\n```\n\n## Methods and Properties\n\n### Machine Context\n\nThe select machine exposes the following context properties:\n\n**`collection`**\nType: `ListCollection<T>`\nDescription: The item collection\n\n**`ids`**\nType: `Partial<{ root: string; content: string; control: string; trigger: string; clearTrigger: string; label: string; hiddenSelect: string; positioner: string; item: (id: string | number) => string; itemGroup: (id: string | number) => string; itemGroupLabel: (id: string | number) => string; }>`\nDescription: The ids of the elements in the select. Useful for composition.\n\n**`name`**\nType: `string`\nDescription: The `name` attribute of the underlying select.\n\n**`form`**\nType: `string`\nDescription: The associate form of the underlying select.\n\n**`disabled`**\nType: `boolean`\nDescription: Whether the select is disabled\n\n**`invalid`**\nType: `boolean`\nDescription: Whether the select is invalid\n\n**`readOnly`**\nType: `boolean`\nDescription: Whether the select is read-only\n\n**`required`**\nType: `boolean`\nDescription: Whether the select is required\n\n**`closeOnSelect`**\nType: `boolean`\nDescription: Whether the select should close after an item is selected\n\n**`onSelect`**\nType: `(details: SelectionDetails) => void`\nDescription: Function called when an item is selected\n\n**`onHighlightChange`**\nType: `(details: HighlightChangeDetails<T>) => void`\nDescription: The callback fired when the highlighted item changes.\n\n**`onValueChange`**\nType: `(details: ValueChangeDetails<T>) => void`\nDescription: The callback fired when the selected item changes.\n\n**`onOpenChange`**\nType: `(details: OpenChangeDetails) => void`\nDescription: Function called when the popup is opened\n\n**`positioning`**\nType: `PositioningOptions`\nDescription: The positioning options of the menu.\n\n**`value`**\nType: `string[]`\nDescription: The controlled keys of the selected items\n\n**`defaultValue`**\nType: `string[]`\nDescription: The initial default value of the select when rendered.\nUse when you don't need to control the value of the select.\n\n**`highlightedValue`**\nType: `string`\nDescription: The controlled key of the highlighted item\n\n**`defaultHighlightedValue`**\nType: `string`\nDescription: The initial value of the highlighted item when opened.\nUse when you don't need to control the highlighted value of the select.\n\n**`loopFocus`**\nType: `boolean`\nDescription: Whether to loop the keyboard navigation through the options\n\n**`multiple`**\nType: `boolean`\nDescription: Whether to allow multiple selection\n\n**`open`**\nType: `boolean`\nDescription: Whether the select menu is open\n\n**`defaultOpen`**\nType: `boolean`\nDescription: Whether the select's open state is controlled by the user\n\n**`scrollToIndexFn`**\nType: `(details: ScrollToIndexDetails) => void`\nDescription: Function to scroll to a specific index\n\n**`composite`**\nType: `boolean`\nDescription: Whether the select is a composed with other composite widgets like tabs or combobox\n\n**`deselectable`**\nType: `boolean`\nDescription: Whether the value can be cleared by clicking the selected item.\n\n**Note:** this is only applicable for single selection\n\n**`dir`**\nType: `\"ltr\" | \"rtl\"`\nDescription: The document's text/writing direction.\n\n**`id`**\nType: `string`\nDescription: The unique identifier of the machine.\n\n**`getRootNode`**\nType: `() => ShadowRoot | Node | Document`\nDescription: A root node to correctly resolve document in custom environments. E.x.: Iframes, Electron.\n\n**`onPointerDownOutside`**\nType: `(event: PointerDownOutsideEvent) => void`\nDescription: Function called when the pointer is pressed down outside the component\n\n**`onFocusOutside`**\nType: `(event: FocusOutsideEvent) => void`\nDescription: Function called when the focus is moved outside the component\n\n**`onInteractOutside`**\nType: `(event: InteractOutsideEvent) => void`\nDescription: Function called when an interaction happens outside the component\n\n### Machine API\n\nThe select `api` exposes the following methods:\n\n**`focused`**\nType: `boolean`\nDescription: Whether the select is focused\n\n**`open`**\nType: `boolean`\nDescription: Whether the select is open\n\n**`empty`**\nType: `boolean`\nDescription: Whether the select value is empty\n\n**`highlightedValue`**\nType: `string`\nDescription: The value of the highlighted item\n\n**`highlightedItem`**\nType: `V`\nDescription: The highlighted item\n\n**`setHighlightValue`**\nType: `(value: string) => void`\nDescription: Function to highlight a value\n\n**`clearHighlightValue`**\nType: `VoidFunction`\nDescription: Function to clear the highlighted value\n\n**`selectedItems`**\nType: `V[]`\nDescription: The selected items\n\n**`hasSelectedItems`**\nType: `boolean`\nDescription: Whether there's a selected option\n\n**`value`**\nType: `string[]`\nDescription: The selected item keys\n\n**`valueAsString`**\nType: `string`\nDescription: The string representation of the selected items\n\n**`selectValue`**\nType: `(value: string) => void`\nDescription: Function to select a value\n\n**`selectAll`**\nType: `VoidFunction`\nDescription: Function to select all values\n\n**`setValue`**\nType: `(value: string[]) => void`\nDescription: Function to set the value of the select\n\n**`clearValue`**\nType: `(value?: string) => void`\nDescription: Function to clear the value of the select.\nIf a value is provided, it will only clear that value, otherwise, it will clear all values.\n\n**`focus`**\nType: `VoidFunction`\nDescription: Function to focus on the select input\n\n**`getItemState`**\nType: `(props: ItemProps<any>) => ItemState`\nDescription: Returns the state of a select item\n\n**`setOpen`**\nType: `(open: boolean) => void`\nDescription: Function to open or close the select\n\n**`collection`**\nType: `ListCollection<V>`\nDescription: Function to toggle the select\n\n**`reposition`**\nType: `(options?: Partial<PositioningOptions>) => void`\nDescription: Function to set the positioning options of the select\n\n**`multiple`**\nType: `boolean`\nDescription: Whether the select allows multiple selections\n\n**`disabled`**\nType: `boolean`\nDescription: Whether the select is disabled\n\n### Data Attributes\n\n**`Root`**\n\n**`data-scope`**: select\n**`data-part`**: root\n**`data-invalid`**: Present when invalid\n**`data-readonly`**: Present when read-only\n\n**`Label`**\n\n**`data-scope`**: select\n**`data-part`**: label\n**`data-disabled`**: Present when disabled\n**`data-invalid`**: Present when invalid\n**`data-readonly`**: Present when read-only\n**`data-required`**: Present when required\n\n**`Control`**\n\n**`data-scope`**: select\n**`data-part`**: control\n**`data-state`**: \"open\" | \"closed\"\n**`data-focus`**: Present when focused\n**`data-disabled`**: Present when disabled\n**`data-invalid`**: Present when invalid\n\n**`ValueText`**\n\n**`data-scope`**: select\n**`data-part`**: value-text\n**`data-disabled`**: Present when disabled\n**`data-invalid`**: Present when invalid\n**`data-focus`**: Present when focused\n\n**`Trigger`**\n\n**`data-scope`**: select\n**`data-part`**: trigger\n**`data-state`**: \"open\" | \"closed\"\n**`data-disabled`**: Present when disabled\n**`data-invalid`**: Present when invalid\n**`data-readonly`**: Present when read-only\n**`data-placement`**: The placement of the trigger\n**`data-placeholder-shown`**: Present when placeholder is shown\n\n**`Indicator`**\n\n**`data-scope`**: select\n**`data-part`**: indicator\n**`data-state`**: \"open\" | \"closed\"\n**`data-disabled`**: Present when disabled\n**`data-invalid`**: Present when invalid\n**`data-readonly`**: Present when read-only\n\n**`Item`**\n\n**`data-scope`**: select\n**`data-part`**: item\n**`data-value`**: The value of the item\n**`data-state`**: \"checked\" | \"unchecked\"\n**`data-highlighted`**: Present when highlighted\n**`data-disabled`**: Present when disabled\n\n**`ItemText`**\n\n**`data-scope`**: select\n**`data-part`**: item-text\n**`data-state`**: \"checked\" | \"unchecked\"\n**`data-disabled`**: Present when disabled\n**`data-highlighted`**: Present when highlighted\n\n**`ItemIndicator`**\n\n**`data-scope`**: select\n**`data-part`**: item-indicator\n**`data-state`**: \"checked\" | \"unchecked\"\n\n**`ItemGroup`**\n\n**`data-scope`**: select\n**`data-part`**: item-group\n**`data-disabled`**: Present when disabled\n\n**`ClearTrigger`**\n\n**`data-scope`**: select\n**`data-part`**: clear-trigger\n**`data-invalid`**: Present when invalid\n\n**`Content`**\n\n**`data-scope`**: select\n**`data-part`**: content\n**`data-state`**: \"open\" | \"closed\"\n**`data-nested`**: listbox\n**`data-has-nested`**: listbox\n**`data-placement`**: The placement of the content\n**`data-activedescendant`**: The id the active descendant of the content\n\n### CSS Variables\n\n<CssVarTable name=\"select\" />\n\n## Accessibility\n\nAdheres to the\n[ListBox WAI-ARIA design pattern](https://www.w3.org/WAI/ARIA/apg/patterns/listbox).\n\n### Keyboard Interactions\n\n**`Space`**\nDescription: <span>When focus is on trigger, opens the select and focuses the first selected item.<br />When focus is on the content, selects the highlighted item.</span>\n\n**`Enter`**\nDescription: <span>When focus is on trigger, opens the select and focuses the first selected item.<br />When focus is on content, selects the focused item.</span>\n\n**`ArrowDown`**\nDescription: <span>When focus is on trigger, opens the select.<br />When focus is on content, moves focus to the next item.</span>\n\n**`ArrowUp`**\nDescription: <span>When focus is on trigger, opens the select.<br />When focus is on content, moves focus to the previous item.</span>\n\n**`Esc`**\nDescription: <span>Closes the select and moves focus to trigger.</span>\n\n**`A-Z + a-z`**\nDescription: <span>When focus is on trigger, selects the item whose label starts with the typed character.<br />When focus is on the listbox, moves focus to the next item with a label that starts with the typed character.</span>","package":"@zag-js/select","editUrl":"https://github.com/chakra-ui/zag/edit/main/website/data/components/select.mdx"}