【EasyExcel】导出excel并支持自定义设置数据行背景颜色等

需求背景:

        根据查询条件将列表数据导出,并筛选出满足某个条件的数据,将满足条件的数据的背景颜色设置成黄色。
        (本文例子如:name出现的次数大于等于2,将相关数据背景颜色都设置为黄色)

一、技术选型:

        1、easyExcel的自定义写策略处理:CellWriteHandler

        2、poi自带的写数据行处理:Workbook

思考选定:

        由于目前系统中多处使用的是file插件导出类,是由统一形成的,直接改动,对其它项目引入,从而导出的性能产生一定的影响,所以选择自定义策略实现,故选1。

二、方案设计:(基于实现 CellWriteHandler 接口)

        1、在 beforeCellCreate 方法中统计出 每个数据行的 name 出现的次数,在 afterCellDispose 方法中处理满足设置背景颜色数据的背景颜色。

        2、直接传入数据行的索引,在 afterCellDispose 方法中处理满足设置背景颜色数据的背景颜色。

note:原本考虑的是选择1,但是在实现的时候,统计name出现次数一直会出现问题,在easeExcel的源码中:beforeCellCreate 操作数据出现问题,待处理。(码友们可自行尝试!!!)故暂选择 方案2 实现当前需求。

三、代码实现:

pom.xml:

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

API:

 @ApiOperation(value = "评论审核导出")
 @GetMapping(value = "/export")
 public void exportExcel(HttpServletResponse response, TestParam param) throws BaseException {
        service.export(response, param);
 }
实现层:
public class TestExcelService {

    private static final String FILE_NAME = "测试文件名字";
    private static final String SHEET_NAME = "测试";

    private final IEasyExcelService easyExcelService;
    public SeedDemandExcelService(IEasyExcelService easyExcelService) {
        this.easyExcelService = easyExcelService;
    }

    public void export(HttpServletResponse response, TestParam param) throws BaseException{
        // 根据查询参数获取查询到的数据(根据自己的查询方法在这里将数据查询出来)
        List<TestExcelData> exportData = this.getExportData(param);
        // Obtain data rows that require background color settings
        // 获取需要设置背景颜色的数据行索引
        List<Integer> index = getIndexList(exportData);
        // export
        try {
            easyExcelService.exportExcelWithBackGround(exportData, response, DemoExcelData.class, FILE_NAME, SHEET_NAME, index);
        } catch (Exception e) {
            throw new Exception(CodeEnum.FAILED, "导出异常,请联系开发人员!异常信息是:" + e.getMessage());
        }
    }
}
工具类:IEasyExcelService
public interface IEasyExcelService {
    /**
     * 导出excel方法
     * @param exportData 需要导出的数据
     * @param response response
     * @param tClass 导出excel的字段实体类
     * @param fileName 文件名字
     * @param sheetName sheet名字
     */
    <T> void exportExcel(List<T> exportData, HttpServletResponse response, Class<T> tClass, String fileName, String sheetName);
    /**
     * 导出excel方法(支持设置背景颜色)
     * @param exportData 需要导出的数据
     * @param response response
     * @param tClass 导出excel的字段实体类
     * @param fileName 文件名字
     * @param sheetName sheet名字
     * @param backGroundIndex 需要设置背景的数据行
     * @param <T> t
     * @throws Exception Exception
     */
    <T> void exportExcelWithBackGround(List<T> exportData, HttpServletResponse response, Class<T> tClass , String fileName, String sheetName, List<Integer> backGroundIndex) throws Exception;
}
工具类:EasyExcelServiceImpl
@Service
@Slf4j
public class EasyExcelServiceImpl implements IEasyExcelService {

    @Override
    public <T> void exportExcel(List<T> exportData, HttpServletResponse response, Class<T> tClass, String fileName, String sheetName){
        try{
            // 使用swagger 会导致各种问题,直接用浏览器或者用postman
            response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
            response.setCharacterEncoding("utf-8");
            // fileName encoder
            String fileNameEncoder = URLEncoder.encode(fileName, "UTF-8").replaceAll("\\+", "%20");
            response.setHeader("Content-disposition", "attachment;filename*=utf-8''" + fileNameEncoder + ".xlsx");
            // write to excel
            EasyExcelFactory.write(response.getOutputStream(), tClass)
                    .autoCloseStream(Boolean.FALSE)
                    .sheet(sheetName)
                    .doWrite(exportData);
        }catch (Exception e){
            log.error("EasyExcelServiceImpl->exportExcel error, message is :{}", e.getMessage());
        }
    }

