easyexcel基于注解的通用的可回调的更精细的单元格格式设置(二),支持富文本回调设置

上片文章easyexcel基于注解的可回调的更精细的单元格格式设置(一)中只能根据本字段的值的情况设置不同样式,但如果该字段单元格样式受到其它字段值影响,则无法实现。于是衍生出了该方案。

        该方案也有方案一中两个Consumer,且多了一个richTextConsumer用于设置富文本,CommonCallBackData只是对于字体和单元格样式类等的封装而已。多了一个List<T> dataList,该dataList也包含在CommonCallBackData中,在回调时会将该集合会作为方法参数传过去,同时会传入relativeRowIndex字段,这样根据这两个字段,就可以获取到某一行的数据,也就可以实现上述需求。代码1处为富文本回调。为了支持富文本,注解也添加了字段是否为富文本,哪个字段需要支持富文本,只需将注解的richText设置为true。若有多个字段都需要支持富文本,则需要根据回调中传过去的Field做判断。

    @ExcelProperty("名称")
    @ColumnWidth(45)
    @ExcelStyle(richText = true)
    private String name;
@Target({ElementType.FIELD,ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface ExcelStyle {
    String fontName() default "宋体";
    short fontHeightInPoints() default 12;
    HorizontalAlignment horizontalAlignment() default HorizontalAlignment.LEFT;
    VerticalAlignment verticalAlignment() default VerticalAlignment.CENTER;
    boolean wrapText() default false;
    boolean richText() default false;
}
package com.tzxx.common.domain.logic.excel;

import com.alibaba.excel.metadata.Head;
import com.alibaba.excel.write.metadata.style.WriteCellStyle;
import com.alibaba.excel.write.style.HorizontalCellStyleStrategy;
import com.tzxx.common.annotation.ExcelStyle;
import lombok.extern.slf4j.Slf4j;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.ss.usermodel.Font;
import org.apache.poi.ss.usermodel.Workbook;

import java.lang.reflect.Field;
import java.util.List;
import java.util.function.Consumer;


@Slf4j
public class ExcelStyleAnnotationAndContainsCommonCallBackCellWriteHandler<T> extends HorizontalCellStyleStrategy {

    private Class<?> c;
    private List<T> dataList;
    private Consumer<CommonCallBackData<T>> fontConsumer;
    private Consumer<CommonCallBackData<T>> cellStyleConsumer;
    private Consumer<CommonCallBackData<T>> richTextConsumer;
    public ExcelStyleAnnotationAndContainsCommonCallBackCellWriteHandler(Class<?> c, WriteCellStyle headWriteCellStyle,
                                                                         WriteCellStyle contentWriteCellStyle,
                                                                         List<T> dataList,
                                                                         Consumer<CommonCallBackData<T>> fontConsumer,
                                                                         Consumer<CommonCallBackData<T>> cellStyleConsumer,
                                                                         Consumer<CommonCallBackData<T>> richTextConsumer) {
        super(headWriteCellStyle, contentWriteCellStyle);
        this.c = c;
        this.fontConsumer = fontConsumer;
        this.cellStyleConsumer = cellStyleConsumer;
        this.richTextConsumer = richTextConsumer;
        this.dataList = dataList;
    }

    @Override
    protected void setContentCellStyle(Cell cell, Head head, Integer relativeRowIndex) {
        try {
            Field declaredField = c.getDeclaredField(head.getFieldName());
            ExcelStyle annotation = declaredField.getAnnotation(ExcelStyle.class);
            if (annotation != null) {
                Workbook wb = cell.getSheet().getWorkbook();
                CellStyle cellStyle = wb.createCellStyle();
                cell.setCellStyle(cellStyle);
                Font font = wb.createFont();
                CommonCallBackData<T> callBackData = create(font,cellStyle,relativeRowIndex,cell,wb,annotation,declaredField);
                font.setFontName(annotation.fontName());
                font.setFontHeightInPoints(annotation.fontHeightInPoints());
                if (fontConsumer != null) {
                    fontConsumer.accept(callBackData);
                }
                cellStyle.setFont(font);
                cellStyle.setAlignment(annotation.horizontalAlignment());
                cellStyle.setVerticalAlignment(annotation.verticalAlignment());
                cellStyle.setWrapText(annotation.wrapText());
                if (cellStyleConsumer != null) {
                    cellStyleConsumer.accept(callBackData);
                }
                //1
                boolean richText = annotation.richText();
                if (richText && richTextConsumer != null) {
                    richTextConsumer.accept(callBackData);
                }
            }else {
                super.setContentCellStyle(cell,head,relativeRowIndex);
            }
        } catch (NoSuchFieldException e) {
            log.error("ExcelStyleAnnotationCellWriteHandler error{0}",e);
        }

    }

    private CommonCallBackData<T> create(Font font, CellStyle cellStyle, Integer relativeRowIndex,Cell cell,Workbook wb,ExcelStyle annotation, Field field){
        CommonCallBackData<T> callBackData = new CommonCallBackData<>();
        callBackData.setFont(font);
        callBackData.setCellStyle(cellStyle);
        callBackData.setRelativeRowIndex(relativeRowIndex);
        callBackData.setDataList(this.dataList);
        callBackData.setCell(cell);
        callBackData.setWorkbook(wb);
        callBackData.setAnnotation(annotation);
        callBackData.setField(field);
        return callBackData;
    }
}
@Data
public class CommonCallBackData<T> {
    private Font font;
    private CellStyle cellStyle;
    private List<T> dataList;
    private Integer relativeRowIndex;
    private Cell cell;
    private Workbook workbook;
    private Field field;
    private ExcelStyle annotation;
}

Consumer示例:

   public static void richTextConsumer(CommonCallBackData<XX> callBackData){
        Integer relativeRowIndex = callBackData.getRelativeRowIndex();
        List<XX> dataList = callBackData.getDataList();
        XX dto = dataList.get(relativeRowIndex);
        if (Boolean.TRUE.equals(dto.getXx))) {
            Workbook workbook = callBackData.getWorkbook();
            Cell cell = callBackData.getCell();
            Font font = workbook.createFont();
            font.setColor(Font.COLOR_RED);
            String big = "富文本";
            String value = cell.getStringCellValue() + big;
            int index = value.lastIndexOf(big);
            //将富文本三个字设置为红色字体
            RichTextString richTextString = new XSSFRichTextString(value);
            richTextString.applyFont(index,index+3,font);
            cell.setCellValue(richTextString);
        }
    }

    public static void cellStyleTextConsumer(CommonCallBackData<XX> callBackData){
        Integer relativeRowIndex = callBackData.getRelativeRowIndex();
        List<XX> dataList = callBackData.getDataList();
        XX dto = dataList.get(relativeRowIndex);
        if (Boolean.TRUE.equals(dto.getXx())) {
            CellStyle cellStyle = callBackData.getCellStyle();
            cellStyle.setAlignment(HorizontalAlignment.CENTER);
        }
    }

调用:为了支持富文本,需要将inMemory设置为true,该设置是将默认的SXSSF替换为XSSF,SXSSF不支持富文本。

        EasyExcelFactory.write(httpServletResponse.getOutputStream(), XX.class)
                .inMemory(true)
                .registerWriteHandler(EasyExcelUtil.getStyleForCustomAnnotationAndContainsCommonCallBack(
                        XX.class,exportList,null,
                        XX::cellStyleTextConsumer,XX::richTextConsumer
                ))
                .sheet("xxxxx表").doWrite(list);

//EasyExcelUtil
    public static <T> ExcelStyleAnnotationAndContainsCommonCallBackCellWriteHandler getStyleForCustomAnnotationAndContainsCommonCallBack(Class<?> c,
                                                                                                                                     List<T> dataList,
                                                                                                                                     Consumer<CommonCallBackData<T>> fontConsumer,
                                                                                                                                     Consumer<CommonCallBackData<T>> cellStyleConsumer, Consumer<CommonCallBackData<T>> richTextConsumer) {
        return new ExcelStyleAnnotationAndContainsCommonCallBackCellWriteHandler(c,getHeadWriteCellStyle(), getContentWriteCellStyle(),dataList,fontConsumer,cellStyleConsumer,richTextConsumer);
    }


    private static WriteCellStyle getHeadWriteCellStyle(){
        // 头的策略
        WriteCellStyle headWriteCellStyle = new WriteCellStyle();
        WriteFont headWriteFont = new WriteFont();
        headWriteFont.setFontHeightInPoints((short)14);
        headWriteFont.setFontName("宋体");
        headWriteCellStyle.setWriteFont(headWriteFont);
        return headWriteCellStyle;
    }
    private static WriteCellStyle getContentWriteCellStyle(){
        // 内容的策略
        WriteCellStyle contentWriteCellStyle = new WriteCellStyle();
        WriteFont contentWriteFont = new WriteFont();
        contentWriteFont.setFontName("宋体");
        contentWriteFont.setFontHeightInPoints((short)13);
        contentWriteCellStyle.setWriteFont(contentWriteFont);
        return contentWriteCellStyle;
    }

猜你喜欢

转载自blog.csdn.net/sinat_33472737/article/details/109219490