封装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>