Cascader 级联选择器
当一个数据集合有清晰的层级结构时,可通过级联选择器逐级查看并选择。
基础用法
请选择
选中值:空
vue
<my-cascader v-model="value" :options="options" />
const options = [
{ label: '北京', value: 'beijing', children: [
{ label: '海淀区', value: 'haidian' },
{ label: '朝阳区', value: 'chaoyang' },
]},
{ label: '上海', value: 'shanghai', children: [...] },
{ label: '广东', value: 'guangdong', children: [
{ label: '广州', value: 'guangzhou', children: [...] },
]},
]有禁用选项
通过 disabled: true 禁用特定选项。
请选择
vue
const options = [
{ label: '上海', value: 'shanghai', disabled: true },
{ label: '北京', value: 'beijing', children: [
{ label: '朝阳区', value: 'chaoyang', disabled: true },
]},
]可清空
clearable 属性在选中后显示清除按钮。
请选择
vue
<my-cascader v-model="value" :options="options" clearable />自定义清除图标
通过 #clearIcon 插槽自定义清除按钮图标。
请选择
vue
<my-cascader v-model="value" :options="options" clearable>
<template #clearIcon>
<svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" stroke-width="2"><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></svg>
</template>
</my-cascader>仅显示最后一级
showAllLevels="false" 时,选中后只展示最后一级的标签。
showAllLevels=true(默认)
请选择
showAllLevels=false
请选择
vue
<my-cascader v-model="value" :options="options" :showAllLevels="false" />
<!-- 选中后显示 "西湖区" 而非 "浙江 / 杭州 / 西湖区" -->多选
multiple 属性开启多选模式,节点前出现复选框。
请选择
已选:0 项
vue
<my-cascader v-model="value" :options="options" multiple clearable />选择任意一级
checkStrictly 允许选择任意层级的节点,不限于叶子节点。
请选择
可选择父节点:空
vue
<my-cascader v-model="value" :options="options" checkStrictly />
<!-- 可选择 "产品" 而不必选择子级 -->动态加载
lazy + lazyLoad 实现子节点异步加载。
请选择
vue
const options = [
{ label: '浙江', value: 'zhejiang', leaf: false },
{ label: '江苏', value: 'jiangsu', leaf: false },
]
function lazyLoad(node, resolve) {
setTimeout(() => {
resolve([{ label: '杭州', value: 'hangzhou' }, ...])
}, 500)
}
<my-cascader v-model="value" :options="options" lazy :lazyLoad="lazyLoad" />可搜索
filterable 开启关键词搜索过滤。
请选择
vue
<my-cascader v-model="value" :options="options" filterable />自定义节点内容
通过 #node 插槽自定义每个节点的渲染内容。
请选择
vue
<my-cascader v-model="value" :options="options">
<template #node="{ node, level }">
<span>{{ node.label }} ({{ node.children?.length || 0 }})</span>
</template>
</my-cascader>级联面板
无触发器的纯面板模式,可嵌入其他容器中使用。
地区选择
选择省份
北京
上海
广东
选择城市
选择区县
选中:空
vue
<!-- 级联面板可直接使用嵌套的菜单结构 -->
<div class="cascade-panel">
<div class="column">
<div class="item">省份</div>
</div>
<div class="column">
<div class="item">城市</div>
</div>
</div>自定义标签
collapseTags 折叠多选标签,溢出的标签折叠为 +N。
collapseTags=false(默认完整展示)
请选择
collapseTags=true(溢出的折叠)
请选择
vue
<my-cascader v-model="value" :options="options" multiple collapseTags />
<!-- 选中多项后显示: "海淀区 +2" -->点击选中节点
checkStrictly + multiple 组合,点击任意层级节点即可选中,适合标签分类场景。
请选择
可选父级和子级:0 项
vue
<my-cascader v-model="value" :options="options" multiple checkStrictly />
<!-- 可同时选中 "产品" 和 "软件" -->自定义头部与底部
#header 和 #footer 插槽自定义面板顶部和底部。
请选择
vue
<my-cascader v-model="value" :options="options">
<template #header>
<span>请选择地区</span>
<span @click="value=[]">重置</span>
</template>
<template #footer>
<my-button size="small">取消</my-button>
<my-button size="small" type="primary">确认</my-button>
</template>
</my-cascader>自定义面板宽度
panelWidth 调整触发器和面板宽度。
请选择
vue
<my-cascader v-model="value" :options="options" panelWidth="320px" />
<my-cascader v-model="value" :options="options" panelWidth="100%" />组件结构
根元素 .my-cascader 包含触发器区域(标签、占位文字、清除按钮、箭头)和下拉面板(可选的头部/底部插槽、搜索框、多列菜单)。
CSS 类名
| 类名 | 说明 |
|---|---|
.my-cascader | 根元素 |
.my-cascader.is-disabled | 禁用状态 |
.my-cascader__trigger | 触发器区域 |
.my-cascader__tags | 多选标签容器 |
.my-cascader__tag | 单个标签 |
.my-cascader__tag-close | 标签关闭按钮 |
.my-cascader__placeholder | 占位文字 |
.my-cascader__value | 已选值文字 |
.my-cascader__clear | 清除按钮 |
.my-cascader__arrow | 下拉箭头 |
.my-cascader__arrow.is-open | 面板打开状态(箭头旋转 180 度) |
.my-cascader__panel | 下拉面板 |
.my-cascader__panel-header | 面板头部(header 插槽) |
.my-cascader__panel-footer | 面板底部(footer 插槽) |
.my-cascader__filter | 搜索过滤区域 |
.my-cascader__filter-input | 搜索输入框 |
.my-cascader__columns | 多列菜单容器 |
.my-cascader__menu | 单列菜单 |
.my-cascader__item | 菜单项 |
.my-cascader__item.is-active | 当前选中项 |
.my-cascader__item.is-disabled | 禁用项 |
.my-cascader__item.is-loading | 加载中状态 |
.my-cascader__label | 菜单项文本 |
.my-cascader__next | 下一级箭头图标 |
.my-cascader__empty | 无数据提示 |
.my-cascader__check | 多选框容器 |
.my-cascader__check-box | 多选框 |
.my-cascader__check-box.is-checked | 已勾选状态 |
API
Cascader Props
| 属性 | 说明 | 类型 | 默认值 |
|---|---|---|---|
| modelValue | 选中值 (v-model) | (string | number)[] | (string | number)[][] | — |
| options | 选项列表 | CascaderOption[] | [] |
| placeholder | 占位文字 | string | '请选择' |
| disabled | 禁用 | boolean | false |
| clearable | 可清空 | boolean | false |
| filterable | 可搜索 | boolean | false |
| multiple | 多选 | boolean | false |
| showAllLevels | 显示完整路径 | boolean | true |
| checkStrictly | 可选任意一级 | boolean | false |
| leafOnly | 仅叶子可选 | boolean | false |
| separator | 路径分隔符 | string | ' / ' |
| collapseTags | 折叠标签 | boolean | false |
| panelWidth | 面板宽度 | string | — |
| lazy | 动态加载 | boolean | false |
| lazyLoad | 加载函数 | (node, resolve) => void | — |
| propsAlias | 字段别名 | { label, value, children, disabled } | — |
Cascader Events
| 事件 | 说明 | 回调 |
|---|---|---|
| update:modelValue | 值变更 | (value) |
| change | 选中值变更 | (value) |
| visible-change | 面板显隐 | (visible: boolean) |
Cascader Slots
| 名称 | 说明 | 作用域 |
|---|---|---|
| node | 自定义节点内容 | { node, level } |
| clearIcon | 自定义清除图标 | — |
| header | 面板头部 | — |
| footer | 面板底部 | — |
CascaderOption
ts
interface CascaderOption {
label: string
value: string | number
children?: CascaderOption[]
disabled?: boolean
leaf?: boolean // 标记叶子节点(无子级)
}