TreeSelect

树形选择器,单面板可展开/收起的树,单选叶子或任意节点;支持 multiple 多选(checkbox + 父子联动 + 多 tag 回显 + 收敛策略)、可搜索过滤(本地/远程 + 命中高亮)、异步加载子节点、虚拟滚动大数据树、自定义字段映射与节点/tag/触发器渲染。

设计文档

如何引入

import { TreeSelect } from '@chenzy-design/svelte';

基础树形选择

在树形结构中选择节点,支持搜索过滤与清空

已选:(未选)

多选与折叠

multiple 开启 checkbox 多选与父子联动,maxTagCount 折叠超出标签

已选 2 项:sh、hz

仅选叶子节点

leafOnly 让父节点只展开不选中,仅叶子可作为最终值

仅叶子可选,当前:install

禁用状态

禁用单个节点(disabled 字段)或整体禁用选择器

禁用单个节点
整体禁用

前缀与清除

自定义 prefix 图标、large 尺寸、默认展开指定节点并可一键清除

带前缀图标 + 可清除,当前:cn

内嵌标签与自定义触发器

insetLabel 触发器内嵌标签;triggerRender 完全替换默认选择框(与 Cascader 一致)

insetLabel 内嵌标签,当前:前端
triggerRender 自定义触发器,当前:(未选)

搜索框在触发器

searchPosition='trigger' 配 filterTreeNode,把搜索输入框内嵌到触发器内而非浮层顶部

搜索框内嵌触发器,当前:(未选)

严格禁用

multiple + disableStrictly:勾选父节点不影响 disabled 子节点,禁用态独立

严格禁用:勾选父节点不影响 disabled 子节点。已选 0 项:(未选)

自定义已选项

renderSelectedItem 具名 snippet 自定义已选 tag 渲染(图标 + 自定义样式)

自定义已选项:已选 2 项

命令式搜索

bind:this 拿实例,调用 ref.search(...) 命令式触发面板内搜索

点击按钮后打开面板即可看到过滤结果,当前:(未选)

虚拟化

virtualize 对象开启大数据树虚拟滚动

虚拟化:约 100 个节点,仅渲染视口内行。当前:(未选)

远程搜索

remote 开启后输入仅触发 onSearch,由外部更新 treeData

remote 只触发 onSearch,结果由外部异步回填。当前:(未选)

标签换行

triggerTagWrap 让 trigger 内多选标签自动换行

triggerTagWrap 让多选标签在 trigger 内自动换行。已选 5 项

默认展开

defaultExpandAll 初始化展开;expandAll 动态展开

defaultExpandAll:初始化时展开全部
expandAll:受控动态展开全部

受控

value 完全受控,配合 onChange

value 由外部完全受控,配合 onChange 回写。当前:fe

选中关系

checkRelation=unRelated 时父子选中互不影响

related(默认):父子级联
unRelated:父子互不影响

异步加载

loadData 展开时动态加载子节点

loadData 在展开时按需拉取子节点(约 500ms)。当前:(未选)

API 参考

TreeSelect

Props

