共计 3010 个字符,预计需要花费 8 分钟才能阅读完成。
<template>
<div class="zz-dynamic-table">
<table class="customTable" border cellpadding="0" cellspacing="0">
<thead>
<tr v-for="(aitem, i) in newTheadData" :key="'a' + i">
<th
:width="bitem.width ? bitem.width :'auto'":style="{width: bitem.width ? bitem.width : 'auto', 'text-align': bitem.align ? bitem.align : 'center'}"v-for="(bitem, j) in aitem":key="'b'+ j"
:rowspan="bitem.rowspan"
:colspan="bitem.colspan"
v-html="bitem.label"
></th>
</tr>
</thead>
<tr v-for="(item, index) in tableData" :key="index">
<td
v-for="(item1, key, index1) in item"
:key="index1"
:align="thArr[index1].align && key === thArr[index1].key ? thArr[index1].align :'center'"
>
{{item1}}
</td>
</tr>
</table>
</div>
</template>
<script>
export default {
name: 'zz-dynamic-table',
props: {
theadData: {
type: Array,
default: () => [{ key: 'date', label: '日期', align: 'left'},
{
label: '配送信息',
children: [{ key: 'name', label: '姓名'},
{
label: '地址',
children: [{ key: 'province', label: '省份'},
{key: 'city', label: '市区'},
{key: 'address', label: '具体 <br/> 地址'}
]
}
]
},
{key: 'zip', label: '编码'}
]
}
},
data() {
return {thArr: [],
rows: 1,
tableData: [
{
date: '323232',
name: 'wang',
province: 'province',
city: 'city',
address: 'address',
zip: 333
},
{
date: '32323221',
name: 'wang1',
province: 'province1',
city: 'city11',
address: 'address1',
zip: 555
}
],
newTheadData: []}
},
created() {this.newTheadData = this.getTheadData(this.theadData)
// console.log('newTheadData=', this.newTheadData, this.rows)
this.thArr = this.treeToFlat(this.theadData, [])
console.log('thArr=', this.thArr)
},
methods: {treeToFlat(arr, res) {
let result = res
arr.forEach(item => {if (item.children?.length) {this.treeToFlat(item.children, result)
} else {result.push(item)
}
})
return result
},
// 获取最终后果返进来
getTableData() {this.$nextTick(() => {
let result = ''
if (this.tableData && this.tableData.length) {result = JSON.stringify(this.tableData)
}
this.$emit('input', result)
})
},
addRow() {this.tableData.push({})
},
// 数组中是否有 children 字段
isHaveChildren(arr) {if (!arr) {return false}
for (let i = 0; i < arr.length; i++) {let item = arr[i]
if (item.children && item.children.length) {return true}
}
return false
},
// 获取该列合并的总数
getColCount(data) {
let sum = 0
if (!data) {return sum}
if (!data.children) {return sum}
let _this = this
let fn = function(arr) {if (!arr) {return sum}
arr.forEach(item => {if (item.children) {fn(item.children)
} else {sum++}
})
}
fn(data.children)
return sum
},
// 重组 thead 数据
getTheadData(p) {let params = JSON.parse(JSON.stringify(p))
if (!params) {return []
}
let data = [],
_this = this
var fn = function(arr) {if (!arr) {return []
}
// 是否领有多级表头
let rowData = []
if (_this.isHaveChildren(arr)) {
arr.forEach(item => {if (item.children) {
item.rowspan = 1
item.colspan = _this.getColCount(item)
fn(item.children)
} else {
item.rowspan = arr.length
item.colspan = 1
}
rowData.push(item)
})
} else {
arr.forEach(item => {
item.rowspan = 1
item.colspan = 1
rowData.push(item)
})
}
data.unshift(rowData)
}
if (this.isHaveChildren(params)) {
// 重组
this.rows = params.length
fn(params)
} else {
// 不重组
data.push(params)
}
return data
}
},
watch: {theadData(value) {this.newTheadData = this.getTheadData(value)
}
}
}
</script>
<style lang="less" scoped>
.zz-dynamic-table {width: 100%;}
table {
width: 100%;
border-color: #777;
// border-color: red;
}
thead {background: #eee;}
tr {width: 100%;}
th {
padding: 3px 2px;
min-width: 10%;
}
td {padding: 3px 2px;}
</style>
正文完
发表至: javascript
2023-03-06