Integrate the Menu UI component
A powerful menu component built on Ariakit that provides hierarchical navigation, search functionality, filtering capabilities, and full keyboard accessibility. Perfect for command palettes, dropdown menus, and complex navigation systems.
Install
You can add the primitive via Tiptap CLI
npx @tiptap/cli@latest add menu
Usage
import {
Menu,
MenuContent,
MenuItem,
MenuGroup,
MenuGroupLabel,
MenuButton,
MenuButtonArrow,
useComboboxValueState,
} from '@/components/tiptap-ui-primitive/menu'
import { Button } from '@/components/tiptap-ui-primitive/button'
import { ComboboxList } from '@/components/tiptap-ui-primitive/combobox'
export default function MyComponent() {
const [searchValue] = useComboboxValueState()
return (
<Menu trigger={<Button>Open Menu</Button>}>
<MenuContent>
<ComboboxList>
<MenuGroup>
<MenuGroupLabel>Actions</MenuGroupLabel>
<MenuItem
onClick={() => console.log('Cut')}
render={<Button data-style="ghost">Cut</Button>}
/>
<MenuItem
onClick={() => console.log('Copy')}
render={<Button data-style="ghost">Copy</Button>}
/>
<MenuItem
onClick={() => console.log('Paste')}
render={<Button data-style="ghost">Paste</Button>}
/>
</MenuGroup>
</ComboboxList>
</MenuContent>
</Menu>
)
}
Components
Menu
The root menu provider that handles state management and context.
Name | Type | Default | Description |
---|---|---|---|
trigger | React.ReactNode | - | Element that triggers the menu |
value | string | - | Current search value (for searchable menus) |
onOpenChange | (open: boolean) => void | - | Callback when menu open state changes |
onValueChange | (value: string) => void | - | Callback when search value changes |
onValuesChange | (values: string[]) => void | - | Callback for multi-selection |
open | boolean | - | Controlled open state |
MenuContent
The container for menu items with positioning and styling.
Name | Type | Default | Description |
---|---|---|---|
onClickOutside | (event: MouseEvent | TouchEvent | FocusEvent) => void | - | Callback when clicking outside menu |
MenuItem
Individual selectable menu item.
Name | Type | Default | Description |
---|---|---|---|
group | string | - | Group identifier for the item |
name | string | - | Name identifier for the item |
parentGroup | string | - | Parent group identifier |
preventClose | boolean | false | Prevent menu from closing when selected |
render | React.ReactElement | - | Custom render element |
Hooks
useComboboxValueState
Hook for accessing and updating the search value in searchable menus.
const [searchValue, setSearchValue] = useComboboxValueState()
Returns: readonly [string, (value: string) => void]
useMenuPlacement
Hook for getting the current menu positioning side.
const side = useMenuPlacement()
Returns: string
- The current side ("top", "bottom", "left", "right")
useMenuItemClick
Hook for handling menu item clicks with optional close prevention.
const handleClick = useMenuItemClick(menu, preventClose)
Parameters:
menu?: Ariakit.MenuStore
- Menu store instancepreventClose?: boolean
- Whether to prevent menu from closing
Filtering and Search
The Menu component includes powerful filtering capabilities:
filterMenuItems
Utility function for filtering menu items based on search criteria.
import { filterMenuItems } from '@/components/tiptap-ui-primitive/menu'
const filteredItems = filterMenuItems({ items: menuItems, label: 'Actions' }, searchValue)
filterMenuGroups
Utility function for filtering entire menu groups.
import { filterMenuGroups } from '@/components/tiptap-ui-primitive/menu'
const filteredGroups = filterMenuGroups(menuGroups, searchValue)
Dependencies
- @ariakit/react - Accessibility and interaction primitives
- combobox - Search functionality
- separator - Visual separation between groups
- label - Group labeling
- use-on-click-outside - Outside click detection
- use-composed-ref - Ref composition utilities