vue.js

关注公众号 jb51net

关闭
首页 > 网络编程 > JavaScript > javascript类库 > vue.js > Vue之vxe-table表格合并行

Vue之vxe-table表格合并行应用指南

作者:风轻轻~

想要表格相同列数据智能合并?vxe-table合并单元格教程来啦!本指南教你使用span-method灵活合并行,并深入讲解如何根据字段进行拓展合并与排序,点击即可掌握让表格显示更清晰的核心技巧

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-methodseq-config 方法:

span-methodseq-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>

总结

以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。

您可能感兴趣的文章:
阅读全文