Element实现动态表格的示例代码
Posted 蓝色人生
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Element实现动态表格的示例代码相关的知识,希望对你有一定的参考价值。
【代码背景】
【代码实现】
1# -> 代码复用的基础是你需要一个可复用的组件
2# -> 在展示页面使用动态表格组件
3# -> 如何给动态表格根据需求动态添加序号列/索引列
【代码背景】
有这样一个业务需求场景,有大概十几张表归属于某个类别,用户希望在同一个页面,通过选择不同的查询指标展示不同的表格,这些表的表头样式类似但是又不完全相同,怎么做呢?
到目前为止所有基于Element UI的表格样式都是直接在页面写死的,像官方这样:
<el-table :data="tableData" style="width: 100%">
<el-table-column prop="date" label="日期" ></el-table-column>
<el-table-column prop="name" label="姓名" ></el-table-column>
<el-table-column prop="address" label="地址"></el-table-column>
</el-table>
要解决上述问题,最简单暴力的方式是为每个表写一个单独组件,然后通过select框触发事件切换不同组件路由渲染页面,当然这种方式很笨,也不符合代码复用的基本原则,所以为了偷懒,为了坚守代码复用的基本原则,开始思考有没有更好的方式来解决这个问题。
仔细观察这个<el-table>,表格数据是通过:data绑定的,表格头部数据则是通过<el-table-column>标签展示的,表头数据是不是也可以通过某种传参的方式结合v-for来渲染<el-table-column>的具体数据呢?在度娘的帮助下,果然有大佬已经这样做了,实现了动态表格,参考链接挂在最底下了哦,在此特别感谢免费分享知识的大佬们,知识无价,学无止境。
现将本项目的具体实现代码记录如下,完善了一些代码的注解,尝试帮助理解。
【代码实现】
1# -> 代码复用的基础是你需要一个可复用的组件
在/components/Table文件夹下新建两个组件
DynamicTable.vue
<template>
<!-- 动态展示表格 -->
<el-table :data="tableData" border stripe : @row-click="handleRowClick">
<!-- v-for 循环取表头数据 -->
<template v-for="item in tableHeader">
<table-column v-if="item.children && item.children.length" :key="item.id" :column-header="item" />
<el-table-column v-else :key="item.id" :label="item.label" :prop="item.prop" align="center" />
</template>
</el-table>
</template>
<script>
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)
}
}
}
</script>
TableColumn.vue
<template>
<el-table-column
:label="columnHeader.label"
:prop="columnHeader.label"
align="center"
<!--columnHeader对应:column-header-->
<template v-for="item in columnHeader.children">
<tableColumn
v-if="item.children && item.children.length"
:key="item.id"
:column-header="item"
/>
<el-table-column
v-else
:key="item.name"
:label="item.label"
:prop="item.prop"
align="center"
/>
</template>
</el-table-column>
</template>
<script>
export default {
name: \'TableColumn\',
props: {
columnHeader: {
type: Object,
required: true
}
}
}
</script>
<style scoped>
</style>
几点重要说明:
(1)表格头部的传参主要分为两类:带children节点和不带children节点的,如下图所示
Element实现动态表格的示例代码
请注意children节点是为了完成复杂表头的渲染,例如上面这个示例最终的表头渲染样式如下:
Element实现动态表格的示例代码
那么问题来了,<el-table-column>是<el-table>的标签,那这个<table-column>是个啥?
(2)DynamicTable.vue调用TableColumn.vue组件
Element实现动态表格的示例代码
DynamicTable.vue通过:column-header给TableColumn.vue传递带children子节点的表头信息,TableColumn.vue接收到这个节点信息后,主要做了以下两件事情:
第一:通过<el-table-column>渲染了一个label标签
第二:继续判断该节点是否存在children子节点
=> 如果存在children节点,继续通过<table-column>进行渲染,继续把这个子节点传给TableColumn.vue组件,重复上述步骤
=> 如果不存在children节点,表示这是一个终止节点,通过<el-table-column>渲染结束
2# -> 在展示页面使用动态表格组件
<template>
<div class="demo">
<el-card>
<!--查询区域-->
<el-row :gutter="10">
<el-col :span="6">
<div class="grid-content bg-purple">
<span style="margin-right: 10px">选择框 -</span>
<el-select
v-model="specified_table"
placeholder="请选择"
>
<el-option
v-for="item in options"
:key="item.zb_code"
:label="item.zb_name"
:value="item.zb_code"
/>
</el-select>
</div>
</el-col>
<el-col :span="6">
<div class="grid-content bg-purple">
<el-button type="primary" plain @click="handleQueryClick">查 询</el-button>
</div>
</el-col>
</el-row>
<!--表格区域-->
<dynamic-table
v-if="dynamicTableShow"
:table-data="tableData"
:table-header="tableHeaders"
:
/>
</el-card>
</div>
</template>
<script>
// 引入组件
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现在更新了
以上是关于Element实现动态表格的示例代码的主要内容,如果未能解决你的问题,请参考以下文章
element-UI table动态增加列,动态增加行,动态合并行。选择编辑表头行数据