優(yōu)雅的將ElementUI表格變身成樹形表格的方法步驟
由于ElementUI目前還未開發(fā)樹形表格組件,也參閱了網(wǎng)絡(luò)上部分基于ElementUI表格封裝的開源樹形組件,如果想進(jìn)行二次開發(fā)的話都不太理想,所以就萌生了自行開發(fā)樹形表格。
本示例提供開發(fā)思路,移除了多余的樣式,比較適合新手入門學(xué)習(xí),如果應(yīng)用于實(shí)際項(xiàng)目還請自行封裝。
目前還僅僅實(shí)現(xiàn)了視覺的樹結(jié)構(gòu)的層級效果和控制結(jié)構(gòu)的顯示隱藏,后續(xù)還會進(jìn)行不斷的完善和優(yōu)化,有必要的話會對組件進(jìn)行二次封裝,有點(diǎn)在重復(fù)造論的感覺哈。
效果圖

完整代碼
頁面(tree-table.vue)
<template>
<div>
TreeTable
<el-table :data="list" :row-style="tableRowStyle" border>
<el-table-column type="selection" width="55"></el-table-column>
<el-table-column prop="id" label="ID" width="180">
<template slot-scope="scope">
<span class="collapse"
:class="collapseClass(scope.row)"
:style="tableRowPaddingStyle(scope.row)"
@click="handleCollapseClick(scope.row)">
</span>
<span>{{ scope.row.id }}</span>
</template>
</el-table-column>
<el-table-column prop="name" label="NAME"></el-table-column>
</el-table>
</div>
</template>
<script lang="ts">
import {Component, Vue} from 'vue-property-decorator'
// 引入兩個封裝好的工具方法
import { arrayToTree } from './utils/array.js'
import { ergodicTree } from './utils/tree.js'
@Component
export default class TreeTable extends Vue {
private list: object[] = [];
private tree: object[] = [];
created() {
// 準(zhǔn)備一組含有父子級關(guān)系的一維數(shù)組方便示例測試
// 在實(shí)際項(xiàng)目應(yīng)用中,理應(yīng)通過后端接口返回
let _list = [
{
id: 'a',
pid: '',
name: '部門a',
children: []
},
{
id: 'a1',
pid: 'a',
name: '子部門a1',
children: []
},
{
id: 'a2',
pid: 'a',
name: '子部門a2',
children: []
},
{
id: 'a2-1',
pid: 'a2',
name: '子部門a2-1',
children: []
},
{
id: 'a2-2',
pid: 'a2',
name: '子部門a2-2',
children: []
},
{
id: 'a3',
pid: 'a',
name: '子部門a3',
children: []
},
{
id: 'a3-1',
pid: 'a3',
name: '子部門a3-1',
children: []
},
{
id: 'b',
pid: '',
name: '部門b',
children: []
},
{
id: 'b1',
pid: 'b',
name: '子部門b1',
children: []
},
{
id: 'c',
pid: '',
name: '部門c',
children: []
},
];
// 將一維數(shù)組轉(zhuǎn)成樹形結(jié)構(gòu)并存儲于tree變量
this.tree = arrayToTree(_list);
// 考慮到實(shí)際應(yīng)用過程中接口返回的數(shù)據(jù)是無序的,所以我們對tree進(jìn)行先序遍歷將節(jié)點(diǎn)一一插入到list變量
this.list = [];
ergodicTree(this.tree, (node: any) => {
this.list.push(node);
// 遍歷過程中并對每個節(jié)點(diǎn)掛載open和show屬性
// open:控制節(jié)點(diǎn)的打開和關(guān)閉
// show:控制節(jié)點(diǎn)的顯示和隱藏
this.$set(node, 'open', true);
this.$set(node, 'show', true)
})
}
// 控制行的顯示和隱藏
tableRowStyle(scope: any) {
return {
'display': scope.row.show ? '' : 'none'
}
}
// 通過每個節(jié)點(diǎn)的深度,設(shè)置行的縮進(jìn)實(shí)現(xiàn)視覺上的層級效果
tableRowPaddingStyle(row: any) {
return {
'margin-left': `${(row._depth - 1) * 24}px`
}
}
// 控制展開按鈕的展開和關(guān)閉狀態(tài)
collapseClass(row: any) {
return {
'collapse--open': row.open == false && row.children && row.children.length > 0,
'collapse--close': row.open == true && row.children && row.children.length > 0
}
}
// 處理展開按鈕的點(diǎn)擊事件
handleCollapseClick(row: any) {
const _open = row.open;
// 通過節(jié)點(diǎn)訪問路徑控制節(jié)點(diǎn)的顯示隱藏,由于內(nèi)存指針的關(guān)系list和tree的節(jié)點(diǎn)操作都會相互影響
ergodicTree(this.tree, (node: any) => {
node._idPath.forEach((pathId: any) => {
if (pathId == row.id) {
this.$set(node, 'show', !_open);
this.$set(node, 'open', !_open)
}
})
});
row.show = true;
row.open = !_open;
}
}
</script>
<style lang="scss" scoped>
.collapse {
display: inline-block;
width: 8px;
cursor: pointer;
margin-right: 8px;
}
.collapse--open:before {
content: '+';
}
.collapse--close:before {
content: '-';
}
</style>
工具方法
考慮數(shù)組轉(zhuǎn)樹和遍歷樹都是在實(shí)際項(xiàng)目中都是非常常用的,所以這邊對這兩個方法進(jìn)行了封裝。
數(shù)組轉(zhuǎn)樹結(jié)構(gòu)(./utils/array.ts)
export function arrayToTree(list: object[], props = {id: 'id', pid: 'pid', children: 'children'}) {
let tree: object[] = [];
let map: any = {};
let listLength = list.length;
for (let i = 0; i < listLength; i++) {
let node: any = list[i];
let nodeId: any = node[props.id];
map[nodeId] = node;
}
for (let i = 0; i < listLength; i++) {
let node: any = list[i];
let nodePid: any = node[props.pid];
let parentNode: any = map[nodePid];
if (parentNode) {
parentNode[props.children] = parentNode[props.children] || [];
parentNode[props.children].push(node)
} else {
tree.push(node)
}
}
return tree
}
遍歷樹結(jié)構(gòu)(./utils/tree.ts)
結(jié)合實(shí)際項(xiàng)目應(yīng)用,我們采用了先序遍歷法對樹進(jìn)行遍歷,為了方便在業(yè)務(wù)代碼里的應(yīng)用,在遍歷過程中會對每個節(jié)點(diǎn)掛載節(jié)點(diǎn)訪問路徑 _idPath 屬性和節(jié)點(diǎn)深度 _depth 屬性。
export function ergodicTree(tree: object[], callback: any = () => {}, props = {id: 'id', pid: 'pid', children: 'children'}) {
function _ergodicTree(tree: object[], parentIdPath?: any[], depth: number = 0) {
const treeLength = tree.length;
for (let i = 0; i < treeLength; i++) {
let node: any = tree[i];
const _idPath: any[] = parentIdPath ? [...parentIdPath, node[props.id]] : [node[props.id]];
const _depth: number = depth + 1;
node._idPath = _idPath;
node._depth = _depth;
callback(node);
if (node[props.children] && node[props.children] instanceof Array) {
_ergodicTree(node[props.children], _idPath, _depth)
}
}
}
_ergodicTree(tree);
return tree;
}
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
- Vue+Element UI+Lumen實(shí)現(xiàn)通用表格分頁功能
- element ui table(表格)實(shí)現(xiàn)點(diǎn)擊一行展開功能
- VUE2.0+ElementUI2.0表格el-table實(shí)現(xiàn)表頭擴(kuò)展el-tooltip
- VUE2.0+ElementUI2.0表格el-table循環(huán)動態(tài)列渲染的寫法詳解
- VUE2.0 ElementUI2.0表格el-table自適應(yīng)高度的實(shí)現(xiàn)方法
- vue+element-ui實(shí)現(xiàn)表格編輯的三種實(shí)現(xiàn)方式
- element-ui 表格數(shù)據(jù)時間格式化的方法
- element-ui表格數(shù)據(jù)轉(zhuǎn)換的示例代碼
- Vue+element-ui 實(shí)現(xiàn)表格的分頁功能示例
- vue中element-ui表格縮略圖懸浮放大功能的實(shí)例代碼
相關(guān)文章
vue使用v-for循環(huán)獲取數(shù)組最后一項(xiàng)
這篇文章主要介紹了vue使用v-for循環(huán)獲取數(shù)組最后一項(xiàng)問題,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教2024-03-03
詳解vue-admin和后端(flask)分離結(jié)合的例子
本篇文章主要介紹了詳解vue-admin和后端(flask)分離結(jié)合的例子,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2018-02-02

