生成抵扣表支付表

This commit is contained in:
2026-05-24 08:48:39 +08:00
parent 27de5decc3
commit 62722a9ce7

View File

@@ -6,6 +6,7 @@ import jakarta.servlet.http.HttpServletResponse;
import org.apache.poi.ss.usermodel.BorderStyle; import org.apache.poi.ss.usermodel.BorderStyle;
import org.apache.poi.ss.usermodel.Cell; import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.CellStyle; import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.ss.usermodel.CellType;
import org.apache.poi.ss.usermodel.ComparisonOperator; import org.apache.poi.ss.usermodel.ComparisonOperator;
import org.apache.poi.ss.usermodel.ConditionalFormattingRule; import org.apache.poi.ss.usermodel.ConditionalFormattingRule;
import org.apache.poi.ss.usermodel.DataFormat; import org.apache.poi.ss.usermodel.DataFormat;
@@ -34,7 +35,6 @@ import java.nio.charset.StandardCharsets;
import java.time.LocalDate; import java.time.LocalDate;
import java.time.format.DateTimeFormatter; import java.time.format.DateTimeFormatter;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Comparator;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
@@ -43,14 +43,24 @@ import java.util.Map;
*/ */
public final class LbDailyUserTradeReportExportSupport { public final class LbDailyUserTradeReportExportSupport {
/** 导出工作簿固定 7 个 sheet顺序与业务模板一致。 */ /** 导出工作簿固定 8 个 sheet顺序与业务模板一致。 */
private static final String[] EXPORT_SHEET_NAMES = { private static final String[] EXPORT_SHEET_NAMES = {
"总表", "抵扣表", "支付", "11点表", "断货表", "临时表2", "结果表" "总表", "抵扣表", "断货", "11点表", "支付表", "支付表检查", "临时表2", "结果表"
}; };
private static final int SUMMARY_SHEET_INDEX = 0; private static final int SUMMARY_SHEET_INDEX = 0;
private static final int DEDUCTION_SHEET_INDEX = 1; private static final int DEDUCTION_SHEET_INDEX = 1;
private static final int OUT_OF_STOCK_SHEET_INDEX = 2;
private static final int ELEVEN_CLOCK_SHEET_INDEX = 3; private static final int ELEVEN_CLOCK_SHEET_INDEX = 3;
private static final int PAYMENT_SHEET_INDEX = 4;
private static final int PAYMENT_CHECK_SHEET_INDEX = 5;
private static final int PAYMENT_COL_NAME = 0;
private static final int PAYMENT_COL_ACTUAL = 1;
/** 支付表:实际收付 < 0 的记录移至 E、F 列 */
private static final int PAYMENT_NEGATIVE_COL_NAME = 4;
private static final int PAYMENT_NEGATIVE_COL_ACTUAL = 5;
private static final int PAYMENT_LAST_COL = PAYMENT_NEGATIVE_COL_ACTUAL;
private static final int COL_NICKNAME = 0; private static final int COL_NICKNAME = 0;
private static final int COL_YESTODAY_BUY = 1; private static final int COL_YESTODAY_BUY = 1;
@@ -67,6 +77,8 @@ public final class LbDailyUserTradeReportExportSupport {
private static final int COL_SEQUENCE_LEFT = 0; private static final int COL_SEQUENCE_LEFT = 0;
private static final String DATA_TYPE_REPORT_SUM = "report_sum"; private static final String DATA_TYPE_REPORT_SUM = "report_sum";
/** 支付表 A/B 列固定追加行姓名 */
private static final String PAYMENT_AB_SPECIAL_NAME = "刘瑞华";
private LbDailyUserTradeReportExportSupport() { private LbDailyUserTradeReportExportSupport() {
} }
@@ -84,11 +96,18 @@ public final class LbDailyUserTradeReportExportSupport {
} }
DateHeaderLabels labels = DateHeaderLabels.of(reportDate); DateHeaderLabels labels = DateHeaderLabels.of(reportDate);
fillSummarySheet(workbook.getSheetAt(SUMMARY_SHEET_INDEX), labels, rows, styles); List<LbDailyUserTradeReport> exportRows = prepareExportRows(rows);
fillSummarySheet(workbook.getSheetAt(SUMMARY_SHEET_INDEX), labels, exportRows, styles);
Map<String, BigDecimal> deductionMap = deductionByUserName == null ? Map.of() : deductionByUserName; Map<String, BigDecimal> deductionMap = deductionByUserName == null ? Map.of() : deductionByUserName;
fillDeductionSheet(workbook.getSheetAt(DEDUCTION_SHEET_INDEX), labels, rows, styles, deductionMap, false, true); fillDeductionSheet(workbook.getSheetAt(DEDUCTION_SHEET_INDEX), labels, exportRows, styles, deductionMap, false, true, false);
// 11点表与抵扣表相同的数据与计算逻辑最左侧序号列不含最后一行汇总 // 断货表:总表中当日买入金额为 0 的明细行,最左侧序号列
fillDeductionSheet(workbook.getSheetAt(ELEVEN_CLOCK_SHEET_INDEX), labels, rows, styles, deductionMap, true, false); fillOutOfStockSheet(workbook.getSheetAt(OUT_OF_STOCK_SHEET_INDEX), labels, exportRows, styles);
// 11点表与抵扣表相同的数据与计算逻辑最左侧序号列不含最后一行汇总数值四舍五入取整
fillDeductionSheet(workbook.getSheetAt(ELEVEN_CLOCK_SHEET_INDEX), labels, exportRows, styles, deductionMap, true, false, true);
// 支付表A/B 列含刘瑞华,按 B 列倒序;< 0 移至 E/F 列
Sheet paymentSheet = workbook.getSheetAt(PAYMENT_SHEET_INDEX);
fillPaymentSheet(paymentSheet, exportRows, styles, deductionMap);
fillPaymentCheckSheet(workbook.getSheetAt(PAYMENT_CHECK_SHEET_INDEX), paymentSheet, styles);
String filename = "当日汇总报表" + reportDate.format(DateTimeFormatter.ofPattern("yyyyMMdd")) + ".xlsx"; String filename = "当日汇总报表" + reportDate.format(DateTimeFormatter.ofPattern("yyyyMMdd")) + ".xlsx";
String encoded = URLEncoder.encode(filename, StandardCharsets.UTF_8).replaceAll("\\+", "%20"); String encoded = URLEncoder.encode(filename, StandardCharsets.UTF_8).replaceAll("\\+", "%20");
@@ -107,46 +126,444 @@ public final class LbDailyUserTradeReportExportSupport {
private static void fillSummarySheet( private static void fillSummarySheet(
Sheet sheet, Sheet sheet,
DateHeaderLabels labels, DateHeaderLabels labels,
List<LbDailyUserTradeReport> rows, List<LbDailyUserTradeReport> exportRows,
SheetStyles styles) { SheetStyles styles) {
int r = writeHeaderRow(sheet, labels, styles, false); fillSummaryLikeSheet(sheet, labels, exportRows, styles, false, false);
sheet.createFreezePane(0, 1);
sheet.setAutoFilter(new CellRangeAddress(0, 0, 0, SUMMARY_LAST_COL));
for (LbDailyUserTradeReport item : rows) {
Row row = sheet.createRow(r++);
applyRowHeight(row, styles);
RowStylePair rowStyles = rowStyles(item, r, styles);
writeBaseDataCells(row, item, rowStyles, roundedInt(item.getDikouAmt()), false);
}
applyDiffNegativeFormatting(sheet, r, false);
autoSizeColumns(sheet, SUMMARY_LAST_COL);
} }
/** /** 断货表复制总表中当日买入金额dailyBuyAmt为 0 的明细行,不含汇总行,最左侧序号列,数值四舍五入取整。 */
* 抵扣表 / 11点表先按总表写入各行抵扣金额列改为 lb_deduction_amount 匹配值; private static void fillOutOfStockSheet(
* 「实际收付」= 抵扣金额 + 原实际收付;明细按实际收付倒序。 Sheet sheet,
* 抵扣表最后一行汇总行的抵扣金额、实际收付为本列明细之和11点表不输出汇总行最左侧为序号列。 DateHeaderLabels labels,
*/ List<LbDailyUserTradeReport> exportRows,
private static void fillDeductionSheet( SheetStyles styles) {
fillSummaryLikeSheet(sheet, labels, filterZeroDailyBuyRows(exportRows), styles, true, true);
}
private static List<LbDailyUserTradeReport> filterZeroDailyBuyRows(List<LbDailyUserTradeReport> exportRows) {
List<LbDailyUserTradeReport> filtered = new ArrayList<>();
for (LbDailyUserTradeReport row : exportRows) {
if (DATA_TYPE_REPORT_SUM.equals(row.getDataType())) {
continue;
}
if (defaultZero(row.getDailyBuyAmt()).compareTo(BigDecimal.ZERO) == 0) {
filtered.add(row);
}
}
return filtered;
}
private static void fillSummaryLikeSheet(
Sheet sheet, Sheet sheet,
DateHeaderLabels labels, DateHeaderLabels labels,
List<LbDailyUserTradeReport> rows, List<LbDailyUserTradeReport> rows,
SheetStyles styles, SheetStyles styles,
Map<String, BigDecimal> deductionByUserName, boolean roundValues,
boolean sequenceOnLeft, boolean sequenceOnLeft) {
boolean includeSummaryRow) {
int lastCol = sequenceOnLeft ? ELEVEN_CLOCK_LAST_COL : SUMMARY_LAST_COL; int lastCol = sequenceOnLeft ? ELEVEN_CLOCK_LAST_COL : SUMMARY_LAST_COL;
int r = writeHeaderRow(sheet, labels, styles, sequenceOnLeft); int r = writeHeaderRow(sheet, labels, styles, sequenceOnLeft);
sheet.createFreezePane(0, 1); sheet.createFreezePane(0, 1);
sheet.setAutoFilter(new CellRangeAddress(0, 0, 0, lastCol)); sheet.setAutoFilter(new CellRangeAddress(0, 0, 0, lastCol));
long totalDikou = 0; int sequence = 0;
long totalActual = 0; for (LbDailyUserTradeReport item : rows) {
Row row = sheet.createRow(r++);
applyRowHeight(row, styles);
RowStylePair rowStyles = rowStyles(item, r, styles, roundValues);
if (sequenceOnLeft) {
sequence++;
createIntCell(row, COL_SEQUENCE_LEFT, sequence, rowStyles.sequenceStyle);
}
writeBaseDataCells(row, item, rowStyles, defaultZero(item.getDikouAmt()), sequenceOnLeft, roundValues);
}
applyDiffNegativeFormatting(sheet, r, sequenceOnLeft);
autoSizeColumns(sheet, lastCol);
}
/**
* 支付表A/B 列含刘瑞华汇总行,与 |F 列总和| 平衡后按 B 列倒序;< 0 写入 E/F 列(升序)。
*/
private static void fillPaymentSheet(
Sheet sheet,
List<LbDailyUserTradeReport> exportRows,
SheetStyles styles,
Map<String, BigDecimal> deductionByUserName) {
boolean roundValues = true;
int r = 0;
Row header = sheet.createRow(r++);
header.setHeightInPoints(20 * styles.rowHeightFactor);
createHeaderCell(header, PAYMENT_COL_NAME, "姓名", styles.headerStyle);
createHeaderCell(header, PAYMENT_COL_ACTUAL, "实际收付", styles.headerStyle);
createHeaderCell(header, PAYMENT_NEGATIVE_COL_NAME, "姓名", styles.headerStyle);
createHeaderCell(header, PAYMENT_NEGATIVE_COL_ACTUAL, "实际收付", styles.headerStyle);
sheet.createFreezePane(0, 1);
sheet.setAutoFilter(new CellRangeAddress(0, 0, 0, PAYMENT_LAST_COL));
List<PaymentAbEntry> abEntries = new ArrayList<>();
List<LbDailyUserTradeReport> negativeRows = new ArrayList<>();
for (LbDailyUserTradeReport item : elevenClockDetailRows(exportRows, deductionByUserName)) {
BigDecimal actual = computeActualReceiptsForDeduction(item, deductionByUserName, roundValues);
if (actual.compareTo(BigDecimal.ZERO) >= 0) {
abEntries.add(PaymentAbEntry.detail(
item.getNickname() == null ? "" : item.getNickname(),
actual,
item));
} else {
negativeRows.add(item);
}
}
abEntries.add(PaymentAbEntry.special(
computeDeductionSheetSummaryActual(exportRows, deductionByUserName)));
balancePaymentSheetColumnTotals(abEntries, negativeRows, deductionByUserName, roundValues);
abEntries.sort((a, b) -> b.sortValue().compareTo(a.sortValue()));
int positiveRow = 1;
for (PaymentAbEntry entry : abEntries) {
Row row = sheet.getRow(positiveRow);
if (row == null) {
row = sheet.createRow(positiveRow);
applyRowHeight(row, styles);
}
if (entry.isSpecialRow()) {
createTextCell(row, PAYMENT_COL_NAME, entry.name(), paymentTextStyle(positiveRow, styles));
createPaymentActualCell(
row, PAYMENT_COL_ACTUAL, entry.actualAbs(), paymentActualStyle(positiveRow, styles));
} else {
RowStylePair rowStyles = rowStyles(entry.detailRow(), positiveRow, styles, roundValues);
createTextCell(row, PAYMENT_COL_NAME, entry.name(), rowStyles.textStyle);
createPaymentActualCell(
row, PAYMENT_COL_ACTUAL, entry.actualAbs(), paymentActualStyle(positiveRow, styles));
}
positiveRow++;
}
negativeRows.sort((a, b) -> computeActualReceiptsForDeduction(a, deductionByUserName, roundValues)
.compareTo(computeActualReceiptsForDeduction(b, deductionByUserName, roundValues)));
int negativeRow = 1;
for (LbDailyUserTradeReport item : negativeRows) {
Row row = sheet.getRow(negativeRow);
if (row == null) {
row = sheet.createRow(negativeRow);
applyRowHeight(row, styles);
}
RowStylePair rowStyles = rowStyles(item, negativeRow, styles, roundValues);
createTextCell(
row,
PAYMENT_NEGATIVE_COL_NAME,
item.getNickname() == null ? "" : item.getNickname(),
rowStyles.textStyle);
createPaymentActualCell(
row,
PAYMENT_NEGATIVE_COL_ACTUAL,
computeActualReceiptsForDeduction(item, deductionByUserName, roundValues),
paymentActualStyle(negativeRow, styles));
negativeRow++;
}
int nextRow = Math.max(positiveRow, negativeRow);
applyPaymentNegativeActualFormatting(sheet, nextRow);
autoSizeColumns(sheet, PAYMENT_LAST_COL);
}
/**
* 支付表检查完整复制支付表末尾追加一行「求和」B、F 列为上方数据行之和。
*/
private static void fillPaymentCheckSheet(Sheet target, Sheet paymentSource, SheetStyles styles) {
copyPaymentSheetContent(paymentSource, target);
BigDecimal sumB = BigDecimal.ZERO;
BigDecimal sumF = BigDecimal.ZERO;
int lastDataRow = paymentSource.getLastRowNum();
for (int rowIdx = 1; rowIdx <= lastDataRow; rowIdx++) {
Row row = paymentSource.getRow(rowIdx);
if (row == null) {
continue;
}
sumB = sumB.add(readNumericCellValue(row.getCell(PAYMENT_COL_ACTUAL)));
sumF = sumF.add(readNumericCellValue(row.getCell(PAYMENT_NEGATIVE_COL_ACTUAL)));
}
int sumRowIdx = lastDataRow + 1;
Row sumRow = target.createRow(sumRowIdx);
applyRowHeight(sumRow, styles);
createTextCell(sumRow, PAYMENT_COL_NAME, "求和", styles.summaryTextStyle);
createPaymentActualCell(sumRow, PAYMENT_COL_ACTUAL, sumB, styles.summaryRoundedAmountStyle);
createPaymentActualCell(sumRow, PAYMENT_NEGATIVE_COL_ACTUAL, sumF, styles.summaryRoundedAmountStyle);
applyPaymentNegativeActualFormatting(target, sumRowIdx);
autoSizeColumns(target, PAYMENT_LAST_COL);
}
private static void copyPaymentSheetContent(Sheet source, Sheet target) {
target.setDefaultRowHeight(source.getDefaultRowHeight());
for (int col = 0; col <= PAYMENT_LAST_COL; col++) {
target.setColumnWidth(col, source.getColumnWidth(col));
}
for (int rowIdx = 0; rowIdx <= source.getLastRowNum(); rowIdx++) {
Row srcRow = source.getRow(rowIdx);
if (srcRow == null) {
continue;
}
Row destRow = target.createRow(rowIdx);
destRow.setHeight(srcRow.getHeight());
for (int col = 0; col <= PAYMENT_LAST_COL; col++) {
Cell srcCell = srcRow.getCell(col);
if (srcCell == null) {
continue;
}
copyCellValueAndStyle(srcCell, destRow.createCell(col));
}
}
target.createFreezePane(0, 1);
target.setAutoFilter(new CellRangeAddress(0, 0, 0, PAYMENT_LAST_COL));
}
private static void copyCellValueAndStyle(Cell source, Cell target) {
target.setCellStyle(source.getCellStyle());
switch (source.getCellType()) {
case STRING -> target.setCellValue(source.getStringCellValue());
case NUMERIC -> target.setCellValue(source.getNumericCellValue());
case BOOLEAN -> target.setCellValue(source.getBooleanCellValue());
case FORMULA -> target.setCellFormula(source.getCellFormula());
case BLANK -> target.setBlank();
default -> {
}
}
}
private static BigDecimal readNumericCellValue(Cell cell) {
if (cell == null || cell.getCellType() == CellType.BLANK) {
return BigDecimal.ZERO;
}
if (cell.getCellType() == CellType.NUMERIC || cell.getCellType() == CellType.FORMULA) {
return BigDecimal.valueOf(cell.getNumericCellValue());
}
if (cell.getCellType() == CellType.STRING) {
String text = cell.getStringCellValue();
if (text == null || text.isBlank()) {
return BigDecimal.ZERO;
}
try {
return new BigDecimal(text.trim());
} catch (NumberFormatException ignored) {
return BigDecimal.ZERO;
}
}
return BigDecimal.ZERO;
}
/** 抵扣表汇总行「实际收付」= 明细行(抵扣金额 + 原实际收付)之和,与 fillDeductionSheet 口径一致。 */
private static BigDecimal computeDeductionSheetSummaryActual(
List<LbDailyUserTradeReport> exportRows,
Map<String, BigDecimal> deductionByUserName) {
BigDecimal totalActual = BigDecimal.ZERO;
for (LbDailyUserTradeReport item : orderRowsForDeductionSheet(exportRows, deductionByUserName, false)) {
if (DATA_TYPE_REPORT_SUM.equals(item.getDataType())) {
continue;
}
totalActual = totalActual.add(
computeActualReceiptsForDeduction(item, deductionByUserName, false));
}
return totalActual;
}
/** 支付表 B 列展示/排序值:实际收付绝对值四舍五入取整。 */
private static BigDecimal paymentAbDisplayValue(BigDecimal actual) {
return roundHalfUp(defaultZero(actual).abs());
}
/** 支付表 F 列展示值:实际收付四舍五入取整(保留符号,与写入 F 列口径一致)。 */
private static BigDecimal paymentFColumnDisplayValue(BigDecimal actual) {
return roundHalfUp(defaultZero(actual));
}
/**
* 支付表 B/F 列平衡:|F 列总和| 与 B 列总和不一致时,加减刘瑞华 B 列数值使两列总和相等。
*/
private static void balancePaymentSheetColumnTotals(
List<PaymentAbEntry> abEntries,
List<LbDailyUserTradeReport> negativeRows,
Map<String, BigDecimal> deductionByUserName,
boolean roundValues) {
BigDecimal fSum = BigDecimal.ZERO;
for (LbDailyUserTradeReport item : negativeRows) {
BigDecimal actual = computeActualReceiptsForDeduction(item, deductionByUserName, roundValues);
fSum = fSum.add(paymentFColumnDisplayValue(actual));
}
BigDecimal fTotalAbs = fSum.abs();
BigDecimal bSum = BigDecimal.ZERO;
for (PaymentAbEntry entry : abEntries) {
bSum = bSum.add(entry.actualAbs());
}
if (bSum.compareTo(fTotalAbs) == 0) {
return;
}
BigDecimal diff = fTotalAbs.subtract(bSum);
for (int i = 0; i < abEntries.size(); i++) {
PaymentAbEntry entry = abEntries.get(i);
if (entry.isSpecialRow()) {
abEntries.set(i, entry.withActualAbs(entry.actualAbs().add(diff)));
return;
}
}
}
private record PaymentAbEntry(String name, BigDecimal actualAbs, LbDailyUserTradeReport detailRow) {
static PaymentAbEntry detail(String name, BigDecimal actual, LbDailyUserTradeReport detailRow) {
return new PaymentAbEntry(name, paymentAbDisplayValue(actual), detailRow);
}
static PaymentAbEntry special(BigDecimal deductionSummaryActual) {
return new PaymentAbEntry(
PAYMENT_AB_SPECIAL_NAME,
paymentAbDisplayValue(deductionSummaryActual),
null);
}
boolean isSpecialRow() {
return detailRow == null;
}
PaymentAbEntry withActualAbs(BigDecimal newActualAbs) {
return new PaymentAbEntry(name, newActualAbs, detailRow);
}
BigDecimal sortValue() {
return actualAbs;
}
}
private static CellStyle paymentActualDecimalStyle(int rowIndex, SheetStyles styles) {
return (rowIndex % 2 == 0) ? styles.zebraPaymentActualDecimalStyle : styles.paymentActualDecimalStyle;
}
private static CellStyle paymentTextStyle(int rowIndex, SheetStyles styles) {
return (rowIndex % 2 == 0) ? styles.zebraTextStyle : styles.textStyle;
}
/** 11点表 / 支付表共用的明细行:按实际收付倒序,不含汇总行。 */
private static List<LbDailyUserTradeReport> elevenClockDetailRows(
List<LbDailyUserTradeReport> exportRows,
Map<String, BigDecimal> deductionByUserName) {
List<LbDailyUserTradeReport> rows = new ArrayList<>();
for (LbDailyUserTradeReport row : orderRowsForDeductionSheet(exportRows, deductionByUserName, true)) {
if (!DATA_TYPE_REPORT_SUM.equals(row.getDataType())) {
rows.add(row);
}
}
return rows;
}
private static void applyPaymentNegativeActualFormatting(Sheet sheet, int nextRowIndex) {
if (nextRowIndex > 1) {
SheetConditionalFormatting scf = sheet.getSheetConditionalFormatting();
ConditionalFormattingRule negative = scf.createConditionalFormattingRule(ComparisonOperator.LT, "0");
FontFormatting ff = negative.createFontFormatting();
ff.setFontColorIndex(IndexedColors.DARK_RED.getIndex());
ff.setFontStyle(false, false);
scf.addConditionalFormatting(
new CellRangeAddress[]{
new CellRangeAddress(
1, nextRowIndex - 1, PAYMENT_NEGATIVE_COL_ACTUAL, PAYMENT_NEGATIVE_COL_ACTUAL)
},
negative);
}
}
/**
* 导出行序:明细按差额倒序,汇总行固定在最后。
* 若库中无 report_sum则按明细字段聚合生成一条汇总行与 calculateReportSum 口径一致)。
*/
private static List<LbDailyUserTradeReport> prepareExportRows(List<LbDailyUserTradeReport> rows) {
if (rows == null || rows.isEmpty()) {
return List.of();
}
List<LbDailyUserTradeReport> details = new ArrayList<>();
LbDailyUserTradeReport summaryFromDb = null;
for (LbDailyUserTradeReport row : rows) {
if (DATA_TYPE_REPORT_SUM.equals(row.getDataType())) {
summaryFromDb = row;
} else {
details.add(row);
}
}
details.sort((a, b) -> {
BigDecimal da = a.getDiffAmt() == null ? BigDecimal.ZERO : a.getDiffAmt();
BigDecimal db = b.getDiffAmt() == null ? BigDecimal.ZERO : b.getDiffAmt();
return db.compareTo(da);
});
LbDailyUserTradeReport summaryRow =
summaryFromDb != null ? summaryFromDb : (details.isEmpty() ? null : buildSummaryRowFromDetails(details));
List<LbDailyUserTradeReport> ordered = new ArrayList<>(details.size() + (summaryRow == null ? 0 : 1));
ordered.addAll(details);
if (summaryRow != null) {
ordered.add(summaryRow);
}
return ordered;
}
private static LbDailyUserTradeReport buildSummaryRowFromDetails(List<LbDailyUserTradeReport> details) {
BigDecimal yestodayBuyAmt = BigDecimal.ZERO;
BigDecimal dailySellAmt = BigDecimal.ZERO;
BigDecimal dailyBuyAmt = BigDecimal.ZERO;
BigDecimal serviceAmt = BigDecimal.ZERO;
BigDecimal diffAmt = BigDecimal.ZERO;
BigDecimal dikouAmt = BigDecimal.ZERO;
for (LbDailyUserTradeReport row : details) {
yestodayBuyAmt = yestodayBuyAmt.add(defaultZero(row.getYestodayBuyAmt()));
dailySellAmt = dailySellAmt.add(defaultZero(row.getDailySellAmt()));
dailyBuyAmt = dailyBuyAmt.add(defaultZero(row.getDailyBuyAmt()));
serviceAmt = serviceAmt.add(defaultZero(row.getServiceAmt()));
diffAmt = diffAmt.add(defaultZero(row.getDiffAmt()));
dikouAmt = dikouAmt.add(defaultZero(row.getDikouAmt()));
}
LbDailyUserTradeReport summary = new LbDailyUserTradeReport();
summary.setDataType(DATA_TYPE_REPORT_SUM);
summary.setYestodayBuyAmt(yestodayBuyAmt);
summary.setDailySellAmt(dailySellAmt);
summary.setDailyBuyAmt(dailyBuyAmt);
summary.setServiceAmt(serviceAmt);
summary.setDiffAmt(diffAmt);
summary.setDikouAmt(dikouAmt);
summary.setActualReceiptsPayments(diffAmt.subtract(serviceAmt));
return summary;
}
private static BigDecimal defaultZero(BigDecimal value) {
return value == null ? BigDecimal.ZERO : value;
}
/**
* 抵扣表 / 11点表先按总表写入各行抵扣金额列改为 lb_deduction_amount 匹配值;
* 「实际收付」= 抵扣金额 + 原实际收付;明细按实际收付倒序。
* 抵扣表最后一行汇总行的抵扣金额、实际收付为本列明细之和11点表不输出汇总行最左侧为序号列数值四舍五入取整。
*/
private static void fillDeductionSheet(
Sheet sheet,
DateHeaderLabels labels,
List<LbDailyUserTradeReport> exportRows,
SheetStyles styles,
Map<String, BigDecimal> deductionByUserName,
boolean sequenceOnLeft,
boolean includeSummaryRow,
boolean roundValues) {
int lastCol = sequenceOnLeft ? ELEVEN_CLOCK_LAST_COL : SUMMARY_LAST_COL;
int r = writeHeaderRow(sheet, labels, styles, sequenceOnLeft);
sheet.createFreezePane(0, 1);
sheet.setAutoFilter(new CellRangeAddress(0, 0, 0, lastCol));
BigDecimal totalDikou = BigDecimal.ZERO;
BigDecimal totalActual = BigDecimal.ZERO;
int sequence = 0; int sequence = 0;
for (LbDailyUserTradeReport item : orderRowsForDeductionSheet(rows, deductionByUserName)) { for (LbDailyUserTradeReport item : orderRowsForDeductionSheet(exportRows, deductionByUserName, roundValues)) {
boolean isSummaryRow = DATA_TYPE_REPORT_SUM.equals(item.getDataType()); boolean isSummaryRow = DATA_TYPE_REPORT_SUM.equals(item.getDataType());
if (!includeSummaryRow && isSummaryRow) { if (!includeSummaryRow && isSummaryRow) {
continue; continue;
@@ -154,33 +571,31 @@ public final class LbDailyUserTradeReportExportSupport {
Row row = sheet.createRow(r++); Row row = sheet.createRow(r++);
applyRowHeight(row, styles); applyRowHeight(row, styles);
RowStylePair rowStyles = rowStyles(item, r, styles); RowStylePair rowStyles = rowStyles(item, r, styles, roundValues);
// 第1步与总表一致其它列含汇总行均沿用报表原值 // 第1步与总表一致其它列含汇总行均沿用报表原值
long dikouFromReport = roundedInt(item.getDikouAmt()); writeBaseDataCells(row, item, rowStyles, defaultZero(item.getDikouAmt()), sequenceOnLeft, roundValues);
long actualReceiptsPayments = roundedInt(item.getActualReceiptsPayments());
writeBaseDataCells(row, item, rowStyles, dikouFromReport, sequenceOnLeft);
if (isSummaryRow) { if (isSummaryRow) {
// 汇总行:抵扣金额、实际收付 = 上方明细行之和 // 汇总行:抵扣金额、实际收付 = 上方明细行之和
createIntCell(row, dataCol(COL_DIKOU, sequenceOnLeft), totalDikou, rowStyles.numberStyle); createNumericCell(row, dataCol(COL_DIKOU, sequenceOnLeft), totalDikou, rowStyles, roundValues);
createIntCell(row, dataCol(COL_ACTUAL, sequenceOnLeft), totalActual, rowStyles.numberStyle); createNumericCell(row, dataCol(COL_ACTUAL, sequenceOnLeft), totalActual, rowStyles, roundValues);
} else { } else {
if (sequenceOnLeft) { if (sequenceOnLeft) {
sequence++; sequence++;
createIntCell(row, COL_SEQUENCE_LEFT, sequence, rowStyles.numberStyle); createIntCell(row, COL_SEQUENCE_LEFT, sequence, rowStyles.sequenceStyle);
} }
// 第2步按昵称 + 报表日匹配 lb_deduction_amount覆盖抵扣金额列 // 第2步按昵称 + 报表日匹配 lb_deduction_amount覆盖抵扣金额列
long dikouFromDb = roundedInt(lookupDeductionAmt(item.getNickname(), deductionByUserName)); BigDecimal dikouFromDb = lookupDeductionAmt(item.getNickname(), deductionByUserName);
createIntCell(row, dataCol(COL_DIKOU, sequenceOnLeft), dikouFromDb, rowStyles.numberStyle); createNumericCell(row, dataCol(COL_DIKOU, sequenceOnLeft), dikouFromDb, rowStyles, roundValues);
// 第3步抵扣金额 + 原实际收付,覆盖「实际收付」列 // 第3步抵扣金额 + 原实际收付,覆盖「实际收付」列
long dikouPlusActual = computeActualReceiptsForDeduction(item, deductionByUserName); BigDecimal dikouPlusActual = computeActualReceiptsForDeduction(item, deductionByUserName, roundValues);
createIntCell(row, dataCol(COL_ACTUAL, sequenceOnLeft), dikouPlusActual, rowStyles.numberStyle); createNumericCell(row, dataCol(COL_ACTUAL, sequenceOnLeft), dikouPlusActual, rowStyles, roundValues);
totalDikou += dikouFromDb; totalDikou = totalDikou.add(dikouFromDb);
totalActual += dikouPlusActual; totalActual = totalActual.add(dikouPlusActual);
} }
} }
@@ -188,34 +603,40 @@ public final class LbDailyUserTradeReportExportSupport {
autoSizeColumns(sheet, lastCol); autoSizeColumns(sheet, lastCol);
} }
/** 抵扣表:明细按计算后的实际收付倒序,汇总行保持在最后。 */ /** 抵扣表:明细按计算后的实际收付倒序,汇总行保持在最后exportRows 已保证末尾有汇总行)。 */
private static List<LbDailyUserTradeReport> orderRowsForDeductionSheet( private static List<LbDailyUserTradeReport> orderRowsForDeductionSheet(
List<LbDailyUserTradeReport> rows, List<LbDailyUserTradeReport> exportRows,
Map<String, BigDecimal> deductionByUserName) { Map<String, BigDecimal> deductionByUserName,
boolean roundValues) {
List<LbDailyUserTradeReport> details = new ArrayList<>(); List<LbDailyUserTradeReport> details = new ArrayList<>();
List<LbDailyUserTradeReport> summaries = new ArrayList<>(); LbDailyUserTradeReport summaryRow = null;
for (LbDailyUserTradeReport row : rows) { for (LbDailyUserTradeReport row : exportRows) {
if (DATA_TYPE_REPORT_SUM.equals(row.getDataType())) { if (DATA_TYPE_REPORT_SUM.equals(row.getDataType())) {
summaries.add(row); summaryRow = row;
} else { } else {
details.add(row); details.add(row);
} }
} }
details.sort((a, b) -> Long.compare( details.sort((a, b) -> computeActualReceiptsForDeduction(b, deductionByUserName, roundValues)
computeActualReceiptsForDeduction(b, deductionByUserName), .compareTo(computeActualReceiptsForDeduction(a, deductionByUserName, roundValues)));
computeActualReceiptsForDeduction(a, deductionByUserName))); List<LbDailyUserTradeReport> ordered = new ArrayList<>(details.size() + (summaryRow == null ? 0 : 1));
List<LbDailyUserTradeReport> ordered = new ArrayList<>(details.size() + summaries.size());
ordered.addAll(details); ordered.addAll(details);
ordered.addAll(summaries); if (summaryRow != null) {
ordered.add(summaryRow);
}
return ordered; return ordered;
} }
private static long computeActualReceiptsForDeduction( private static BigDecimal computeActualReceiptsForDeduction(
LbDailyUserTradeReport item, LbDailyUserTradeReport item,
Map<String, BigDecimal> deductionByUserName) { Map<String, BigDecimal> deductionByUserName,
long dikouFromDb = roundedInt(lookupDeductionAmt(item.getNickname(), deductionByUserName)); boolean roundValues) {
long actualReceiptsPayments = roundedInt(item.getActualReceiptsPayments()); BigDecimal dikou = lookupDeductionAmt(item.getNickname(), deductionByUserName);
return dikouFromDb + actualReceiptsPayments; BigDecimal actual = defaultZero(item.getActualReceiptsPayments());
if (roundValues) {
return roundHalfUp(dikou).add(roundHalfUp(actual));
}
return dikou.add(actual);
} }
private static int dataCol(int col, boolean sequenceOnLeft) { private static int dataCol(int col, boolean sequenceOnLeft) {
@@ -248,28 +669,39 @@ public final class LbDailyUserTradeReportExportSupport {
Row row, Row row,
LbDailyUserTradeReport item, LbDailyUserTradeReport item,
RowStylePair rowStyles, RowStylePair rowStyles,
long dikouAmt, BigDecimal dikouAmt,
boolean sequenceOnLeft) { boolean sequenceOnLeft,
boolean roundValues) {
createTextCell( createTextCell(
row, row,
dataCol(COL_NICKNAME, sequenceOnLeft), dataCol(COL_NICKNAME, sequenceOnLeft),
item.getNickname() == null ? "" : item.getNickname(), item.getNickname() == null ? "" : item.getNickname(),
rowStyles.textStyle); rowStyles.textStyle);
createIntCell(row, dataCol(COL_YESTODAY_BUY, sequenceOnLeft), roundedInt(item.getYestodayBuyAmt()), rowStyles.numberStyle); createNumericCell(row, dataCol(COL_YESTODAY_BUY, sequenceOnLeft), item.getYestodayBuyAmt(), rowStyles, roundValues);
createIntCell(row, dataCol(COL_DAILY_SELL, sequenceOnLeft), roundedInt(item.getDailySellAmt()), rowStyles.numberStyle); createNumericCell(row, dataCol(COL_DAILY_SELL, sequenceOnLeft), item.getDailySellAmt(), rowStyles, roundValues);
createIntCell(row, dataCol(COL_DAILY_BUY, sequenceOnLeft), roundedInt(item.getDailyBuyAmt()), rowStyles.numberStyle); createNumericCell(row, dataCol(COL_DAILY_BUY, sequenceOnLeft), item.getDailyBuyAmt(), rowStyles, roundValues);
createIntCell(row, dataCol(COL_SERVICE, sequenceOnLeft), roundedInt(item.getServiceAmt()), rowStyles.numberStyle); createNumericCell(row, dataCol(COL_SERVICE, sequenceOnLeft), item.getServiceAmt(), rowStyles, roundValues);
createIntCell(row, dataCol(COL_DIFF, sequenceOnLeft), roundedInt(item.getDiffAmt()), rowStyles.numberStyle); createNumericCell(row, dataCol(COL_DIFF, sequenceOnLeft), item.getDiffAmt(), rowStyles, roundValues);
createIntCell(row, dataCol(COL_ACTUAL, sequenceOnLeft), roundedInt(item.getActualReceiptsPayments()), rowStyles.numberStyle); createNumericCell(row, dataCol(COL_ACTUAL, sequenceOnLeft), item.getActualReceiptsPayments(), rowStyles, roundValues);
createIntCell(row, dataCol(COL_DIKOU, sequenceOnLeft), dikouAmt, rowStyles.numberStyle); createNumericCell(row, dataCol(COL_DIKOU, sequenceOnLeft), dikouAmt, rowStyles, roundValues);
} }
private static RowStylePair rowStyles(LbDailyUserTradeReport item, int rowIndex, SheetStyles styles) { private static RowStylePair rowStyles(LbDailyUserTradeReport item, int rowIndex, SheetStyles styles, boolean roundValues) {
boolean isSummary = DATA_TYPE_REPORT_SUM.equals(item.getDataType()); boolean isSummary = DATA_TYPE_REPORT_SUM.equals(item.getDataType());
boolean zebra = (rowIndex % 2 == 0); boolean zebra = (rowIndex % 2 == 0);
CellStyle textStyle = isSummary ? styles.summaryTextStyle : (zebra ? styles.zebraTextStyle : styles.textStyle); CellStyle textStyle = isSummary ? styles.summaryTextStyle : (zebra ? styles.zebraTextStyle : styles.textStyle);
CellStyle numberStyle = isSummary ? styles.summaryIntStyle : (zebra ? styles.zebraIntStyle : styles.intStyle); CellStyle numberStyle;
return new RowStylePair(textStyle, numberStyle); if (roundValues) {
numberStyle = isSummary
? styles.summaryRoundedAmountStyle
: (zebra ? styles.zebraRoundedAmountStyle : styles.roundedAmountStyle);
} else {
numberStyle = isSummary
? styles.summaryAmountStyle
: (zebra ? styles.zebraAmountStyle : styles.amountStyle);
}
CellStyle sequenceStyle = isSummary ? styles.summarySequenceStyle : (zebra ? styles.zebraSequenceStyle : styles.sequenceStyle);
return new RowStylePair(textStyle, numberStyle, sequenceStyle);
} }
private static BigDecimal lookupDeductionAmt(String nickname, Map<String, BigDecimal> deductionByUserName) { private static BigDecimal lookupDeductionAmt(String nickname, Map<String, BigDecimal> deductionByUserName) {
@@ -317,13 +749,6 @@ public final class LbDailyUserTradeReportExportSupport {
} }
} }
private static long roundedInt(BigDecimal value) {
if (value == null) {
return 0L;
}
return value.setScale(0, RoundingMode.HALF_UP).longValue();
}
private static void createHeaderCell(Row row, int col, String text, CellStyle style) { private static void createHeaderCell(Row row, int col, String text, CellStyle style) {
Cell cell = row.createCell(col); Cell cell = row.createCell(col);
cell.setCellValue(text); cell.setCellValue(text);
@@ -342,6 +767,37 @@ public final class LbDailyUserTradeReportExportSupport {
cell.setCellStyle(style); cell.setCellStyle(style);
} }
private static void createDecimalCell(Row row, int col, BigDecimal value, CellStyle style) {
Cell cell = row.createCell(col);
cell.setCellValue(defaultZero(value).doubleValue());
cell.setCellStyle(style);
}
private static CellStyle paymentActualStyle(int rowIndex, SheetStyles styles) {
return (rowIndex % 2 == 0) ? styles.zebraPaymentActualStyle : styles.paymentActualStyle;
}
private static void createPaymentActualCell(Row row, int col, BigDecimal value, CellStyle style) {
createIntCell(row, col, roundHalfUp(value).longValue(), style);
}
private static void createNumericCell(
Row row,
int col,
BigDecimal value,
RowStylePair rowStyles,
boolean roundValues) {
if (roundValues) {
createIntCell(row, col, roundHalfUp(value).longValue(), rowStyles.numberStyle);
} else {
createDecimalCell(row, col, value, rowStyles.numberStyle);
}
}
private static BigDecimal roundHalfUp(BigDecimal value) {
return defaultZero(value).setScale(0, RoundingMode.HALF_UP);
}
private record DateHeaderLabels(String yestodayBuyLabel, String dailySellLabel, String dailyBuyLabel) { private record DateHeaderLabels(String yestodayBuyLabel, String dailySellLabel, String dailyBuyLabel) {
static DateHeaderLabels of(LocalDate reportDate) { static DateHeaderLabels of(LocalDate reportDate) {
DateTimeFormatter mmdd = DateTimeFormatter.ofPattern("MM-dd"); DateTimeFormatter mmdd = DateTimeFormatter.ofPattern("MM-dd");
@@ -351,7 +807,7 @@ public final class LbDailyUserTradeReportExportSupport {
} }
} }
private record RowStylePair(CellStyle textStyle, CellStyle numberStyle) { private record RowStylePair(CellStyle textStyle, CellStyle numberStyle, CellStyle sequenceStyle) {
} }
private static final class SheetStyles { private static final class SheetStyles {
@@ -359,26 +815,56 @@ public final class LbDailyUserTradeReportExportSupport {
final CellStyle headerStyle; final CellStyle headerStyle;
final CellStyle textStyle; final CellStyle textStyle;
final CellStyle zebraTextStyle; final CellStyle zebraTextStyle;
final CellStyle intStyle; final CellStyle amountStyle;
final CellStyle zebraIntStyle; final CellStyle zebraAmountStyle;
final CellStyle roundedAmountStyle;
final CellStyle zebraRoundedAmountStyle;
final CellStyle paymentActualStyle;
final CellStyle zebraPaymentActualStyle;
final CellStyle paymentActualDecimalStyle;
final CellStyle zebraPaymentActualDecimalStyle;
final CellStyle sequenceStyle;
final CellStyle zebraSequenceStyle;
final CellStyle summaryTextStyle; final CellStyle summaryTextStyle;
final CellStyle summaryIntStyle; final CellStyle summaryAmountStyle;
final CellStyle summaryRoundedAmountStyle;
final CellStyle summarySequenceStyle;
private SheetStyles( private SheetStyles(
CellStyle headerStyle, CellStyle headerStyle,
CellStyle textStyle, CellStyle textStyle,
CellStyle zebraTextStyle, CellStyle zebraTextStyle,
CellStyle intStyle, CellStyle amountStyle,
CellStyle zebraIntStyle, CellStyle zebraAmountStyle,
CellStyle roundedAmountStyle,
CellStyle zebraRoundedAmountStyle,
CellStyle paymentActualStyle,
CellStyle zebraPaymentActualStyle,
CellStyle paymentActualDecimalStyle,
CellStyle zebraPaymentActualDecimalStyle,
CellStyle sequenceStyle,
CellStyle zebraSequenceStyle,
CellStyle summaryTextStyle, CellStyle summaryTextStyle,
CellStyle summaryIntStyle) { CellStyle summaryAmountStyle,
CellStyle summaryRoundedAmountStyle,
CellStyle summarySequenceStyle) {
this.headerStyle = headerStyle; this.headerStyle = headerStyle;
this.textStyle = textStyle; this.textStyle = textStyle;
this.zebraTextStyle = zebraTextStyle; this.zebraTextStyle = zebraTextStyle;
this.intStyle = intStyle; this.amountStyle = amountStyle;
this.zebraIntStyle = zebraIntStyle; this.zebraAmountStyle = zebraAmountStyle;
this.roundedAmountStyle = roundedAmountStyle;
this.zebraRoundedAmountStyle = zebraRoundedAmountStyle;
this.paymentActualStyle = paymentActualStyle;
this.zebraPaymentActualStyle = zebraPaymentActualStyle;
this.paymentActualDecimalStyle = paymentActualDecimalStyle;
this.zebraPaymentActualDecimalStyle = zebraPaymentActualDecimalStyle;
this.sequenceStyle = sequenceStyle;
this.zebraSequenceStyle = zebraSequenceStyle;
this.summaryTextStyle = summaryTextStyle; this.summaryTextStyle = summaryTextStyle;
this.summaryIntStyle = summaryIntStyle; this.summaryAmountStyle = summaryAmountStyle;
this.summaryRoundedAmountStyle = summaryRoundedAmountStyle;
this.summarySequenceStyle = summarySequenceStyle;
} }
static SheetStyles create(Workbook workbook) { static SheetStyles create(Workbook workbook) {
@@ -410,22 +896,58 @@ public final class LbDailyUserTradeReportExportSupport {
zebraTextStyle.cloneStyleFrom(textStyle); zebraTextStyle.cloneStyleFrom(textStyle);
zebraTextStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND); zebraTextStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
CellStyle intStyle = workbook.createCellStyle(); CellStyle amountStyle = workbook.createCellStyle();
intStyle.setAlignment(HorizontalAlignment.RIGHT); amountStyle.setAlignment(HorizontalAlignment.RIGHT);
intStyle.setVerticalAlignment(VerticalAlignment.CENTER); amountStyle.setVerticalAlignment(VerticalAlignment.CENTER);
intStyle.setDataFormat(dataFormat.getFormat("#,##0")); amountStyle.setDataFormat(dataFormat.getFormat("#,##0.##########"));
intStyle.setBorderTop(BorderStyle.THIN); amountStyle.setBorderTop(BorderStyle.THIN);
intStyle.setBorderBottom(BorderStyle.THIN); amountStyle.setBorderBottom(BorderStyle.THIN);
intStyle.setBorderLeft(BorderStyle.THIN); amountStyle.setBorderLeft(BorderStyle.THIN);
intStyle.setBorderRight(BorderStyle.THIN); amountStyle.setBorderRight(BorderStyle.THIN);
CellStyle zebraIntStyle = workbook.createCellStyle(); CellStyle zebraAmountStyle = workbook.createCellStyle();
zebraIntStyle.cloneStyleFrom(intStyle); zebraAmountStyle.cloneStyleFrom(amountStyle);
zebraIntStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND); zebraAmountStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
CellStyle roundedAmountStyle = workbook.createCellStyle();
roundedAmountStyle.cloneStyleFrom(amountStyle);
roundedAmountStyle.setDataFormat(dataFormat.getFormat("#,##0"));
CellStyle zebraRoundedAmountStyle = workbook.createCellStyle();
zebraRoundedAmountStyle.cloneStyleFrom(roundedAmountStyle);
zebraRoundedAmountStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
CellStyle paymentActualStyle = workbook.createCellStyle();
paymentActualStyle.cloneStyleFrom(roundedAmountStyle);
paymentActualStyle.setDataFormat(dataFormat.getFormat("0"));
CellStyle zebraPaymentActualStyle = workbook.createCellStyle();
zebraPaymentActualStyle.cloneStyleFrom(paymentActualStyle);
zebraPaymentActualStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
CellStyle paymentActualDecimalStyle = workbook.createCellStyle();
paymentActualDecimalStyle.cloneStyleFrom(paymentActualStyle);
paymentActualDecimalStyle.setDataFormat(dataFormat.getFormat("0.##########"));
CellStyle zebraPaymentActualDecimalStyle = workbook.createCellStyle();
zebraPaymentActualDecimalStyle.cloneStyleFrom(paymentActualDecimalStyle);
zebraPaymentActualDecimalStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
CellStyle sequenceStyle = workbook.createCellStyle();
sequenceStyle.cloneStyleFrom(amountStyle);
sequenceStyle.setDataFormat(dataFormat.getFormat("#,##0"));
CellStyle zebraSequenceStyle = workbook.createCellStyle();
zebraSequenceStyle.cloneStyleFrom(sequenceStyle);
zebraSequenceStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
XSSFColor zebraFill = new XSSFColor(new Color(242, 244, 248), null); XSSFColor zebraFill = new XSSFColor(new Color(242, 244, 248), null);
((XSSFCellStyle) zebraTextStyle).setFillForegroundColor(zebraFill); ((XSSFCellStyle) zebraTextStyle).setFillForegroundColor(zebraFill);
((XSSFCellStyle) zebraIntStyle).setFillForegroundColor(zebraFill); ((XSSFCellStyle) zebraAmountStyle).setFillForegroundColor(zebraFill);
((XSSFCellStyle) zebraRoundedAmountStyle).setFillForegroundColor(zebraFill);
((XSSFCellStyle) zebraPaymentActualStyle).setFillForegroundColor(zebraFill);
((XSSFCellStyle) zebraPaymentActualDecimalStyle).setFillForegroundColor(zebraFill);
((XSSFCellStyle) zebraSequenceStyle).setFillForegroundColor(zebraFill);
CellStyle summaryTextStyle = workbook.createCellStyle(); CellStyle summaryTextStyle = workbook.createCellStyle();
summaryTextStyle.cloneStyleFrom(textStyle); summaryTextStyle.cloneStyleFrom(textStyle);
@@ -436,15 +958,45 @@ public final class LbDailyUserTradeReportExportSupport {
summaryTextStyle.setFont(summaryFont); summaryTextStyle.setFont(summaryFont);
summaryTextStyle.setBorderTop(BorderStyle.THIN); summaryTextStyle.setBorderTop(BorderStyle.THIN);
CellStyle summaryIntStyle = workbook.createCellStyle(); CellStyle summaryAmountStyle = workbook.createCellStyle();
summaryIntStyle.cloneStyleFrom(intStyle); summaryAmountStyle.cloneStyleFrom(amountStyle);
summaryIntStyle.setFillForegroundColor(IndexedColors.LEMON_CHIFFON.getIndex()); summaryAmountStyle.setFillForegroundColor(IndexedColors.LEMON_CHIFFON.getIndex());
summaryIntStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND); summaryAmountStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
summaryIntStyle.setFont(summaryFont); summaryAmountStyle.setFont(summaryFont);
summaryIntStyle.setBorderTop(BorderStyle.THIN); summaryAmountStyle.setBorderTop(BorderStyle.THIN);
CellStyle summaryRoundedAmountStyle = workbook.createCellStyle();
summaryRoundedAmountStyle.cloneStyleFrom(roundedAmountStyle);
summaryRoundedAmountStyle.setFillForegroundColor(IndexedColors.LEMON_CHIFFON.getIndex());
summaryRoundedAmountStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
summaryRoundedAmountStyle.setFont(summaryFont);
summaryRoundedAmountStyle.setBorderTop(BorderStyle.THIN);
CellStyle summarySequenceStyle = workbook.createCellStyle();
summarySequenceStyle.cloneStyleFrom(sequenceStyle);
summarySequenceStyle.setFillForegroundColor(IndexedColors.LEMON_CHIFFON.getIndex());
summarySequenceStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
summarySequenceStyle.setFont(summaryFont);
summarySequenceStyle.setBorderTop(BorderStyle.THIN);
return new SheetStyles( return new SheetStyles(
headerStyle, textStyle, zebraTextStyle, intStyle, zebraIntStyle, summaryTextStyle, summaryIntStyle); headerStyle,
textStyle,
zebraTextStyle,
amountStyle,
zebraAmountStyle,
roundedAmountStyle,
zebraRoundedAmountStyle,
paymentActualStyle,
zebraPaymentActualStyle,
paymentActualDecimalStyle,
zebraPaymentActualDecimalStyle,
sequenceStyle,
zebraSequenceStyle,
summaryTextStyle,
summaryAmountStyle,
summaryRoundedAmountStyle,
summarySequenceStyle);
} }
} }
} }