vue el-tree主键id重复 添加自增id 以及原相同节点同步勾选 同步操作

树数据只提供了nodeId,且存在不同节点重复nodeId的问题,由于树组件的node-key需要唯一性,所有这个时候我们需要给数据添加自增id (延申问题:操作某个节点的时候,同步操作与他nodeId相同的节点),代码如下

复制代码
<template>
  <div>
    <el-tree
      :data="treeList"
      show-checkbox
      ref="tree"
      :check-strictly="false"
      node-key="id"
      :props="props"
      @check-change="treeCheckChange"
    >
    </el-tree>
  </div>
</template>

<script>
export default {
  data() {
    return {
      props: {
        label: "label",
        children: "children",
      },
      initData: [], // 初始化数据
      treeList: [], // 树数据
      idAndNodeId: [], // 非目录节点id与nodeId直接的关系
      nodeIdMap: {}, // 非目录节点id和nodeId的关系对象 具体作用往下看
    };
  },

  mounted() {
    var arr = [
      {
        nodeId: "1",
        nodeName: "目录1",
        parentId: "-1",
        nodeType: 1,
        children: [
          {
            nodeId: "001",
            nodeName: "子节点1",
            nodeType: 2,
            parentId: "1",
          },
          {
            nodeId: "002",
            nodeName: "子节点2",
            nodeType: 2,
            parentId: "1",
          },
          {
            nodeId: "003",
            nodeName: "子节点3",
            nodeType: 2,
            parentId: "1",
          },
        ],
      },
      {
        nodeId: "2",
        nodeName: "目录2",
        parentId: "-1",
        nodeType: 1,
        children: [
          {
            nodeId: "001",
            nodeName: "子节点1",
            nodeType: 2,
            parentId: "2",
          },
          {
            nodeId: "002",
            nodeName: "子节点2",
            nodeType: 2,
            parentId: "2",
          },
          {
            nodeId: "004",
            nodeName: "子节点24",
            nodeType: 2,
            parentId: "2",
          },
        ],
      },
    ];
    this.id = 0;
    arr = this.circulationTreeData(arr);
    this.treeList = arr;

    this.idAndNodeId = [];
    this.getIdAndNodeId(arr, 1);

    // 生成一个nodeIdMap
    // 遍历数组,将每个对象的nodeId作为属性名,将对象存入属性值中
    // 例如:{ "001": [{...}, {...}], "002": [{...}, {...}] }
    // 这样查找相同nodeId的设备时直接通过属性名取就行了
    var mapKey = "nodeId";
    this.nodeIdMap = this.idAndNodeId.reduce((carry, item) => {
      if (item.nodeType == 2) {
        carry[item[mapKey]] = carry[item[mapKey]] || [];
        carry[item[mapKey]].push(item);
      }
      return carry;
    }, {});
  },

  methods: {
    // 递归处理数据 添加自增id
    circulationTreeData(data) {
      let children = [];
      data.forEach((item, index) => {
        if (item.children && item.children.length > 0) {
          children.push({
            ...item,
            label: item.nodeName,
            id: this.id++,
            parentId: item.parentId,
            children: this.circulationTreeData(item.children),
          });
        } else {
          children.push({
            ...item,
            label: item.nodeName,
            id: this.id++,
            parentId: item.parentId,
          });
        }
      });
      return children;
    },
    //递归获取id和node_id的联系
    getIdAndNodeId(data, level) {
      data.forEach((item) => {
        if (item.children && item.children.length > 0) {
          this.getIdAndNodeId(item.children, level + 1);
        } else {
          this.idAndNodeId.push({
            ...item,
            level: level,
          });
        }
      });
    },
    // 节点勾选
    treeCheckChange(data, ischeck) {
      if (data.nodeType == 1) return;
      // 方法1 遍历idAndNodeId查找相同nodeId的节点 速度慢不推荐
      // if (ischeck) {
      //   this.idAndNodeId.forEach((item) => {
      //     if (item.nodeId == data.nodeId) {
      //       this.$refs.tree.setChecked(item.id, true);
      //     }
      //   });
      // } else {
      //   this.idAndNodeId.forEach((item) => {
      //     if (item.nodeId == data.nodeId) {
      //       this.$refs.tree.setChecked(item.id, false);
      //     }
      //   });
      // }
      // 方法2 直接取对象对应属性 速度快 推荐!!!
      let arrs = this.nodeIdMap[data.nodeId] || [];
      console.log(arrs);
      arrs.forEach((item) => {
        if (item.id != data.id) this.$refs.tree.setChecked(item.id, ischeck);
      });
    },
  },
};
</script>
相关推荐
usdoc文档预览2 小时前
USDOC系列之PPT文件在线编辑-VUE前端实现在线浏览器在线编辑PPT文档
前端·vue.js·编辑器·office365·ppt在线编辑·office文件在线编辑·文件在线编辑
Java小卷2 小时前
面向 schema 编程,轻松搞定 Element 虚拟化表格复杂应用场景
vue.js·低代码·element
用户2705077725242 小时前
Agent 调工具卡住?3 种超时与取消策略实测对比
前端
LuHang3 小时前
我一行代码没写,把领导派的活做成了公司内部系统😭
前端
明月_清风3 小时前
Meta 开源了一个 AI Native 组件库:Astryx,150+ React 组件,专为 AI Agent 而设计
前端·人工智能·ai编程
仨孩子的爹4 小时前
Lodop、hiprint 与 vue-print-designer:打印控件选型对比
vue.js
用户850869276154 小时前
秒杀系统中 Shell 脚本并发控制 Bug:究竟哪里出了
前端
程序员大阳5 小时前
HTML+CSS+JS对话式实战(3)-活动管理页实现查询、新增、删除API后端接口
javascript·css·html·实战·删除·查询·新增
炫酷的大高个6 小时前
6 亿播放的闪身步,我用前端算出 15 倍重心差
前端·javascript
不可能片场6 小时前
内容运营自动化 配图折行别把词切两半
前端·electron