十年匠心定制 · 商业建站与技术教学双线并行 咨询热线:400-886-1026 service@lmnt.cn
ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

radix-vue 的 Combobox 组件完全指南:从基础用法到虚拟化与 Command Menu 实战

radix-vue 的 Combobox 组件完全指南:从基础用法到虚拟化与 Command Menu 实战 radix-vue 的 Combobox 组件完全指南从基础用法到虚拟化与 Command Menu 实战【免费下载链接】radix-vueAn open-source UI component library for building high-quality, accessible design systems and web apps for Vue. Previously Radix Vue项目地址: https://gitcode.com/GitHub_Trending/ra/radix-vue本指南以仓库文档 docs/content/docs/components/combobox.md 为骨架结合packages/core/src/Combobox/下的源码实现展开带你掌握 reka-ui即 radix-vue 仓库发布的 UI 组件库中 Combobox 组件的完整 API、两种定位模式、自定义过滤、列表虚拟化以及无障碍键盘交互并给出可直接复制的 Vue 实战代码。Combobox 是 radix-vue 提供的一个带输入框的可搜索选择器组件用户可以在输入框中键入关键字从建议列表中挑选一个或多个值。它是构建搜索选择器、标签输入器、命令面板Command Menu等高级交互的基础。读完本文你将能够独立组装 Combobox 的 16 个部件part、用v-model绑定任意对象值、接入自定义过滤逻辑、处理十万级数据量的虚拟列表以及基于原始部件抽象出自己的 Command Menu 组件。功能特性一览从官方文档的 Features 列表见 combobox.md可以确认该组件具备以下能力受控与非受控modelValue/open可受控绑定也可通过defaultValue/defaultOpen非受控使用两种定位模式inline默认用 CSS 控制位置与popper自动计算位置与 Popover、DropdownMenu 一致丰富的结构支持支持单项、标签、分组、分隔符、空状态、取消按钮等焦点完全托管打开/关闭、选中、高亮后的焦点行为由组件内部管理完整的键盘导航方向键移动高亮、Enter 选中、Esc 关闭并还原自定义占位符输入框支持placeholderRTL 支持通过dirrtl或全局ConfigProvider继承。安装与导入组件随reka-ui包发布使用包管理器安装即可pnpm add reka-ui # 或 npm install reka-ui在仓库的示例文档与 Anatomy 示例 中所有部件均从reka-ui导入import { ComboboxAnchor, ComboboxArrow, ComboboxCancel, ComboboxContent, ComboboxEmpty, ComboboxGroup, ComboboxInput, ComboboxItem, ComboboxItemIndicator, ComboboxLabel, ComboboxPortal, ComboboxRoot, ComboboxSeparator, ComboboxTrigger, ComboboxViewport, } from reka-ui组件解剖Anatomy组合使用全部部件即可得到完整结构。以官方文档的 Anatomy 示例为准script setup langts import { ComboboxAnchor, ComboboxArrow, ComboboxCancel, ComboboxContent, ComboboxEmpty, ComboboxGroup, ComboboxInput, ComboboxItem, ComboboxItemIndicator, ComboboxLabel, ComboboxPortal, ComboboxRoot, ComboboxSeparator, ComboboxTrigger, ComboboxViewport, } from reka-ui /script template ComboboxRoot ComboboxAnchor ComboboxInput / ComboboxTrigger / ComboboxCancel / /ComboboxAnchor ComboboxPortal ComboboxContent ComboboxViewport ComboboxEmpty / ComboboxItem ComboboxItemIndicator / /ComboboxItem ComboboxSeparator / ComboboxGroup ComboboxLabel / ComboboxItem ComboboxItemIndicator / /ComboboxItem /ComboboxGroup /ComboboxViewport ComboboxArrow / /ComboboxContent /ComboboxPortal /ComboboxRoot /template各部件分工明确ComboboxRoot持有所有状态与逻辑ComboboxAnchor是定位锚点ComboboxInput承担搜索输入ComboboxTrigger负责切换展开ComboboxCancel一键清空搜索词ComboboxViewport是滚动容器ComboboxVirtualizer提供虚拟滚动。可运行的最小组合只需ComboboxRootComboboxInputComboboxContentComboboxItem。仓库中提供了两套完整的可运行示例适合对照查看真实样式CSS 版本在 docs/components/demo/Combobox/css/Tailwind 版本在 docs/components/demo/Combobox/tailwind/。API ReferenceRoot 与输入相关部件官方 API 文档通过 docs/content/meta/ 目录下的自动生成文件维护每个部件一个文件例如 ComboboxRoot.md。下面汇总关键部件的 Props、Emits 与用法。ComboboxRoot根容器包含 Combobox 的所有部分。默认渲染为div可通过as/asChild改变。名称类型默认值说明modelValueT \| T[]-受控值配合v-model使用defaultValueT \| T[]-初始值非受控multiplebooleanfalse是否多选openboolean-受控展开状态配合v-model:opendefaultOpenboolean-初始展开状态非受控disabledbooleanfalse禁用整个列表dirltr \| rtl继承ConfigProvider阅读方向bystring \| ((a, b) boolean)-对象比较方式按字段名或自定义比较函数ignoreFilterbooleanfalse为true时关闭内置过滤highlightOnHoverbooleantrue悬停是否触发高亮openOnFocusbooleanfalse输入框聚焦时是否展开openOnClickbooleanfalse点击输入框时是否展开resetSearchTermOnBlurbooleantrue失焦时是否重置搜索词resetSearchTermOnSelectbooleantrue选中后是否重置搜索词resetModelValueOnClearbooleanfalse清空时是否将modelValue重置为null多选为[]namestring-随表单提交的字段名requiredboolean-必填标记Emitsupdate:modelValue值变化、update:open展开状态变化、highlight高亮项变化payload 为{ ref: HTMLElement, value: T }。Slots默认插槽暴露open与modelValue两个作用域插槽属性。从源码 ComboboxRoot.vue 可以确认Root 的实现由PopperRoot包裹ListboxRoot组合而成——也就是说Combobox 复用了库内 Listbox列表选择与 Popper浮层定位两套底层能力再叠加搜索过滤、展开控制和输入同步逻辑。filterState是一个computed会遍历allItems挂载时由每个 Item 注册进 Map 的textValue/文本内容并用containssensitivity: base的大小写不敏感包含匹配计算命中项当ignoreFilter为真或搜索词为空时直接放行所有项。ComboboxInput搜索输入框默认渲染为原生input见 ComboboxInput.md名称类型默认值说明modelValuestring-受控的搜索词配合v-modeldisplayValue(val: any) string-选中项在输入框中的展示文本多选时不可用autoFocusboolean-挂载时聚焦disabledboolean-禁用源码 ComboboxInput.vue 在渲染层面复用了ListboxFilter并补上rolecombobox、aria-autocompletelist、autocompleteoff等无障碍属性。值得注意的两个实现细节输入即展开processInputValue在输入框未展开时写入值并自动调用onOpenChange(true)展开列表并高亮第一项已展开时则直接更新filterSearch。IME 兼容通过useComposing组合事件钩子在中文等输入法组合输入期间isComposing忽略方向键与输入事件避免 IME 候选词导航被吞掉见handleKeyDown与shouldDeferInput逻辑。displayValue与modelValue的同步在resetSearchTerm中完成若有displayValue则调用它以模型值为入参生成展示文本否则对基本类型调用toString()对对象类型则清空。ComboboxTrigger切换展开的按钮默认渲染为buttonProps 仅as/asChild/disabled见 ComboboxTrigger.md。它渲染data-stateopen/closed与data-disabled数据属性便于样式化。ComboboxCancel清空搜索词的按钮。在 ComboboxCancel.md 中有完整 Props 说明配合resetModelValueOnClear可将选中值一并重置。文档演示了在 Anchor 内输入框旁放置取消按钮的布局。API Reference弹出层部件ComboboxPortal默认情况下内容渲染在组件当前位置使用ComboboxPortal可将内容传送到body下规避overflow/transform等父级样式裁剪。若希望像 Popover 那样自动计算位置需要给ComboboxContent设置positionpopper见 ComboboxPortal.md。ComboboxContentCombobox 展开时弹出的面板默认渲染为div基于Presence管理挂载/卸载见 ComboboxContent.vue因此支持进出场动画——这也是文档中专门放置PresenceCallout /的原因组件卸载后 DOM 不会立即移除方便配合 Vue 过渡或动画库做关闭动画配合forceMount可完全接管挂载时机。Content 同时继承了 Popper 与 DismissableLayer 的能力见 ComboboxContentImpl.vue因此拥有完整的位置计算与点击外部/按 Esc 关闭行为。其定位相关 Props 与库内 Popover / DropdownMenu 完全一致核心参数如下完整列表见 ComboboxContent.md名称类型说明positioninline \| popper定位模式默认inlinesidetop \| right \| bottom \| left相对触发器的首选方位sideOffsetnumber与触发器的像素间距alignstart \| center \| end首选对齐方式alignOffsetnumber对齐偏移量avoidCollisionsboolean碰撞时覆盖 side/align 偏好collisionBoundaryElement \| (Element \| null)[] \| null碰撞边界默认 viewportcollisionPaddingnumber \| PartialRecordtop\|right\|bottom\|left, number边界留白stickypartial \| always对齐轴上的粘性行为hideWhenDetachedboolean触发器被完全遮挡时隐藏内容hideWhenEmptyboolean无匹配项时隐藏内容bodyLockboolean展开时锁定 body 滚动forceMountboolean强制挂载配合动画库positionStrategyfixed \| absoluteCSS position 类型updatePositionStrategyalways \| optimized每帧更新策略disableOutsidePointerEventsboolean禁用外部指针事件Content 还会派发escapeKeyDown、focusOutside、interactOutside、pointerDownOutside等可阻止preventDefault的 DismissableLayer 事件——这在后面封装 Command Menu 时会用到。Content 的数据属性data-stateopen/closeddata-sideleft/right/bottom/topdata-alignstart/end/centerdata-empty当没有匹配项时存在Content 的 CSS 变量仅positionpopper时提供供做跟随箭头方向的入场动画--reka-combobox-content-transform-origin由内容与箭头位置/偏移计算出的transform-origin--reka-combobox-content-available-width/--reka-combobox-content-available-height触发器到边界剩余的宽/高--reka-combobox-trigger-width/--reka-combobox-trigger-height触发器自身宽/高这些变量由底层 Popper 在 ComboboxContentImpl.vue 中从--reka-popper-*映射而来例如--reka-combobox-content-transform-origin直接取自var(--reka-popper-transform-origin)。ComboboxViewport包含所有条目的滚动视口默认渲染为div。虚拟化场景下需要用它包裹ComboboxVirtualizer。ComboboxArrow可选的箭头元素用于视觉上连接触发器与内容。必须渲染在ComboboxContent内部且仅在positionpopper时可用。API Reference列表项与分组部件ComboboxItem单个条目默认渲染为div见 ComboboxItem.md名称类型必填说明valueT是选中后写入modelValue的值不能是空字符串disabledboolean否禁用该项textValuestring否条目的纯文本表示用于过滤与类型前置当 children 不是纯文本如含图片/图标时必须显式提供Emitsselect——选中事件可通过event.preventDefault()阻止默认行为。数据属性data-statechecked/uncheckeddata-highlighted高亮时存在data-disabled禁用时存在源码 ComboboxItem.vue 中有两个值得注意的细节空字符串值保护若value 会直接抛出错误因为 Combobox 约定空字符串用于清除选中以显示占位符不能作为真实条目值。过滤渲染isRendercomputed 在非虚拟化、非忽略过滤且存在搜索词时依据 Root 的filterState决定是否渲染同时onMounted时把textValue缺省用textContent/innerText注册进 Root 的allItemsMap 供过滤使用。选中逻辑上单选时选中即preventDefault并关闭面板、写入modelValue多选时保持展开并把焦点还给输入框方便连续选择。ComboboxItemIndicator选中项时渲染可直接设置样式也可作为包装器放入图标或两者兼用文档原话You can style this element directly, or you can use it as a wrapper to put an icon into, or both。ComboboxGroup 与 ComboboxLabelComboboxGroup用于分组多个条目与ComboboxLabel搭配可借助自动关联实现良好的无障碍标注自动 labelling。ComboboxLabel渲染组标题不会被方向键聚焦。源码中 Group 通过 context 记录 groupId 与条目 id 的集合见 ComboboxRoot.vue 的allGroups过滤时只有至少包含一个可见条目的组才会保留。ComboboxSeparator在条目间做视觉分隔默认渲染为div。ComboboxEmpty当没有任何条目匹配搜索词时显示的空状态提示。ComboboxVirtualizer虚拟容器实现列表虚拟化见 ComboboxVirtualizer.md名称类型必填说明optionsT是条目列表estimateSizenumber \| ((index) number)否每条预估高度pxoverscannumber否可视区外额外渲染的条数textContent(option: T) string否每条用于 type-ahead 的文本插槽暴露option、virtualizertanstack/vue-virtual的Virtualizer实例、virtualItem三个作用域属性。源码 ComboboxVirtualizer.vue 基于ListboxVirtualizer实现挂载时会把 Root 上下文的isVirtual置为true从而让 Root 跳过内置过滤虚拟化场景下过滤必须手动完成见下文示例。实战示例以下示例全部继承自官方文档 Examples 章节可直接复制运行。1. 绑定对象作为值与原生表单控件只接受字符串不同reka-ui 支持把复杂对象直接作为值。务必设置displayValue否则选中后输入框无法回显文本script setup langts import { ComboboxContent, ComboboxInput, ComboboxItem, ComboboxPortal, ComboboxRoot } from reka-ui import { ref } from vue const people [ { id: 1, name: Durward Reynolds }, { id: 2, name: Kenton Towne }, { id: 3, name: Therese Wunsch }, { id: 4, name: Benedict Kessler }, { id: 5, name: Katelyn Rohan }, ] const selectedPeople ref(people[0]) /script template ComboboxRoot v-modelselectedPeople ComboboxInput :display-value(v) v.name / ComboboxPortal ComboboxContent ComboboxItem v-forperson in people :keyperson.id :valueperson :disabledperson.unavailable {{ person.name }} /ComboboxItem /ComboboxContent /ComboboxPortal /ComboboxRoot /template要点displayValue接收当前模型值、返回字符串ComboboxItem的:valueperson直接绑定整个对象。当两个对象需要按特定字段比较时可在 Root 上设置byid。2. 多选为 Root 传入数组类型的v-model即可开启多选script setup langts import { ComboboxRoot } from reka-ui import { ref } from vue const people [ { id: 1, name: Durward Reynolds }, { id: 2, name: Kenton Towne }, { id: 3, name: Therese Wunsch }, { id: 4, name: Benedict Kessler }, { id: 5, name: Katelyn Rohan }, ] const selectedPeople ref([people[0], people[1]]) /script template ComboboxRoot v-modelselectedPeople multiple … /ComboboxRoot /template多选模式下选中项不会关闭面板displayValue不生效配合ComboboxTagsInput可构建标签式多选输入仓库示例见 docs/components/examples/ComboboxTagsInput/。3. 自定义过滤Root 内部默认基于条目渲染文本过滤但你也可以用useFilter组合自己的逻辑并设置ignoreFiltertrue关闭内置过滤script setup langts import { ComboboxContent, ComboboxInput, ComboboxItem, ComboboxPortal, ComboboxRoot, useFilter } from reka-ui import { ref } from vue const people [ { id: 1, name: Durward Reynolds }, { id: 2, name: Kenton Towne }, { id: 3, name: Therese Wunsch }, { id: 4, name: Benedict Kessler }, { id: 5, name: Katelyn Rohan }, ] const selectedPeople ref(people[0]) const searchTerm ref() const { startsWith } useFilter({ sensitivity: base }) const filteredPeople computed(() people.filter(p startsWith(p.name, searchTerm.value))) /script template ComboboxRoot v-modelselectedPeople :ignore-filtertrue ComboboxInput v-modelsearchTerm / ComboboxPortal ComboboxContent ComboboxItem v-forperson in filteredPeople :keyperson.id :valueperson {{ person.name }} /ComboboxItem /ComboboxContent /ComboboxPortal /ComboboxRoot /templateuseFilter是库导出的过滤工具{ sensitivity: base }表示大小写不敏感除startsWith外还提供contains等谓词见下方虚拟化示例。此时ComboboxInput的v-model绑定搜索词本身过滤完全由你掌控。4. 自定义标签无障碍标注默认情况下Combobox 用输入内容作为屏幕阅读器的标签如需更精确地控制朗读内容使用 Label 组件详见 docs/content/meta/Label.mdscript setup langts import { ComboboxInput, ComboboxRoot, Label } from reka-ui import { ref } from vue /script template ComboboxRoot v-modelselectedPeople Label forpersonPerson: /Label ComboboxInput idperson placeholderSelect a person / … /ComboboxRoot /template5. 禁用条目通过data-disabled属性为禁用项添加特殊样式template ComboboxRoot ComboboxInput / ComboboxPortal ComboboxContent ComboboxItem classComboboxItem disabled … /ComboboxItem /ComboboxContent /ComboboxPortal /ComboboxRoot /template/* styles.css */ .ComboboxItem[data-disabled] { color: gainsboro; }6. 使用分隔符用ComboboxSeparator在条目之间插入分隔线template ComboboxRoot ComboboxInput / ComboboxPortal ComboboxContent ComboboxItem…/ComboboxItem ComboboxItem…/ComboboxItem ComboboxItem…/ComboboxItem ComboboxSeparator / ComboboxItem…/ComboboxItem ComboboxItem…/ComboboxItem ComboboxItem…/ComboboxItem /ComboboxContent /ComboboxPortal /ComboboxRoot /template7. 分组条目用ComboboxGroup与ComboboxLabel把条目组织成带标题的分区template ComboboxRoot ComboboxInput / ComboboxPortal ComboboxContent ComboboxGroup ComboboxLabelLabel/ComboboxLabel ComboboxItem…/ComboboxItem ComboboxItem…/ComboboxItem ComboboxItem…/ComboboxItem /ComboboxGroup /ComboboxContent /ComboboxPortal /ComboboxRoot /template8. 复杂条目内容条目内可以使用任意自定义内容头像、图标等。注意当 children 不是纯文本时应给ComboboxItem设置textValue以保证搜索命中template ComboboxRoot ComboboxInput / ComboboxPortal ComboboxContent ComboboxItem img src… Adolfo Hess ComboboxItemIndicator / /ComboboxItem … /ComboboxContent /ComboboxPortal /ComboboxRoot /template9. 阻止默认选中行为默认情况下选中ComboboxItem会关闭面板并更新modelValue。通过select.prevent可阻止这一行为——这在自定义 Command Menu 中正是关键手段template ComboboxRoot ComboboxInput / ComboboxPortal ComboboxContent ComboboxItem select.prevent Item A /ComboboxItem … /ComboboxContent /ComboboxPortal /ComboboxRoot /template10. 带可用过滤的虚拟化 Combobox虚拟化场景下过滤必须手动完成后再传给虚拟器文档中的警告原文Combobox itemsmustbe filtered manually before passing them over to the virtualizer因为内置过滤依赖真实 DOM 文本而虚拟化只渲染可视区条目。下方示例生成 10 万条数据用useFilter的contains手动过滤script setup langts import { ComboboxContent, ComboboxInput, ComboboxItem, ComboboxPortal, ComboboxRoot, ComboboxViewport, ComboboxVirtualizer, useFilter } from reka-ui import { computed, ref } from vue const people Array.from({ length: 100000 }).map((_, id) ({ id, name: Person #${id} })) const selectedPeople ref(people[0]) const searchTerm ref() const { contains } useFilter({ sensitivity: base }) const filteredPeople computed(() people.filter(p contains(p.name, searchTerm.value))) /script template ComboboxRoot v-modelselectedPeople ComboboxInput v-modelsearchTerm / ComboboxPortal ComboboxContent classmax-h-[40vh] overflow-hidden ComboboxViewport ComboboxVirtualizer v-slot{ option } :optionsfilteredPeople :text-content(x) x.name :estimate-size24 ComboboxItem :valueoption {{ option.name }} /ComboboxItem /ComboboxVirtualizer /ComboboxViewport /ComboboxContent /ComboboxPortal /ComboboxRoot /templatetextContent用于类型前置type-ahead功能estimate-size为条目预估高度虚拟器底层基于tanstack/vue-virtual见 ComboboxVirtualizer.vue。虚拟化的通用机制可进一步阅读仓库的 虚拟化指南。无障碍与键盘交互组件遵循 WAI-ARIA 的 Combobox 设计模式ARIA 模式下参照 Listbox 模式相关标准说明见文档 combobox.md。键盘交互汇总如下按键行为Enter焦点在ComboboxItem上时选中当前聚焦条目ArrowDown焦点在ComboboxInput上时展开列表焦点在条目上时移动到下一项ArrowUp焦点在ComboboxInput上时展开列表焦点在条目上时移动到上一项Esc关闭列表并把选中项还原回ComboboxInput输入框结合源码来看方向键的输入框上展开逻辑位于 ComboboxInput.vue 的handleKeyDownkeydown.down.up触发先preventDefault再展开条目间的高亮移动由底层 Listbox 的 roving focus 管理Esc 关闭与焦点还原由 DismissableLayer / FocusScope 协作完成handleBlur中通过requestAnimationFrame延迟判断避免在两个 Combobox 之间切换焦点时误关列表。自定义 API用 Combobox 构建 Command Menu你可以把原始部件抽象成自己的组件构建自定义 API。官方文档以Command Menu命令面板为例把ComboboxRoot包装为Command、ComboboxItem包装为CommandItem。Usagescript setup langts import { Command, CommandItem } from ./your-command /script template Command CommandItem value1 Item 1 /CommandItem CommandItem value2 Item 2 /CommandItem CommandItem value3 Item 3 /CommandItem /Command /templateImplementation导出文件// your-command.ts export { default as Command } from Command.vue export { default as CommandItem } from CommandItem.vueCommand.vue的实现要点利用useForwardPropsEmits透传全部 Root Props/Emits强制:opentrue常开对ComboboxContent逐一声明escape-key-down.prevent、focus-outside.prevent、interact-outside.prevent、pointer-down-outside.prevent使面板在命令面板语义下不因外部交互而关闭!-- Command.vue -- script setup langts import type { ComboboxRootEmits, ComboboxRootProps } from reka-ui import { CheckIcon, ChevronDownIcon, ChevronUpIcon, } from radix-icons/vue import { ComboboxContent, ComboboxInput, ComboboxPortal, ComboboxRoot, useForwardPropsEmits } from reka-ui const props definePropsComboboxRootProps() const emits defineEmitsComboboxRootEmits() const forward useForwardPropsEmits(props, emits) /script template ComboboxRoot v-bindforward :opentrue model-value ComboboxInput placeholderType a command or search… / ComboboxPortal ComboboxContent escape-key-down.prevent focus-outside.prevent interact-outside.prevent pointer-down-outside.prevent ComboboxViewport slot / /ComboboxViewport /ComboboxContent /ComboboxPortal /ComboboxRoot /templateComboboxItem.vue同样透传全部 Props并加上select.prevent——命令面板选中命令后不关闭、不写入值而是交给你的业务逻辑处理!-- ComboboxItem.vue -- script setup langts import type { ComboboxItemProps } from reka-ui import { CheckIcon } from radix-icons/vue import { ComboboxItem } from reka-ui const props definePropsComboboxItemProps() /script template ComboboxItem v-bindprops select.prevent slot / /ComboboxItem /template这个模式的关键是属性透传 事件阻止正是前文select事件可preventDefault、escapeKeyDown等 DismissableLayer 事件可阻止的 API 设计所支撑的。仓库还有更完整的 Command Menu 示例可以参考 docs/components/examples/DialogCommandMenu/它把命令面板与 Dialog 结合模拟了 CmdK 唤起搜索的场景。源码结构速查如果想深入源码推荐从以下文件入手packages/core/src/Combobox/ComboboxRoot.vue状态中枢PopperRoot ListboxRoot 组合filterState过滤计算packages/core/src/Combobox/ComboboxInput.vue输入、IME 组合输入、焦点/展开联动、displayValue回显packages/core/src/Combobox/ComboboxItem.vue条目注册、过滤渲染、单选/多选选中逻辑、空字符串值校验packages/core/src/Combobox/ComboboxContentImpl.vuePopper 定位、DismissableLayer、hideWhenEmpty、CSS 变量映射packages/core/src/Combobox/ComboboxVirtualizer.vue虚拟化容器与isVirtual标记packages/core/src/Combobox/Combobox.test.ts组件行为测试用例packages/core/src/Combobox/story/多场景故事文件多选、异步选项、对象值、虚拟列表、手动过滤等。小结Combobox 是 radix-vue 中最具组合能力的输入型组件之一它复用 Listbox 的选择状态与 Popper 的浮层定位通过 16 个职责单一的部件拼装出从简单搜索下拉到复杂命令面板的完整方案。把握住三个关键点即可上手Root 持有全部状态modelValue/open/filterState、Content 决定定位与挂载方式inline/popper/forceMount、Item 负责过滤注册与选中行为textValue/select.prevent。结合useFilter与ComboboxVirtualizer即使面对数十万条数据也能构建出过滤流畅、键盘友好、符合 WAI-ARIA 规范的搜索选择体验。【免费下载链接】radix-vueAn open-source UI component library for building high-quality, accessible design systems and web apps for Vue. Previously Radix Vue项目地址: https://gitcode.com/GitHub_Trending/ra/radix-vue创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表