【vue】基于ElementUI实现动态表格 您所在的位置:网站首页 vue基于什么 【vue】基于ElementUI实现动态表格

【vue】基于ElementUI实现动态表格

2023-06-06 16:07| 来源: 网络整理| 查看: 265

【代码背景】 

        有这样一个业务需求场景,有大概十几张表归属于某个类别,用户希望在同一个页面,通过选择不同的查询指标展示不同的表格,这些表的表头样式类似但是又不完全相同,怎么做呢?

        到目前为止所有基于Element UI的表格样式都是直接在页面写死的,像官方这样:

        要解决上述问题,最简单暴力的方式是为每个表写一个单独组件,然后通过select框触发事件切换不同组件路由渲染页面,当然这种方式很笨,也不符合代码复用的基本原则,所以为了偷懒,为了坚守代码复用的基本原则,开始思考有没有更好的方式来解决这个问题。

        仔细观察这个,表格数据是通过:data绑定的,表格头部数据则是通过标签展示的,表头数据是不是也可以通过某种传参的方式结合v-for来渲染的具体数据呢?在度娘的帮助下,果然有大佬已经这样做了,实现了动态表格,参考链接挂在最底下了哦,在此特别感谢免费分享知识的大佬们,知识无价,学无止境。

        现将本项目的具体实现代码记录如下,完善了一些代码的注解,尝试帮助理解。

【代码实现】

#1# -> 代码复用的基础是你需要一个可复用的组件

在/components/Table文件夹下新建两个组件

DynamicTable.vue

import TableColumn from '@/components/Table/TableColumn' export default { name: 'DynamicTable', components: { TableColumn }, props: { // 表格的数据 tableData: { type: Array, required: true }, // 多级表头的数据 tableHeader: { type: Array, required: true }, // 表格的高度 height: { type: String, default: '300' } }, methods: { // 行点击事件 handleRowClick (row, column, event) { // console.log(row) // console.log(column) // console.log(event) // 通知调用父组件的row-click事件 // row作为参数传递过去 this.$emit('row-click', row) } } }

TableColumn.vue

export default { name: 'TableColumn', props: { columnHeader: { type: Object, required: true } } }

 几点重要说明:

(1)表格头部的传参主要分为两类:带children节点和不带children节点的,如下图所示

请注意children节点是为了完成复杂表头的渲染,例如上面这个示例最终的表头渲染样式如下:

那么问题来了,是的标签,那这个是个啥?

(2)DynamicTable.vue调用TableColumn.vue组件

DynamicTable.vue通过:column-header给TableColumn.vue传递带children子节点的表头信息,TableColumn.vue接收到这个节点信息后,主要做了以下两件事情:

第一:通过渲染了一个label标签

第二:继续判断该节点是否存在children子节点

=> 如果存在children节点,继续通过进行渲染,继续把这个子节点传给TableColumn.vue组件,重复上述步骤

=> 如果不存在children节点,表示这是一个终止节点,通过渲染结束

 #2# -> 在展示页面使用动态表格组件

选择框 - 查 询 // 引入组件 import DynamicTable from '@/components/Table/DynamicTable' // 获取表头信息 import { getTableHeader02_1, getTableHeader02_2, getTableHeader02_3, getTableHeader02_4 } from '@/api/table-header' export default { name: 'Index', components: { // 组件注册 DynamicTable }, data () { return { // -- 查询 ---------------------- options: [ // { zb_name: '指标名', zb_code: '指标代码' } ], specified_table: '', // 指标值 // -- 表格 ---------------------- dynamicTableShow: true, // DynamicTable组件重新渲染变量 // 表头数据 tableHeaders: [], // 表格数据 tableData: [] } }, created () { // api-获取指标的下拉框数据 getSpecifiedTable().then(res => { this.options = res.data }) }, methods: { // 判断值是否在数组中 isExistArr (arr, val) { return arr.includes(val) }, // 重新渲染表格 refreshTable (zb_code) { // 根据value值获取label值 const obj = this.options.find((item) => { return item.zb_code === zb_code }) console.log(zb_code) console.log(obj.zb_name) // 设置dynamicTableShow为false,使得DynamicTable组件重新渲染 this.dynamicTableShow = false // 根据不同指标渲染不同的表头 const TBArr01 = ['M01', 'M02', 'M03', 'M05'] // 第1类表 const TBArr02 = ['M04', 'M07', 'M08', 'M12'] // 第2类表 const TBArr03 = ['M09', 'M10', 'M11'] // 第3类表 const TBArr04 = ['M06'] // 第4类表 if (this.isExistArr(TBArr01, zb_code)) { this.tableHeaders = getTableHeader02_1(obj.zb_name) // 渲染表头样式1 } if (this.isExistArr(TBArr02, zb_code)) { this.tableHeaders = getTableHeader02_2(obj.zb_name) // 渲染表头样式2 } if (this.isExistArr(TBArr03, zb_code)) { this.tableHeaders = getTableHeader02_3(obj.zb_name) // 渲染表头样式3 } if (this.isExistArr(TBArr04, zb_code)) { this.tableHeaders = getTableHeader02_4(obj.zb_name) // 渲染表头样式4 } // api - 获取表格数据 getTableList02(zb_code).then(res => { this.tableData = res.data }) // 此处是DOM还没有更新,此处的代码是必须的 this.$nextTick(() => { // DOM现在更新了 this.dynamicTableShow = true }) }, // 点击[查询]事件 handleQueryClick () { const zb_code = this.specified_table // 校验查询条件不能为空 if (zb_code === '' || zb_code === undefined) { this.$message.warning('指标不能为空!') } else { console.log('zb_code: ' + zb_code) // 重新渲染表头和表格 this.refreshTable(zb_code) } } } }

使用动态表格组件相对来说比较简单,唯一需要注意的地方是,渲染表格头部跟数据时必须需要添加以下代码,不然页面无法按照预期完成渲染。

this.$nextTick(() => { // DOM现在更新了 this.dynamicTableShow = true })

 关于this.$nextTick()可以参考官网:https://cn.vuejs.org/v2/guide/reactivity.html

 #3# -> 如何给动态表格根据需求动态添加序号列/索引列

在Element UI官方例子中,如果需要给table添加一个序号列或者索引列非常简单,直接在里声明一个特殊的即可。

那如何在动态表格组件里添加序号列呢?更甚者如果根据需要自行添加或者不添加?

首先我们来改造 DynamicTable.vue

像官方例子一样,我们先在里也声明一个

注意到这里有一个v-if绑定了一个isIndex值,这个值就是我们需要在父组件进行传值的关键了

在props里声明isIndex为Boolean类型

props: { // 表格的数据 tableData: { type: Array, required: true }, // 多级表头的数据 tableHeader: { type: Array, required: true }, // 表格的高度 height: { type: String, default: '300' }, // 是否需要添加序号列 isIndex: { type: Boolean } }

在展示页面使用组件时通过:is-index传入指定参数

在同页面表头需要切换的情况下,上面这种写法容易在页面初始化时候单独显示一个序号列,就像下面这样,非常不美观

 

我希望序号列可以和其他普通列一样在表头渲染的时候同时加载,可以这样做

将原本的常量“true”修改成一个变量isAddIndex替代,然后在表头渲染完成的时候将其值修改成true

this.isAddIndex = true

这样序号列就能跟其他普通列同时进行渲染了。 

【参考资料】

https://www.jianshu.com/p/9c4ba833658f

https://www.cnblogs.com/llcdxh/p/9473458.html  



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有