属性说明类型默认值
valueTreeKey|TreeKey[]|nullundefined
defaultValueTreeKey|TreeKey[]|nullnull
treeData树数据源;字段名可经 fieldNames 自定义TreeNode[][]
fieldNames自定义节点字段名映射,适配任意后端数据(如 { key:'id', label:'name', children:'sub' })。派生只读映射;onChange 回传的 key 即原始字段值{ key?: string; label?: string; children?: string }{ key:'key', label:'label', children:'children' }
openbooleanundefined
defaultOpenbooleanfalse
multiplecheckbox 多选 + 父子联动,多 tag 回显booleanfalse
checkStrictly多选时父子勾选互不影响(向后兼容,等价 checkRelation=unRelated)booleanfalse
checkRelation多选父子是否级联联动;unRelated 互不影响。checkStrictly=true 强制 unRelated'related'|'unRelated''related'
showCheckedStrategy回填值/Tag 收敛策略:all 全部勾选节点;parent 折叠为父;child 仅叶子。仅 related 生效'all'|'parent'|'child''all'
maxTagCount多选回填 Tag 最大展示数,超出折叠为 +N(仅影响显示)numberundefined
placeholderstring'请选择'
size'small'|'default'|'large'default
status'default'|'warning'|'error'default
disabledbooleanfalse
showClear值不为空时 trigger 展示清除按钮(对齐 Semi)booleanfalse
leafOnlybooleanfalse
defaultExpandAllbooleanfalse
defaultExpandedKeys默认展开的节点 key(非受控初始展开集,与 defaultExpandAll 取并集;对齐 Semi)TreeKey[][]
filterable面板搜索框过滤节点 + 高亮命中booleanfalse
filterTreeNode按输入筛选节点(对齐 Semi):true 开启搜索并默认按 treeNodeFilterProp 包含匹配;函数则自定义匹配谓词。与 filterable 其一为真即显示搜索框boolean | ((inputValue: string, treeNodeString: string, data?: TreeNode) => boolean)undefined
remote远程搜索:输入防抖后仅触发 onSearch,不本地过滤(外部更新 treeData)booleanfalse
searchDebounceonSearch 防抖毫秒(remote 时生效)number300
onSearch远程搜索输入回调(防抖后)(query: string) => voidundefined
showIcon是否预留节点图标位(icon 提供时渲染在 label 前),与 Tree 对齐booleantrue
loadData异步加载子节点:展开未加载的非叶子节点时调用,返回该节点子节点数组(加载中显示 spinner,竞态去重,不写回 treeData)。与 Tree 的 loadData 对齐(node: TreeNode) => Promise<TreeNode[]>undefined
virtualize列表虚拟化(对齐 Semi):传入对象即开启,仅渲染视口内可见行;height 视口高(默认 224)、itemSize 行高(默认 32)。复用 Tree 范式(core fixedRange),保持 role=tree/treeitem 语义{ height?: number; width?: number | string; itemSize?: number }undefined
icon自定义节点图标,showIcon 为真时渲染在 label 前;参数含节点与展开态,与 Tree 的 icon API 对齐Snippet<[{ node: TreeNode; expanded: boolean; level: number }]>undefined
triggerRender完全自定义触发器渲染(替换默认选择框);参数含当前 value/placeholder/isOpen/disabled,与 Cascader.triggerRender 对齐Snippet<[{ value: TreeKey|TreeKey[]|null|undefined; placeholder: string; isOpen: boolean; disabled: boolean }]>undefined
insetLabel触发器内嵌标签,渲染在回填值/占位符之前(对齐 Semi insetLabel),消费 --cd-color/font-tree-select-label tokenSnippet | stringundefined
insetLabelId内嵌标签的 id(a11y 关联用),对齐 Semi insetLabelIdstringundefined
motion下拉浮层开合动画(淡入);与 Cascader/Dropdown 的 motion 对齐。reduced-motion 退化booleantrue
onChange多选返回 checked 全集数组,单选返回单 key(value: TreeKey|TreeKey[]|null) => voidundefined
onOpenChange(open: boolean) => voidundefined
ariaLabelstringundefined
virtualizeThreshold可见扁平行数 ≥ 此值时自动开启虚拟化;传入 virtualize 对象强制开启(超集,Semi 无)number100
position浮层弹出位置(对齐 Semi,参考 Tooltip position);映射到 use:floating placementstring'bottomLeft'
dropdownMatchSelectWidth浮层宽度对齐触发器(min-inline-size = 触发器宽)booleantrue
getPopupContainer浮层挂载容器,缺省 ConfigProvider 全局值再回退 document.body() => HTMLElement | null | undefinedundefined
destroyOnClose关闭即从 DOM 卸载浮层(重开重建);默认首开后保留 DOM 仅隐藏booleanfalse
borderless无边框模式:trigger 边框透明booleanfalse
prefixtrigger 前缀Snippet | stringundefined
suffixtrigger 后缀Snippet | stringundefined
clearIcon自定义清除按钮图标Snippetundefined
expandIcon自定义展开图标;也可传无参 Snippet 统一渲染Snippet<[{ node: TreeNode; expanded: boolean; level: number }]>undefined
arrowIcon自定义右侧下拉箭头(expandIcon 的别名)Snippetundefined
showLine显示节点连接线(垂直导引线)booleanfalse
labelEllipsis节点 label 单行省略截断,可关闭以允许换行booleantrue
style选择框样式stringundefined
autoAdjustOverflow浮层遮挡时自动调整方向booleantrue
validateStatusstatus 的别名(优先于 status)'default'|'error'|'warning'undefined
onBlur失焦回调(e: FocusEvent) => voidundefined
onFocus聚焦回调(e: FocusEvent) => voidundefined
preventScroll聚焦时阻止滚动booleanfalse
outerTopSlot面板顶部外层 slot(在搜索框之上)Snippetundefined
outerBottomSlot面板底部外层 slot(在树之下)Snippetundefined
searchAutoFocus面板打开时搜索框自动获焦booleanfalse
searchPosition搜索框位置:'dropdown' 面板内;'trigger' trigger 内'dropdown'|'trigger''dropdown'
searchPlaceholder搜索框占位文字stringundefined
treeNodeFilterProp搜索过滤属性string'label'
showSearchClear搜索框右侧显示清除按钮(有内容时)booleantrue
showFilteredOnly搜索激活时仅显示命中节点,不显示祖先链booleanfalse
emptyContent无匹配/无数据占位内容(对齐 Semi emptyContent);未传回退 i18n TreeSelect.emptyTextstring | Snippetundefined
searchRender自定义搜索框渲染:false 隐藏内置搜索框;Snippet 完全接管渲染(回调回填输入)boolean | Snippet<[{ value: string; onInput: (v: string) => void; onKeydown: (e: KeyboardEvent) => void; placeholder: string }]>undefined
expandedKeys受控展开的节点 keysTreeKey[]undefined
expandAll动态全部展开(受控/动态,区别于 defaultExpandAll)booleanfalse
expandAction行点击展开方式:false 仅展开按钮;'click' 单击行;'doubleClick' 双击行false | 'click' | 'doubleClick'false
autoExpandParent展开节点时自动展开其所有祖先链booleanfalse
motionExpand展开/折叠动画booleantrue
onExpand节点展开回调(expandedKeys: TreeKey[], info: { expanded: boolean; node: unknown }) => voidundefined
autoMergeValue自动合并值:父节点全选时 value 不含后代(等价 showCheckedStrategy='parent')booleantrue
onChangeWithObjectonChange 回调携带完整节点对象而非仅 keybooleanfalse
showRestTagsPopover多选 maxTagCount 折叠出 +N 时,hover +N 用 Popover 浮层展示折叠掉的剩余全部 Tagbooleanfalse
restTagsPopoverProps透传给剩余 Tag Popover 浮层的额外 props(在默认 trigger=hover/position=top 之后展开,可覆盖)Record<string, unknown>undefined
triggerTagWraptrigger 多选 tags 换行显示(默认单行截断折叠)booleanfalse
renderLabel自定义节点 label 渲染(仅替换文字部分)Snippet<[{ label: string; data: TreeNode; searchWord: string }]>undefined
renderFullLabel完全自定义节点行渲染(替换整行内容)Snippet<[{ node: TreeNode; expanded: boolean; level: number; checked: boolean; halfChecked: boolean; selected: boolean }]>undefined
renderSelectedItem自定义 trigger 已选 tag 渲染(多选时每个 tag 独立渲染)Snippet<[{ node: TreeNode; onRemove: () => void }]>undefined
treeNodeLabelProp节点数据中用作显示 label 的字段名string'label'
keyMaps自定义 key/label/value 字段映射(优先级高于 fieldNames 的 key/label 部分){ key?: string; label?: string; value?: string }undefined
optionListStyle选项列表容器的内联 stylestring | Record<string, string>undefined
loadedKeys受控已加载的节点 keysSet<TreeKey>undefined
clickToHide单选选中后自动关闭面板booleantrue
clickTriggerToHide面板开启时点击 trigger 关闭面板booleantrue
disableStrictly严格禁用:disabled 节点不因父节点联动而影响,禁用态独立booleanfalse
dropdownMargin浮层与 trigger 的额外间距(px);数字映射到浮层 offset,对象取 marginTopnumber | { marginTop?: number; marginBottom?: number; marginLeft?: number; marginRight?: number }undefined
dropdownClassName追加到浮层根节点的自定义类名(与内置类名并存)stringundefined
dropdownStyle合并进浮层根节点的内联样式(不覆盖内置定位样式)string | Record<string, string>undefined
zIndex浮层层级(z-index),未传由 CSS 控制numberundefined
onClear点击清除按钮回调(e: MouseEvent) => voidundefined
onSelect节点选中回调(selectedKey: TreeKey, selected: boolean, node: unknown) => voidundefined
onLoad异步加载完成回调(含已加载 key 集合与当前节点)(loadedKeys: TreeKey[], treeNode: TreeNode) => voidundefined
onVisibleChange面板可见性变化回调(与 onOpenChange 语义相同,Semi 风格别名)(isVisible: boolean) => voidundefined

