@zag-js/listbox
Version:
Core logic for the listbox widget implemented as a state machine
291 lines (283 loc) • 9.96 kB
TypeScript
import * as _zag_js_anatomy from '@zag-js/anatomy';
import { CollectionOptions, ListCollection, CollectionItem, GridCollectionOptions, GridCollection, SelectionMode, Selection } from '@zag-js/collection';
export { CollectionItem, CollectionOptions, GridCollection, GridCollectionOptions, ListCollection, SelectionMode } from '@zag-js/collection';
import * as _zag_js_core from '@zag-js/core';
import { EventObject, Machine, Service } from '@zag-js/core';
import { RequiredBy, DirectionProperty, CommonProperties, OrientationProperty, PropTypes, NormalizeProps } from '@zag-js/types';
import { TypeaheadState } from '@zag-js/dom-query';
declare const anatomy: _zag_js_anatomy.AnatomyInstance<"label" | "input" | "item" | "itemText" | "itemIndicator" | "itemGroup" | "itemGroupLabel" | "content" | "root" | "valueText">;
declare const collection: {
<T extends unknown>(options: CollectionOptions<T>): ListCollection<T>;
empty(): ListCollection<CollectionItem>;
};
declare const gridCollection: {
<T extends unknown>(options: GridCollectionOptions<T>): GridCollection<T>;
empty(): GridCollection<CollectionItem>;
};
interface ValueChangeDetails<T extends CollectionItem = CollectionItem> {
value: string[];
items: T[];
}
interface HighlightChangeDetails<T extends CollectionItem = CollectionItem> {
highlightedValue: string | null;
highlightedItem: T | null;
highlightedIndex: number;
}
interface ScrollToIndexDetails {
index: number;
immediate?: boolean | undefined;
}
interface SelectionDetails {
value: string;
}
type ElementIds = Partial<{
root: string;
content: string;
label: string;
item(id: string | number): string;
itemGroup(id: string | number): string;
itemGroupLabel(id: string | number): string;
}>;
interface ListboxProps<T extends CollectionItem = CollectionItem> extends DirectionProperty, CommonProperties, OrientationProperty {
/**
* The item collection
*/
collection: ListCollection<T> | GridCollection<T>;
/**
* The ids of the elements in the listbox. Useful for composition.
*/
ids?: ElementIds | undefined;
/**
* Whether the listbox is disabled
*/
disabled?: boolean | undefined;
/**
* Whether to disallow selecting all items when `meta+a` is pressed
*/
disallowSelectAll?: boolean | undefined;
/**
* The callback fired when the highlighted item changes.
*/
onHighlightChange?: ((details: HighlightChangeDetails<T>) => void) | undefined;
/**
* The callback fired when the selected item changes.
*/
onValueChange?: ((details: ValueChangeDetails<T>) => void) | undefined;
/**
* The controlled keys of the selected items
*/
value?: string[] | undefined;
/**
* The initial default value of the listbox when rendered.
* Use when you don't need to control the value of the listbox.
*
* @default []
*/
defaultValue?: string[] | undefined;
/**
* The controlled key of the highlighted item
*/
highlightedValue?: string | null | undefined;
/**
* The initial value of the highlighted item when opened.
* Use when you don't need to control the highlighted value of the listbox.
*/
defaultHighlightedValue?: string | null | undefined;
/**
* Whether to loop the keyboard navigation through the options
* @default false
*/
loopFocus?: boolean | undefined;
/**
* How multiple selection should behave in the listbox.
*
* - `single`: The user can select a single item.
* - `multiple`: The user can select multiple items without using modifier keys.
* - `extended`: The user can select multiple items by using modifier keys.
*
* @default "single"
*/
selectionMode?: SelectionMode | undefined;
/**
* Function to scroll to a specific index
*/
scrollToIndexFn?: ((details: ScrollToIndexDetails) => void) | undefined;
/**
* Whether to select the item when it is highlighted
*/
selectOnHighlight?: boolean | undefined;
/**
* Whether to disallow empty selection
*/
deselectable?: boolean | undefined;
/**
* Whether to enable typeahead on the listbox
*/
typeahead?: boolean | undefined;
/**
* Function called when an item is selected
*/
onSelect?: ((details: SelectionDetails) => void) | undefined;
}
type PropsWithDefault = "collection" | "selectionMode";
interface ListboxSchema<T extends CollectionItem = CollectionItem> {
state: "idle";
props: RequiredBy<ListboxProps<T>, PropsWithDefault>;
context: {
value: string[];
highlightedValue: string | null;
highlightedItem: T | null;
selectedItems: T[];
focused: boolean;
};
computed: {
hasSelectedItems: boolean;
isTypingAhead: boolean;
isInteractive: boolean;
selection: Selection;
multiple: boolean;
valueAsString: string;
};
refs: {
typeahead: TypeaheadState;
prevCollection: ListCollection<T> | null;
};
action: string;
guard: string;
effect: string;
event: EventObject;
}
type ListboxService<T extends CollectionItem = CollectionItem> = Service<ListboxSchema<T>>;
type ListboxMachine<T extends CollectionItem = CollectionItem> = Machine<ListboxSchema<T>>;
interface ItemProps<T extends CollectionItem = CollectionItem> {
/**
* The item to render
*/
item: T;
/**
* Whether to highlight the item on hover
*/
highlightOnHover?: boolean | undefined;
}
interface ItemState {
/**
* The underlying value of the item
*/
value: string;
/**
* Whether the item is disabled
*/
disabled: boolean;
/**
* Whether the item is selected
*/
selected: boolean;
/**
* Whether the item is highlighted
*/
highlighted: boolean;
}
interface ItemGroupProps {
id: string;
}
interface ItemGroupLabelProps {
htmlFor: string;
}
interface InputProps {
/**
* Whether to automatically highlight the item when typing
* @default false
*/
autoHighlight?: boolean | undefined;
}
interface ListboxApi<T extends PropTypes = PropTypes, V extends CollectionItem = CollectionItem> {
/**
* Whether the select value is empty
*/
empty: boolean;
/**
* The value of the highlighted item
*/
highlightedValue: string | null;
/**
* The highlighted item
*/
highlightedItem: V | null;
/**
* Function to highlight a value
*/
highlightValue(value: string): void;
/**
* Function to clear the highlighted value
*/
clearHighlightedValue(): void;
/**
* The selected items
*/
selectedItems: V[];
/**
* Whether there's a selected option
*/
hasSelectedItems: boolean;
/**
* The selected item keys
*/
value: string[];
/**
* The string representation of the selected items
*/
valueAsString: string;
/**
* Function to select a value
*/
selectValue(value: string): void;
/**
* Function to select all values.
*
* **Note**: This should only be called when the selectionMode is `multiple` or `extended`.
* Otherwise, an exception will be thrown.
*/
selectAll(): void;
/**
* Function to set the value of the select
*/
setValue(value: string[]): void;
/**
* Function to clear the value of the select.
* If a value is provided, it will only clear that value, otherwise, it will clear all values.
*/
clearValue(value?: string): void;
/**
* Returns the state of a select item
*/
getItemState(props: ItemProps): ItemState;
/**
* Function to toggle the select
*/
collection: ListCollection<V>;
/**
* Whether the select is disabled
*/
disabled: boolean;
getInputProps(props?: InputProps): T["input"];
getRootProps(): T["element"];
getLabelProps(): T["label"];
getValueTextProps(): T["element"];
getContentProps(): T["element"];
getItemProps(props: ItemProps): T["element"];
getItemTextProps(props: ItemProps): T["element"];
getItemIndicatorProps(props: ItemProps): T["element"];
getItemGroupProps(props: ItemGroupProps): T["element"];
getItemGroupLabelProps(props: ItemGroupLabelProps): T["element"];
}
declare function connect<T extends PropTypes, V extends CollectionItem = CollectionItem>(service: Service<ListboxSchema<V>>, normalize: NormalizeProps<T>): ListboxApi<T, V>;
declare const machine: _zag_js_core.Machine<ListboxSchema<any>>;
declare const props: (keyof ListboxProps<any>)[];
declare const splitProps: <Props extends Partial<ListboxProps<any>>>(props: Props) => [Partial<ListboxProps<any>>, Omit<Props, keyof ListboxProps<any>>];
declare const itemProps: (keyof ItemProps<any>)[];
declare const splitItemProps: <Props extends ItemProps<any>>(props: Props) => [ItemProps<any>, Omit<Props, keyof ItemProps<any>>];
declare const itemGroupProps: "id"[];
declare const splitItemGroupProps: <Props extends ItemGroupProps>(props: Props) => [ItemGroupProps, Omit<Props, "id">];
declare const itemGroupLabelProps: "htmlFor"[];
declare const splitItemGroupLabelProps: <Props extends ItemGroupLabelProps>(props: Props) => [ItemGroupLabelProps, Omit<Props, "htmlFor">];
export { type ListboxApi as Api, type ElementIds, type HighlightChangeDetails, type InputProps, type ItemGroupLabelProps, type ItemGroupProps, type ItemProps, type ItemState, type ListboxMachine as Machine, type ListboxProps as Props, type ScrollToIndexDetails, type SelectionDetails, type ListboxService as Service, type ValueChangeDetails, anatomy, collection, connect, gridCollection, itemGroupLabelProps, itemGroupProps, itemProps, machine, props, splitItemGroupLabelProps, splitItemGroupProps, splitItemProps, splitProps };