文章目录
- 一、项目初始化
- 1.1 技术栈说明
- 1.2 项目结构图(Mermaid)
- 二、构建基础表格组件
- 2.1 创建基本表格结构
- 三、实现行拖拽排序
- 3.1 安装依赖
- 3.2 使用 `vuedraggable` 实现拖拽
- 四、实现列宽拖拽调整
- 4.1 基本样式设置
- 4.2 添加拖拽逻辑
- 五、实现列拖拽排序
- 5.1 转换列为可拖拽结构
- 5.2 保证数据对应正确列
- 六、可拓展功能实现
- 6.1 固定列实现(示意)
- 6.2 列顺序保存到本地存储
- 七、总结
一、项目初始化
1.1 技术栈说明
- Vue 3 Composition API
vuedraggable
:用于实现拖拽排序- 原生 DOM 操作:用于列宽调整
- Element Plus(可选):用于样式和表格基础结构
1.2 项目结构图(Mermaid)
二、构建基础表格组件
2.1 创建基本表格结构
<!-- TableComponent.vue -->
<template><div class="table-container"><table><thead><tr><th v-for="(col, index) in columns" :key="col.key">{{ col.label }}</th></tr></thead><tbody><tr v-for="(row, rowIndex) in tableData" :key="row.id"><td v-for="col in columns" :key="col.key">{{ row[col.key] }}</td></tr></tbody></table></div>
</template><script setup>
import { ref } from 'vue'const columns = ref([{ label: '姓名', key: 'name' },{ label: '年龄', key: 'age' },{ label: '地址', key: 'address' }
])const tableData = ref([{ id: 1, name: '小明', age: 25, address: '北京' },{ id: 2, name: '小红', age: 30, address: '上海' },{ id: 3, name: '小刚', age: 28, address: '广州' }
])
</script>
三、实现行拖拽排序
3.1 安装依赖
npm install vuedraggable
3.2 使用 vuedraggable
实现拖拽
<template><draggable v-model="tableData" tag="tbody" item-key="id"><tr v-for="row in tableData" :key="row.id"><td v-for="col in columns" :key="col.key">{{ row[col.key] }}</td></tr></draggable>
</template><script setup>
import draggable from 'vuedraggable'
</script>
四、实现列宽拖拽调整
4.1 基本样式设置
th {position: relative;padding-right: 8px;
}.resizer {position: absolute;top: 0;right: 0;width: 5px;cursor: col-resize;user-select: none;
}
4.2 添加拖拽逻辑
<thv-for="(col, index) in columns":key="col.key":style="{ width: col.width + 'px' }"@mousedown="startResize($event, index)"
>{{ col.label }}<span class="resizer"></span>
</th>let startX, startWidthconst startResize = (e, index) => {startX = e.clientXstartWidth = columns.value[index].width || 100document.addEventListener('mousemove', resize)document.addEventListener('mouseup', stopResize)function resize(e) {const newWidth = startWidth + (e.clientX - startX)columns.value[index].width = Math.max(newWidth, 60)}function stopResize() {document.removeEventListener('mousemove', resize)document.removeEventListener('mouseup', stopResize)}
}
五、实现列拖拽排序
5.1 转换列为可拖拽结构
<draggable v-model="columns" tag="tr" item-key="key" direction="horizontal"><thv-for="(col, index) in columns":key="col.key":style="{ width: col.width + 'px' }"@mousedown="startResize($event, index)">{{ col.label }}<span class="resizer"></span></th>
</draggable>
5.2 保证数据对应正确列
<tr v-for="row in tableData" :key="row.id"><td v-for="col in columns" :key="col.key">{{ row[col.key] }}</td>
</tr>
六、可拓展功能实现
6.1 固定列实现(示意)
<th :class="{ 'sticky-left': index === 0 }"> ... </th>
.sticky-left {position: sticky;left: 0;background-color: #fff;z-index: 2;
}
6.2 列顺序保存到本地存储
watch(columns, (val) => {localStorage.setItem('columns', JSON.stringify(val))
}, { deep: true })onMounted(() => {const saved = localStorage.getItem('columns')if (saved) {columns.value = JSON.parse(saved)}
})
七、总结
通过本文,我们使用 Vue 3 实现了一个具备以下功能的可配置表格组件:
- ✅ 行拖拽排序
- ✅ 列宽度调整
- ✅ 列顺序拖拽
- ✅ 固定列支持
- ✅ 用户列设置持久化
该组件可广泛应用于数据管理后台、内容管理系统等场景,未来可继续拓展如列隐藏、分组列头、自定义渲染等功能。
到这里,这篇文章就和大家说再见啦!我的主页里还藏着很多 篇 前端 实战干货,感兴趣的话可以点击头像看看,说不定能找到你需要的解决方案~
创作这篇内容花了很多的功夫。如果它帮你解决了问题,或者带来了启发,欢迎:
点个赞❤️ 让更多人看到优质内容
关注「前端极客探险家」🚀 每周解锁新技巧
收藏文章⭐️ 方便随时查阅
📢 特别提醒:
转载请注明原文链接,商业合作请私信联系
感谢你的阅读!我们下篇文章再见~ 💕