Methods

属性类型说明
search(sugInput)命令式搜索:把值置给内部搜索态并触发过滤(对齐 Semi,用于外部自定义搜索框)

Accessibility

ARIA rolecombobox
  • combobox 触发器 + role="tree" 面板 + role="treeitem"
  • 有 children 节点 aria-expanded 标记展开态
  • aria-selected 标记选中节点
  • leafOnly 时非叶子节点仅切换展开,不可选

设计变量

变量默认值用法
--cd-color-tree-option-bg-active var(--cd-color-primary-light-default)树选项选中/激活背景($color-tree_option-bg-active)
--cd-color-tree-option-bg-hover var(--cd-color-fill-0)树选项悬停背景($color-tree_option-bg-hover)
--cd-color-tree-option-disabled-text-default var(--cd-color-disabled-text)禁用树选项文字颜色($color-tree_option_disabled-text-default)
--cd-color-tree-option-draggable-insert-border-default var(--cd-color-primary)可拖拽插入指示线颜色($color-tree_option_draggable_insert-border-default)
--cd-color-tree-option-highlight-text var(--cd-color-primary)搜索命中高亮文本色($color-tree_option_hightlight-text)
--cd-color-tree-option-icon-active var(--cd-color-black)展开图标按下色($color-tree_option-icon-active)
--cd-color-tree-option-icon-default var(--cd-color-text-2)展开箭头 / 节点图标颜色($color-tree_option-icon-default)
--cd-color-tree-option-icon-hover var(--cd-color-text-0)展开图标悬停色($color-tree_option-icon-hover)
--cd-color-tree-option-line var(--cd-color-text-3)showLine 连接线颜色(Semi 用 --semi-color-text-3)
--cd-color-tree-option-loading-icon-default var(--cd-color-primary)树选项加载 spin 颜色($color-tree_option_loading-icon-default)