Vue - vxe-table 表格合并行应用
Vue - vxe-table 表格合并行应用
vxe-table 地址:https://vxetable.cn/v2/#/table/start/install
一. 将相同的列数据合并为一行
实现效果
实现方法
使用 API 中的
span-method
方法:
span-method
使用方法<vxe-grid border resizable align="center" :columns="tableColumn" :data="tableData" :span-method="rowspanMethod" > </vxe-grid>
// 将相同的列数据合并为一行 rowspanMethod({ row, _rowIndex, column, visibleData }) { // 需要合并的列字段 let fields = []; const cellValue = row[column.property]; if (cellValue && fields.includes(column.property)) { const prevRow = visibleData[_rowIndex - 1]; let nextRow = visibleData[_rowIndex + 1]; if (prevRow && prevRow[column.property] === cellValue) { return { rowspan: 0, colspan: 0 }; } else { let countRowspan = 1; while (nextRow && nextRow[column.property] === cellValue) { nextRow = visibleData[++countRowspan + _rowIndex]; } if (countRowspan > 1) { return { rowspan: countRowspan, colspan: 1 }; } } } }
- 完整代码
<template> <div class="page"> <vxe-grid border resizable align="center" :columns="tableColumn" :data="tableData" :span-method="rowspanMethod" > </vxe-grid> </div> </template> <script> export default { data() { return { tableColumn: [ { type: "seq", field: "seq", width: 50 }, { field: "bus", title: "公交班次" }, { field: "upDown", title: "上下行" }, { field: "strStation", title: "进站" }, { field: "endStation", title: "出站" }, { field: "guestNum", title: "上下行总客数" } ], tableData: [ { bus: "1路", upDown: "上行", strStation: "B站", endStation: "A站", guestNum: 98 }, { bus: "1路", upDown: "下行", strStation: "A站", endStation: "B站", guestNum: 98 }, { bus: "2路", upDown: "下行", strStation: "C站", endStation: "B站", guestNum: 95 }, { bus: "2路", upDown: "上行", strStation: "B站", endStation: "C站", guestNum: 95 }, { bus: "3路", upDown: "上行", strStation: "B站", endStation: "D站", guestNum: 95 }, { bus: "3路", upDown: "下行", strStation: "D站", endStation: "B站", guestNum: 95 }, { bus: "4路", upDown: "下行", strStation: "D站", endStation: "C站", guestNum: 102 }, { bus: "4路", upDown: "上行", strStation: "C站", endStation: "D站", guestNum: 102 } ] }; }, methods: { // 将相同的列数据合并为一行 rowspanMethod({ row, _rowIndex, column, visibleData }) { // 需要合并的列字段 let fields = ["bus", "upDown", "strStation", "endStation", "guestNum"]; const cellValue = row[column.property]; if (cellValue && fields.includes(column.property)) { const prevRow = visibleData[_rowIndex - 1]; let nextRow = visibleData[_rowIndex + 1]; if (prevRow && prevRow[column.property] === cellValue) { return { rowspan: 0, colspan: 0 }; } else { let countRowspan = 1; while (nextRow && nextRow[column.property] === cellValue) { nextRow = visibleData[++countRowspan + _rowIndex]; } if (countRowspan > 1) { return { rowspan: countRowspan, colspan: 1 }; } } } } } }; </script> <style scoped> .page { width: 100%; height: 100%; padding: 20px; box-sizing: border-box; } </style>
二. 拓展合并:根据某个字段合并后的数据 进行合并其他字段列
需求: 排序字段 根据 公交班次 合并后的数据进行排序,上下行总客数 根据 公交班次 合并后的数据
实现效果
实现方法
使用 API 中的
span-method
、seq-config
方法:
-
span-method
、seq-config
使用方法<vxe-grid border resizable align="center" :columns="tableColumn" :data="tableData" :span-method="rowspanMethod" :seq-config="{ seqMethod }" > </vxe-grid>
columns 列配置 中的排序项 需要添加
field: "seq"
tableColumn: [ { type: "seq", field: "seq", width: 50 }, { field: "bus", title: "公交班次" }, { field: "upDown", title: "上下行" }, { field: "strStation", title: "进站" }, { field: "endStation", title: "出站" }, { field: "guestNum", title: "上下行总客数" } ],
/** *自定义合并:根据某个字段合并后的数据 进行合并其他字段列 */ rowspanMethod({ row, items, seq, rowIndex, $rowIndex, _rowIndex, column, visibleData, data }) { /** * 相同的列数据 自定义合并 * 此处自定义合并的字段:seq、guestNum * 此处的合并参考字段:bus */ if (column.property === "seq") { // 合并参考字段,根据此字段进行合并行 const referenceField = "bus"; if (rowIndex > 0) { if (row[referenceField] === items[rowIndex - 1][referenceField]) { row.seq = items[rowIndex - 1].seq; } else { row.seq = items[rowIndex - 1].seq + 1; } } else if (rowIndex === 0) { row.seq = seq; } let prevRow = data[$rowIndex - 1]; let nextRow = data[$rowIndex + 1]; if (prevRow && prevRow[referenceField] === row[referenceField]) { return { rowspan: 0, colspan: 0 }; } else { let countRowspan = 1; while (nextRow && nextRow[referenceField] === row[referenceField]) { nextRow = data[++countRowspan + $rowIndex]; } if (countRowspan > 1) { return { rowspan: countRowspan, colspan: 1 }; } } } else { /** * 相同的列数据 默认合并 * 此处合并的列字段:["bus"] */ // 需要合并的列字段 let fields = ["bus"]; const cellValue = row[column.property]; if (cellValue && fields.includes(column.property)) { const prevRow = visibleData[_rowIndex - 1]; let nextRow = visibleData[_rowIndex + 1]; if (prevRow && prevRow[column.property] === cellValue) { return { rowspan: 0, colspan: 0 }; } else { let countRowspan = 1; while (nextRow && nextRow[column.property] === cellValue) { nextRow = visibleData[++countRowspan + _rowIndex]; } if (countRowspan > 1) { return { rowspan: countRowspan, colspan: 1 }; } } } } }, /** * 自定义排序 * 此处的合并参考字段:bus */ seqMethod(obj) { // 合并参考字段 const referenceField = "bus"; obj.row.seq = obj.seq; if (obj.rowIndex > 0) { if (obj.seq - obj.items[obj.rowIndex - 1].seq > 1) { if ( obj.row[referenceField] === obj.items[obj.rowIndex - 1][referenceField] ) { obj.row.seq = obj.items[obj.rowIndex - 1].seq; return obj.items[obj.rowIndex - 1].seq; } else { obj.row.seq = obj.items[obj.rowIndex - 1].seq + 1; return obj.items[obj.rowIndex - 1].seq + 1; } } else { obj.row.seq = obj.items[obj.rowIndex - 1].seq + 1; return obj.items[obj.rowIndex - 1].seq + 1; } } else { return obj.seq; } }
-
完整代码
<template> <div class="page"> <vxe-grid border resizable align="center" :columns="tableColumn" :data="tableData" :span-method="rowspanMethod" :seq-config="{ seqMethod }" > </vxe-grid> </div> </template> <script> export default { data() { return { tableColumn: [ { type: "seq", field: "seq", width: 50 }, { field: "bus", title: "公交班次" }, { field: "upDown", title: "上下行" }, { field: "strStation", title: "进站" }, { field: "endStation", title: "出站" }, { field: "guestNum", title: "上下行总客数" } ], tableData: [ { bus: "1路", upDown: "上行", strStation: "B站", endStation: "A站", guestNum: 98 }, { bus: "1路", upDown: "下行", strStation: "A站", endStation: "B站", guestNum: 98 }, { bus: "2路", upDown: "下行", strStation: "C站", endStation: "B站", guestNum: 95 }, { bus: "2路", upDown: "上行", strStation: "B站", endStation: "C站", guestNum: 95 }, { bus: "3路", upDown: "上行", strStation: "B站", endStation: "D站", guestNum: 95 }, { bus: "3路", upDown: "下行", strStation: "D站", endStation: "B站", guestNum: 95 }, { bus: "4路", upDown: "下行", strStation: "D站", endStation: "C站", guestNum: 102 }, { bus: "4路", upDown: "上行", strStation: "C站", endStation: "D站", guestNum: 102 } ] }; }, methods: { /** *自定义合并:根据某个字段合并后的数据 进行合并其他字段列 */ rowspanMethod({ row, items, seq, rowIndex, $rowIndex, _rowIndex, column, visibleData, data }) { /** * 相同的列数据 自定义合并 * 自定义合并的字段:seq、guestNum * 此处的合并参考字段:bus */ if (column.property === "seq" || column.property === "guestNum") { // 合并参考字段,根据此字段进行合并行 const referenceField = "bus"; if (rowIndex > 0) { if (row[referenceField] === items[rowIndex - 1][referenceField]) { row.seq = items[rowIndex - 1].seq; } else { row.seq = items[rowIndex - 1].seq + 1; } } else if (rowIndex === 0) { row.seq = seq; } let prevRow = data[$rowIndex - 1]; let nextRow = data[$rowIndex + 1]; if (prevRow && prevRow[referenceField] === row[referenceField]) { return { rowspan: 0, colspan: 0 }; } else { let countRowspan = 1; while (nextRow && nextRow[referenceField] === row[referenceField]) { nextRow = data[++countRowspan + $rowIndex]; } if (countRowspan > 1) { return { rowspan: countRowspan, colspan: 1 }; } } } else { /** * 相同的列数据 默认合并 * 此处合并的列字段:["bus"] */ // 需要合并的列字段 let fields = ["bus"]; const cellValue = row[column.property]; if (cellValue && fields.includes(column.property)) { const prevRow = visibleData[_rowIndex - 1]; let nextRow = visibleData[_rowIndex + 1]; if (prevRow && prevRow[column.property] === cellValue) { return { rowspan: 0, colspan: 0 }; } else { let countRowspan = 1; while (nextRow && nextRow[column.property] === cellValue) { nextRow = visibleData[++countRowspan + _rowIndex]; } if (countRowspan > 1) { return { rowspan: countRowspan, colspan: 1 }; } } } } }, /** * 自定义排序 * 此处的合并参考字段:bus */ seqMethod(obj) { // 合并参考字段 const referenceField = "bus"; obj.row.seq = obj.seq; if (obj.rowIndex > 0) { if (obj.seq - obj.items[obj.rowIndex - 1].seq > 1) { if ( obj.row[referenceField] === obj.items[obj.rowIndex - 1][referenceField] ) { obj.row.seq = obj.items[obj.rowIndex - 1].seq; return obj.items[obj.rowIndex - 1].seq; } else { obj.row.seq = obj.items[obj.rowIndex - 1].seq + 1; return obj.items[obj.rowIndex - 1].seq + 1; } } else { obj.row.seq = obj.items[obj.rowIndex - 1].seq + 1; return obj.items[obj.rowIndex - 1].seq + 1; } } else { return obj.seq; } } } }; </script> <style scoped> .page { width: 100%; height: 100%; padding: 20px; box-sizing: border-box; } </style>