element-ui 目前基本成为前端pc网页端标准ui框架,但是目前element-ui研发团队已经停止element-ui 的更新,但是在业务需求在不断更新,逻辑不断加强,页面不断优化中,element-ui中就有很多组件满足不了开发者的需要,今天我就以我们项目的tree需求跟小伙伴们讨论一下。
element-ui的组件是这样的,只是单纯的用
defaultProps: {
children: 'children',
label: 'label' }
+ filterText(val) {
this.$refs.tree.filter(val);
}
实现监听筛选功能,但是我们的业务需求数据有三种不同的下级菜单数据,而且每个下级菜单里面的参数还有不同的status,要根据不同的参数显示不同的图片做图标。
功能图如下:
我们后台返回的数据结构是这样的:
有俩种不同的数据返回,每种下级数据里面还有俩种类型:
为了解析数据为tree框架的格式,我用了多个for循环,一个递归函数,共俩个函数:
递归函数,原来同上
这就实现了tree下级不同数组时处理方案,以下是我的HTML代码:
还有tree各种操作对应的函数,在线,离线的筛选,标题的筛选
代码如下,希望能帮到你:
<template>
<div class="left">
<div class="trees">
<el-input placeholder="输入关键字进行过滤" v-model="filterText"></el-input>
<el-tree
style="margin-top:14px;overflow: auto;height: 100%;"
class="filter-tree"
default-expand-all
node-key="GroupId"
:data="data2"
:props="defaultProps"
:filter-node-method="filterNode"
@node-contextmenu="show"
@node-click="click"
ref="tree"
>
<span class="custom-tree-node" slot-scope="{ node,data}">
<span>
<img
v-if="node.expanded && data.Type === 1"
src="../../assets/icon/New/file_01.png"
alt
/>
<img
v-if="!node.expanded && data.Type === 1"
src="../../assets/icon/New/file_02.png"
alt
/>
<img
v-if="data.Type === 2&&data.Status === 1"
src="../../assets/icon/New/shop_ls.png"
alt
/>
<img
v-if="data.Type === 2&&data.Status === 2"
src="../../assets/icon/New/shop_cf.png"
alt
/>
<img
v-if="data.Type === 2&&data.Status === 3"
src="../../assets/icon/New/shop_lx.png"
alt
/>
<img
v-if="data.Type === 2&&data.Status === 4"
src="../../assets/icon/New/shop_bf.png"
alt
/>
<img
v-if="data.Type === 2&&data.Status === 5"
src="../../assets/icon/New/shop_lx.png"
alt
/>
<img v-if="data.Type === 3" src="../../assets/icon/New/ship.png" alt />
{{node.label}}
</span>
</span>
</el-tree>
</div>
<!--自定义右键菜单html代码-->
<div v-show="ev" id="menu">
<div class="menu" @click="defence(1)">布防</div>
<div class="menu" @click="defence(2)">撤防</div>
<div class="menu" @click="defence(3)">留守</div>
<div class="menu" @click="leftgroup()">刷新</div>
<!-- <div class="menu" @click="change1()">全部展开</div>
<div class="menu" @click="change2()">全部收缩</div>-->
</div>
<div class="police">
<!-- <p>
<img src="../../assets/icon/New/报警_静态.png" alt />
</p>-->
<p
class="whole"
@click="index=0;list=[];sta(0)"
:class="[ index === 0?'color':'']"
>全部:{{bufang+lixian+chefang+liushou}}</p>
<div>
<p
@click="index=6;list=[];sta(6)"
:class="[ index === 6?'color':'']"
>在线:{{bufang+chefang+liushou}}</p>
<p @click="index=3;list=[];sta(3,data2)" :class="[ index === 3?'color':'']">离线:{{lixian}}</p>
</div>
<div>
<p @click="index=1;list=[];sta(1,data2)" :class="[ index === 1?'color':'']">布防:{{bufang}}</p>
<p @click="index=2;list=[];sta(2,data2)" :class="[ index === 2?'color':'']">撤防:{{chefang}}</p>
</div>
<div>
<p @click="index=4;list=[];sta(4,data2)" :class="[ index === 4?'color':'']">留守:{{liushou}}</p>
<p
@click="index=7;list=[];sta(7)"
:class="[ index === 7?'color':'']"
>未布防:{{chefang+lixian}}</p>
</div>
<p style="text-align: center;">系统时间:{{time}}</p>
</div>
</div>
</template>
data(){
return{
filterText: "",
ev: false,
data2: [],
defaultProps: {
children: "GroupSon",
label: "GroupName"
},
}
},
watch: {
// tree 树节点筛选
filterText(val) {
this.$refs.tree.filter(val);
}
},
methods:{
//优化之后的代码 不管有几级都可以适用
filterNode(value, data, node) {
if (!value) {
return true;
}
let level = node.level;
let _array = []; //这里使用数组存储 只是为了存储值。
this.getReturnNode(node, _array, value);
let result = false;
_array.forEach(item => {
result = result || item;
});
return result;
},
// 筛选树节点
getReturnNode(node, _array, value) {
if (typeof value == "number") {
if (value === 6) {
if (
(node.data && node.data.Status === 1) ||
(node.data && node.data.Status === 2) ||
(node.data && node.data.Status === 4)
) {
var isPass = true;
}
} else if (value === 7) {
if (
(node.data && node.data.Status === 3) ||
(node.data && node.data.Status === 2)
) {
var isPass = true;
}
} else if (node.data && node.data.Status === value) {
var isPass = true;
}
} else {
var isPass =
node.data &&
node.data.GroupName &&
node.data.GroupName.indexOf(value) !== -1;
}
isPass ? _array.push(isPass) : "";
this.index2++;
if (!isPass && node.level != 1 && node.parent) {
this.getReturnNode(node.parent, _array, value);
}
},
// 左侧菜单状态变化
sta(index, data) {
this.$refs.tree.filter(index);
// this.$refs.tree.filter(index);
},
// 数据去重
arrayUnique2(arr, name) {
var hash = {};
return arr.reduce(function(item, next) {
hash[next[name]] ? "" : (hash[next[name]] = true && item.push(next));
return item;
}, []);
},
// 左侧列表右键操作
defence(i) {
if (!this.list.EquipmentIdString) {
this.$message("只能操作有设备ID的终端!");
return false;
}
this.$axiosPost(this.$api.action, {
ActionType: i,
EquipmentIdString: this.list.EquipmentIdString,
TerminalId: this.list.GroupId
}).then(res => {
if (res.Code === 200) {
this.$message({
message: res.Msg,
type: "success"
});
} else {
this.$message(res.Msg);
}
});
},
// 数据处理
gu2(list) {
if (list.Terminals) {
for (var p = 0; p < list.Terminals.length; p++) {
var a = list.Terminals[p].Videos
? list.Terminals[p].Videos.length
: 0;
for (var s = 0; s < list.Terminals[p].Videos.length; s++) {
var ship = {};
list.Terminals[p].GroupSon = [];
ship.GroupId = list.Terminals[p].Videos[s].VedioId;
ship.GroupName = list.Terminals[p].Videos[s].VedioName;
ship.Type = list.Terminals[p].Videos[s].Type;
list.Terminals[p].GroupSon.push(ship);
}
if (list.Terminals[p].Status === 1) {
this.bufang++;
} else if (list.Terminals[p].Status === 3) {
this.lixian++;
} else if (list.Terminals[p].Status === 2) {
this.chefang++;
} else if (list.Terminals[p].Status === 4) {
this.liushou++;
}
var data = {};
data.GroupId = list.Terminals[p].TerminalId;
data.GroupName = list.Terminals[p].TerminalName;
data.Type = list.Terminals[p].Type;
data.GroupSon = list.Terminals.GroupSon;
data.state = 1;
data.Lng = list.Terminals[p].Lng;
data.Lat = list.Terminals[p].Lat;
data.Status = list.Terminals[p].Status;
data.EquipmentIdString = list.Terminals[p].EquipmentIdString;
list.GroupSon.push(data);
}
}
if (list.GroupSon) {
for (var n = 0; n < list.GroupSon.length; n++) {
if (!list.GroupSon.state) {
this.gu2(list.GroupSon[n]);
}
}
}
},
// 左侧菜单栏
leftgroup() {
this.$axiosPost(this.$api.leftgroup).then(res => {
if (res.Code === 200) {
var data3 = {
GroupId: 0,
GroupName: "终端数据",
Type: 1,
GroupSon: []
};
this.data2 = res.Data.GroupData;
for (var i = 0; i < this.data2.length; i++) {
if (this.data2[i].Status === 1) {
this.bufang++;
} else if (this.data2[i].Status === 3) {
this.lixian++;
} else if (this.data2[i].Status === 2) {
this.chefang++;
} else if (this.data2[i].Status === 4) {
this.liushou++;
}
if (this.data2[i].Terminals) {
for (var p = 0; p < this.data2[i].Terminals.length; p++) {
for (
var s = 0;
s < this.data2[i].Terminals[p].Videos.length;
s++
) {
var ship = {};
this.data2[i].Terminals[p].GroupSon = [];
ship.GroupId = this.data2[i].Terminals[p].Videos[s].VedioId;
ship.GroupName = this.data2[i].Terminals[p].Videos[
s
].VedioName;
ship.Type = this.data2[i].Terminals[p].Videos[s].Type;
this.data2[i].Terminals[p].GroupSon.push(ship);
}
if (this.data2[i].Terminals[p].Status === 1) {
this.bufang++;
} else if (this.data2[i].Terminals[p].Status === 3) {
this.lixian++;
} else if (this.data2[i].Terminals[p].Status === 2) {
this.chefang++;
} else if (this.data2[i].Terminals[p].Status === 4) {
this.liushou++;
}
var data2 = {};
data2.GroupId = this.data2[i].Terminals[p].TerminalId;
data2.GroupName = this.data2[i].Terminals[p].TerminalName;
data2.Type = this.data2[i].Terminals[p].Type;
data2.state = 1;
data2.Lng = this.data2[i].Terminals[p].Lng;
data2.Lat = this.data2[i].Terminals[p].Lat;
data2.Status = this.data2[i].Terminals[p].Status;
data2.EquipmentIdString = this.data2[i].Terminals[
p
].EquipmentIdString;
data2.GroupSon = this.data2[i].Terminals[p].GroupSon;
this.data2[i].GroupSon.push(data2);
}
}
for (var n = 0; n < this.data2[i].GroupSon.length; n++) {
if (!this.data2[i].GroupSon.state) {
this.gu2(this.data2[i].GroupSon[n]);
}
}
}
for (var o = 0; o < res.Data.TerminalData.length; o++) {
var data = {};
data.GroupId = res.TerminalData[o].TerminalId;
data.GroupName = res.TerminalData[o].TerminalName;
data.Type = res.TerminalData[o].Type;
data.state = 5;
data3.GroupSon.push(data);
}
if (data3.length > 0) {
this.data2.push(data3);
}
} else {
this.$message(res.Msg);
}
});
},
// 左边菜单栏点击事件
click(a, b, c) {
// console.log(a, b, c);
// Lat: "37.8623608478594"
// Lng: "113.587616662875"
if (a.Lat && a.Lng) {
this.ditu(a.Lat, a.Lng, a.GroupName);
}
this.ev = false;
},
},