diff --git a/doc/font/SimHei.ttf b/doc/font/SimHei.ttf new file mode 100644 index 0000000..8d3f158 Binary files /dev/null and b/doc/font/SimHei.ttf differ diff --git a/fastexcel-core/pom.xml b/fastexcel-core/pom.xml index 7cc2e8e..3ba486e 100644 --- a/fastexcel-core/pom.xml +++ b/fastexcel-core/pom.xml @@ -16,6 +16,10 @@ fastexcel-core ${revision} + + 7.1.15 + + org.apache.commons @@ -61,5 +65,47 @@ fastexcel-support 0.0.1 + + + com.itextpdf + itext7-core + ${itext.version} + pom + + + com.itextpdf + kernel + ${itext.version} + + + com.itextpdf + io + ${itext.version} + + + com.itextpdf + layout + ${itext.version} + + + com.itextpdf + forms + ${itext.version} + + + com.itextpdf + pdfa + ${itext.version} + + + com.itextpdf + pdftest + ${itext.version} + + + com.itextpdf + font-asian + ${itext.version} + diff --git a/fastexcel-core/src/main/java/cn/idev/excel/FastExcel.java b/fastexcel-core/src/main/java/cn/idev/excel/FastExcel.java index 3859fc1..08a7d5f 100644 --- a/fastexcel-core/src/main/java/cn/idev/excel/FastExcel.java +++ b/fastexcel-core/src/main/java/cn/idev/excel/FastExcel.java @@ -1,5 +1,10 @@ package cn.idev.excel; +import cn.idev.excel.fileconvertor.ExcelConverter; +import cn.idev.excel.fileconvertor.FileConverterContext; + +import java.io.File; + /** * This is actually {@link FastExcelFactory}, and short names look better. * @@ -7,4 +12,18 @@ package cn.idev.excel; */ public class FastExcel extends FastExcelFactory { + /** + * Convert excel to pdf + * + * @param excelFile excel file + * @param pdfFile pdf file + * @param fontPath font path for pdf can be null + * @param sheets sheet index to convert, if null convert all sheets + */ + public static void convertToPdf(File excelFile, File pdfFile, String fontPath, int[] sheets) { + FileConverterContext context = new FileConverterContext(excelFile, pdfFile, fontPath, sheets); + ExcelConverter excelConverter = context.getExcelConverter(); + excelConverter.convertToPdf(); + } + } diff --git a/fastexcel-core/src/main/java/cn/idev/excel/FastExcelFactory.java b/fastexcel-core/src/main/java/cn/idev/excel/FastExcelFactory.java index a165c05..6cb6b80 100644 --- a/fastexcel-core/src/main/java/cn/idev/excel/FastExcelFactory.java +++ b/fastexcel-core/src/main/java/cn/idev/excel/FastExcelFactory.java @@ -353,4 +353,25 @@ public class FastExcelFactory { } return excelReaderSheetBuilder; } + + /** + * Build excel the 'readSheet' + * @param sheetNo Index of sheet,0 base. + * @param sheetName The name of sheet. + * @param numRows The number of rows to read, the default is all, start with 0. + * @return + */ + public static ExcelReaderSheetBuilder readSheet(Integer sheetNo, String sheetName,Integer numRows) { + ExcelReaderSheetBuilder excelReaderSheetBuilder = new ExcelReaderSheetBuilder(); + if (sheetNo != null) { + excelReaderSheetBuilder.sheetNo(sheetNo); + } + if (sheetName != null) { + excelReaderSheetBuilder.sheetName(sheetName); + } + if (numRows !=null) { + excelReaderSheetBuilder.numRows(numRows); + } + return excelReaderSheetBuilder; + } } diff --git a/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/BaseExcelConverter.java b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/BaseExcelConverter.java new file mode 100644 index 0000000..a0d1a01 --- /dev/null +++ b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/BaseExcelConverter.java @@ -0,0 +1,172 @@ +package cn.idev.excel.fileconvertor; + +import com.itextpdf.layout.element.Table; +import com.itextpdf.layout.property.TextAlignment; +import org.apache.poi.ss.usermodel.*; +import org.apache.poi.ss.util.CellRangeAddress; + +import java.io.IOException; +import java.util.List; + +public abstract class BaseExcelConverter implements ExcelConverter { + + private final FileConverterContext context; + + public BaseExcelConverter(FileConverterContext context) { + this.context = context; + } + + @Override + public void convertToPdf() { + try { + for (int sheetIndex : context.getSheets()) { + processSheet(sheetIndex); + } + context.getDocument().close(); + } catch (Exception e) { + throw new RuntimeException(e); + } + } + + private void processSheet(int sheetIndex) throws IOException { + Sheet sheet = context.getWorkbook().getSheetAt(sheetIndex); + if (sheet == null || sheet.getRow(0) == null) { + return; + } + float[] columnWidths = getColumnWidths(sheet); + Table table = new Table(columnWidths); + + addRowsToTable(table, sheet, columnWidths, context.getFountPath()); +// addPicsToTable(table, sheet); + + context.getDocument().add(table); + } + + protected abstract void addPicsToTable(Table table, Sheet sheet); + + private void addRowsToTable(Table table, Sheet sheet, float[] columnWidths, String fontPath) throws IOException { + int lastRowNum = sheet.getLastRowNum() + 1; + int lastCellNum = sheet.getRow(0).getLastCellNum(); + for (int i = 0; i < lastRowNum; i++) { + Row row = sheet.getRow(i); + addRowToTable(table, row, lastCellNum, columnWidths, fontPath); + } + } + + private void addRowToTable(Table table, Row row, int lastCellNum, float[] columnWidths, String fontPath) throws IOException { + if (row == null) { + addEmptyCells(table, lastCellNum); // 0 for empty row + return; + } + + for (int j = 0; j < lastCellNum; j++) { + Cell cell = row.getCell(j); + if (cell != null && !isCellProcessed(cell)) { +// addCellToTable(table, cell, columnWidths, fontPath); + CellRangeAddress cellRange = getCellRangeAddress(cell); + int rowspan = (cellRange != null) ? (cellRange.getLastRow() - cellRange.getFirstRow() + 1) : 1; + int colspan = (cellRange != null) ? (cellRange.getLastColumn() - cellRange.getFirstColumn() + 1) : 1; + if ((cellRange != null)) { + j = cellRange.getLastColumn(); + } + float maxWidth = (cellRange != null) ? calculateMaxWidth(columnWidths, cellRange) : columnWidths[j]; + + com.itextpdf.layout.element.Cell pdfCell = convertCell(cell, rowspan, colspan, maxWidth, fontPath); + table.addCell(pdfCell); + } else if (cell == null) { + addEmptyCell(table); + } + } + } + + private float calculateMaxWidth(float[] columnWidths, CellRangeAddress cellRange) { + float maxWidth = 0; + for (int k = cellRange.getFirstColumn(); k < cellRange.getLastColumn(); k++) { + maxWidth += columnWidths[k]; + } + return maxWidth; + } + + private void addEmptyCell(Table table) { + com.itextpdf.layout.element.Cell pdfCell = new com.itextpdf.layout.element.Cell(); + pdfCell.setBorder(com.itextpdf.layout.borders.Border.NO_BORDER); + table.addCell(pdfCell); + } + + private void addEmptyCells(Table table, int numberOfCells) { + for (int j = 0; j < numberOfCells; j++) { + addEmptyCell(table); + } + } + + protected abstract com.itextpdf.layout.element.Cell convertCell(Cell cell, int rowspan, int colspan, float maxWidth, String fontPath) throws IOException; + + public static com.itextpdf.layout.property.VerticalAlignment getVerticalAlignment(VerticalAlignment verticalAlignment) { + switch (verticalAlignment) { + case TOP: + return com.itextpdf.layout.property.VerticalAlignment.TOP; + case BOTTOM: + return com.itextpdf.layout.property.VerticalAlignment.BOTTOM; + case JUSTIFY: + case CENTER: + return com.itextpdf.layout.property.VerticalAlignment.MIDDLE; + } + return com.itextpdf.layout.property.VerticalAlignment.MIDDLE; + } + + public static TextAlignment getTextAlignment(org.apache.poi.ss.usermodel.HorizontalAlignment alignment, CellType cellType) { + switch (alignment) { + case LEFT: + return TextAlignment.LEFT; + case RIGHT: + return TextAlignment.RIGHT; + case CENTER: + return TextAlignment.CENTER; + case JUSTIFY: + return TextAlignment.JUSTIFIED; + case GENERAL: + if (cellType == CellType.NUMERIC) { + return TextAlignment.RIGHT; + } else if (cellType == CellType.BOOLEAN) { + return TextAlignment.CENTER; + } + } + return TextAlignment.LEFT; + } + + private float[] getColumnWidths(Sheet sheet) { + short lastCellNum = sheet.getRow(0).getLastCellNum(); + float[] widths = new float[lastCellNum]; + for (int i = 0; i < lastCellNum; i++) { + widths[i] = sheet.getColumnWidthInPixels(i); + } + return widths; + } + + private boolean isCellProcessed(Cell cell) { + List mergedRegions = cell.getSheet().getMergedRegions(); + int rowIndex = cell.getRowIndex(); + int columnIndex = cell.getColumnIndex(); + + for (CellRangeAddress cellAddresses : mergedRegions) { + if (cellAddresses.getFirstRow() <= rowIndex && cellAddresses.getLastRow() >= rowIndex + && cellAddresses.getFirstColumn() <= columnIndex && cellAddresses.getLastColumn() >= columnIndex) { + return !(cellAddresses.getFirstRow() == rowIndex && cellAddresses.getFirstColumn() == columnIndex); + } + } + return false; + } + + private CellRangeAddress getCellRangeAddress(Cell cell) { + List mergedRegions = cell.getSheet().getMergedRegions(); + int rowIndex = cell.getRowIndex(); + int columnIndex = cell.getColumnIndex(); + + for (CellRangeAddress cellAddresses : mergedRegions) { + if (cellAddresses.getFirstRow() == rowIndex && cellAddresses.getFirstColumn() == columnIndex) { + return cellAddresses; + } + } + return null; + } +} \ No newline at end of file diff --git a/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/Excel2PdfUtils.java b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/Excel2PdfUtils.java new file mode 100644 index 0000000..d490d64 --- /dev/null +++ b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/Excel2PdfUtils.java @@ -0,0 +1,45 @@ +package cn.idev.excel.fileconvertor; + +import org.apache.poi.ss.usermodel.Cell; +import org.apache.poi.ss.usermodel.CellType; +import org.apache.poi.ss.usermodel.DateUtil; +import org.apache.poi.util.LocaleUtil; + +import java.text.SimpleDateFormat; + +public class Excel2PdfUtils { + private static final String DATE_FORMAT = "yyyy-MM-dd HH:mm:ss"; // 日期格式 + private static final String TRUE_STRING = "TRUE"; + private static final String FALSE_STRING = "FALSE"; + private static final String EMPTY_STRING = ""; + + // 使用单例模式确保 SimpleDateFormat 只被创建一次 + private static final ThreadLocal DATE_FORMATTER = ThreadLocal.withInitial(() -> + new SimpleDateFormat(DATE_FORMAT, LocaleUtil.getUserLocale()) + ); + + public static String getValue(Cell cell) { + if (cell == null) { + return EMPTY_STRING; + } + + CellType cellType = cell.getCellType(); + switch (cellType) { + case BOOLEAN: + return cell.getBooleanCellValue() ? TRUE_STRING : FALSE_STRING; + case NUMERIC: + return getNumericCellValue(cell); + case STRING: + return cell.getStringCellValue(); + default: + return EMPTY_STRING; + } + } + + private static String getNumericCellValue(Cell cell) { + if (DateUtil.isCellDateFormatted(cell)) { + return DATE_FORMATTER.get().format(cell.getDateCellValue()); + } + return String.valueOf(cell.getNumericCellValue()); + } +} diff --git a/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/ExcelConverter.java b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/ExcelConverter.java new file mode 100644 index 0000000..f5bd14c --- /dev/null +++ b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/ExcelConverter.java @@ -0,0 +1,17 @@ +package cn.idev.excel.fileconvertor; + +import java.io.File; + +/** + * Excel convert to other file + * @author jipengfei + */ +public interface ExcelConverter { + + /** + * excel to pdf + * + */ + void convertToPdf(); + +} diff --git a/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/FileConverterContext.java b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/FileConverterContext.java new file mode 100644 index 0000000..e0948d4 --- /dev/null +++ b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/FileConverterContext.java @@ -0,0 +1,74 @@ +package cn.idev.excel.fileconvertor; + +import cn.idev.excel.read.metadata.ReadWorkbook; +import cn.idev.excel.support.ExcelTypeEnum; +import com.itextpdf.kernel.geom.PageSize; +import com.itextpdf.kernel.pdf.PdfDocument; +import com.itextpdf.kernel.pdf.PdfWriter; +import com.itextpdf.layout.Document; +import lombok.Getter; +import lombok.Setter; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; +import org.apache.poi.openxml4j.exceptions.InvalidFormatException; +import org.apache.poi.ss.usermodel.Workbook; +import org.apache.poi.xssf.usermodel.XSSFWorkbook; + +import java.io.File; +import java.io.FileInputStream; +import java.io.IOException; + +@Getter +@Setter +public class FileConverterContext { + + private File inputFile; + private File outputFile; + private String fountPath; + private Workbook workbook; + private Document document; + private int[] sheets; + private ExcelTypeEnum excelTypeEnum; + + public FileConverterContext(File inputFile, File outputFile, String fountPath, int[] sheets) { + try { + this.inputFile = inputFile; + this.outputFile = outputFile; + this.fountPath = fountPath; + ReadWorkbook readWorkbook = new ReadWorkbook(); + readWorkbook.setFile(inputFile); + excelTypeEnum = ExcelTypeEnum.valueOf(readWorkbook); + if (excelTypeEnum == ExcelTypeEnum.XLSX) { + this.workbook = new XSSFWorkbook(inputFile); + } else if (excelTypeEnum == ExcelTypeEnum.XLS) { + this.workbook = new HSSFWorkbook(new FileInputStream(inputFile)); + } else { + throw new IllegalArgumentException("Not supported excel type"); + } + PdfDocument pdfDocument = new PdfDocument(new PdfWriter(outputFile)); + this.document = new Document(pdfDocument, PageSize.A4.rotate()); + if (sheets == null) { + this.sheets = new int[workbook.getNumberOfSheets()]; + for (int i = 0; i < workbook.getNumberOfSheets(); i++) { + this.sheets[i] = i; + } + } else { + this.sheets = sheets; + } + } catch (IOException e) { + throw new RuntimeException(e); + } catch (InvalidFormatException e) { + throw new RuntimeException(e); + } + } + + public ExcelConverter getExcelConverter() { + if (excelTypeEnum == ExcelTypeEnum.XLSX) { + return new cn.idev.excel.fileconvertor.v07.XlsxConverter(this); + } else if (excelTypeEnum == ExcelTypeEnum.XLS) { + return new cn.idev.excel.fileconvertor.v03.XlsConverter(this); + } + throw new IllegalArgumentException("Not supported excel type"); + } + + +} diff --git a/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v03/XlsConverter.java b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v03/XlsConverter.java new file mode 100644 index 0000000..680c339 --- /dev/null +++ b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v03/XlsConverter.java @@ -0,0 +1,150 @@ +package cn.idev.excel.fileconvertor.v03; + +import cn.idev.excel.fileconvertor.BaseExcelConverter; +import cn.idev.excel.fileconvertor.Excel2PdfUtils; +import cn.idev.excel.fileconvertor.FileConverterContext; +import cn.idev.excel.util.StringUtils; +import com.itextpdf.io.font.PdfEncodings; +import com.itextpdf.kernel.colors.Color; +import com.itextpdf.kernel.colors.ColorConstants; +import com.itextpdf.kernel.colors.DeviceRgb; +import com.itextpdf.kernel.font.PdfFontFactory; +import com.itextpdf.layout.borders.*; +import com.itextpdf.layout.element.*; +import com.itextpdf.layout.element.Cell; +import com.itextpdf.layout.element.Table; +import org.apache.poi.hssf.usermodel.*; +import org.apache.poi.hssf.util.HSSFColor; +import org.apache.poi.ss.usermodel.*; + +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +public class XlsConverter extends BaseExcelConverter { + public XlsConverter(FileConverterContext context) { + super(context); + } + + @Override + public void addPicsToTable(Table table, Sheet sheet) { + HSSFPatriarch drawingPatriarch = ((HSSFSheet) sheet).getDrawingPatriarch(); + if (drawingPatriarch != null) { + List pictures = new ArrayList<>(); + for (HSSFShape shape : drawingPatriarch.getChildren()) { + if (shape instanceof HSSFPicture) { + pictures.add((HSSFPicture) shape); + } + } + table.setNextRenderer(new XlsImageTableRenderer(table, pictures, (HSSFSheet) sheet)); + } + } + + @Override + public Cell convertCell(org.apache.poi.ss.usermodel.Cell cell, int rowspan, int colspan, float maxWidth, String fontPath) throws IOException { + String value = Excel2PdfUtils.getValue(cell); + Cell pdfCell = createPdfCell(rowspan, colspan, cell, value, maxWidth, fontPath); + + return pdfCell; + } + + private Cell createPdfCell(int rowspan, int colspan, org.apache.poi.ss.usermodel.Cell cell, String value, float maxWidth, String fontPath) throws IOException { + float cellHeight = cell.getRow().getHeightInPoints() * 1.2f; + Cell pdfCell = new Cell(rowspan, colspan) + .setHeight(cellHeight) + .setPadding(0); + Text text = new Text(value); + setPdfCellFont((HSSFCell) cell, text, fontPath); + + Paragraph paragraph = new Paragraph(text).setPadding(0f).setMargin(0f); + HSSFCellStyle cellStyle = ((HSSFCell) cell).getCellStyle(); + if (cellStyle.getWrapText()) { + paragraph.setMaxWidth(maxWidth); + } + + pdfCell.add(paragraph); + + setCellStyles(cell, pdfCell); + return pdfCell; + } + + private void setCellStyles(org.apache.poi.ss.usermodel.Cell cell, Cell pdfCell) throws IOException { + HSSFCellStyle cellStyle = ((HSSFCell) cell).getCellStyle(); + // Layout + pdfCell.setVerticalAlignment(getVerticalAlignment(cellStyle.getVerticalAlignment())); + pdfCell.setTextAlignment(getTextAlignment(cellStyle.getAlignment(), cell.getCellType())); + + // Set borders + transformBorders((HSSFCell) cell, pdfCell); + + // Set background color + setBackgroundColor(cellStyle, pdfCell, cell); + } + + private void setBackgroundColor(HSSFCellStyle cellStyle, Cell pdfCell, org.apache.poi.ss.usermodel.Cell cell) { + short colorIndex = cellStyle.getFillForegroundColor(); + HSSFWorkbook workbook = (HSSFWorkbook) cell.getSheet().getWorkbook(); + HSSFColor color = workbook.getCustomPalette().getColor(colorIndex); + if (color != null && color.getIndex() != 64) { + short[] triplet = color.getTriplet(); + int r = Math.min(triplet[0] + 32, 255); + int g = Math.min(triplet[1] + 90, 255); + int b = Math.min(triplet[2] + 60, 255); + pdfCell.setBackgroundColor(new DeviceRgb(r, g, b)); + } + } + + public static void transformBorders(HSSFCell cell, Cell pdfCell) { + HSSFCellStyle cellStyle = cell.getCellStyle(); + pdfCell.setBorderBottom(getBorder(cellStyle.getBorderBottom(), cellStyle.getBottomBorderColor(), cell)); + pdfCell.setBorderLeft(getBorder(cellStyle.getBorderLeft(), cellStyle.getLeftBorderColor(), cell)); + pdfCell.setBorderRight(getBorder(cellStyle.getBorderRight(), cellStyle.getRightBorderColor(), cell)); + pdfCell.setBorderTop(getBorder(cellStyle.getBorderTop(), cellStyle.getTopBorderColor(), cell)); + } + + private void setPdfCellFont(HSSFCell cell, Text text, String fontPath) throws IOException { + HSSFCellStyle cellStyle = cell.getCellStyle(); + HSSFFont font = cellStyle.getFont(cell.getSheet().getWorkbook()); + text.setFont(StringUtils.isEmpty(fontPath) ? PdfFontFactory.createFont() : PdfFontFactory.createFont(fontPath, PdfEncodings.IDENTITY_H)); + text.setFontSize(font.getFontHeightInPoints()); + + // Set font color + HSSFColor hssfColor = font.getHSSFColor(cell.getSheet().getWorkbook()); + if (hssfColor != null && hssfColor.getIndex() != 64) { + short[] triplet = hssfColor.getTriplet(); + text.setFontColor(new DeviceRgb(triplet[0], triplet[1], triplet[2])); + } + + // Set font styles + if (font.getBold()) text.setBold(); + if (font.getItalic()) text.setItalic(); + if (font.getUnderline() == 1) text.setUnderline(0.5f, -1f); + } + + public static Border getBorder(BorderStyle borderStyle, short colorIndex, HSSFCell cell) { + HSSFPalette customPalette = cell.getSheet().getWorkbook().getCustomPalette(); + HSSFColor color = customPalette.getColor(colorIndex); + Color defaultColor = (color != null && color.getIndex() != 64) + ? new DeviceRgb(color.getTriplet()[0], color.getTriplet()[1], color.getTriplet()[2]) + : ColorConstants.BLACK; + + switch (borderStyle) { + case THIN: + return new SolidBorder(defaultColor, 0.3f); + case MEDIUM: + return new SolidBorder(defaultColor, 0.5f); + case DASHED: + return new DashedBorder(defaultColor, 0.3f); + case DOTTED: + return new DottedBorder(defaultColor, 0.3f); + case THICK: + return new SolidBorder(defaultColor, 1f); + case DOUBLE: + return new DoubleBorder(defaultColor, 0.3f); + case MEDIUM_DASHED: + return new DashedBorder(defaultColor, 0.5f); + default: + return Border.NO_BORDER; + } + } +} diff --git a/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v03/XlsImageTableRenderer.java b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v03/XlsImageTableRenderer.java new file mode 100644 index 0000000..a77094b --- /dev/null +++ b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v03/XlsImageTableRenderer.java @@ -0,0 +1,116 @@ +package cn.idev.excel.fileconvertor.v03; + +import com.itextpdf.io.image.ImageData; +import com.itextpdf.io.image.ImageDataFactory; +import com.itextpdf.kernel.geom.Rectangle; +import com.itextpdf.layout.element.Table; +import com.itextpdf.layout.renderer.CellRenderer; +import com.itextpdf.layout.renderer.DrawContext; +import com.itextpdf.layout.renderer.IRenderer; +import com.itextpdf.layout.renderer.TableRenderer; +import org.apache.poi.hssf.usermodel.HSSFClientAnchor; +import org.apache.poi.hssf.usermodel.HSSFPicture; +import org.apache.poi.hssf.usermodel.HSSFSheet; + +import java.util.List; + +/** + * Renders images from an Excel sheet onto a PDF table. + */ +public class XlsImageTableRenderer extends TableRenderer { + private List hSSFPictures; + private HSSFSheet sheet; + + public XlsImageTableRenderer(Table modelElement, List hSSFPictures, HSSFSheet sheet) { + super(modelElement); + this.hSSFPictures = hSSFPictures; + this.sheet = sheet; + } + + @Override + public void drawChildren(DrawContext drawContext) { + super.drawChildren(drawContext); + drawExcelImages(drawContext); + } + + private void drawExcelImages(DrawContext drawContext) { + for (HSSFPicture picture : hSSFPictures) { + HSSFClientAnchor clientAnchor = picture.getClientAnchor(); + Rectangle imageRect = calculateImageRectangle(clientAnchor); + ImageData imageData = ImageDataFactory.create(picture.getPictureData().getData()); + drawContext.getCanvas().addImage(imageData, + imageRect.getWidth(), + 0, + 0, + imageRect.getHeight(), + imageRect.getLeft(), + imageRect.getTop()); + } + } + + private Rectangle calculateImageRectangle(HSSFClientAnchor clientAnchor) { + CellRenderer cellRenderer1 = rows.get(clientAnchor.getRow1())[clientAnchor.getCol1()]; + Rectangle rect1 = cellRenderer1.getOccupiedAreaBBox(); + + CellRenderer cellRenderer2 = rows.get(clientAnchor.getRow2())[clientAnchor.getCol2()]; + Rectangle rect2 = cellRenderer2.getOccupiedAreaBBox(); + + float widthRate = calculateWidthRate(rect2); + float heightRate = calculateHeightRate(rect2); + + float width = calculateImageWidth(clientAnchor, widthRate); + float height = calculateImageHeight(clientAnchor, heightRate); + + float x = rect1.getLeft() + clientAnchor.getDx1() * widthRate; + float y = rect1.getTop() - height - clientAnchor.getDy1() * heightRate; + + return new Rectangle(x, y, width, height); + } + + private float calculateWidthRate(Rectangle rect2) { + return (super.getOccupiedAreaBBox().getWidth() + rect2.getWidth()) / getExcelWidth(sheet); + } + + private float calculateHeightRate(Rectangle rect2) { + return (super.getOccupiedAreaBBox().getHeight() - rect2.getHeight()) / getExcelHeight(sheet); + } + + private float calculateImageWidth(HSSFClientAnchor clientAnchor, float widthRate) { + float width = 0f; + for (int j = clientAnchor.getCol1(); j < clientAnchor.getCol2(); j++) { + width += sheet.getColumnWidth(j); + } + return Math.abs(width - clientAnchor.getDx1() + clientAnchor.getDx2()) * widthRate; + } + + private float calculateImageHeight(HSSFClientAnchor clientAnchor, float heightRate) { + float height = 0f; + for (int j = clientAnchor.getRow1(); j < clientAnchor.getRow2(); j++) { + height += sheet.getRow(j).getHeight(); + } + return Math.abs(height - clientAnchor.getDy1() + clientAnchor.getDy2()) * heightRate; + } + + private float getExcelHeight(HSSFSheet sheet) { + int physicalNumberOfRows = sheet.getPhysicalNumberOfRows(); + float result = 0; + for (int i = 0; i < physicalNumberOfRows; i++) { + result += sheet.getRow(i).getHeight(); + } + return result; + } + + private float getExcelWidth(HSSFSheet sheet) { + short lastCellNum = sheet.getRow(0).getLastCellNum(); + float result = 0; + for (int i = 0; i < lastCellNum; i++) { + result += sheet.getColumnWidth(i); + } + return result; + } + + @Override + public IRenderer getNextRenderer() { + return new XlsImageTableRenderer((Table) modelElement, hSSFPictures, sheet); + } +} diff --git a/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v07/XlsxConverter.java b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v07/XlsxConverter.java new file mode 100644 index 0000000..8ab1bbc --- /dev/null +++ b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v07/XlsxConverter.java @@ -0,0 +1,161 @@ +package cn.idev.excel.fileconvertor.v07; + +import cn.idev.excel.fileconvertor.BaseExcelConverter; +import cn.idev.excel.fileconvertor.Excel2PdfUtils; +import cn.idev.excel.fileconvertor.FileConverterContext; +import cn.idev.excel.util.StringUtils; +import com.itextpdf.io.font.PdfEncodings; +import com.itextpdf.kernel.colors.DeviceRgb; +import com.itextpdf.kernel.font.PdfFontFactory; +import com.itextpdf.layout.borders.*; +import com.itextpdf.layout.element.Paragraph; +import com.itextpdf.layout.element.Table; +import com.itextpdf.layout.element.Text; +import org.apache.poi.ss.usermodel.*; +import org.apache.poi.xssf.usermodel.*; + +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +public class XlsxConverter extends BaseExcelConverter { + private static final String DEFAULT_FONT_PATH = System.getProperty("user.dir") + "/doc/font/SimHei.TTF"; + + public XlsxConverter(FileConverterContext context) { + super(context); + } + + @Override + public void addPicsToTable(Table table, Sheet sheet) { + XSSFDrawing drawing = (XSSFDrawing) sheet.createDrawingPatriarch(); + if (drawing != null) { + List pictures = new ArrayList<>(); + for (XSSFShape shape : drawing.getShapes()) { + if (shape instanceof XSSFPicture) { + pictures.add((XSSFPicture) shape); + } + } + table.setNextRenderer(new XlsxImageTableRenderer(table, pictures, (XSSFSheet) sheet)); + } + } + + @Override + public com.itextpdf.layout.element.Cell convertCell(Cell cell, int rowspan, int colspan, float maxWidth, String fontPath) throws IOException { + String value = Excel2PdfUtils.getValue(cell); + com.itextpdf.layout.element.Cell pdfCell = createPdfCell(rowspan, colspan, cell, value, maxWidth, fontPath); + return pdfCell; + } + + public static void transformBorder(XSSFCell cell, com.itextpdf.layout.element.Cell pdfCell) { + XSSFCellStyle cellStyle = cell.getCellStyle(); + BorderStyle borderBottom = cellStyle.getBorderBottom(); + pdfCell.setBorderBottom(getBorder(borderBottom, cellStyle.getBottomBorderXSSFColor())); + + BorderStyle borderLeft = cellStyle.getBorderLeft(); + pdfCell.setBorderLeft(getBorder(borderLeft, cellStyle.getLeftBorderXSSFColor())); + + BorderStyle borderRight = cellStyle.getBorderRight(); + pdfCell.setBorderRight(getBorder(borderRight, cellStyle.getRightBorderXSSFColor())); + + BorderStyle borderTop = cellStyle.getBorderTop(); + pdfCell.setBorderTop(getBorder(borderTop, cellStyle.getTopBorderXSSFColor())); + } + + private com.itextpdf.layout.element.Cell createPdfCell(int rowspan, int colspan, Cell cell, String value, float maxWidth, String fontPath) throws IOException { + com.itextpdf.layout.element.Cell pdfCell = new com.itextpdf.layout.element.Cell(rowspan, colspan) + .setHeight(cell.getRow().getHeightInPoints() * 1.2f) + .setPadding(0); + Text text = new Text(value); + setPdfCellFont((XSSFCell) cell, text, fontPath); + Paragraph paragraph = new Paragraph(text).setPadding(0f).setMargin(0f); + XSSFCellStyle cellStyle = ((XSSFCell) cell).getCellStyle(); + if (cellStyle.getWrapText()) { + paragraph.setMaxWidth(maxWidth); + } + pdfCell.add(paragraph); + setCellStyles((XSSFCell)cell, pdfCell); + return pdfCell; + } + + private void setCellStyles( XSSFCell cell,com.itextpdf.layout.element.Cell pdfCell) throws IOException { + XSSFCellStyle cellStyle = cell.getCellStyle(); + pdfCell.setVerticalAlignment(getVerticalAlignment(cellStyle.getVerticalAlignment())) + .setTextAlignment(getTextAlignment(cellStyle.getAlignment(), cell.getCellType())); + + // Set borders and background color + setBorders(pdfCell, cellStyle); + setBackgroundColor(pdfCell, cellStyle); + } + + private void setBorders(com.itextpdf.layout.element.Cell pdfCell, XSSFCellStyle cellStyle) { + pdfCell.setBorderBottom(getBorder(cellStyle.getBorderBottom(), cellStyle.getBottomBorderXSSFColor())); + pdfCell.setBorderLeft(getBorder(cellStyle.getBorderLeft(), cellStyle.getLeftBorderXSSFColor())); + pdfCell.setBorderRight(getBorder(cellStyle.getBorderRight(), cellStyle.getRightBorderXSSFColor())); + pdfCell.setBorderTop(getBorder(cellStyle.getBorderTop(), cellStyle.getTopBorderXSSFColor())); + } + + private void setBackgroundColor(com.itextpdf.layout.element.Cell pdfCell, XSSFCellStyle cellStyle) { + XSSFColor fillColor = cellStyle.getFillForegroundXSSFColor(); + if (fillColor != null) { + byte[] rgb = fillColor.getRGB(); + if (rgb != null) { + pdfCell.setBackgroundColor(new DeviceRgb(Byte.toUnsignedInt(rgb[0]), Byte.toUnsignedInt(rgb[1]), Byte.toUnsignedInt(rgb[2]))); + } + } + } + + private void setPdfCellFont(XSSFCell cell, Text text,String fontPath) throws IOException { + XSSFCellStyle cellStyle = cell.getCellStyle(); + short fontHeight = cellStyle.getFont().getFontHeightInPoints(); + cellStyle.getFont().getFontName(); + text.setFont(StringUtils.isEmpty(fontPath) ? PdfFontFactory.createFont() : PdfFontFactory.createFont(fontPath, PdfEncodings.IDENTITY_H)); + text.setFontSize(fontHeight); + setFontColor(cellStyle.getFont(), text); + setFontStyles(cell.getCellStyle().getFont(), text); + } + + private void setFontColor(XSSFFont font, Text text) { + XSSFColor xssfColor = font.getXSSFColor(); + if (xssfColor != null && xssfColor.getIndex() != 64) { + byte[] rgb = xssfColor.getRGB(); + if (rgb != null) { + text.setFontColor(new DeviceRgb(Byte.toUnsignedInt(rgb[0]), Byte.toUnsignedInt(rgb[1]), Byte.toUnsignedInt(rgb[2]))); + } + } + } + + private void setFontStyles(XSSFFont font, Text text) { + if (font.getBold()) text.setBold(); + if (font.getItalic()) text.setItalic(); + if (font.getUnderline() == 1) text.setUnderline(0.5f, -1f); + } + + public static com.itextpdf.layout.borders.Border getBorder(BorderStyle borderStyle, XSSFColor xSSFColor) { + DeviceRgb defaultColor = new DeviceRgb(0, 0, 0); // Default to black + if (xSSFColor != null) { + byte[] rgb = xSSFColor.getRGB(); + if (rgb != null) { + defaultColor = new DeviceRgb(Byte.toUnsignedInt(rgb[0]), Byte.toUnsignedInt(rgb[1]), Byte.toUnsignedInt(rgb[2])); + } + } + + switch (borderStyle) { + case THIN: + return new SolidBorder(defaultColor, 0.3f); + case MEDIUM: + return new SolidBorder(defaultColor, 0.5f); + case DASHED: + return new DashedBorder(defaultColor, 0.3f); + case DOTTED: + return new DottedBorder(defaultColor, 0.3f); + case THICK: + return new SolidBorder(defaultColor, 1f); + case DOUBLE: + return new DoubleBorder(defaultColor, 0.3f); + case MEDIUM_DASHED: + return new DashedBorder(defaultColor, 0.5f); + default: + return Border.NO_BORDER; + } + } +} \ No newline at end of file diff --git a/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v07/XlsxImageTableRenderer.java b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v07/XlsxImageTableRenderer.java new file mode 100644 index 0000000..017704b --- /dev/null +++ b/fastexcel-core/src/main/java/cn/idev/excel/fileconvertor/v07/XlsxImageTableRenderer.java @@ -0,0 +1,101 @@ +package cn.idev.excel.fileconvertor.v07; + +import com.itextpdf.io.image.ImageData; +import com.itextpdf.io.image.ImageDataFactory; +import com.itextpdf.kernel.geom.Rectangle; +import com.itextpdf.layout.element.Table; +import com.itextpdf.layout.renderer.CellRenderer; +import com.itextpdf.layout.renderer.DrawContext; +import com.itextpdf.layout.renderer.IRenderer; +import com.itextpdf.layout.renderer.TableRenderer; +import org.apache.poi.xssf.usermodel.XSSFClientAnchor; +import org.apache.poi.xssf.usermodel.XSSFPicture; +import org.apache.poi.xssf.usermodel.XSSFSheet; + +import java.util.List; + +/** + * Renders images from an Excel sheet onto a PDF table. + */ +public class XlsxImageTableRenderer extends TableRenderer { + private List xssfPictures; + private XSSFSheet sheet; + + public XlsxImageTableRenderer(Table modelElement, List xssfPictures, XSSFSheet sheet) { + super(modelElement); + this.xssfPictures = xssfPictures; + this.sheet = sheet; + } + + @Override + public void drawChildren(DrawContext drawContext) { + super.drawChildren(drawContext); + renderExcelImages(drawContext); + } + + private void renderExcelImages(DrawContext drawContext) { + for (XSSFPicture picture : xssfPictures) { + XSSFClientAnchor clientAnchor = picture.getClientAnchor(); + Rectangle imageRect = calculateImageRectangle(clientAnchor); + ImageData imageData = ImageDataFactory.create(picture.getPictureData().getData()); + drawContext.getCanvas().addImage(imageData, + imageRect.getWidth(), + 0, + 0, + imageRect.getHeight(), + imageRect.getLeft(), + imageRect.getTop()); + } + } + + private Rectangle calculateImageRectangle(XSSFClientAnchor clientAnchor) { + CellRenderer cellRenderer1 = rows.get(clientAnchor.getRow1())[clientAnchor.getCol1()]; + CellRenderer cellRenderer2 = rows.get(clientAnchor.getRow2())[clientAnchor.getCol2()]; + Rectangle rect1 = cellRenderer1.getOccupiedAreaBBox(); + Rectangle rect2 = cellRenderer2.getOccupiedAreaBBox(); + + float widthRate = (super.getOccupiedAreaBBox().getWidth() + rect2.getWidth()) / getExcelWidth(sheet); + float heightRate = (super.getOccupiedAreaBBox().getHeight() - rect2.getHeight()) / getExcelHeight(sheet); + + float width = calculateImageWidth(clientAnchor, widthRate); + float height = calculateImageHeight(clientAnchor, heightRate); + + float x = rect1.getLeft() + clientAnchor.getDx1() * widthRate; + float y = rect1.getTop() - height - clientAnchor.getDy1() * heightRate; + + return new Rectangle(x, y, width, height); + } + + private float calculateImageWidth(XSSFClientAnchor clientAnchor, float widthRate) { + float width = 0f; + for (int j = clientAnchor.getCol1(); j < clientAnchor.getCol2(); j++) { + width += sheet.getColumnWidth(j); + } + return Math.abs(width - clientAnchor.getDx1() + clientAnchor.getDx2()) * widthRate; + } + + private float calculateImageHeight(XSSFClientAnchor clientAnchor, float heightRate) { + float height = 0f; + for (int j = clientAnchor.getRow1(); j < clientAnchor.getRow2(); j++) { + height += sheet.getRow(j).getHeight(); + } + return Math.abs(height - clientAnchor.getDy1() + clientAnchor.getDy2()) * heightRate; + } + + private float getExcelHeight(XSSFSheet sheet) { + float totalHeight = 0; + for (int i = 0; i < sheet.getPhysicalNumberOfRows(); i++) { + totalHeight += sheet.getRow(i).getHeight(); + } + return totalHeight; + } + + private float getExcelWidth(XSSFSheet sheet) { + return (short)sheet.getRow(0).getLastCellNum() * sheet.getColumnWidth(0); + } + + @Override + public IRenderer getNextRenderer() { + return new XlsxImageTableRenderer((Table) modelElement, xssfPictures, sheet); + } +} diff --git a/fastexcel-core/src/main/java/cn/idev/excel/read/builder/ExcelReaderBuilder.java b/fastexcel-core/src/main/java/cn/idev/excel/read/builder/ExcelReaderBuilder.java index bc24ac6..a0330fb 100644 --- a/fastexcel-core/src/main/java/cn/idev/excel/read/builder/ExcelReaderBuilder.java +++ b/fastexcel-core/src/main/java/cn/idev/excel/read/builder/ExcelReaderBuilder.java @@ -211,6 +211,12 @@ public class ExcelReaderBuilder extends AbstractExcelReaderParameterBuilder implements ReadListener { /** * Default single handle the amount of data */ - public static int BATCH_COUNT = 100; + public static int BATCH_COUNT = 1; /** * Temporary storage of data */ diff --git a/fastexcel-core/src/main/java/cn/idev/excel/read/listener/ReadListener.java b/fastexcel-core/src/main/java/cn/idev/excel/read/listener/ReadListener.java index 9558ece..3d98558 100644 --- a/fastexcel-core/src/main/java/cn/idev/excel/read/listener/ReadListener.java +++ b/fastexcel-core/src/main/java/cn/idev/excel/read/listener/ReadListener.java @@ -6,6 +6,9 @@ import cn.idev.excel.event.Listener; import cn.idev.excel.context.AnalysisContext; import cn.idev.excel.metadata.CellExtra; import cn.idev.excel.metadata.data.ReadCellData; +import cn.idev.excel.read.metadata.holder.ReadRowHolder; +import cn.idev.excel.read.metadata.holder.ReadSheetHolder; +import cn.idev.excel.read.metadata.holder.ReadWorkbookHolder; /** * Interface to listen for read results @@ -31,7 +34,8 @@ public interface ReadListener extends Listener { * @param headMap * @param context */ - default void invokeHead(Map> headMap, AnalysisContext context) {} + default void invokeHead(Map> headMap, AnalysisContext context) { + } /** * When analysis one row trigger invoke function. @@ -47,7 +51,8 @@ public interface ReadListener extends Listener { * @param extra extra information * @param context analysis context */ - default void extra(CellExtra extra, AnalysisContext context) {} + default void extra(CellExtra extra, AnalysisContext context) { + } /** * if have something to do after all analysis @@ -63,6 +68,24 @@ public interface ReadListener extends Listener { * @return */ default boolean hasNext(AnalysisContext context) { + if (context == null + || context.readRowHolder() == null + || context.readSheetHolder() == null + || context.readSheetHolder().getReadSheet() == null + || context.readWorkbookHolder().getReadWorkbook() == null + ) { + return true; + } + ReadRowHolder readRowHolder = context.readRowHolder(); + int index = readRowHolder.getRowIndex(); + + Integer limit = context.readSheetHolder().getReadSheet().getNumRows(); + if (limit == null) { + limit = context.readWorkbookHolder().getReadWorkbook().getNumRows(); + } + if (limit != null && index >= limit) { + return false; + } return true; } } diff --git a/fastexcel-core/src/main/java/cn/idev/excel/read/metadata/ReadSheet.java b/fastexcel-core/src/main/java/cn/idev/excel/read/metadata/ReadSheet.java index 36c5246..f570b05 100644 --- a/fastexcel-core/src/main/java/cn/idev/excel/read/metadata/ReadSheet.java +++ b/fastexcel-core/src/main/java/cn/idev/excel/read/metadata/ReadSheet.java @@ -15,6 +15,11 @@ public class ReadSheet extends ReadBasicParameter { */ private String sheetName; + /** + * The number of rows to read, the default is all, start with 0. + */ + public Integer numRows; + public ReadSheet() {} public ReadSheet(Integer sheetNo) { @@ -26,6 +31,12 @@ public class ReadSheet extends ReadBasicParameter { this.sheetName = sheetName; } + public ReadSheet(Integer sheetNo, String sheetName,Integer numRows) { + this.sheetNo = sheetNo; + this.sheetName = sheetName; + this.numRows = numRows; + } + public Integer getSheetNo() { return sheetNo; } @@ -42,6 +53,15 @@ public class ReadSheet extends ReadBasicParameter { this.sheetName = sheetName; } + + public Integer getNumRows() { + return numRows; + } + + public void setNumRows(Integer numRows) { + this.numRows = numRows; + } + public void copyBasicParameter(ReadSheet other) { if (other == null) { return; @@ -53,6 +73,7 @@ public class ReadSheet extends ReadBasicParameter { this.setCustomConverterList(other.getCustomConverterList()); this.setAutoTrim(other.getAutoTrim()); this.setUse1904windowing(other.getUse1904windowing()); + this.setNumRows(other.getNumRows()); } @Override diff --git a/fastexcel-core/src/main/java/cn/idev/excel/read/metadata/ReadWorkbook.java b/fastexcel-core/src/main/java/cn/idev/excel/read/metadata/ReadWorkbook.java index 79b8640..a103fb1 100644 --- a/fastexcel-core/src/main/java/cn/idev/excel/read/metadata/ReadWorkbook.java +++ b/fastexcel-core/src/main/java/cn/idev/excel/read/metadata/ReadWorkbook.java @@ -115,4 +115,9 @@ public class ReadWorkbook extends ReadBasicParameter { * @see CellExtraTypeEnum */ private Set extraReadSet; + + /** + * The number of rows to read, the default is all, start with 0. + */ + private Integer numRows; } diff --git a/fastexcel-core/src/main/java/cn/idev/excel/read/processor/DefaultAnalysisEventProcessor.java b/fastexcel-core/src/main/java/cn/idev/excel/read/processor/DefaultAnalysisEventProcessor.java index 7a90811..8351a51 100644 --- a/fastexcel-core/src/main/java/cn/idev/excel/read/processor/DefaultAnalysisEventProcessor.java +++ b/fastexcel-core/src/main/java/cn/idev/excel/read/processor/DefaultAnalysisEventProcessor.java @@ -118,6 +118,7 @@ public class DefaultAnalysisEventProcessor implements AnalysisEventProcessor { throw new ExcelAnalysisStopException(); } } + } private void buildHead(AnalysisContext analysisContext, Map> cellDataMap) { diff --git a/fastexcel-test/src/test/java/cn/idev/excel/test/demo/read/ReadTest.java b/fastexcel-test/src/test/java/cn/idev/excel/test/demo/read/ReadTest.java index 4abde03..769c0c9 100644 --- a/fastexcel-test/src/test/java/cn/idev/excel/test/demo/read/ReadTest.java +++ b/fastexcel-test/src/test/java/cn/idev/excel/test/demo/read/ReadTest.java @@ -53,7 +53,7 @@ public class ReadTest { for (DemoData demoData : dataList) { log.info("读取到一条数据{}", JSON.toJSONString(demoData)); } - })).sheet().doRead(); + })).numRows(2).sheet().doRead(); // 写法2: // 匿名内部类 不用额外写一个DemoDataListener @@ -105,6 +105,7 @@ public class ReadTest { try (ExcelReader excelReader = EasyExcel.read(fileName, DemoData.class, new DemoDataListener()).build()) { // 构建一个sheet 这里可以指定名字或者no ReadSheet readSheet = EasyExcel.readSheet(0).build(); + readSheet.setNumRows(2); // 读取一个sheet excelReader.read(readSheet); } @@ -124,7 +125,7 @@ public class ReadTest { public void indexOrNameRead() { String fileName = TestFileUtil.getPath() + "demo" + File.separator + "demo.xlsx"; // 这里默认读取第一个sheet - EasyExcel.read(fileName, IndexOrNameData.class, new IndexOrNameDataListener()).sheet().doRead(); + EasyExcel.read(fileName, IndexOrNameData.class, new IndexOrNameDataListener()).numRows(1).sheet().doRead(); } /** diff --git a/fastexcel-test/src/test/resources/compatibility/t01.xls b/fastexcel-test/src/test/resources/compatibility/t01.xls index e69de29..eb0782f 100644 Binary files a/fastexcel-test/src/test/resources/compatibility/t01.xls and b/fastexcel-test/src/test/resources/compatibility/t01.xls differ diff --git a/fastexcel-test/src/test/resources/compatibility/t02.xlsx b/fastexcel-test/src/test/resources/compatibility/t02.xlsx index e69de29..b8d755d 100644 Binary files a/fastexcel-test/src/test/resources/compatibility/t02.xlsx and b/fastexcel-test/src/test/resources/compatibility/t02.xlsx differ diff --git a/fastexcel-test/src/test/resources/compatibility/t03.xlsx b/fastexcel-test/src/test/resources/compatibility/t03.xlsx index e69de29..3a31ef7 100644 Binary files a/fastexcel-test/src/test/resources/compatibility/t03.xlsx and b/fastexcel-test/src/test/resources/compatibility/t03.xlsx differ diff --git a/fastexcel-test/src/test/resources/compatibility/t04.xlsx b/fastexcel-test/src/test/resources/compatibility/t04.xlsx index e69de29..7c95d42 100644 Binary files a/fastexcel-test/src/test/resources/compatibility/t04.xlsx and b/fastexcel-test/src/test/resources/compatibility/t04.xlsx differ diff --git a/fastexcel-test/src/test/resources/compatibility/t05.xlsx b/fastexcel-test/src/test/resources/compatibility/t05.xlsx index e69de29..248ec7d 100644 Binary files a/fastexcel-test/src/test/resources/compatibility/t05.xlsx and b/fastexcel-test/src/test/resources/compatibility/t05.xlsx differ diff --git a/fastexcel-test/src/test/resources/compatibility/t06.xlsx b/fastexcel-test/src/test/resources/compatibility/t06.xlsx index e69de29..b27be02 100644 Binary files a/fastexcel-test/src/test/resources/compatibility/t06.xlsx and b/fastexcel-test/src/test/resources/compatibility/t06.xlsx differ diff --git a/fastexcel-test/src/test/resources/compatibility/t07.xlsx b/fastexcel-test/src/test/resources/compatibility/t07.xlsx index e69de29..a7b0eac 100644 Binary files a/fastexcel-test/src/test/resources/compatibility/t07.xlsx and b/fastexcel-test/src/test/resources/compatibility/t07.xlsx differ diff --git a/fastexcel-test/src/test/resources/compatibility/t09.xlsx b/fastexcel-test/src/test/resources/compatibility/t09.xlsx index e69de29..0b29141 100644 Binary files a/fastexcel-test/src/test/resources/compatibility/t09.xlsx and b/fastexcel-test/src/test/resources/compatibility/t09.xlsx differ diff --git a/fastexcel-test/src/test/resources/converter/converter03.xls b/fastexcel-test/src/test/resources/converter/converter03.xls index e69de29..89c2ab6 100644 Binary files a/fastexcel-test/src/test/resources/converter/converter03.xls and b/fastexcel-test/src/test/resources/converter/converter03.xls differ diff --git a/fastexcel-test/src/test/resources/converter/converter07.xlsx b/fastexcel-test/src/test/resources/converter/converter07.xlsx index e69de29..99ace69 100644 Binary files a/fastexcel-test/src/test/resources/converter/converter07.xlsx and b/fastexcel-test/src/test/resources/converter/converter07.xlsx differ diff --git a/fastexcel-test/src/test/resources/converter/img.jpg b/fastexcel-test/src/test/resources/converter/img.jpg index e69de29..953f39f 100644 Binary files a/fastexcel-test/src/test/resources/converter/img.jpg and b/fastexcel-test/src/test/resources/converter/img.jpg differ diff --git a/fastexcel-test/src/test/resources/dataformat/dataformat.xls b/fastexcel-test/src/test/resources/dataformat/dataformat.xls index e69de29..95c306c 100644 Binary files a/fastexcel-test/src/test/resources/dataformat/dataformat.xls and b/fastexcel-test/src/test/resources/dataformat/dataformat.xls differ diff --git a/fastexcel-test/src/test/resources/dataformat/dataformat.xlsx b/fastexcel-test/src/test/resources/dataformat/dataformat.xlsx index e69de29..34a05cc 100644 Binary files a/fastexcel-test/src/test/resources/dataformat/dataformat.xlsx and b/fastexcel-test/src/test/resources/dataformat/dataformat.xlsx differ diff --git a/fastexcel-test/src/test/resources/dataformat/dataformatv2.xlsx b/fastexcel-test/src/test/resources/dataformat/dataformatv2.xlsx index e69de29..c49aa04 100644 Binary files a/fastexcel-test/src/test/resources/dataformat/dataformatv2.xlsx and b/fastexcel-test/src/test/resources/dataformat/dataformatv2.xlsx differ diff --git a/fastexcel-test/src/test/resources/demo/cellDataDemo.xlsx b/fastexcel-test/src/test/resources/demo/cellDataDemo.xlsx index e69de29..947229c 100644 Binary files a/fastexcel-test/src/test/resources/demo/cellDataDemo.xlsx and b/fastexcel-test/src/test/resources/demo/cellDataDemo.xlsx differ diff --git a/fastexcel-test/src/test/resources/demo/demo.xlsx b/fastexcel-test/src/test/resources/demo/demo.xlsx index e69de29..662bb97 100644 Binary files a/fastexcel-test/src/test/resources/demo/demo.xlsx and b/fastexcel-test/src/test/resources/demo/demo.xlsx differ diff --git a/fastexcel-test/src/test/resources/demo/extra.xlsx b/fastexcel-test/src/test/resources/demo/extra.xlsx index e69de29..4936b05 100644 Binary files a/fastexcel-test/src/test/resources/demo/extra.xlsx and b/fastexcel-test/src/test/resources/demo/extra.xlsx differ diff --git a/fastexcel-test/src/test/resources/demo/fill/complex.xlsx b/fastexcel-test/src/test/resources/demo/fill/complex.xlsx index e69de29..5376713 100644 Binary files a/fastexcel-test/src/test/resources/demo/fill/complex.xlsx and b/fastexcel-test/src/test/resources/demo/fill/complex.xlsx differ diff --git a/fastexcel-test/src/test/resources/demo/fill/complexFillWithTable.xlsx b/fastexcel-test/src/test/resources/demo/fill/complexFillWithTable.xlsx index e69de29..4de1a1e 100644 Binary files a/fastexcel-test/src/test/resources/demo/fill/complexFillWithTable.xlsx and b/fastexcel-test/src/test/resources/demo/fill/complexFillWithTable.xlsx differ diff --git a/fastexcel-test/src/test/resources/demo/fill/composite.xlsx b/fastexcel-test/src/test/resources/demo/fill/composite.xlsx index e69de29..c76a2b1 100644 Binary files a/fastexcel-test/src/test/resources/demo/fill/composite.xlsx and b/fastexcel-test/src/test/resources/demo/fill/composite.xlsx differ diff --git a/fastexcel-test/src/test/resources/demo/fill/horizontal.xlsx b/fastexcel-test/src/test/resources/demo/fill/horizontal.xlsx index e69de29..c8b4564 100644 Binary files a/fastexcel-test/src/test/resources/demo/fill/horizontal.xlsx and b/fastexcel-test/src/test/resources/demo/fill/horizontal.xlsx differ diff --git a/fastexcel-test/src/test/resources/demo/fill/list.xlsx b/fastexcel-test/src/test/resources/demo/fill/list.xlsx index e69de29..d29e05e 100644 Binary files a/fastexcel-test/src/test/resources/demo/fill/list.xlsx and b/fastexcel-test/src/test/resources/demo/fill/list.xlsx differ diff --git a/fastexcel-test/src/test/resources/demo/fill/simple.xlsx b/fastexcel-test/src/test/resources/demo/fill/simple.xlsx index e69de29..7514d1d 100644 Binary files a/fastexcel-test/src/test/resources/demo/fill/simple.xlsx and b/fastexcel-test/src/test/resources/demo/fill/simple.xlsx differ diff --git a/fastexcel-test/src/test/resources/extra/extra.xls b/fastexcel-test/src/test/resources/extra/extra.xls index e69de29..89f389b 100644 Binary files a/fastexcel-test/src/test/resources/extra/extra.xls and b/fastexcel-test/src/test/resources/extra/extra.xls differ diff --git a/fastexcel-test/src/test/resources/extra/extra.xlsx b/fastexcel-test/src/test/resources/extra/extra.xlsx index e69de29..4936b05 100644 Binary files a/fastexcel-test/src/test/resources/extra/extra.xlsx and b/fastexcel-test/src/test/resources/extra/extra.xlsx differ diff --git a/fastexcel-test/src/test/resources/extra/extraRelationships.xlsx b/fastexcel-test/src/test/resources/extra/extraRelationships.xlsx index e69de29..5784cd8 100644 Binary files a/fastexcel-test/src/test/resources/extra/extraRelationships.xlsx and b/fastexcel-test/src/test/resources/extra/extraRelationships.xlsx differ diff --git a/fastexcel-test/src/test/resources/fill/annotation.xls b/fastexcel-test/src/test/resources/fill/annotation.xls index e69de29..de09678 100644 Binary files a/fastexcel-test/src/test/resources/fill/annotation.xls and b/fastexcel-test/src/test/resources/fill/annotation.xls differ diff --git a/fastexcel-test/src/test/resources/fill/annotation.xlsx b/fastexcel-test/src/test/resources/fill/annotation.xlsx index e69de29..2a4a92b 100644 Binary files a/fastexcel-test/src/test/resources/fill/annotation.xlsx and b/fastexcel-test/src/test/resources/fill/annotation.xlsx differ diff --git a/fastexcel-test/src/test/resources/fill/byName.xls b/fastexcel-test/src/test/resources/fill/byName.xls index e69de29..e07fd50 100644 Binary files a/fastexcel-test/src/test/resources/fill/byName.xls and b/fastexcel-test/src/test/resources/fill/byName.xls differ diff --git a/fastexcel-test/src/test/resources/fill/byName.xlsx b/fastexcel-test/src/test/resources/fill/byName.xlsx index e69de29..327e055 100644 Binary files a/fastexcel-test/src/test/resources/fill/byName.xlsx and b/fastexcel-test/src/test/resources/fill/byName.xlsx differ diff --git a/fastexcel-test/src/test/resources/fill/complex.xls b/fastexcel-test/src/test/resources/fill/complex.xls index e69de29..d575895 100644 Binary files a/fastexcel-test/src/test/resources/fill/complex.xls and b/fastexcel-test/src/test/resources/fill/complex.xls differ diff --git a/fastexcel-test/src/test/resources/fill/complex.xlsx b/fastexcel-test/src/test/resources/fill/complex.xlsx index e69de29..5376713 100644 Binary files a/fastexcel-test/src/test/resources/fill/complex.xlsx and b/fastexcel-test/src/test/resources/fill/complex.xlsx differ diff --git a/fastexcel-test/src/test/resources/fill/composite.xls b/fastexcel-test/src/test/resources/fill/composite.xls index e69de29..e48aa0c 100644 Binary files a/fastexcel-test/src/test/resources/fill/composite.xls and b/fastexcel-test/src/test/resources/fill/composite.xls differ diff --git a/fastexcel-test/src/test/resources/fill/composite.xlsx b/fastexcel-test/src/test/resources/fill/composite.xlsx index e69de29..c76a2b1 100644 Binary files a/fastexcel-test/src/test/resources/fill/composite.xlsx and b/fastexcel-test/src/test/resources/fill/composite.xlsx differ diff --git a/fastexcel-test/src/test/resources/fill/horizontal.xls b/fastexcel-test/src/test/resources/fill/horizontal.xls index e69de29..570f901 100644 Binary files a/fastexcel-test/src/test/resources/fill/horizontal.xls and b/fastexcel-test/src/test/resources/fill/horizontal.xls differ diff --git a/fastexcel-test/src/test/resources/fill/horizontal.xlsx b/fastexcel-test/src/test/resources/fill/horizontal.xlsx index e69de29..c8b4564 100644 Binary files a/fastexcel-test/src/test/resources/fill/horizontal.xlsx and b/fastexcel-test/src/test/resources/fill/horizontal.xlsx differ diff --git a/fastexcel-test/src/test/resources/fill/simple.xls b/fastexcel-test/src/test/resources/fill/simple.xls index e69de29..317ef6d 100644 Binary files a/fastexcel-test/src/test/resources/fill/simple.xls and b/fastexcel-test/src/test/resources/fill/simple.xls differ diff --git a/fastexcel-test/src/test/resources/fill/simple.xlsx b/fastexcel-test/src/test/resources/fill/simple.xlsx index e69de29..a441eba 100644 Binary files a/fastexcel-test/src/test/resources/fill/simple.xlsx and b/fastexcel-test/src/test/resources/fill/simple.xlsx differ diff --git a/fastexcel-test/src/test/resources/fill/style.xls b/fastexcel-test/src/test/resources/fill/style.xls index e69de29..3127743 100644 Binary files a/fastexcel-test/src/test/resources/fill/style.xls and b/fastexcel-test/src/test/resources/fill/style.xls differ diff --git a/fastexcel-test/src/test/resources/fill/style.xlsx b/fastexcel-test/src/test/resources/fill/style.xlsx index e69de29..062540d 100644 Binary files a/fastexcel-test/src/test/resources/fill/style.xlsx and b/fastexcel-test/src/test/resources/fill/style.xlsx differ diff --git a/fastexcel-test/src/test/resources/large/fill.xlsx b/fastexcel-test/src/test/resources/large/fill.xlsx index e69de29..c3c376d 100644 Binary files a/fastexcel-test/src/test/resources/large/fill.xlsx and b/fastexcel-test/src/test/resources/large/fill.xlsx differ diff --git a/fastexcel-test/src/test/resources/large/large07.xlsx b/fastexcel-test/src/test/resources/large/large07.xlsx index e69de29..a317e71 100644 Binary files a/fastexcel-test/src/test/resources/large/large07.xlsx and b/fastexcel-test/src/test/resources/large/large07.xlsx differ diff --git a/fastexcel-test/src/test/resources/multiplesheets/multiplesheets.xls b/fastexcel-test/src/test/resources/multiplesheets/multiplesheets.xls index e69de29..a560128 100644 Binary files a/fastexcel-test/src/test/resources/multiplesheets/multiplesheets.xls and b/fastexcel-test/src/test/resources/multiplesheets/multiplesheets.xls differ diff --git a/fastexcel-test/src/test/resources/multiplesheets/multiplesheets.xlsx b/fastexcel-test/src/test/resources/multiplesheets/multiplesheets.xlsx index e69de29..f90680a 100644 Binary files a/fastexcel-test/src/test/resources/multiplesheets/multiplesheets.xlsx and b/fastexcel-test/src/test/resources/multiplesheets/multiplesheets.xlsx differ diff --git a/fastexcel-test/src/test/resources/simple/simple07.xlsx b/fastexcel-test/src/test/resources/simple/simple07.xlsx index e69de29..3d25fcd 100644 Binary files a/fastexcel-test/src/test/resources/simple/simple07.xlsx and b/fastexcel-test/src/test/resources/simple/simple07.xlsx differ diff --git a/fastexcel-test/src/test/resources/temp/issue1663/template.xlsx b/fastexcel-test/src/test/resources/temp/issue1663/template.xlsx index e69de29..a968ff4 100644 Binary files a/fastexcel-test/src/test/resources/temp/issue1663/template.xlsx and b/fastexcel-test/src/test/resources/temp/issue1663/template.xlsx differ diff --git a/fastexcel-test/src/test/resources/temp/issue2443/date1.xlsx b/fastexcel-test/src/test/resources/temp/issue2443/date1.xlsx index e69de29..92ef811 100644 Binary files a/fastexcel-test/src/test/resources/temp/issue2443/date1.xlsx and b/fastexcel-test/src/test/resources/temp/issue2443/date1.xlsx differ diff --git a/fastexcel-test/src/test/resources/temp/issue2443/date2.xlsx b/fastexcel-test/src/test/resources/temp/issue2443/date2.xlsx index e69de29..c6feb32 100644 Binary files a/fastexcel-test/src/test/resources/temp/issue2443/date2.xlsx and b/fastexcel-test/src/test/resources/temp/issue2443/date2.xlsx differ diff --git a/fastexcel-test/src/test/resources/template/template03.xls b/fastexcel-test/src/test/resources/template/template03.xls index e69de29..7c17eee 100644 Binary files a/fastexcel-test/src/test/resources/template/template03.xls and b/fastexcel-test/src/test/resources/template/template03.xls differ diff --git a/fastexcel-test/src/test/resources/template/template07.xlsx b/fastexcel-test/src/test/resources/template/template07.xlsx index e69de29..a046fbc 100644 Binary files a/fastexcel-test/src/test/resources/template/template07.xlsx and b/fastexcel-test/src/test/resources/template/template07.xlsx differ