递归循环获得tree树形结构数据VUE + ElementUI tree组件树形数据处理(不限层级)
⼀、tree组件代码
<el-tree
class="tree_s"
:data="treeData"
highlight-current
:expand-on-click-node="false"
node-key="id"
default-expand-all
:props="defaultProps"
@node-click="nodeClickFn"
></el-tree>
⼆、数据分析
后台返回数据:id表⽰项⽬唯⼀性id、depth表⽰层级、parentId表⽰⽗级id、name表⽰节点名称。
[
{
"id":1,//唯⼀性id
"parentId":0,//⽗级id
"depth":1,//层级
"name":"第⼀节点",//节点名称
},
{
"id":2,
"parentId":1,
"depth":2,
"name":"第⼆节点",
},
{
"id":3,
"parentId":2,
"depth":3,
"name":"第三节点",
}
]
三、数据处理
转换数据结构,json转化为树形结构
methods: {
//获取后台数据
getDataList(){
//AJAX获取数据
this.data = res;//⽰例
this.handleData(this.data);
},
//先出第⼀层级,然后往⾥追加数据
handleData(arr) {
let dataArray = [];
arr.forEach(function (data) {
let parentId = data.parentId;
if ( parentId == 0 ) {
let objTemp = {
id: data.id,
label: data.name,
depth: data.depth,
parentId: parentId,
}
dataArray.push(objTemp);
}
})
this.data2treeDG(arr, dataArray)
},
//递归追加数据
data2treeDG(datas, dataArray) {
for (let j = 0; j < dataArray.length; j++) {
let dataArrayIndex = dataArray[j];
let childrenArray = [];
let Id = dataArrayIndex.id;
for (let i = 0; i < datas.length; i++) {
let data = datas[i];
let parentId = data.parentId;
if (parentId == Id) {//判断是否为⼉⼦节点            let objTemp = {
id: data.id,
label: data.name,
depth: data.depth,
parentId: parentId,
}
childrenArray.push(objTemp);
}
}
dataArrayIndex.children = childrenArray;        //有⼉⼦节点则递归
if (childrenArray.length > 0) {
this.data2treeDG(datas, childrenArray)        }
}
return dataArray;
},
}
四、格式化后数据结构
格式化后数据结构可满⾜tree组件需求
[
{
"id":1,
"parentId":0,
"depth":1,
"label":"第⼀节点",
"children": [
{
"id":2,
"parentId":1,
"depth":2,
"label":"第⼆节点",
"children": [
{
"id":3,
"parentId":2,
"depth":3,
"label":"第三节点",
}
]
},
]
}
]
五、总结
此解决问题思路,也可⽤于动态导航栏数据处理。
六、优化
methods: {
// 树形数据处理公⽤⽅法——先出第⼀层级,然后往children⾥追加数据
/**
* @param {Array} arr  resData列表原始数据
* @param {Array} keys ⾃定义字段数组
* @param {Number} originId 根⽬录parentId,默认为0, 可⾃定义传⼊如‘-1’
* @returns
*/
handleData(arr = [], keys = [], originId = 0) {
//如果后端没有返回根⽬录节点数据,则需要⾃定义根节点如下:
if (originId < 0) arr.push({ id: 0, value: 0, label: '全部', name: '全部', depth: 0, parentId: originId })            const dataArray = []
for (let i = 0; i < arr.length; i++) {
const data = arr[i]
const parentId = data.parentId
if (parentId == originId) {
const objTemp = {
id: data.id,
value: data.id,
label: data.name,
name: data.name,
depth: data.depth,
parentId: parentId,
disabled: data.disabled
}
// 追加额外参数**********
if (Array.isArray(keys)) {
keys.forEach(key => {
objTemp[key] = data[key] ? data[key] : ''
})
} else if (keys && typeof keys === 'string') {
objTemp[keys] = data[key] ? data[key] : ''
}
dataArray.push(objTemp)
break
}
}
return this.data2treeDG(arr, dataArray, keys, originId)        },
// 递归追加数据
data2treeDG(datas, dataArray, keys, originId) {
for (let j = 0; j < dataArray.length; j++) {
const dataArrayIndex = dataArray[j]
const childrenArray = []
const Id = dataArrayIndex.id
for (let i = 0; i < datas.length; i++) {
const data = datas[i]
const parentId = data.parentId
if (parentId == Id) { // 判断是否为⼉⼦节点
const objTemp = {
id: data.id,
value: data.id,
name: data.name,
label: data.name,
depth: data.depth,
parentId: parentId,
disabled: data.disabled
}
// 追加额外参数**********
if (Array.isArray(keys)) {
keys.forEach(key => {
objTemp[key] = data[key]
})
} else if (keys && typeof keys === 'string') {
objTemp[keys] = data[keys]
}
childrenArray.push(objTemp)
}
}
// 有⼉⼦节点则递归
if (childrenArray.length > 0) {
dataArrayIndex.children = childrenArray
this.data2treeDG(datas, childrenArray, keys)
}
}
return originId ? dataArray[0].children : dataArray
},
// 获取⽗⼦级字符串组合
typeof arraygetCascaderStr(id) {
if (!id) return []
const resData_ = sData
const typesStrArr = []
const nowTypeObj = this.checkTypeObj(id)
typesStrArr.unshift(nowTypeObj.name)
checkId(nowTypeObj.parentId)
return typesStrArr
function checkId(parentId) {
for (let i = 0; i < resData_.length; i++) {
const el = resData_[i]
if (parentId == el.id && parentId != 0) {
typesStrArr.unshift(el.name)
checkId(el.parentId)
break
}
}
}
},
// 获取⽗⼦级ID组合数组
getCascaderArr(id) {
if (!id) return []
const resData_ = sData
const typesArr = []
const nowTypeObj = this.checkTypeObj(id)            typesArr.unshift(nowTypeObj.id)
checkId(nowTypeObj.parentId)
return typesArr
function checkId(parentId) {
for (let i = 0; i < resData_.length; i++) {                    const el = resData_[i]
if (parentId == el.id && parentId != 0) {                        typesArr.unshift(el.id)
checkId(el.parentId)
break
}
}
}
},
//根据id 遍历数组返回⽬标对象
checkTypeObj(id) {
const resData_ = sData
let nowTypeObj_ = null
for (let i = 0; i < resData_.length; i++) {
const el = resData_[i]
if (el.id == id) {
nowTypeObj_ = el
break
}
}
return nowTypeObj_
}
}```

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。