Java导出Excel并合并单元格

发布时间:2024年01月18日

需求:需要在导出excel时合并指定的单元格

?ruoyi excel

项目基于若伊框架二次开发,本着能用现成的就不自己写的原则,先是尝试了@Excel注解中needMerge属性

     /**
     * 是否需要纵向合并单元格,应对需求:含有list集合单元格)
     */
    public boolean needMerge() default false;

查了一圈别人的使用,大致是需要定义一个List集合,集合元素为对象,对象中的属性标注@Excel注解,并表明name属性

照葫芦画瓢

@Getter
@Setter
@ToString
public class CutterControlVO {

    /** 主键 */
    private Long id;

    /** 工厂编码 */
    @Excel(name = "工厂编码",needMerge = true)
    private String factoryCode;

    /** 产线编码 */
    @Excel(name = "产线编码",needMerge = true)
    private String productionLineCode;

    /** 设备编号 */
    @Excel(name = "设备编号",needMerge = true)
    private String deviceNumber;

    /** 设备名称 */
    @Excel(name = "设备名称",needMerge = true)
    private String deviceName;

    @Excel(name = "检测刀具编码",needMerge = true)
    private String cutterCode;

    /** 换刀时间 */
    @JsonFormat(timezone="GMT+8", pattern="yyyy-MM-dd HH:mm:ss")
    @DateTimeFormat(pattern="yyyy-MM-dd HH:mm:ss")
    @Excel(name = "换刀时间",dateFormat = "yyyy-MM-dd HH:mm:ss",needMerge = true)
    private Date cutterChangeTime;

    /** 上刀数 */
    @Excel(name = "上刀数",needMerge = true)
    private Integer upperKnifeNumber;

    /** 下刀数 */
    @Excel(name = "下刀数",needMerge = true)
    private Integer lowerKnifeNumber;

    @Excel(name = "更换人员",needMerge = true)
    private String modifyUser;

    /** 备注 */
    @Excel(name = "备注",needMerge = true)
    private String remark;

    @Excel(name = "换刀位置")
    private List<CutterVO> cutterChangePosition;

    @Excel(name = "累计分切米数")
    private List<CutterVO> accumulatedCuttingMeters;


}
@Getter
@Setter
@ToString
public class CutterVO {

    @Excel(name = "上刀左")
    private Integer upperKnifeLeft;

    @Excel(name = "上刀中")
    private Integer upperKnifeCenter;

    @Excel(name = "上刀右")
    private Integer upperKnifeRight;

    @Excel(name = "下刀左")
    private Integer lowerKnifeLeft;

    @Excel(name = "下刀中")
    private Integer lowerKnifeCenter;

    @Excel(name = "下刀右")
    private Integer lowerKnifeRight;
}
@PostMapping("/export")
public void export(HttpServletResponse response) throws Exception{
    List<CutterControl> cutterControlList = cutterControlService.getCutterControlList();
    //设置导出的数据表格式
    List<CutterControlVO> cutterControlVOList = new ArrayList<>();
    CutterControlVO cutterControlVO = null;
    for (CutterControl cutterControl : cutterControlList) {
        cutterControlVO = new CutterControlVO();
        CutterVO cutterPosition = new CutterVO();
        cutterPosition.setUpperKnifeLeft(cutterControl.getCutterChangePositionUpperKnifeLeft());
        cutterPosition.setUpperKnifeCenter(cutterControl.getCutterChangePositionUpperKnifeCenter());
        cutterPosition.setUpperKnifeRight(cutterControl.getCutterChangePositionUpperKnifeRight());
        cutterPosition.setLowerKnifeLeft(cutterControl.getCutterChangePositionLowerKnifeLeft());
        cutterPosition.setLowerKnifeCenter(cutterControl.getCutterChangePositionLowerKnifeCenter());
        cutterPosition.setLowerKnifeRight(cutterControl.getCutterChangePositionLowerKnifeRight());

        CutterVO accumulatedCuttingMeters = new CutterVO();
        accumulatedCuttingMeters.setUpperKnifeLeft(cutterControl.getAccumulatedCuttingMetersUpperKnifeLeft());
        accumulatedCuttingMeters.setUpperKnifeCenter(cutterControl.getAccumulatedCuttingMetersUpperKnifeCenter());
        accumulatedCuttingMeters.setUpperKnifeRight(cutterControl.getAccumulatedCuttingMetersUpperKnifeRight());
        accumulatedCuttingMeters.setLowerKnifeLeft(cutterControl.getAccumulatedCuttingMetersLowerKnifeLeft());
        accumulatedCuttingMeters.setLowerKnifeCenter(cutterControl.getAccumulatedCuttingMetersLowerKnifeCenter());
        accumulatedCuttingMeters.setLowerKnifeRight(cutterControl.getAccumulatedCuttingMetersLowerKnifeRight());

        BeanUtils.copyProperties(cutterControl,cutterControlVO);
        cutterControlVO.setCutterChangePosition(Arrays.asList(cutterPosition));
        cutterControlVO.setAccumulatedCuttingMeters(Arrays.asList(accumulatedCuttingMeters));
        cutterControlVOList.add(cutterControlVO);
    }

    ExcelUtil<CutterControlVO> util = new ExcelUtil<CutterControlVO>(CutterControlVO.class);

    util.exportExcel(response,cutterControlVOList,"切刀管控台账数据");
}

