- 新建src/hooks/useTableMerge.js,computeCell方法遍历整个表格数组,根据传入的字段生成一个数据,例如表格有8行,第一列需要纵向合并8个单元格,那么会返回一个数组[8,0,0,0,0,0,0,0,0],表示,在第一行的位置进行合并合并数量为8,第二列需要纵列两两合并,那么返回数组[2,0,2,0,2,0,2,0]
export default function () {
/**
* 根据表体数据,指定需要合并单元格的字段是那个
* 返回统计出来的需要纵向合并的单元格信息
* */
const computeCell = (tableBody, key) => {
let cellList = [];
let count;
for (let i = 0; i < tableBody.length; i++) {
if (i === 0) {
cellList.push(1);
count = 0;
} else {
if (tableBody[i][key] === tableBody[i - 1][key]) {
cellList[count] += 1;
cellList.push(0);
} else {
cellList.push(1);
count = i;
}
}
}
return cellList;
}
/**
* 根据计算出来的需要纵向合并的单元格信息去合并
* 返回的对象数据给到element UI objectSpanMethod使用
* */
const mergeCellVertical = (cellList, rowIndex) => {
const rowCell = cellList[rowIndex];
if (rowCell > 0) {
const colCell = 1;
return {
rowspan: rowCell,
colspan: colCell,
};
} else {
return {
rowspan: 0,
colspan: 0,
};
}
}
return {
computeCell,
mergeCellVertical
}
}
- 在组件中引入
import useTableMerge from '@/hooks/useTableMerge'
const {computeCell, mergeCellVertical} = useTableMerge()
onMounted(() => {
calculateMerge()
})
// 第一列合并单元格信息
const cellList1_1 = ref([])
// 第二列合并单元格信息
const cellList1_2 = ref([])
const calculateMerge = () => {
cellList1_1.value = computeCell(tableData1.value, "primaryIndicator");
cellList1_2.value = computeCell(tableData1.value, "secondaryIndicator");
}
const tableData1 = ref([
{
primaryIndicator: '产出指标60分',
secondaryIndicator: '数量指标(20分)',
tertiaryIndicator: '',
indicatorNature: '',
indicatorValue: '',
measurementUnit: '',
weight: '',
sort: 1
}
...
]
/**
* 计算单元格的合并范围。
* 此方法用于确定表格中特定单元格是否应该被合并。它通过对行索引和列索引进行检查,来决定合并的逻辑。
*
* @param {Object} param0 包含单元格的行索引和列索引的对象。
* @param {number} param0.rowIndex 单元格的行索引。
* @param {number} param0.columnIndex 单元格的列索引。
* @returns {Object|null} 返回一个对象来指定单元格的合并范围,如果不需要合并则返回null。
*/
const objectSpanMethod1 = ({ rowIndex, columnIndex}) => {
// 当列索引为0或1时,检查是否需要进行纵向合并
// 第一列的合并(竖向)
if (columnIndex === 0) {
return mergeCellVertical(cellList1_1.value, rowIndex);
}
// 第二列合并(竖向)
if (columnIndex === 1) {
return mergeCellVertical(cellList1_2.value, rowIndex);
}
}
- 页面数据
<el-table :data="tableData1" :span-method="objectSpanMethod1"
border>
<el-table-column prop="primaryIndicator" label="一级指标"/>
<el-table-column prop="secondaryIndicator" label="二级指标">
<template #default="scope">
<div>{{ scope.row.secondaryIndicator }}</div>
<el-button link type="primary" size="small" @click="addItem(scope)">新增三级指标
</el-button>
</template>
</el-table-column>
<el-table-column prop="tertiaryIndicator" label="三级指标"/>
<el-table-column prop="indicatorNature" label="绩效指标性质"/>
<el-table-column prop="indicatorValue" label="绩效指标值"/>
<el-table-column prop="measurementUnit" label="绩效度量单位"/>
<el-table-column prop="weight" label="权重"/>
<el-table-column fixed="right" label="操作" v-if="props.isEdit">
<template #default="scope">
<el-button link type="primary" size="small" @click="editItem(scope)">编辑
</el-button>
<el-popconfirm
title="确认移除该条数据吗?"
@confirm="removeItem(scope)"
>
<template #reference>
<el-button size="small" link type="danger">移除
</el-button>
</template>
</el-popconfirm>
</template>
</el-table-column>
</el-table>
新增编辑移除
//新增
const addItem = ({$index, row}) => {
operationTpe.value = 'add'
operation.value = '新增指标'
tableIndex.value = $index
Object.keys(form).map(key => {
form[key] = ''
})
form.primaryIndicator = row.primaryIndicator
form.secondaryIndicator = row.secondaryIndicator
dialogFormVisible.value = true
}
//新增确认
const confirm = () => {
tableData1.value[tableIndex.value] = {...form}
//将新增的数据添加到表格的指定位置后,需要重新合并一下表格
calculateMerge()
dialogFormVisible.value = false
}
新增三级指标
删除编辑同上