Clark.Pan 发表于 2020-3-26 11:47:51

如何在导出Excel时带有自动合并(AutoMerge)效果(二)

上回介绍了byRow,byColumn的算法实现,这期我们介绍剩下的byRowColumn,byColumnRow的实现逻辑
首先byRowColumn,byColumnRow的实现需要基于byRow,byColumn的算法实现,具体操作可以参考上一期的内容:如何在导出Excel时带有自动合并(AutoMerge)效果(一)
byRowColumn:
byRowColumn的原理就是在基于按行去合并的基础上,在按列合并所有可合并的单元格,也就是行优先的行列合并。
所以首先需要做的的byRow的操作,在byRow的基础上再循环判断进行byColumn的操作。
function spanbyrowcolumn(range){
      var spans = spanbyrow(range);
      for(var i=0;i<spans.length;i++){
          var row = spans.row;
          var col = spans.col;
          var rowCount = spans.rowCount;
          var colCount = spans.colCount;
          var sourceValue = sheet.getValue(spans.row,spans.col);
          var spanRowCount = rowCount;
          for(var j=spans.row+spans.rowCount;j<range.row+range.rowCount;j++){
            var spanFlag = true;
            for(var k=spans.col;k<spans.col+spans.colCount;k++){
                  var tempSpan = findSpan(j,k);
                  if(tempSpan && tempSpan.colCount != colCount){
                      spanFlag = false;
                      break;
                  }
                  if(sourceValue!=sheet.getValue(j,k)){
                      spanFlag = false;
                      break;
                  }
            }
            if(spanFlag){
                  spanRowCount++
                  sheet.removeSpan(j,col);
            }else{
                  break;
            }
          }
          if(spanRowCount>1){
            var compareSpan = findSpan(row,col);
            var currentSpan = new GC.Spread.Sheets.Range(row,col,spanRowCount,colCount);
            if(compareSpan !=null){
                  if(!containSpan(currentSpan,compareSpan)){
                      sheet.removeSpan(row,col);
                      sheet.addSpan(row,col,spanRowCount,colCount);
                  }
            }else{
                  sheet.removeSpan(row,col);
                  sheet.addSpan(row,col,spanRowCount,colCount);
            }
          }
      }
                }
这里还需要一些对特殊情况的判断,例如在做列合并的时候上下两列如果都是合并单元格的处理方式,边界的判断等。
合并的结果如下:

之后导出Excel,结果如下:

byColumnRow:
原理与byRowColumn刚好相反,先做列合并再做行合并,核心代码如下:
function spanbycolumnrow(range){
    var spans = spanbycolumn(range);
    for(var i=0;i<spans.length;i++){
      var row = spans.row;
      var col = spans.col;
      var rowCount = spans.rowCount;
      var colCount = spans.colCount;
      var sourceValue = sheet.getValue(spans.row,spans.col);
      var spanColCount = colCount;
      for(var j=spans.col+spans.colCount;j<range.col+range.colCount;j++){
            var spanFlag = true;
            for(var k=spans.row;k<spans.row+spans.rowCount;k++){
                var currentValue = sheet.getValue(k,j);
                if(sourceValue!=sheet.getValue(k,j)){
                  spanFlag = false;
                  break;
                }
            }
            if(spanFlag){
                spanColCount++
                sheet.removeSpan(row,j);
            }else{
                break;
            }
      }合并的结果如下:

导出后结果如下图所示:


以上就是4种合并方式的讲解,具体可以参考附件的demo(需要替换引用的相关js为本地的资源)。
上述的算法仅供参考,只是基于思路的基本实现,没有经过过多的优化,具体应用可以在此基础上再进行一些优化来提升程序的健壮性和性能。

it_idgcapital 发表于 2020-3-26 13:15:29

6666,谢谢分享

favori 发表于 2020-6-16 17:52:47

:)

果果xxxxk 发表于 2021-5-14 14:30:15

楼主可以提供下findSpan的实现方法吗?

Clark.Pan 发表于 2021-5-14 15:34:26

在帖子1楼的最下面,附件demo里面有,您可以下下来仔细详看

果果xxxxk 发表于 2021-5-15 13:20:13

Clark.Pan 发表于 2021-5-14 15:34
在帖子1楼的最下面,附件demo里面有,您可以下下来仔细详看

看到了,感谢

Derrick.Jiao 发表于 2021-5-17 08:54:32

果果xxxxk 发表于 2021-5-15 13:20
看到了,感谢

:mj72:

Ellia.Duan 发表于 2023-11-3 16:49:15

我们在新版本中已经有public 接口实现了这部分内容,欢迎大家点击下面这个链接查看测试:
https://gcdn.grapecity.com.cn/showtopic-198053-1-1.html
页: [1]
查看完整版本: 如何在导出Excel时带有自动合并(AutoMerge)效果(二)