查看导出效果:

黑人问号脸?

突然想到别人都是采用的是一个List集合,于是我注释了一个List,此时效果如下:

?可以看到,一个List效果是正常显示的,数据获取和显示也是正常的。

若伊使用的Excel导出工具类底层采用apache poi ,只能导出简单的excel表格,涉及复杂excel表格或者需要自定义表格时就比较难操作

使用阿里的easyExcel来实现复杂excel表格的导出

easyExcel

首先引入POM依赖

    <dependency>
      <groupId>com.alibaba</groupId>
      <artifactId>easyexcel</artifactId>
      <version>2.2.7</version>
    </dependency>

1、不合并单元格的写法

实体类

@Getter
@Setter
public class CutterControl {

    /** 主键 */
    @ExcelIgnore
    private Long id;

    /** 工厂编码 */
    @ExcelProperty(value = "工厂编码")
    private String factoryCode;

    /** 产线编码 */
    @ExcelProperty(value = "产线编码")
    private String productionLineCode;

    /** 设备编号 */
    @ExcelProperty(value = "设备编号")
    private String deviceNumber;

    /** 设备名称 */
    @ExcelProperty(value = "设备名称")
    private String deviceName;

    @ExcelProperty(value = "检测刀具编码")
    private String cutterCode;

    @ExcelProperty(value = "上刀左")
    private Integer cutterChangePositionUpperKnifeLeft;

    @ExcelProperty(value = "上刀中")
    private Integer cutterChangePositionUpperKnifeCenter;

    @ExcelProperty(value = "上刀右")
    private Integer cutterChangePositionUpperKnifeRight;

    @ExcelProperty(value = "下刀左")
    private Integer cutterChangePositionLowerKnifeLeft;

    @ExcelProperty(value = "下刀中")
    private Integer cutterChangePositionLowerKnifeCenter;

    @ExcelProperty(value = "下刀右")
    private Integer cutterChangePositionLowerKnifeRight;

    @ExcelProperty(value = "上刀左")
    private Integer accumulatedCuttingMetersUpperKnifeLeft;

    @ExcelProperty(value = "上刀中")
    private Integer accumulatedCuttingMetersUpperKnifeCenter;

    @ExcelProperty(value = "上刀右")
    private Integer accumulatedCuttingMetersUpperKnifeRight;

    @ExcelProperty(value = "下刀左")
    private Integer accumulatedCuttingMetersLowerKnifeLeft;

    @ExcelProperty(value = "下刀中")
    private Integer accumulatedCuttingMetersLowerKnifeCenter;

    @ExcelProperty(value = "下刀右")
    private Integer accumulatedCuttingMetersLowerKnifeRight;

    /** 换刀时间 */
    @JsonFormat(timezone="GMT+8", pattern="yyyy-MM-dd HH:mm:ss")
    @DateTimeFormat(pattern="yyyy-MM-dd HH:mm:ss")
    @ExcelProperty(value = "换刀时间")
    @ColumnWidth(20)
    private Date cutterChangeTime;

    /** 上刀数 */
    @ExcelProperty(value = "上刀数")
    private Integer upperKnifeNumber;

    /** 下刀数 */
    @ExcelProperty(value = "下刀数")
    private Integer lowerKnifeNumber;

    @ExcelProperty(value = "更换人员")
    private String modifyUser;

    /** 备注 */
    @ExcelProperty(value = "备注")
    private String remark;

}

@ExcelIgnore :设置表格忽略该属性

@ColumnWidth(20): 设置列宽

controller代码

  @PostMapping("/export")
    public void export(HttpServletResponse response) throws Exception{
        List<CutterControl> cutterControlList = cutterControlService.getCutterControlList();
        String fileName = System.getProperty("user.dir") + "/" + System.currentTimeMillis() + ".xlsx";
        // 构建ExcelWriter
        ExcelWriter excelWriter = EasyExcel.write(fileName).excelType(ExcelTypeEnum.XLSX).build();
        // 构建sheet
        WriteSheet writeSheet = EasyExcel.writerSheet("切刀管控台账数据").head(CutterControl.class).build();
        // 写sheet
        excelWriter.write(cutterControlList, writeSheet);
        excelWriter.finish();
    }
