
UI组件前端【免费下载链接】ariakitToolkit with accessible components, styles, and examples for your next web app项目地址https://gitcode.com/gh_mirrors/ar/ariakit点击查看免费下载在 Ariakit(Toolkit with accessible components, styles, and examples for your next web app)中,Menu提供了带键盘导航与无障碍语义的下拉菜单,Combobox提供了带自动完成能力的搜索输入框。将两者嵌套组合,即可得到一个内置搜索框、能实时过滤菜单项的下拉菜单——这正是 examples/menu-combobox/readme.md 所描述的 Menu with Combobox 方案。读完本文,你将能够复制该示例的完整代码,理解ComboboxProvider、MenuProvider双层 Provider 的状态协作方式,并掌握resetValueOnHide、setValueOnClick、autoSelect等关键参数的作用与底层实现。方案概述:为什么是 Menu ComboboxAriakit 的组件全部由无头组件 Store构成:MenuProvider/Menu/MenuButton负责弹出层与焦点管理,ComboboxProvider/Combobox/ComboboxItem负责搜索过滤与值管理。把Combobox输入框直接渲染在Menu面板内部,就能得到一个打开菜单 → 顶部出现搜索框 → 边输入边过滤的交互模式(类似 Notion 的 Add block 按钮)。该示例的标签为 Menu、Combobox、Dropdowns、Concurrent React、Search,其中 Concurrent React 提示了本方案的一个重要卖点:利用startTransition让过滤逻辑不阻塞 UI。完整示例代码示例入口为 examples/menu-combobox/index.react.tsx,完整代码如下:import * as Ariakit from ariakit/react; import { matchSorter } from match-sorter; import { startTransition, useMemo, useState } from react; import list from ./list.ts; import ./style.css; export default function Example() { const [searchValue, setSearchValue] useState(); const matches useMemo(() { return matchSorter(list, searchValue, { baseSort: (a, b) (a.index b.index ? -1 : 1), }); }, [searchValue]); return ( Ariakit.ComboboxProvider resetValueOnHide setValue{(value) { startTransition(() { setSearchValue(value); }); }} Ariakit.MenuProvider Ariakit.MenuButton classNamebutton Add block Ariakit.MenuButtonArrow / /Ariakit.MenuButton Ariakit.Menu classNamemenu Ariakit.MenuArrow / Ariakit.Combobox autoSelect placeholderSearch... classNamecombobox / Ariakit.ComboboxList classNamecombobox-list {matches.map((value) ( Ariakit.ComboboxItem key{value} value{value} focusOnHover setValueOnClick{false} classNamemenu-item / ))} /Ariakit.ComboboxList /Ariakit.Menu /Ariakit.MenuProvider /Ariakit.ComboboxProvider ); }菜单项数据来自 examples/menu-combobox/list.ts,是一个包含 Paragraph、Heading、List、Quote、Code、Image、Video 等 35 个条目的字符串数组,用于模拟页面构建器中的块类型列表。代码结构解读整个组件由两层 Provider 嵌套而成,各自管理一套 Store:ComboboxProvider(外层):管理搜索输入状态(inputValue)与选中值。这里传入了两个关键配置:resetValueOnHide:弹出层收起时自动清空搜索框,保证每次打开菜单都从空白搜索状态开始;setValue:在输入值变化时被调用的回调,示例用它在外部维护一个searchValuestate,并借此驱动matchSorter的过滤结果。注意从源码文档看,setValue已被标记为废弃(deprecated Use setInputValue instead),新代码建议改用setInputValue(见 combobox-store.ts 中的ComboboxStoreOptions定义,setInputValue与setValue在内部共用同一逻辑:setInputValue: props.setInputValue ?? props.setValue,见 combobox-store.ts)。MenuProvider(内层):管理菜单的打开/关闭、方向与焦点。MenuButtonMenuButtonArrow是触发器,MenuMenuArrow是弹出面板。Combobox输入框:渲染在Menu内部而非MenuButton内,因此搜索框只出现在面板顶部。autoSelect属性表示当虚拟焦点(virtual focus)移动时自动高亮选中项,其生效条件是state.virtualFocus autoSelectProp(见 combobox.tsx)。ComboboxListComboboxItem:列表项由外部的matches(经过matchSorter过滤排序后的数组)映射生成,而不是渲染全部list——这就是搜索过滤的实现位置。过滤逻辑:matchSorter 与稳定排序const matches useMemo(() { return matchSorter(list, searchValue, { baseSort: (a, b) (a.index b.index ? -1 : 1), }); }, [searchValue]);matchSorter来自第三方库match-sorter,负责按输入串做模糊匹配与相关度排序;baseSort保证当搜索词为空或命中度相同时,列表回落到原始顺序(按index升序),避免菜单项在输入过程中跳序。过滤结果通过useMemo缓存,仅在searchValue变化时重新计算。并发友好:startTransition 的作用setValue{(value) { startTransition(() { setSearchValue(value); }); }}输入时每次按键都会触发setSearchValue,如果菜单项很多、matchSorter计算较重,同步的 state 更新可能阻塞输入框本身的响应。将其包裹在startTransition中,React 会将其标记为低优先级更新:输入框文本的呈现保持高优先级即时响应,而过滤并重新渲染列表可被中断、降优先级执行。这正是文档标签中 Concurrent React 的含义。ComboboxItem 的两个关键属性focusOnHover:鼠标悬停到某个ComboboxItem时自动移动焦点,使菜单项与鼠标位置保持一致,符合菜单的常规交互预期。setValueOnClick{false}:这是本示例的一个易错点。ComboboxItem的setValueOnClick默认值为!selectMode !multiSelectable(即默认为true,见 combobox-item.tsx),意味着点击菜单项会把该值写入selectedValue。在添加块这类场景中,点击菜单项只是触发业务动作,并不需要在搜索框里留下选中值,因此显式关闭它,避免点击后selectedValue改变进而触发输入框回填。样式要点examples/menu-combobox/style.css 复用了基础菜单样式并做三处定制:.menu { apply p-0 overflow-visible max-h-[min(var(--popover-available-height,300px),300px)]; } .combobox { apply w-fit h-10 rounded border-none px-4 m-2 flex-none text-base bg-gray-150 hover:bg-gray-200 focus-visible:ariakit-outline-input; } .combobox-list { apply p-2 overflow-auto overscroll-contain rounded-bl-[inherit] rounded-br-[inherit] border-t border-t-gray-250; }.menu用--popover-available-heightCSS 变量把菜单最大高度限制在 300px 以内(取可用高度与 300px 的较小值),这是 Ariakit 弹出层体系提供的响应式高度变量;.combobox把输入框做成面板顶部的嵌入式样式(无边框、灰底、固定高度),并用flex-none防止列表撑开时输入框被压缩;.combobox-list可滚动且overscroll-contain(滚动到边界时不滚到父级),顶部分隔线把搜索区与列表区在视觉上切开。底层实现:状态是如何重置的示例中resetValueOnHide的行为值得深入一层。在框架无关的核心 Store 中,存在一段针对resetValueOnHide与mounted的同步逻辑(见 combobox-store.ts):setup(combobox, () sync(combobox, [resetValueOnHide, mounted], (state) { if (!state.resetValueOnHide) return; if (state.mounted) return; combobox.setState(inputValue, inputValue); }), );即:当 Store 卸载/弹出层收起(mounted变为false)且设置了resetValueOnHide时,自动把inputValue重置回初始值。由于示例在外部用searchValuestate 驱动过滤,收起菜单后下次再打开,搜索框即为空白,列表恢复全量,行为与每次打开都是全新搜索的直觉一致。另外从源码结构看,React 层的useComboboxStore由Core.createComboboxStore创建,并叠加了 Composite 与 Popover 两套 Store 能力(见 combobox-store.ts 中ComboboxStoreState同时继承CompositeStoreState与PopoverStoreState)。这意味着Combobox天然具备复合列表的焦点管理(上下键、Home/End)与弹出层的定位/方向能力——所以ComboboxList能直接嵌进Menu并复用其键盘导航,而无需额外胶水代码。组件文档入口两个参与组合的组件在仓库中各有独立文档,可进一步查阅 API 细节:Menu 组件文档Combobox 组件文档相关示例readme 中列出了六个方向相近的官方示例,均在仓库examples/目录下,可作为扩展起点:示例路径适用场景带 Combobox 的嵌套菜单examples/menu-nested-combobox多级菜单 搜索过滤带 Combobox 的 Selectexamples/select-combobox用 Combobox 增强的 Select 模式导航式 Menubarexamples/menubar-navigation顶部导航栏菜单带 Tabs 的 Comboboxexamples/combobox-tabs多 Tab 分组的搜索列表对话框 Combobox CommandMenuexamples/dialog-combobox-command-menu命令面板式对话框对话框 Combobox Tab CommandMenuexamples/dialog-combobox-tab-command-menu多页签命令面板小结用ComboboxProvider包裹MenuProvider,把Combobox输入框放进Menu面板顶部,即可获得可搜索的下拉菜单;过滤逻辑放在外部(matchSorteruseMemo),setValue(推荐迁移到setInputValue)回调里用startTransition更新 state,保证输入响应不被过滤计算阻塞;resetValueOnHide让每次打开菜单都重置搜索框;ComboboxItem上关闭setValueOnClick、开启focusOnHover,使菜单项点击只触发动作而不回填选中值;样式上借助--popover-available-height约束菜单高度,列表区滚动并overscroll-contain,搜索区与列表区用分隔线区隔。以上行为均可在 examples/menu-combobox 目录及 packages/ariakit-react-components/src/combobox 的源码中对照验证。赞分享UI组件前端【免费下载链接】ariakitToolkit with accessible components, styles, and examples for your next web app项目地址https://gitcode.com/gh_mirrors/ar/ariakit点击查看免费下载相关推荐ARIAKIT Combobox 搜索过滤实战用 setValue 与 startTransition 构建响应式搜索下拉ARIAKIT Combobox 搜索过滤实战用 setValue 与 startTransition 构建响应式搜索下拉 本文基于 ARIAKIT 仓库中的UI组件前端Ariakit React 实战用 Dialog Tab Combobox 组合出可搜索的分页命令菜单Command PaletteAriakit React 实战用 Dialog Tab Combobox 组合出可搜索的分页命令菜单Command Palette 本文基于 AUI组件前端Ariakit Combobox 与 Tab 组合实战构建支持键盘、鼠标与读屏器的分组搜索下拉框Ariakit Combobox 与 Tab 组合实战构建支持键盘、鼠标与读屏器的分组搜索下拉框 本篇基于仓库中的 combobox tabs 示例 httpUI组件前端上一篇最完整指南vue-i18n与React VR的国际化融合方案下一篇>创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考