Vxetable v3.6.9 合并单元格+虚拟滚动问题

Vxetable v3.6.9 合并单元格+虚拟滚动问题

使用版本

vue:2.7.16

vxe-table:3.6.9

下面示例使用的是:scroll-y="{}" 加:merge-cells="{}" 方式

重要说明 本案例使用的的版本比较老,因为是老项目。官网连接:Vxe Table v3.8

示例:这里使用 虚拟滚动+ 合并单元格单元格方式

需求说明:实现根据层级实现一对多合并单元格,并且数据量大

说明:这里代码示例是使用的项目中封装方法。
封装组件ElXTable/index.vue

vue 复制代码
<template>
  <vxe-table
    id="eTable"
    ref="singleTable"
    class="my-vxe-table"
    :scroll-y="{ enabled: isVirtual, gt: 0, mode: 'wheel', ...scrollY }"
    :height="height"
    :data="pageData.data || dataList"
    border
    show-overflow
    keep-source
    :row-id="rowKey"
    size="medium"
    :merge-cells="mergeCells"
    >
    <slot />
  </vxe-table>
  // 分页
  <vxe-pager
    :hide-on-single-page="false"
    :current-page="pageData.currentPage"
    :page-sizes="[50, 100, 200, 500, 1000]"
    :page-size="pageData.pageSize"
    size="small"
    :pager-count="5"
    :layouts="['Total', 'Sizes', 'PrevPage', 'JumpNumber', 'NextPage', 'FullJump']"
    :total="pageData.total"
    @page-change="handleCurrentChange"
  />
  </div>
</template>
<script>
export default {
  methods:{
    // 获取当前表格的列 {collectColumn, fullColumn, visibleColumn, tableColumn}
    getTableColumn() {
      return this.$refs.singleTable.getTableColumn().fullColumn
    },
    
    // 获取表格的可视的列 Array (及不包含隐藏的列 - 工具栏隐藏功能)
    getColumns() {
      return this.$refs.singleTable.getColumns()
    }
  }
}
</script>
 

page/index.vue

vue 复制代码
<template>
    <ElXTable
        ref="xTable"
        isVirtual
        rowKey="id"
        :dataList="tableData"
        :mergeCells="mergeCells"
    >
        <vxe-column type="checkbox" width="60" />
        <vxe-column type="seq" title="序号" width="55" />
        <vxe-column field="data1" title="数据1"></vxe-column>
        ...
    </ElXTable>
</template>
<script>
import ElXTable from "@/components/ElXTable"
export default {
  components: {
    ElXTable
  },
  data() {
    return {
      tableData: [],  // 表格数据 
      mergeCells: [], // 合并单后数据
      // 字段层级分类
      propertyLvObj: {
        l1: ["data1", ...],
        l2: [...],
        l3: [...],
        l4: [...]
      },
    }
  },
  mounted() {
      this.getTableData()
  },
  methods: {
      //获取表格数据
      getTableData(){
          // 这里调用接口
          const res = await $https.getVerifyPlan()
          if (res) {
            this.tableData = res.records
            this.getMergeCells(res.records)
          }
      },
     getMergeCells(data) {
      let column = this.$refs.xTable.getColumns()
      this.mergeCells = []
      this.tableData.forEach((row, _rowIndex) => {
        column.forEach((column, index) => {
          let r = this.spanMethod({ row, _rowIndex, column, data })
          if (r) {
            this.mergeCells.push({ ...r, row: _rowIndex, col: index })
          }
        })
      })
    },
    // 通用行合并函数(将相同多列数据合并为一行)
    /**
     *  思路 根据相邻行对应id 相同  才合并 需要注意的是 数据返回需要后端排序
     */
    spanMethod({ row, _rowIndex, column, data }) {
      // 需要合并的列
      const fields = []
      Object.keys(this.propertyLvObj).forEach((item) => {
        fields.push(...this.propertyLvObj[item])
      })
      const cellValue = row[column.property] // 当前行数据的值
      if (fields.includes(column.property)) {
        const prevRow = data[_rowIndex - 1] // 上一行数据
        let nextRow = data[_rowIndex + 1] // 下一行数据
        if (prevRow && fields.includes(column.property) && this.filterFields(row, prevRow, column.property)) {
          return { rowspan: 0, colspan: 0 }
        } else {
          let countRowspan = 1
          while (nextRow && fields.includes(column.property) && this.filterFields(row, nextRow, column.property)) {
            nextRow = data[++countRowspan + _rowIndex]
          }
          if (countRowspan > 1) {
            return { rowspan: countRowspan, colspan: 1 }
          }
        }
      }
    },

     /**
     *  特定的字段列 判断条件不一样
     *  根据相邻行数据前面的 mergeId1、mergeId2 来判断是否相同
     */
    filterFields(currRow, row, property) {
      if (this.propertyLvObj["l1"].includes(property) && currRow["mergeId1"] === row["mergeId1"]) {
        return true
      }
      if (this.propertyLvObj["l2"].includes(property) && currRow["mergeId2"] === row["mergeId2"]) {
        return true
      }
      if (this.propertyLvObj["l3"].includes(property) && currRow["mergeId3"] === row["mergeId3"]) {
        return true
      }
      if (this.propertyLvObj["l4"].includes(property) && currRow["mergeId4"] === row["mergeId4"]) {
        return true
      }
      return false
    },
  }
}
</script>

这里重点说明下官网 vxetable3.0版本 的虚拟滚动和合并单元不能同时使用问题。官网说的不能同时使用合并方法使用的是自定义 span-method合并方法。如果是数据量小不需要虚拟滚动建议使用。除此以外建议使用merge-cells

相关推荐
变与不变8066 小时前
jQuery怎么使用
前端·javascript
神膘护体小月半6 小时前
flex 布局的 order 属性
前端·css
paopaokaka_luck6 小时前
流浪动物救助与收养系统(DeepSeek AI对话、 ECharts多维分析、救助流程衔接、领养与回访衔接、 捐赠确认与公示、志愿者协作)
java·前端·javascript·人工智能·mysql·echarts·推荐算法
仰望.6 小时前
vue 表格组件 vxe-table 树表格懒加载支持拖拽排序的详细用法
前端·javascript·vue.js·vxe-table
前端 贾公子6 小时前
vite-plugin-uni-manifest 升级指南
前端
小码哥_常6 小时前
iPhone 用户传了张 HEIC,我的前端崩了
前端
小码哥_常7 小时前
你发的原图可能暴露你家地址——聊聊图片 EXIF 隐私
前端
java1234_小锋7 小时前
【技术专题】CSS3 网页技术 - CSS3 优先级
前端·css·css3
鸿蒙开发8 小时前
共享 Schema 与 SchemaFactory
前端·后端·harmonyos
屏什么录8 小时前
录屏超过两小时就卡顿崩盘?从参数调优到代码实现,一文彻底搞定长时间录屏
前端·音视频开发