使用导出带图片的Excel文件,支持一个单元格带多张图片

时间:2025-03-24 21:13:32

使用导出带图片的Excel文件,支持一个单元格带多张图片

官方网站

  • 官方网站:/
  • github地址:/alibaba/easyexcel
  • gitee地址:/easyexcel/easyexcel

导入依赖

easyexcel一定要使用以上版本,和更低的版本都不支持多张图片写入在一个单元格中

 <developer>    
    <groupId></groupId>
    <artifactId>easyexcel</artifactId>
    <version>3.1.2</version>
 </developer>

创建需要导出的对象

参考官方文档

@Getter
@Setter
@EqualsAndHashCode
public class DemoData {
    @ExcelProperty("标题名称", index = 0)
    private String string;
    @ExcelProperty("日期标题")
    private Date date;
    @ExcelProperty("数字标题")
    private Double doubleData;
    @ExcelProperty("图片或图片组")
    private WriteCellData<Void> writeCellDataFile;
    /**
     * 忽略这个字段
     */
    @ExcelIgnore
    private String ignore;
}

响应对象的设置

设置导出的文件类型为excel

    /**
     * 配置Response
     * @param response      HttpServletResponse
     * @param fileName      导出文件名称
     * @throws IOException  IO异常
     */
    private static void setResponse(HttpServletResponse response, String fileName) throws IOException {
        response.setContentType("application/-excel");
        response.setCharacterEncoding(StandardCharsets.UTF_8.name());
        fileName = URLEncoder.encode(fileName, StandardCharsets.UTF_8.name());
        response.setHeader("Content-disposition", "attachment;filename=" + fileName + ".xlsx");
    }

导入图片

创建图片对象

参考官方文档

        // 从图片文件所在路径读取图片
        String imagePath = TestFileUtil.getPath() + "converter" + File.separator + "";
        InputStream inputStream = FileUtils.openInputStream(new File(imagePath));

        // 创建图片列表,支持多张图片的导出
        List<ImageData> imageDataList = new ArrayList<>();

        // 放入第一张图片
        ImageData imageData = new ImageData();
        imageData.setImage(FileUtils.readFileToByteArray(new File(imagePath))); // 将图片转换为二进制格式
        imageData.setImageType(ImageData.ImageType.PICTURE_TYPE_PNG);
        imageDataList.add(imageData);

        // 放入第二个图片
        ImageData imageTwo = new ImageData();
        imageTwo.setImage(FileUtils.readFileToByteArray(new File(imagePath)));
        imageTwo.setImageType(ImageData.ImageType.PICTURE_TYPE_PNG);
        // 上 右 下 左 需要留空
        // 这个类似于 css 的 margin
        // 这里实测 不能设置太大 超过单元格原始大小后 打开会提示修复。暂时未找到很好的解法。
        imageTwo.setTop(5);
        imageTwo.setRight(5);
        imageTwo.setBottom(5);
        imageTwo.setLeft(50);
        // 设置图片的位置 假设 现在目标 是 覆盖 当前单元格 和当前单元格右边的单元格
        // 起点相对于当前单元格为0 当然可以不写
        imageTwo.setRelativeFirstRowIndex(0);
        imageTwo.setRelativeFirstColumnIndex(0);
        imageTwo.setRelativeLastRowIndex(0);
        // 前面3个可以不写  下面这个需要写 也就是 结尾 需要相对当前单元格 往右移动一格
        // 也就是说 这个图片会覆盖当前单元格和 后面的那一格
        imageTwo.setRelativeLastColumnIndex(1);
        imageDataList.add(imageTwo);

        // 向Excel中写入图片数据
        DemoData imageDemoData = new DemoData();
        WriteCellData<Void> writeCellData = new WriteCellData<>();

导出Excel

最简单的导出

    /**
     * 导出
     * @param response      HttpServletResponse
     * @param fileName      文件名称
     * @param sheetName     表单名称
     * @param dataList      数据列表
     * @param clazz         数据类型
     * @param <T>           泛型
     * @throws IOException  IO异常
     */
    public static <T> void export(HttpServletResponse response, String fileName, String sheetName, List<T> dataList, Class<T> clazz) throws IOException {
        setResponse(response, fileName);
        EasyExcel.write(response.getOutputStream(), clazz).sheet(sheetName).doWrite(dataList);
    }

指定列导出

    /**
     * 指定字段导出
     * @param response          HttpServletResponse
     * @param fileName          文件名称
     * @param sheetName         表单名称
     * @param dataList          数据列表
     * @param clazz             数据类型
     * @param includeColumns    待导出字段
     * @param <T>               泛型
     * @throws IOException      IO异常
     */
    public static <T> void export(HttpServletResponse response, String fileName, String sheetName, List<T> dataList, Class<T> clazz, List<String> includeColumns) throws IOException {
        setResponse(response, fileName);
        EasyExcel.write(response.getOutputStream(), clazz).includeColumnFieldNames(includeColumns).sheet(sheetName).doWrite(dataList);
    }