一座城池

成功就是不懈的努力加上一点点机会,努力是加法,机会是乘法,两者兼备才会得到最大的结果!
当前位置 - 首页 - VueJs - 基于vue.js实现树形表格的封装

基于vue.js实现树形表格的封装

2018/7/24 17:15:00  发表于:2018/7/24 17:15:00  VueJs 次浏览 
字体大小切换:

vue-tree-table


前言

由于公司产品(基于vue.js)需要,要实现一个树形表格的功能,百度、google找了一通,并没有发现很靠谱的,也不是很灵活。所以就用vue自己撸了一个,还望大家多多指教。

主要技术点:vue子组件的递归实现及相关样式的实现

树形表格实现

  • 效果图 
  • 主要代码

index.vue页面实现业务逻辑代码,比如树表格上面的一些操作按钮的实现及数据获取。

<template>
  <div class="contains">
    <h1>树表格实现</h1>
    <tree-table ref="recTree" :list.sync="treeDataSource" @actionFunc="actionFunc" @deleteFunc="deleteFunc" @orderByFunc="orderByFunc"></tree-table>
  </div>
</template>
<script> import treeTable from '@/components/tree-table.vue' export default {  data() {  return {  list: [], // 请求原始数据  treeDataSource: [] // 组合成树表格接收的数据  }  },  components: {  treeTable  },  methods: {  orderByFunc(val) {  alert('排序')  alert(val)  },  actionFunc(m) {  alert('编辑')  },  deleteFunc(m) {  alert('删除')  }  } } </script>
原始数据`list`:是不包含子数据的数据结构,即没有层级结构,例如:
[{id:111,parentId:0,name:'父及'},{id:111,parentId:111,name:'子级'}...],通过parentId来获取对应父子层级结构 `treeDataSource`:是树表格需要的数据结构,例如:
[{id:0,name:'父及',children:[{id:10,name:'子级',children:[]}]},...]

如果后台返回给你的是原始数据格式,就可以用下面方法封装成树表格可以使用的数据结构:

    getTreeData() {
      // 取父节点 let parentArr = this.list.filter(l => l.parentId === 0)
      this.treeDataSource = this.getTreeData(this.list, parentArr)
    },
    // 这里处理没有children结构的数据
    getTreeData(list, dataArr) {
      dataArr.map((pNode, i) => {  let childObj = []  list.map((cNode, j) => {  if (pNode.Id === cNode.parentId) {  childObj.push(cNode)  }  })  pNode.children = childObj  if (childObj.length > 0) {  this.getTreeData(list, childObj)  }  })  return dataArr  }

tree-table.vue页面。此页面是实现树表格的关健页面。主要代码如下:

<template>
	<div class="tree-table">
		<div class="tree-head">
			<table>
				<tr>
					<td class="td1">职位名称</td>
					<td class="td2">负责人</td>
					<td class="td3" @click="isDesc=!isDesc">
						创建时间
						<div class="arrow">
							<span class="up-arrow" :class="{'sort':isDesc}"></span>
							<span class="down-arrow" :class="{'sort':!isDesc}"></span>
						</div>
					</td>
					<td class="td4">工作经验</td>
					<td class="td5">发布时间</td>
					<td class="td6">操作</td>
				</tr>
			</table>
		</div>
		<div id="scrollWrap" class="tree-wrap">
			<div class="tree-body">
				<table v-if='treeDataSource.length>0'>
					<tbody>
						<tr>
							<td>
								<tree-item v-for="(model,i) in treeDataSource" :key="'root_node_'+i" :root="0" :num="i" @actionFunc="actionFunc" @deleteFunc="deleteFunc" :nodes="treeDataSource.length" :trees.sync="treeDataSource" :model.sync="model">
								</tree-item>
							</td>
						</tr>
					</tbody>
				</table>
			</div>
		</div>
	</div>
</template>

首先这里的子组件tree-item没有在页面上有引入,但是也可以正常使用。这里就是关健点,因为这个子组件是需要递归实现,所以,需要动态注册到当前组件中。代码如下(由于代码太多,先贴图说明吧,点击这里可以看源码):

这里子组件看起来是不是挺奇怪的,但是为了递归他本身,暂时也只想到这种办法。如果有更好的办法,欢迎留言指正。
那么,树表格的结构实现在哪里呢??对,就是在子组件的模版(template)里面,这里就不贴代码了,可以移步到源码查看。

补充一点:不要只看js部分,css部分才是这个树表格的关健所在。当然里面我采用了大量的计算属性去判断各种样式的展示,还有一种方法,就是在initTreeData方法里面去实现,这个方法就是处理或添加一些我们树表格所使用的信息。比如我现在在里面实现的层级线的偏移量m.bLeft = level === 1 ? 34 : (level - 2) * 16 + 34 这个计算如果没有看明白,可以留言。

  • 源码地址github,欢迎star。

参考资源隔壁家的老黄

关键字:
上一篇::亲,已经是第一篇了!
下一篇::亲,已经是最后一篇了!

推荐阅读:

    同类下暂无推荐的资讯...
Top