vue 树形控件可编辑_VUE饿了么树形控件添加增删改功能的示例代码

本文详细介绍了如何在Vue中使用饿了么UI库的树形控件添加编辑、删除和增加功能。通过自定义渲染内容,实现了节点的增删改,并提供了相应的示例代码,包括监听输入、节点点击事件处理等。文章还涵盖了新增节点时的限制,如最大层级限制,以及编辑状态的控制。最后提到了一些额外需求的实现,如节点高亮、添加顶级节点和默认展开等。
摘要由CSDN通过智能技术生成

本文介绍了VUE饿了么树形控件添加增删改功能的示例代码,分享给大家,具体如下:

element-ui树形控件:地址

在原文档中有个案例是有新增和删除功能,但是后来发现其修改的数据并不能直接影响到树形数据,所以采用了 render-content 的API重新写了个组件。

写个开发的步骤,所以文章比较长emmm

大致效果如图:

1.省市API

在网上复制了个省市的list,有两个属性是新增的

isEdit :控制编辑状态

maxexpandId :为现下id的最大值

export default{

maxexpandId: 95,

treelist: [{

id: 1,

name: "北京市",

ProSort: 1,

remark: "直辖市",

pid: '',

isEdit: false,

children: [{

id: 35,

name: "朝阳区",

pid: 1,

remark: '',

isEdit: false,

children: []

}]

}{...}]

}

2.el-tree Component基本

咱们一步步来,先写个饿了么的组件

v-if="isLoadingTree"

:data="setTree"

node-key="id"

highlight-current

:props="defaultProps"

:expand-on-click-node="false"

:render-content="renderContent"

:default-expanded-keys="defaultExpandKeys">

同时引入API和节点渲染的组件

import TreeRender from '@/components/tree_render'

import api from '@/resource/api'

然后搭建好基础

data(){

return{

maxexpandId: api.maxexpandId,//新增节点开始id

non_maxexpandId: api.maxexpandId,//新增节点开始id(不更改)

isLoadingTree: false,//是否加载节点树

setTree: api.treelist,//节点树数据

defaultProps: {

children: 'children',

label: 'name'

},

defaultExpandKeys: [],//默认展开节点列表

}

},

添加个渲染的method

methods: {

renderContent(h,{node,data,store}){

let that = this;//指向vue

return h(TreeRender,{

props: {

DATA: data,//节点数据

NODE: node,//节点内容

STORE: store,//完整树形内容

},

on: {//绑定方法

nodeAdd: ((s,d,n) => that.handleAdd(s,d,n)),

nodeEdit: ((s,d,n) => that.handleEdit(s,d,n)),

nodeDel: ((s,d,n) => that.handleDelete(s,d,n))

}

});

},

handleAdd(s,d,n){//增加节点

console.log(s,d,n)

},

handleEdit(s,d,n){//编辑节点

console.log(s,d,n)

},

handleDelete(s,d,n){//删除节点

console.log(s,d,n)

}

}

3.tree_render Component基本

渲染组件:

{{DATA.name}}

添加好几个按钮(element-ui自带icon:地址)对应的方法:

export default{

props: ['NODE', 'DATA', 'STORE'],

methods: {

nodeAdd(s,d,n){//新增

this.$emit('nodeAdd',s,d,n)

},

nodeEdit(s,d,n){//编辑

this.$emit('nodeEdit',s,d,n)

},

nodeDel(s,d,n){//删除

this.$emit('nodeDel',s,d,n)

}

}

}

4.改

我们用isEdit来切换input和span的显示状态,首先加个input:

:ref="'treeInput'+DATA.id"

v-model="DATA.name">

{{DATA.name}}

编辑的时候按钮同时消失,那么什么时候编辑完成呢?

编辑完按enter键=》监听input的enter输入

点击其他节点=》input失焦-blur=》编辑时自动聚焦-focus

点击当前节点范围

当以上三点发生一项,节点对应的data都要isEdit = false;

1、enter键

添加方法:

//tree_render component

methods: {

nodeEditPass(s,d,n){

d.isEdit = false;

}

}

2、focus or blur

后来发现第一次编辑时能让input聚焦,点击第二个input就不起作用了,加了autofocus属性也同样如此。所以我们要在点击编辑icon的时候,用原生的input autofocus。

修改方法:

//tree_render component

