import { Service, EventObject, Machine } from '@zag-js/core'; import { DismissableElementHandlers } from '@zag-js/dismissable'; import { ModifierKeys, TypeaheadState, AnimationFrame } from '@zag-js/dom-query'; import { PositioningOptions, Placement } from '@zag-js/popper'; export { PositioningOptions } from '@zag-js/popper'; import { Point } from '@zag-js/rect-utils'; export { Point } from '@zag-js/rect-utils'; import { PropTypes, RequiredBy, DirectionProperty, CommonProperties } from '@zag-js/types'; interface OpenChangeDetails { /** * Whether the menu is open */ open: boolean; } interface TriggerValueChangeDetails { /** * The value of the trigger */ value: string | null; /** * The trigger element */ triggerElement: HTMLElement | null; } interface SelectionDetails { /** * The value of the selected menu item */ value: string; /** * The modifier keys held when the item was activated */ modifiers: ModifierKeys; } interface HighlightChangeDetails { /** * The value of the highlighted menu item */ highlightedValue: string | null; } interface NavigateDetails { value: string; node: HTMLAnchorElement; href: string; /** * The modifier keys held when the item was activated */ modifiers: ModifierKeys; } interface ElementIds { trigger?: (string | ((value?: string) => string)) | undefined; contextTrigger?: (string | ((value?: string) => string)) | undefined; content?: string | undefined; groupLabel?: ((id: string) => string) | undefined; group?: ((id: string) => string) | undefined; positioner?: string | undefined; arrow?: string | undefined; } interface MenuProps extends DirectionProperty, CommonProperties, DismissableElementHandlers { /** * The ids of the elements in the menu. Useful for composition. */ ids?: ElementIds | undefined; /** * The initial highlighted value of the menu item when rendered. * Use when you don't need to control the highlighted value of the menu item. */ defaultHighlightedValue?: string | null | undefined; /** * The controlled highlighted value of the menu item. */ highlightedValue?: string | null | undefined; /** * Function called when the highlighted menu item changes. */ onHighlightChange?: ((details: HighlightChangeDetails) => void) | undefined; /** * Function called when a menu item is selected. */ onSelect?: ((details: SelectionDetails) => void) | undefined; /** * The positioning point for the menu. Can be set by the context menu trigger or the button trigger. */ anchorPoint?: Point | null | undefined; /** * Whether to loop the keyboard navigation. * @default false */ loopFocus?: boolean | undefined; /** * The options used to dynamically position the menu */ positioning?: PositioningOptions | undefined; /** * Whether to close the menu when an option is selected * @default true */ closeOnSelect?: boolean | undefined; /** * The accessibility label for the menu */ "aria-label"?: string | undefined; /** * The controlled open state of the menu */ open?: boolean | undefined; /** * Function called when the menu opens or closes */ onOpenChange?: ((details: OpenChangeDetails) => void) | undefined; /** * The initial open state of the menu when rendered. * Use when you don't need to control the open state of the menu. */ defaultOpen?: boolean | undefined; /** * Whether the pressing printable characters should trigger typeahead navigation * @default true */ typeahead?: boolean | undefined; /** * Whether the menu is a composed with other composite widgets like a combobox or tabs * @default true */ composite?: boolean | undefined; /** * Function to navigate to the selected item if it's an anchor element */ navigate?: ((details: NavigateDetails) => void) | null | undefined; /** * The controlled trigger value */ triggerValue?: string | null | undefined; /** * The initial trigger value when rendered. * Use when you don't need to control the trigger value. */ defaultTriggerValue?: string | null | undefined; /** * Function called when the trigger value changes. */ onTriggerValueChange?: ((details: TriggerValueChangeDetails) => void) | undefined; } type PropsWithDefault = "closeOnSelect" | "typeahead" | "composite" | "positioning" | "loopFocus"; interface MenuSchema { props: RequiredBy; context: { highlightedValue: string | null; lastHighlightedValue: string | null; currentPlacement: Placement | undefined; intentPolygon: Point[] | null; anchorPoint: Point | null; isSubmenu: boolean; triggerValue: string | null; pointerRoutingMode: "interactive" | "locked"; }; computed: { isRtl: boolean; isTypingAhead: boolean; highlightedId: string | null; }; refs: { parent: MenuService | null; children: Record; pointerRoutingLocked: boolean; typeaheadState: TypeaheadState; positioningOverride: Partial; focusMenuFrame: AnimationFrame; }; action: string; effect: string; guard: string; event: EventObject; state: "idle" | "open" | "closed" | "opening" | "closing" | "opening:contextmenu" | "opening:requested"; tag: "open" | "closed"; } type MenuService = Service; type MenuMachine = Machine; type ChildMenuService = MenuService; type ParentMenuService = MenuService; interface TriggerProps { /** * The value that identifies this specific trigger */ value?: string; } interface Api { getItemProps: (props: ItemProps) => Record; getTriggerProps: () => Record; } interface ItemProps { /** * The unique value of the menu item option. */ value: string; /** * Whether the menu item is disabled */ disabled?: boolean | undefined; /** * The textual value of the option. Used in typeahead navigation of the menu. * If not provided, the text content of the menu item will be used. */ valueText?: string | undefined; /** * Whether the menu should be closed when the option is selected. */ closeOnSelect?: boolean | undefined; } interface ItemListenerProps { /** * The id of the item. Can be obtained from the `getItemState` function. */ id: string; /** * Function called when the item is selected */ onSelect?: VoidFunction | undefined; } interface OptionItemProps extends Partial { /** * Whether the option is checked */ checked: boolean; /** * Whether the option is a radio or a checkbox */ type: "radio" | "checkbox"; /** * The value of the option */ value: string; /** * Function called when the option state is changed */ onCheckedChange?: ((checked: boolean) => void) | undefined; } interface ItemState { /** * The unique id of the item */ id: string; /** * Whether the item is disabled */ disabled: boolean; /** * Whether the item is highlighted */ highlighted: boolean; } interface OptionItemState extends ItemState { /** * Whether the option item is checked */ checked: boolean; } interface ItemGroupProps { /** * The `id` of the element that provides accessibility label to the option group */ id: string; } interface ItemGroupLabelProps { /** * The `id` of the group this refers to */ htmlFor: string; } interface ItemBaseProps { value: string; disabled?: boolean | undefined; checked?: boolean | undefined; valueText?: string | undefined; } interface MenuApi { /** * Whether the menu is open */ open: boolean; /** * Function to open or close the menu */ setOpen: (open: boolean) => void; /** * The trigger value */ triggerValue: string | null; /** * Function to set the trigger value */ setTriggerValue: (value: string | null) => void; /** * The id of the currently highlighted menuitem */ highlightedValue: string | null; /** * Function to set the highlighted menuitem */ setHighlightedValue: (value: string) => void; /** * Function to register a parent menu. This is used for submenus */ setParent: (parent: MenuService) => void; /** * Function to register a child menu. This is used for submenus */ setChild: (child: MenuService) => void; /** * Function to reposition the popover */ reposition: (options?: Partial) => void; /** * Returns the state of the option item */ getOptionItemState: (props: OptionItemProps) => OptionItemState; /** * Returns the state of the menu item */ getItemState: (props: ItemProps) => ItemState; /** * Setup the custom event listener for item selection event */ addItemListener: (props: ItemListenerProps) => VoidFunction | undefined; getContextTriggerProps: (props?: TriggerProps) => T["element"]; getTriggerItemProps: (childApi: A) => T["element"]; getTriggerProps: (props?: TriggerProps) => T["button"]; getIndicatorProps: () => T["element"]; getPositionerProps: () => T["element"]; getArrowProps: () => T["element"]; getArrowTipProps: () => T["element"]; getContentProps: () => T["element"]; getSeparatorProps: () => T["element"]; getItemProps: (options: ItemProps) => T["element"]; getOptionItemProps: (option: OptionItemProps) => T["element"]; getItemIndicatorProps: (option: ItemBaseProps) => T["element"]; getItemTextProps: (option: ItemBaseProps) => T["element"]; getItemGroupLabelProps: (options: ItemGroupLabelProps) => T["element"]; getItemGroupProps: (options: ItemGroupProps) => T["element"]; } export type { Api, ChildMenuService, ElementIds, HighlightChangeDetails, ItemBaseProps, ItemGroupLabelProps, ItemGroupProps, ItemListenerProps, ItemProps, ItemState, MenuApi, MenuMachine, MenuProps, MenuSchema, MenuService, NavigateDetails, OpenChangeDetails, OptionItemProps, OptionItemState, ParentMenuService, SelectionDetails, TriggerProps, TriggerValueChangeDetails };