Appearance
Combobox 组合框
输入关键词过滤并选择候选项。异步请求由业务层处理。
命令行安装
bash
npx @loongship-kit/ui add combobox组件结构
| 角色 | 组件 | 职责 | 使用条件 |
|---|---|---|---|
| 根组件 | Combobox | 管理选中值、搜索词和展开状态 | 必需 |
| 输入与锚点 | ComboboxAnchor、ComboboxInput | 输入搜索词并确定浮层锚点 | 常规用法需要 |
| 内容容器 | ComboboxContent、ComboboxViewport | 定位内容并承载结果列表 | 常规用法需要 |
| 结果内容 | ComboboxItem、ComboboxEmpty | 渲染可选项和空状态 | 选项必需,空状态按需 |
基础用法
查看代码
vue
<Combobox v-model="port">
<ComboboxAnchor>
<ComboboxInput placeholder="Search port" />
</ComboboxAnchor>
<ComboboxContent>
<ComboboxViewport>
<ComboboxEmpty>No port found.</ComboboxEmpty>
<ComboboxItem v-for="item in ports" :key="item" :value="item">
{{ item }}
</ComboboxItem>
</ComboboxViewport>
</ComboboxContent>
</Combobox>多选
已选择:无
查看代码
vue
<template>
<div class="vp-demo-control">
<Combobox v-model="selectedPorts" multiple>
<ComboboxAnchor><ComboboxInput placeholder="Select ports" /></ComboboxAnchor>
<ComboboxContent>
<ComboboxViewport>
<ComboboxEmpty>No port found.</ComboboxEmpty>
<ComboboxItem v-for="item in ports" :key="item" :value="item">{{ item }}</ComboboxItem>
</ComboboxViewport>
</ComboboxContent>
</Combobox>
<p>已选择:{{ selectedPorts.join(', ') || '无' }}</p>
</div>
</template>远程搜索
处理远程请求竞态
远程搜索时设置 ignore-filter,由业务代码请求并渲染结果。下面用延时模拟接口;生产环境还应取消或忽略过期请求。ShipSearch 已封装船舶搜索场景。
查看代码
vue
<template>
<div class="vp-demo-control">
<Combobox v-model="remotePort" ignore-filter>
<ComboboxAnchor>
<ComboboxInput placeholder="Search remote ports" @update:model-value="searchPorts" />
</ComboboxAnchor>
<ComboboxContent>
<ComboboxViewport>
<div v-if="remoteLoading">Loading...</div>
<template v-else>
<ComboboxEmpty>No port found.</ComboboxEmpty>
<ComboboxItem v-for="item in remoteItems" :key="item" :value="item">{{
item
}}</ComboboxItem>
</template>
</ComboboxViewport>
</ComboboxContent>
</Combobox>
</div>
</template>API
Combobox(主组件)
属性
| 属性 | 类型 | 默认值 | 说明 |
|---|---|---|---|
v-model | T | T[] | - | 当前值 |
defaultValue | T | T[] | - | 非受控模式的初始值 |
v-model:open | boolean | - | 展开状态 |
defaultOpen | boolean | false | 非受控模式的初始展开状态 |
multiple | boolean | false | 是否允许多选 |
disabled | boolean | false | 是否禁用 |
name | string | - | 表单字段名 |
required | boolean | false | 是否为必填表单字段 |
by | string | ((a, b) => boolean) | - | 对象选项的比较字段或比较函数 |
dir | 'ltr' | 'rtl' | 'ltr' | 阅读方向 |
ignoreFilter | boolean | false | 禁用内置过滤,常用于远程搜索 |
openOnFocus | boolean | false | 输入框聚焦时展开 |
openOnClick | boolean | false | 点击输入框时展开 |
resetSearchTermOnBlur | boolean | true | 输入框失焦时重置搜索词 |
resetSearchTermOnSelect | boolean | true | 选择选项后重置搜索词 |
resetModelValueOnClear | boolean | false | 清空搜索词时同时清空选中值 |
highlightOnHover | boolean | true | 指针悬停选项时是否高亮 |
事件
| 事件 | 参数 | 说明 |
|---|---|---|
update:modelValue | value: T | T[] | 选中值变化 |
update:open | value: boolean | 展开状态变化 |
highlight | { ref: HTMLElement, value: T } | undefined | 高亮选项变化 |
插槽
| 插槽 | 参数 | 说明 |
|---|---|---|
default | { open: boolean, modelValue: T | T[] } | 放置输入框和选项内容 |
子组件
ComboboxInput — 搜索输入框
属性
| 属性 | 类型 | 默认值 | 说明 |
|---|---|---|---|
v-model | string | - | 搜索词 |
displayValue | (value: T) => string | - | 单选对象值在输入框中的显示文本 |
autoFocus | boolean | false | 挂载后自动聚焦 |
disabled | boolean | false | 是否禁用 |
as | string | Component | 'input' | 渲染元素 |
asChild | boolean | false | 将行为绑定到唯一子元素 |
事件
| 事件 | 参数 | 说明 |
|---|---|---|
update:modelValue | value: string | 搜索词变化 |
插槽
| 插槽 | 参数 | 说明 |
|---|---|---|
default | 无 | asChild 时放置唯一的自定义输入元素 |
ComboboxContent — 结果浮层容器
属性
| 属性 | 类型 | 默认值 | 说明 |
|---|---|---|---|
position | 'inline' | 'popper' | 'inline' | 定位模式 |
bodyLock | boolean | false | 展开时是否锁定页面滚动 |
hideWhenEmpty | boolean | false | 没有匹配项时是否隐藏内容 |
disableOutsidePointerEvents | boolean | false | 是否阻止浮层外的指针交互 |
side | 'top' | 'right' | 'bottom' | 'left' | 'bottom' | popper 模式的方向 |
sideOffset | number | 0 | 与锚点的距离 |
align | 'start' | 'center' | 'end' | 'center' | 与锚点的对齐方式 |
alignOffset | number | 0 | 对齐偏移 |
事件
| 事件 | 参数 | 说明 |
|---|---|---|
escapeKeyDown | KeyboardEvent | 按下 Escape |
pointerDownOutside | PointerDownOutsideEvent | 在内容外按下指针;可阻止默认行为 |
focusOutside | FocusOutsideEvent | 焦点移到内容外;可阻止默认行为 |
interactOutside | PointerDownOutsideEvent | FocusOutsideEvent | 在内容外发生交互 |
插槽
| 插槽 | 参数 | 说明 |
|---|---|---|
default | 无 | 放置 ComboboxViewport 和结果内容 |
ComboboxItem — 可选择结果项
属性
| 属性 | 类型 | 默认值 | 说明 |
|---|---|---|---|
value | T | - | 选择该项时写入的值,必填 |
disabled | boolean | false | 是否禁用该项 |
textValue | string | - | 非纯文本内容用于过滤的文本表示 |
as | string | Component | 'div' | 渲染元素 |
asChild | boolean | false | 将行为绑定到唯一子元素 |
事件
| 事件 | 参数 | 说明 |
|---|---|---|
select | CustomEvent | 选中前触发;可调用 preventDefault() |
插槽
| 插槽 | 参数 | 说明 |
|---|---|---|
default | 无 | 渲染选项内容 |
ComboboxAnchor / ComboboxViewport / ComboboxEmpty — 锚点、视口与空状态
| 组件 | 常用属性 | 默认插槽 |
|---|---|---|
ComboboxAnchor | as、asChild、reference | 放置 ComboboxInput |
ComboboxViewport | as、asChild、nonce | 放置选项和空状态 |
ComboboxEmpty | as、asChild | 没有匹配项时显示的内容 |