结果:

2、自定义列合并策略

参考eastExcel文档可知,在实体类上添加属性即可实现我想要的效果

写Excel | Easy Excel

@Getter
@Setter
@EqualsAndHashCode
public class ComplexHeadData {
    @ExcelProperty({"主标题", "字符串标题"})
    private String string;
    @ExcelProperty({"主标题", "日期标题"})
    private Date date;
    @ExcelProperty({"主标题", "数字标题"})
    private Double doubleData;
}

再次照葫芦画瓢

@Getter
@Setter
public class CutterControl {

    /** 主键 */
    @ExcelIgnore
    private Long id;

    /** 工厂编码 */
    @ExcelProperty(value = "工厂编码")
    private String factoryCode;

    /** 产线编码 */
    @ExcelProperty(value = "产线编码")
    private String productionLineCode;

    /** 设备编号 */
    @ExcelProperty(value = "设备编号")
    private String deviceNumber;

    /** 设备名称 */
    @ExcelProperty(value = "设备名称")
    private String deviceName;

    @ExcelProperty(value = "检测刀具编码")
    private String cutterCode;

    @ExcelProperty({"换刀位置", "上刀左"})
    private Integer cutterChangePositionUpperKnifeLeft;

    @ExcelProperty({"换刀位置", "上刀中"})
    private Integer cutterChangePositionUpperKnifeCenter;

    @ExcelProperty({"换刀位置", "上刀右"})
    private Integer cutterChangePositionUpperKnifeRight;

    @ExcelProperty({"换刀位置", "下刀左"})
    private Integer cutterChangePositionLowerKnifeLeft;

    @ExcelProperty({"换刀位置", "下刀中"})
    private Integer cutterChangePositionLowerKnifeCenter;

    @ExcelProperty({"换刀位置", "下刀右"})
    private Integer cutterChangePositionLowerKnifeRight;

    @ExcelProperty({"累计分切米数", "上刀左"})
    private Integer accumulatedCuttingMetersUpperKnifeLeft;

    @ExcelProperty({"累计分切米数", "上刀中"})
    private Integer accumulatedCuttingMetersUpperKnifeCenter;

    @ExcelProperty({"累计分切米数", "上刀右"})
    private Integer accumulatedCuttingMetersUpperKnifeRight;

    @ExcelProperty({"累计分切米数", "下刀左"})
    private Integer accumulatedCuttingMetersLowerKnifeLeft;

    @ExcelProperty({"累计分切米数", "下刀中"})
    private Integer accumulatedCuttingMetersLowerKnifeCenter;

    @ExcelProperty({"累计分切米数", "下刀右"})
    private Integer accumulatedCuttingMetersLowerKnifeRight;

    /** 换刀时间 */
    @JsonFormat(timezone="GMT+8", pattern="yyyy-MM-dd HH:mm:ss")
    @DateTimeFormat(pattern="yyyy-MM-dd HH:mm:ss")
    @ExcelProperty(value = "换刀时间")
    @ColumnWidth(20)
    private Date cutterChangeTime;

    /** 上刀数 */
    @ExcelProperty(value = "上刀数")
    private Integer upperKnifeNumber;

    /** 下刀数 */
    @ExcelProperty(value = "下刀数")
    private Integer lowerKnifeNumber;

    @ExcelProperty(value = "更换人员")
    private String modifyUser;

    /** 备注 */
    @ExcelProperty(value = "备注")
    private String remark;

}

其余不用修改

效果如下:

若需要导出excel在浏览器,修改Controller代码如下:

 @GetMapping("/export")
    public void export(HttpServletResponse response) throws Exception{
        List<CutterControl> cutterControlList = cutterControlService.getCutterControlList();
        String fileName = new String("切刀管控台账数据.xlsx");
        fileName = URLEncoder.encode(fileName, "UTF-8");
        response.setContentType("application/vnd.ms-excel");
        response.setCharacterEncoding("utf8");
        response.setHeader("Content-disposition", "attachment;filename=" + fileName );

        EasyExcel.write(response.getOutputStream(),CutterControl.class)
                .sheet("切刀管控台账数据")
                .doWrite(cutterControlList);
    }

3、自定义行合并策略

具体业务暂时用不到,需要的可参考这个博客

https://www.cnblogs.com/monianxd/p/16359369.html

文章来源:https://blog.csdn.net/qq_41481924/article/details/135665922
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。