vue实现穿梭框树组件
Vue 穿梭框树组件实现
穿梭框树组件(Tree Transfer)结合了树形结构和穿梭框功能,常用于权限分配、数据分类等场景。以下是基于 Vue 2/3 的实现方案:
核心功能设计
-
数据结构
树形数据需包含id,label,children等字段,例如:const treeData = [ { id: 1, label: '一级节点', children: [ { id: 4, label: '二级节点-1' }, { id: 5, label: '二级节点-2' } ] } ] -
组件拆分
- 左侧源树(可勾选)
- 右侧目标树(已选择项)
- 中间操作按钮(移动、全选等)
基础实现步骤
1. 树形组件渲染
使用递归组件渲染树形结构,支持复选框勾选:
<template>
<div class="tree-node" v-for="node in data" :key="node.id">
<input
type="checkbox"
v-model="node.checked"
@change="handleCheck(node)"
>
<span>{{ node.label }}</span>
<tree-node
v-if="node.children"
:data="node.children"
@check-change="handleChildCheck"
/>
</div>
</template>
2. 穿梭逻辑
通过 checkedNodes 数组记录已选节点,点击按钮时移动数据:
methods: {
transferToRight() {
this.rightData = [...this.rightData, ...this.getCheckedNodes(this.leftData)];
this.clearChecked(this.leftData);
}
}
3. 父子联动
实现勾选父节点时自动选中所有子节点:

function toggleChildren(node, checked) {
if (node.children) {
node.children.forEach(child => {
child.checked = checked;
this.toggleChildren(child, checked);
});
}
}
进阶优化方案
虚拟滚动支持
对大数据量使用虚拟滚动优化性能:
<virtual-list
:size="50"
:remain="8"
:data="flattenTreeData"
>
<template v-slot="{ item }">
<!-- 树节点渲染 -->
</template>
</virtual-list>
懒加载支持
异步加载子节点数据:
async function loadChildren(node) {
if (!node.childrenLoaded) {
const res = await api.getChildren(node.id);
node.children = res.data;
node.childrenLoaded = true;
}
}
拖拽排序
添加 draggable 属性实现节点拖拽:

<div
draggable
@dragstart="handleDragStart(node)"
@drop="handleDrop(targetNode)"
>
完整示例代码
查看 CodeSandbox 示例
包含以下功能:
- 双向数据绑定
- 搜索过滤
- 自定义图标
- 多级联动选择
第三方库推荐
-
Vue-Element-Tree
基于 ElementUI 的树形穿梭框,支持大量现成功能。 -
Vue-Treeselect
提供树形选择+穿梭框的混合组件,适合复杂场景。 -
Vue-Draggable-Nested-Tree
支持拖拽排序的树形组件,可自行扩展穿梭功能。
实现时需根据项目需求选择合适方案,注意性能优化和可访问性设计。