nodeEdit(s,d,n){//编辑

d.isEdit = true;

this.$nextTick(() => {

this.$refs['treeInput'+d.id].$refs.input.focus()

})

this.$emit('nodeEdit',s,d,n)

}

3、当前节点点击

采用el-tree已有的API——node-click

添加methods:

//el-tree component

methods: {

handleNodeClick(d,n,s){//点击节点

d.isEdit = false;//放弃编辑状态

}

}

问题来了,如果在编辑状态下点击此节点也同样会影响input,这就无法进入编辑,所以要阻止input事件冒泡:

添加methods:

//tree_render component

methods: {

nodeEditFocus(){}

}

4、v-show代替v-if

这里有个新的问题,当用户经常编辑修改,v-if模板的开销更高,所以改用v-show。而后者不支持template模板,所以要适当调整一下位置:

v-model="DATA.name"

:ref="'treeInput'+DATA.id"

@click.stop.native="nodeEditFocus"

@blur="nodeEditPass(STORE,DATA,NODE)"

@keyup.enter.native="nodeEditPass(STORE,DATA,NODE)">

{{DATA.name}}

5.增

新增节点 =》添加一条数据

新增的同时展开父节点

是否考虑无限新增

//el-tree component

handleAdd(s,d,n){//增加节点

console.log(s,d,n)

if(n.level >=6){

this.$message.error("最多只支持五级!")

return false;

}

//添加数据

d.children.push({

id: ++this.maxexpandId,

name: '新增节点',

pid: d.id,

isEdit: false,

children: []

});

//展开节点

if(!n.expanded){

n.expanded = true;

}

}

新增节点字体加粗 =》给节点添加一个class =》 如何判断是否新增?

我们有一个参数maxexpandId

给tree_render添加一个prop:

//el-tree component

renderContent(h,{node,data,store}){//加载节点

let that = this;

return h(TreeRender,{

props: {

...

maxexpandId: that.non_maxexpandId

},

on: {...}

});

}

根据id判断:

//tree_render component

props: ['NODE', 'DATA', 'STORE', 'maxexpandId']

:class="[DATA.id > maxexpandId ? 'tree-new tree-label' : 'tree-label']"

:ref="'treeLabel'+DATA.id">

{{DATA.name}}

.tree-expand .tree-label.tree-new{

font-weight:600;

}

6.删

跟新增同义:删除节点 =》删除一条数据

新增节点直接删除

已有节点需提示再删除

已有子级节点不能删除

handleDelete(s,d,n){//删除节点

console.log(s,d,n)

let that = this;

//有子级不删除

if(d.children && d.children.length !== 0){

this.$message.error("此节点有子级,不可删除!")

return false;

}else{

//删除操作

let delNode = () => {

let list = n.parent.data.children || n.parent.data,

//节点同级数据,顶级节点时无children

_index = 99999;//要删除的index

list.map((c,i) => {

if(d.id == c.id){

_index = i;

}

})

let k = list.splice(_index,1);

//console.log(_index,k)

this.$message.success("删除成功!")

}

let isDel = () => {

that.$confirm("是否删除此节点?","提示",{

confirmButtonText: "确认",

cancelButtonText: "取消",

type: "warning"

}).then(() => {

delNode()//此处可通过ajax做删除操作

}).catch(() => {

return false;

})

}

//新增节点直接删除,否则要通过请求数据删除

d.id > this.non_maxexpandId ? delNode() : isDel()

}

}

7.拓展

还有一些特别的需求,例如:

1、点击高亮的时候显示icon

.expand-tree .is-current>.el-tree-node__content .tree-btn,

.expand-tree .el-tree-node__content:hover .tree-btn{

display: inline-block;

}

2、添加顶级节点

添加按钮:

添加顶级节点

添加methods:

//el-tree component

methods: {

handleAddTop(){

this.setTree.push({

id: ++this.maxexpandId,

name: '新增节点',

pid: '',

isEdit: false,

children: []

})

}

}

3、默认展开树形第一级

//el-tree component

mounted(){

this.initExpand()

},

methods: {

initExpand(){

//isLoadingTree用意也是在此

this.setTree.map((a) => {

this.defaultExpandKeys.push(a.id)

});

this.isLoadingTree = true;

},

}

8.github

还有些具体的样式都放在github了

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值