    @Override
    public <T> void exportExcelWithBackGround(List<T> exportData, HttpServletResponse response, Class<T> tClass,
                                              String fileName, String sheetName, List<Integer> backGroundIndex) throws Exception {
        // 使用swagger 会导致各种问题,直接用浏览器或者用postman
        response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
        response.setCharacterEncoding("utf-8");
        // fileName encoder
        String fileNameEncoder = URLEncoder.encode(fileName, "UTF-8").replaceAll("\\+", "%20");
        response.setHeader("Content-disposition", "attachment;filename*=utf-8''" + fileNameEncoder + ".xlsx");
        // 自定义策略
        Set<Integer> yellowRowsSet = new HashSet<>(backGroundIndex);
        RowBackGroundWriteHandler handler = new RowBackGroundWriteHandler(yellowRowsSet);
        // write to excel
        EasyExcelFactory.write(response.getOutputStream(), tClass)
                // 自定义背景颜色策略
                .registerWriteHandler(handler)
                .inMemory(Boolean.TRUE)
                .autoCloseStream(Boolean.FALSE)
                .sheet(sheetName)
                .doWrite(exportData);
    }

}
(其中registerWriteHandler支持扩展多个,可以通过HorizontalCellStyleStrategy策略设置全局的配置,如背景颜色、字体、合并单元格等)

自定义Handle:(自定义设置数据行背景颜色)

import com.alibaba.excel.metadata.data.WriteCellData;
import com.alibaba.excel.util.BooleanUtils;
import com.alibaba.excel.write.handler.CellWriteHandler;
import com.alibaba.excel.write.handler.context.CellWriteHandlerContext;
import com.alibaba.excel.write.metadata.style.WriteCellStyle;
import org.apache.poi.ss.usermodel.FillPatternType;
import java.util.Set;

/**
 * Set background color
 * @author liaoguang
 */
public class RowBackGroundWriteHandler implements CellWriteHandler {

    /**
     * Set background color row index set
     */
    private final Set<Integer> yellowRowIndex;
    /**
     * The background color that needs to be set
     */
    private final short indexColors;

    public RowBackGroundWriteHandler(Set<Integer> yellowRowIndex, short indexColors) {
        this.yellowRowIndex = yellowRowIndex;
        this.indexColors = indexColors;
    }

    @Override
    public void beforeCellCreate(CellWriteHandlerContext context) {
        // Row in source code context to be optimized: supports parameter input to obtain the number of
        // occurrences of the required field and set the background color
        // to do:(row.getCell(columnIndex)lose efficacy)
    }

    @Override
    public void afterCellDispose(CellWriteHandlerContext context) {
        if (BooleanUtils.isNotTrue(context.getHead())) {
            // get current row index
            Integer currentRowIndex = context.getRowIndex();
            // judge yellowRowIndex's
            if (yellowRowIndex.contains(currentRowIndex)) {
                WriteCellData<?> cellData = context.getFirstCellData();
                WriteCellStyle writeCellStyle = cellData.getOrCreateStyle();
                // set index color
                writeCellStyle.setFillForegroundColor(indexColors);
                writeCellStyle.setFillPatternType(FillPatternType.SOLID_FOREGROUND);
            }
        }
    }

}
DemoExcelData:(导出字段实体类)
@Data
@EqualsAndHashCode
public class DemoExcelData{

    @ExcelProperty(value = "TaskID", index = 0)
    private String name;
    @ExcelProperty(value = "taskName", index = 1)
    private String sex;
    @ExcelProperty(value = "taskName", index = 2)
    private String age;
}

End:

        👍如果对你有帮助,给博主一个免费的点赞以示鼓励
欢迎各位🔎点赞👍评论收藏⭐️

  • 7
    点赞
  • 22
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 7
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

程序猿七度

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值