This commit is contained in:
Looly 2023-01-16 12:31:05 +08:00
parent 3f811c9f82
commit 43f4f4f6ec
3 changed files with 57 additions and 37 deletions

View File

@ -16,6 +16,7 @@ import cn.hutool.core.map.multi.Table;
import cn.hutool.core.net.url.URLEncoder;
import cn.hutool.core.text.StrUtil;
import cn.hutool.core.util.CharsetUtil;
import cn.hutool.poi.excel.cell.CellEditor;
import cn.hutool.poi.excel.cell.CellLocation;
import cn.hutool.poi.excel.cell.CellUtil;
import cn.hutool.poi.excel.style.Align;
@ -82,6 +83,10 @@ public class ExcelWriter extends ExcelBase<ExcelWriter> {
* 标题项对应列号缓存每次写标题更新此缓存
*/
private Map<String, Integer> headLocationCache;
/**
* 单元格值处理接口
*/
private CellEditor cellEditor;
// -------------------------------------------------------------------------- Constructor start
@ -187,6 +192,18 @@ public class ExcelWriter extends ExcelBase<ExcelWriter> {
// -------------------------------------------------------------------------- Constructor end
/**
* 设置单元格值处理逻辑<br>
* 当Excel中的值并不能满足我们的读取要求时通过传入一个编辑接口可以对单元格值自定义例如对数字和日期类型值转换为字符串等
*
* @param cellEditor 单元格值处理接口
* @return this
*/
public ExcelWriter setCellEditor(final CellEditor cellEditor) {
this.cellEditor = cellEditor;
return this;
}
@Override
public ExcelWriter setSheet(final int sheetIndex) {
// 切换到新sheet需要重置开始行
@ -735,7 +752,7 @@ public class ExcelWriter extends ExcelBase<ExcelWriter> {
// 设置内容
if (null != content) {
final Cell cell = getOrCreateCell(firstColumn, firstRow);
CellUtil.setCellValue(cell, content, cellStyle);
CellUtil.setCellValue(cell, content, cellStyle, this.cellEditor);
}
return this;
}
@ -945,7 +962,7 @@ public class ExcelWriter extends ExcelBase<ExcelWriter> {
Cell cell;
for (final Object value : rowData) {
cell = row.createCell(i);
CellUtil.setCellValue(cell, value, this.styleSet, true);
CellUtil.setCellValue(cell, value, this.styleSet, true, this.cellEditor);
this.headLocationCache.put(StrUtil.toString(value), i);
i++;
}
@ -977,7 +994,7 @@ public class ExcelWriter extends ExcelBase<ExcelWriter> {
}
if (iterator.hasNext()) {
cell = row.createCell(i);
CellUtil.setCellValue(cell, iterator.next(), this.styleSet, true);
CellUtil.setCellValue(cell, iterator.next(), this.styleSet, true, this.cellEditor);
} else {
break;
}
@ -1073,7 +1090,7 @@ public class ExcelWriter extends ExcelBase<ExcelWriter> {
location = this.headLocationCache.get(StrUtil.toString(cell.getColumnKey()));
}
if (null != location) {
CellUtil.setCellValue(CellUtil.getOrCreateCell(row, location), cell.getValue(), this.styleSet, false);
CellUtil.setCellValue(CellUtil.getOrCreateCell(row, location), cell.getValue(), this.styleSet, false, this.cellEditor);
}
}
} else {
@ -1093,7 +1110,7 @@ public class ExcelWriter extends ExcelBase<ExcelWriter> {
*/
public ExcelWriter writeRow(final Iterable<?> rowData) {
Assert.isFalse(this.isClosed, "ExcelWriter has been closed!");
RowUtil.writeRow(this.sheet.createRow(this.currentRow.getAndIncrement()), rowData, this.styleSet, false);
RowUtil.writeRow(this.sheet.createRow(this.currentRow.getAndIncrement()), rowData, this.styleSet, false, this.cellEditor);
return this;
}
@ -1121,7 +1138,7 @@ public class ExcelWriter extends ExcelBase<ExcelWriter> {
*/
public ExcelWriter writeCellValue(final int x, final int y, final Object value) {
final Cell cell = getOrCreateCell(x, y);
CellUtil.setCellValue(cell, value, this.styleSet, false);
CellUtil.setCellValue(cell, value, this.styleSet, false, this.cellEditor);
return this;
}

View File

@ -88,27 +88,29 @@ public class RowUtil {
/**
* 写一行数据无样式非标题
*
* @param row
* @param rowData 一行的数据
* @param row
* @param rowData 一行的数据
* @param cellEditor 单元格值编辑器可修改单元格值或修改单元格{@code null}表示不编辑
*/
public static void writeRow(final Row row, final Iterable<?> rowData) {
writeRow(row, rowData, null, false);
public static void writeRow(final Row row, final Iterable<?> rowData, final CellEditor cellEditor) {
writeRow(row, rowData, null, false, cellEditor);
}
/**
* 写一行数据
*
* @param row
* @param rowData 一行的数据
* @param styleSet 单元格样式集包括日期等样式null表示无样式
* @param isHeader 是否为标题行
* @param row
* @param rowData 一行的数据
* @param styleSet 单元格样式集包括日期等样式null表示无样式
* @param isHeader 是否为标题行
* @param cellEditor 单元格值编辑器可修改单元格值或修改单元格{@code null}表示不编辑
*/
public static void writeRow(final Row row, final Iterable<?> rowData, final StyleSet styleSet, final boolean isHeader) {
public static void writeRow(final Row row, final Iterable<?> rowData, final StyleSet styleSet, final boolean isHeader, final CellEditor cellEditor) {
int i = 0;
Cell cell;
for (final Object value : rowData) {
cell = row.createCell(i);
CellUtil.setCellValue(cell, value, styleSet, isHeader);
CellUtil.setCellValue(cell, value, styleSet, isHeader, cellEditor);
i++;
}
}

View File

@ -134,12 +134,13 @@ public class CellUtil {
* 根据传入的styleSet自动匹配样式<br>
* 当为头部样式时默认赋值头部样式但是头部中如果有数字日期等类型将按照数字日期样式设置
*
* @param cell 单元格
* @param value
* @param styleSet 单元格样式集包括日期等样式null表示无样式
* @param isHeader 是否为标题单元格
* @param cell 单元格
* @param value
* @param styleSet 单元格样式集包括日期等样式null表示无样式
* @param isHeader 是否为标题单元格
* @param cellEditor 单元格值编辑器可修改单元格值或修改单元格{@code null}表示不编辑
*/
public static void setCellValue(final Cell cell, final Object value, final StyleSet styleSet, final boolean isHeader) {
public static void setCellValue(final Cell cell, final Object value, final StyleSet styleSet, final boolean isHeader, final CellEditor cellEditor) {
if (null == cell) {
return;
}
@ -148,7 +149,7 @@ public class CellUtil {
cell.setCellStyle(styleSet.getStyleByValueType(value, isHeader));
}
setCellValue(cell, value);
setCellValue(cell, value, cellEditor);
}
/**
@ -156,17 +157,14 @@ public class CellUtil {
* 根据传入的styleSet自动匹配样式<br>
* 当为头部样式时默认赋值头部样式但是头部中如果有数字日期等类型将按照数字日期样式设置
*
* @param cell 单元格
* @param value
* @param style 自定义样式null表示无样式
* @param cell 单元格
* @param value
* @param style 自定义样式null表示无样式
* @param cellEditor 单元格值编辑器可修改单元格值或修改单元格{@code null}表示不编辑
*/
public static void setCellValue(final Cell cell, final Object value, final CellStyle style) {
setCellValue(cell, (CellSetter) cell1 -> {
setCellValue(cell, value);
if (null != style) {
cell1.setCellStyle(style);
}
});
public static void setCellValue(final Cell cell, final Object value, final CellStyle style, final CellEditor cellEditor) {
cell.setCellStyle(style);
setCellValue(cell, value, cellEditor);
}
/**
@ -174,11 +172,12 @@ public class CellUtil {
* 根据传入的styleSet自动匹配样式<br>
* 当为头部样式时默认赋值头部样式但是头部中如果有数字日期等类型将按照数字日期样式设置
*
* @param cell 单元格
* @param value 值或{@link CellSetter}
* @param cell 单元格
* @param value 值或{@link CellSetter}
* @param cellEditor 单元格值编辑器可修改单元格值或修改单元格{@code null}表示不编辑
* @since 5.6.4
*/
public static void setCellValue(final Cell cell, final Object value) {
public static void setCellValue(final Cell cell, Object value, final CellEditor cellEditor) {
if (null == cell) {
return;
}
@ -187,10 +186,13 @@ public class CellUtil {
// 在使用BigWriter(SXSSF)模式写出数据时单元格值为直接值非引用值is标签
// 而再使用ExcelWriter(XSSF)编辑时会写出引用值导致失效
// 此处做法是先清空单元格值再写入
if(CellType.BLANK != cell.getCellType()){
if (CellType.BLANK != cell.getCellType()) {
cell.setBlank();
}
if (null != cellEditor) {
value = cellEditor.edit(cell, value);
}
CellSetterFactory.createCellSetter(value).setValue(cell);
}
@ -326,7 +328,6 @@ public class CellUtil {
}
/**
* 合并单元格可以根据设置的值来合并行和列
*