使用Z-tree

封装ztree组件

<template>
  <div class="earl-tree">
    <div v-if="showSearch" style="margin-bottom: 12px;">
      <a-input
        placeholder="输入检索信息..."
        v-model="q"
        :style="{ width: width + 'px' }"
        v-jquery-enter="loadTree"
        @search="loadTree"
      ></a-input>
    </div>
    <div class="p-r">
      <div style="overflow-y: hidden; overflow-x: auto;" :style="{ width: width + 'px' }">
        <ul ref="treeUL" :id="treeId" class="ztree"></ul>
      </div>
      <a-spin :spinning="ifSub" style="position: absolute; top: 0; left: 45%;"></a-spin>
    </div>
  </div>
</template>
<script>
/* eslint-disable */
import '../../plugins/zTree/js/jquery.ztree.all.min.js'
import UUID from '../../utils/UUID'
import jqueryEnter from '../../directives/jquery-enter'

export default {
  //type 类型 等于checkbox 增加选中框
  //treeNodeClick 树节点被点击时出发
  //loadUrl 树加载URL
  props: {
    type: {
      type: String,
    },
    radioType: {
      type: String,
      default: 'all',
    },
    loadUrl: {
      type: Object,
    },
    height: {
      type: Number,
    },
    otherParams: {
      //其他参数,请求数据时会一并发送到服务端
      type: Object,
      default: () => {
        return {}
      },
    },
    autoLoad: {
      type: Boolean,
      default: true,
    },
    width: {
      type: Number,
      default: 256,
    },
    showIcon: {
      type: Boolean,
      default: false,
    },
    showSearch: {
      type: Boolean,
      default: false,
    },
    showEdit: {
      type: Boolean,
      default: true,
    },
  },
  data() {
    return {
      treeObj: null,
      ifSub: false,
      treeId: new UUID(),
      q: '',
    }
  },
  mounted() {
    if (this.autoLoad) {
      this.loadTree()
    }
  },
  methods: {
    loadTree() {
      if (this.ifSub) return
      let mouseClick = 0
      let treeNodeId
      const self = this
      const setting = {
        check:
          self.type === 'checkbox' || self.type === 'radio'
            ? {
                enable: true,
                chkStyle: self.type,
                chkboxType: { Y: '', N: 'p' },
                radioType: self.radioType,
              }
            : { enable: false },
        view: {
          selectedMulti: false,
          // 增加添加按钮
          addHoverDom: (treeId, treeNode) => {
            if (!self.showEdit) {
              return
            }
            const sObj = $('#' + treeNode.tId + '_span')
            if (!treeNode.addBtnFlag || $('#addBtn_' + treeNode.tId).length > 0) return
            var addStr =
              "<span class='button add' id='addBtn_" +
              treeNode.tId +
              "' title='添加节点' onfocus='this.blur();'></span>"
            sObj.after(addStr)
            var btn = $('#addBtn_' + treeNode.tId)
            if (btn)
              btn.bind('click', function () {
                self.$emit('addClick', treeNode)
                return false
              })
          },
          removeHoverDom: (treeId, treeNode) => {
            $('#addBtn_' + treeNode.tId)
              .unbind()
              .remove()
          },
          showIcon: self.showIcon,
        },
        data: {
          simpleData: {
            enable: true,
          },
        },
        callback: {
          onClick: function (treeId, treeName, treeNode) {
            if (treeNodeId === treeNode.id) {
              if (treeId.timeStamp - mouseClick < 500) {
                mouseClick = treeId.timeStamp
                treeNodeId = treeNode.id
                return
              }
            }
            treeNodeId = treeNode.id
            mouseClick = treeId.timeStamp
            //                if(treeNode.isParent){
            //                    treeObj.expandNode(treeNode);
            //                }
            self.getOne(treeNode)
          },
          onCheck: function (event, treeId, treeNode) {
            $('#' + self.treeId)
              .find('a')
              .removeClass('curSelectedNode')
            if (treeNode.checked) {
              $('#' + treeNode.tId + '_a').addClass('curSelectedNode')
            }
            self.$emit('checkClick', self.treeObj.getCheckedNodes(true))
          },
          beforeRemove: (treeId, treeNode) => {
            self.$emit('deleteClick', treeNode)
            return false
          },
          beforeRename: (treeId, newName, treeNode, isCancel) => {
            self.$emit('editClick', treeNode, newName, isCancel)
            return true
          },
        },
        edit: this.showEdit
          ? {
              enable: true,
              removeTitle: '删除节点',
              renameTitle: '编辑节点',
              showRenameBtn: false,
              drag: {
                isMove: false,
                isCopy: false,
              },
            }
          : {},
      }
      let treeObj
      const data = this.otherParams
      if (this.showSearch) {
        data['q'] = this.q
      }
      this.$http(self, {
        url: self.loadUrl,
        noTips: true,
        data: data,
        success: function (data) {
          $.fn.zTree.init($(self.$refs.treeUL), setting, data.body)
          treeObj = $.fn.zTree.getZTreeObj(self.treeId)
          self.treeObj = treeObj
          if (self.type !== 'checkbox' && self.type !== 'radio') {
            const treeNode = treeObj.getNodes()[0]
            treeObj.selectNode(treeNode)
            treeObj.expandNode(treeNode)
            self.getOne(treeNode)
          } else {
            self.treeObj.expandAll(true)
          }
          self.$emit('init-success')
        },
      })
    },
    getOne(treeNode) {
      if (this.type === 'checkbox' || this.type === 'radio') {
        $('#' + this.treeId)
          .find('a')
          .removeClass('curSelectedNode')
        //点击名称还未设置选中和未选中 这里需要取!
        if (!treeNode.checked) {
          $('#' + treeNode.tId + '_a').addClass('curSelectedNode')
        }
        this.treeObj.checkNode(treeNode, !treeNode.checked, true, false)
        this.$emit('checkClick', this.treeObj.getCheckedNodes(true))
      }
      this.$emit('treeNodeClick', treeNode)
    },
    updateSelectNode(data) {
      const treeObj = this.treeObj
      let selectNode = treeObj.getSelectedNodes()[0] //获取选择的节点
      //重置一下tree中节点数据
      Object.assign(selectNode, data)
      treeObj.updateNode(selectNode)
      //获取修改后节点的父节点Id
      let pId = data.pId
      //移动节点
      let allNodes,
        i = 0
      if (pId === 'begin') {
        //修改为顶级节点
        allNodes = treeObj.getNodes()
      } else {
        allNodes = treeObj.getNodesByParam('pId', pId)
        if (allNodes.length === 1) {
          //当前节点下没有子节点
          //获取父节点
          let node = treeObj.getNodeByParam('id', pId)
          treeObj.moveNode(node, selectNode, 'inner')
          return
        }
      }
      for (i = 0; i < allNodes.length; i++) {
        //判断节点需要移动到的位置
        if (allNodes[i].id === selectNode.id) continue
        let nextNode
        if (i === allNodes.length - 1) {
          //已经到最后一个了,
          if (allNodes[i].sorter > data.sorter) {
            treeObj.moveNode(allNodes[i], selectNode, 'prev')
          } else {
            treeObj.moveNode(allNodes[i], selectNode, 'next')
          }
          return
        }

        //判断当前节点是否已经大于移动节点
        if (allNodes[i].sorter >= data.sorter) {
          treeObj.moveNode(allNodes[i], selectNode, 'prev')
          break
        }

        nextNode = allNodes[i + 1]
        //如果下一个节点为自己
        if (nextNode.id === selectNode.id) {
          //获取下下个节点,如果已经不存在下下个节点了,
          if (i === allNodes.length - 2) {
            //已经不存在下下节点,这时直接进行判断并移动节点
            if (allNodes[i].sorter > data.sorter) {
              treeObj.moveNode(allNodes[i], selectNode, 'prev')
            } else {
              treeObj.moveNode(allNodes[i], selectNode, 'next')
            }
            break
          }
          nextNode = allNodes[i + 2]
        }
        if (allNodes[i].sorter < data.sorter && data.sorter <= nextNode.sorter) {
          //在此节点前插入修改的节点.
          treeObj.moveNode(allNodes[i], selectNode, 'next')
          break
        }
      }
    },
    //添加节点后,或触发选中事件
    addNode(data) {
      const treeObj = this.treeObj
      //根据当前节点pId获取父节点
      //把数据按sorter插入到当前获取到的节点中
      let pId = data.pId
      let treeNode,
        parentNode,
        allNodes,
        i = 0
      if (pId === 'begin') {
        //修改为顶级节点
        allNodes = treeObj.getNodes()
      } else {
        allNodes = treeObj.getNodesByParam('pId', pId)
        if (allNodes.length === 0) {
          //当前节点下没有子节点
          //获取父节点
          parentNode = treeObj.getNodeByParam('id', pId)
          treeNode = treeObj.addNodes(parentNode, i, data)
        }
      }
      if (!treeNode) {
        let index = -1
        for (i = 0; i < allNodes.length; i++) {
          //判断节点需要添加到的位置
          let nextNode
          if (i === allNodes.length - 1) {
            //已经到最后一个了,
            if (allNodes[i].sorter >= data.sorter) {
              index = i - 1
              if (index < 0) index = 0
            }
            parentNode = allNodes[i].getParentNode()
            break
          }

          if (allNodes[i].sorter >= data.sorter) {
            index = i
            parentNode = allNodes[i].getParentNode()
            break
          }

          nextNode = allNodes[i + 1]
          if (allNodes[i].sorter < data.sorter && data.sorter <= nextNode.sorter) {
            //在此节点前插入修改的节点.
            index = i + 1
            parentNode = allNodes[i].getParentNode()
            break
          }
        }
        treeNode = treeObj.addNodes(parentNode, index, data)
      }
      treeObj.selectNode(treeNode[0]) //选中节点
      //自动触发选中事件
      this.getOne(treeNode[0])
    },
    /**
     * 删除选中节点,单选节点
     * 会触发选中节点
     */
    deleteSelectNode() {
      const selectNode = this.treeObj.getSelectedNodes()[0]
      this.deleteNode(selectNode)
    },
    deleteNode(treeNode) {
      const treeObj = this.treeObj
      const selectOne = this.treeObj.getSelectedNodes()[0].id === treeNode.id
      //移除节点
      treeObj.removeNode(treeNode)
      if (selectOne) {
        //设置第一个节点选中
        const chooseNode = treeObj.getNodes()[0]
        treeObj.selectNode(chooseNode)
        this.getOne(chooseNode)
      }
    },
    /**
     * 获取所有选中节点
     */
    getAllSelectNode() {
      if (!this.treeObj) return []
      return this.treeObj.getCheckedNodes()
    },
    /**
     * 通过ID s 选中节点
     */
    selectNodesById(ids) {
      if (ids && this.treeObj) {
        //取消所有选中
        this.resetSelectNode()
        ids.forEach((x) => {
          console.log(ids, '545')
          console.log(x)
          console.log(this.treeObj.getNodeByParam, '123+++')
          const treeNode = this.treeObj.getNodeByParam('id', x)
          console.log(treeNode, '456+++')
          console.log(this.treeObj, '789+++')
          this.treeObj.getCheckedNodes(ids)
          //this.treeObj.checkNode(treeNode, true, false);
        })
      }
    },
    /**
     * 取消所有选中节点
     */
    resetSelectNode() {
      if (!this.treeObj) return
      this.treeObj.checkAllNodes(false)
    },
    destroy() {
      if (this.treeObj) {
        this.treeObj.destroy()
      }
    },
    clearHandle() {
      this.q = ''
    },
  },
  directives: {
    jqueryEnter,
  },
}
</script>

页面调用

import ZTree from '../../../components/ztree/index'    // 引入

<z-tree    //  组件
                  ref="treeRef"
                  :load-url="treeLoadUrl"
                  @deleteClick="treeDeleteClickHandle"  // 删除节点调用的方法
                  @addClick="treeAddClickHandle" // 添加节点
                  @treeNodeClick="treeNodeClickHandle"
                ></z-tree>
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值