el-table动态合并单元格

1,335 阅读2分钟

实现动态合并单元格的需求。

实现效果

  • 每列可自由合并
  • 可多列联动合并
  • 可复制合并,如库区名称列,库区面积列等均是复制库区编号列的合并规则 如:图中列表的库区编号列基于仓库分区列合并;库区名称列基于仓库分区列和库区编号列合并

image.png juejin.cn/post/684490… 作者大大已经给出了几个方法,在开发过程中,由于需求较为复杂,将上文方法二进行了优化。

核心代码

/**
     * @description: 动态合并单元格
     * @param {array} data 要处理的数据
     * @param {array} merge 要合并的列
     * @param {string or array} lastp 基于的列,能否合并的附加条件,比如A温层的ZONE库区,和B温层的ZONE库区,将不会合并
     * 每一行的row[lastp所包含的每一列]均和上一列相同,才合并当前merge中的m
     * @return {*}
     */
    mergeTableRow(data, merge, lastp) {
      if (!merge || merge.length === 0) {
        return data
      }
      merge.forEach(m => {
        const mList = {}
        data = data.map((v, index) => {
          const rowVal = v[m]
          let key,
            diffitems = []
          if (lastp && typeof lastp === 'string') {
            key = m + '-span-' + v[lastp]
          } else if (lastp && lastp instanceof Array) {
            key = m + '-span-' + lastp.join('-')
            diffitems = index > 0 && lastp.filter(x => v[x] != data[index - 1][x])
          } else {
            key = m + '-span'
          }
          if (
            mList[rowVal] &&
            mList[rowVal].newIndex === index &&
            (!lastp ||
              (index > 0 && typeof lastp === 'string' && v[lastp] === data[index - 1][lastp]) ||
              (index > 0 && lastp instanceof Array && diffitems.length === 0))
          ) {
            mList[rowVal]['num']++
            mList[rowVal]['newIndex']++
            data[mList[rowVal]['index']][key].rowspan++
            v[key] = {
              rowspan: 0,
              colspan: 0
            }
          } else {
            mList[rowVal] = { num: 1, index: index, newIndex: index + 1 }
            v[key] = {
              rowspan: 1,
              colspan: 1
            }
          }
          return v
        })
      })
      return data
    },
 /**
     * @description: copy 每一行的base列的rowspan和colspan
     * @param {array} data 要处理的数据
     * @param {array} merge 要合并的列
     * @param {string} base 被copy的列
     * @return {array} 处理后的data
     */
    mergeCopy(data, merge, base) {
      merge.forEach(m => {
        data = data.map(v => {
          let key = Object.keys(v).find(i => i.includes(base + '-span'))
          v[m + '-span'] = { ...v[key] }
          return v
        })
      })
      return data
    },

span-method也要稍稍优化一下:

objectSpanMethod({ row, column }) {
      const span = column['property'] + '-span'
      if (row[span]) {
        return row[span]
      } else {
        let newSpan = Object.keys(row).find(i => i.includes(span))
        return row[newSpan]
      }
    },