diff --git a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/controller/BusProjectController.java b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/controller/BusProjectController.java index c4f9ac84..0b03b326 100644 --- a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/controller/BusProjectController.java +++ b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/controller/BusProjectController.java @@ -215,20 +215,4 @@ public class BusProjectController extends BaseController { return R.ok(projectService.getSafetyDay(id)); } - /** - * 生成模板 - */ - @GetMapping("/generateTemplate") - public R generateTemplate() { - return R.ok(projectService.testExcel()); - } - - /** - * 生成模板 - */ - @GetMapping("/generateTemplate/dp") - public R generateTemplateDP() { - return R.ok(projectService.testExcel()); - } - } diff --git a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/service/IBusProjectService.java b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/service/IBusProjectService.java index 577bc5a2..b2e1fb89 100644 --- a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/service/IBusProjectService.java +++ b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/service/IBusProjectService.java @@ -254,9 +254,4 @@ public interface IBusProjectService extends IService { Boolean updatePosition(ProjectUpdateDto dto); - /** - * 生成项目周报模板 - */ - String testExcel(); - } diff --git a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/service/impl/BusProjectServiceImpl.java b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/service/impl/BusProjectServiceImpl.java index 59b25dd8..ed1342ca 100644 --- a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/service/impl/BusProjectServiceImpl.java +++ b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/project/service/impl/BusProjectServiceImpl.java @@ -7,7 +7,6 @@ import cn.hutool.core.convert.Convert; import cn.hutool.core.util.PhoneUtil; import cn.hutool.core.util.RandomUtil; import cn.hutool.json.JSONUtil; -import com.alibaba.excel.ExcelWriter; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper; import com.baomidou.mybatisplus.core.toolkit.Wrappers; @@ -17,9 +16,6 @@ import com.github.benmanes.caffeine.cache.Cache; import com.github.benmanes.caffeine.cache.Caffeine; import jakarta.annotation.Resource; import lombok.extern.slf4j.Slf4j; -import org.apache.poi.ss.usermodel.*; -import org.apache.poi.ss.util.CellRangeAddress; -import org.apache.poi.xssf.usermodel.XSSFWorkbook; import org.dromara.bigscreen.domain.dto.ProjectUpdateDto; import org.dromara.bigscreen.domain.dto.TanchuangInfoReq; import org.dromara.bigscreen.domain.vo.MilestoneVo; @@ -78,9 +74,6 @@ import org.springframework.scheduling.annotation.Async; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; -import java.io.File; -import java.io.FileOutputStream; -import java.io.IOException; import java.math.BigDecimal; import java.time.LocalDate; import java.util.*; @@ -176,6 +169,7 @@ public class BusProjectServiceImpl extends ServiceImpl WEATHER_CACHE = Caffeine.newBuilder().initialCapacity(1024) .maximumSize(10000L) @@ -1686,925 +1680,6 @@ public class BusProjectServiceImpl extends ServiceImpl 7) { - jkCell.setCellValue(progressData[i][7]); // 第8个元素是下周计划完成数据 - } - jkCell.setCellStyle(contentStyle); - addMergedRegionSafe(sheet, startRow + 1 + i, startRow + 1 + i, 9, 10); - - // 设置L列(备注)- 使用数据数组的第9个元素 - Cell lCell = row.createCell(11); // L列 - if (progressData[i].length > 8) { - lCell.setCellValue(progressData[i][8]); // 第9个元素是备注数据 - } - lCell.setCellStyle(contentStyle); - } - - // 设置合并区域 - try { - // A11:A18合并(序号6) - sheet.addMergedRegion(new CellRangeAddress(startRow, startRow + 7, 0, 0)); - // B11:B18合并(标题) - sheet.addMergedRegion(new CellRangeAddress(startRow, startRow + 7, 1, 1)); - // D12:D15合并(光伏区) - sheet.addMergedRegion(new CellRangeAddress(startRow + 1, startRow + 4, 3, 3)); - // D16:D18合并(线路工程) - sheet.addMergedRegion(new CellRangeAddress(startRow + 5, startRow + 7, 3, 3)); - // L12:L18合并(备注) - sheet.addMergedRegion(new CellRangeAddress(startRow + 1, startRow + 7, 11, 11)); - } catch (IllegalStateException e) { - System.err.println("施工进度表合并区域设置失败: " + e.getMessage()); - } - } - - /** - * 设备材料表格(第19-23行)- 修正数据赋值问题 - */ - private static void createEquipmentMaterialTable(Sheet sheet, Workbook workbook, int startRow, - CellStyle headerStyle, CellStyle contentStyle, - CellStyle tableHeaderStyle) { - // 表头行(第19行) - Row headerRow = sheet.createRow(startRow); - - // A19与A20:A23合并,内容为7 - Cell a19Cell = headerRow.createCell(0); - a19Cell.setCellValue("7"); - a19Cell.setCellStyle(headerStyle); - - // B19与B20:B23合并,内容为:主要设备材料到货情况(列出主要材料即可) - Cell b19Cell = headerRow.createCell(1); - b19Cell.setCellValue("主要设备材料到货情况(列出主要材料即可)"); - b19Cell.setCellStyle(headerStyle); - - // C19内容为:设备材料名称 - Cell c19Cell = headerRow.createCell(2); - c19Cell.setCellValue("设备材料名称"); - c19Cell.setCellStyle(tableHeaderStyle); - - // 其他表头 - 从D列开始 - String[] headers = {"", "单位", "设计数量", "本周到货量", "累计到货量", "累计到货率"}; - for (int i = 0; i < headers.length; i++) { - Cell cell = headerRow.createCell(i + 3); // D列开始 - cell.setCellValue(headers[i]); - cell.setCellStyle(tableHeaderStyle); - } - - // J19:K19合并,内容为:计划到货日期 - Cell j19Cell = headerRow.createCell(9); - j19Cell.setCellValue("计划到货日期"); - j19Cell.setCellStyle(tableHeaderStyle); - addMergedRegionSafe(sheet, startRow, startRow, 9, 10); - - // L19内容为:备注,背景颜色与左边保持一致 - Cell l19Cell = headerRow.createCell(11); - l19Cell.setCellValue("备注"); - l19Cell.setCellStyle(tableHeaderStyle); - - // 数据行 - 从第20行开始(共4行数据)- 修正数据位置和赋值 - String[][] materialData = { - {"檩条、斜撑", "", "根", "131728", "3752", "106745", "81.0%", "", ""}, - {"立杆", "", "根", "133841", "5549", "53372", "39.9%", "", ""}, - {"光伏组件", "", "块", "576548", "25880", "177360", "30.8%", "", ""}, - {"预埋件", "", "套", "164728", "0", "113000", "68.6%", "", ""} - }; - - for (int i = 0; i < materialData.length; i++) { - Row row = sheet.createRow(startRow + 1 + i); - row.setHeightInPoints(20); - - // A列和B列不设置内容(在合并区域中) - - // 从C列开始设置数据(C-I列) - for (int j = 0; j < 7; j++) { // 只设置前7列数据(C-I列) - Cell cell = row.createCell(j + 2); // C列开始 - if (j < materialData[i].length) { - cell.setCellValue(materialData[i][j]); - } - cell.setCellStyle(contentStyle); - } - - // 设置J,K列(计划到货日期)- 使用数据数组的第8个元素 - Cell jkCell = row.createCell(9); // J列 - if (materialData[i].length > 7) { - jkCell.setCellValue(materialData[i][7]); // 第8个元素是计划到货日期数据 - } - jkCell.setCellStyle(contentStyle); - addMergedRegionSafe(sheet, startRow + 1 + i, startRow + 1 + i, 9, 10); - - // 设置L列(备注)- 使用数据数组的第9个元素 - Cell lCell = row.createCell(11); // L列 - if (materialData[i].length > 8) { - lCell.setCellValue(materialData[i][8]); // 第9个元素是备注数据 - } - lCell.setCellStyle(contentStyle); - } - - // 设置合并区域 - try { - // A19:A23合并(序号7) - sheet.addMergedRegion(new CellRangeAddress(startRow, startRow + 4, 0, 0)); - // B19:B23合并(标题) - sheet.addMergedRegion(new CellRangeAddress(startRow, startRow + 4, 1, 1)); - // L20:L23合并(备注) - sheet.addMergedRegion(new CellRangeAddress(startRow + 1, startRow + 4, 11, 11)); - } catch (IllegalStateException e) { - System.err.println("设备材料表合并区域设置失败: " + e.getMessage()); - } - } - - /** - * 修正其他相关模块的行号引用 - */ - private static void createProblemsModule(Sheet sheet, Workbook workbook, int startRow, - CellStyle headerStyle, CellStyle contentStyle) { - Row problemsRow = sheet.createRow(startRow); - - Cell seqCell = problemsRow.createCell(0); - seqCell.setCellValue("8"); - seqCell.setCellStyle(headerStyle); - - Cell titleCell = problemsRow.createCell(1); - titleCell.setCellValue("存在问题及需要协调的事项"); - titleCell.setCellStyle(headerStyle); - - Cell contentCell = problemsRow.createCell(2); - contentCell.setCellValue("1、场区围栏选型问题一直未能确定,班组迟迟不能采购;\n" + - "2、道路青赔费用本月需支付20万、外苏三户村名青赔增加费用30万需支付;\n" + - "3、管理人员工资8、9两月需支付;\n" + - "4、班组应付款项未能及时支付,造成班组材料采购都成问题。"); - contentCell.setCellStyle(contentStyle); - addMergedRegionSafe(sheet, startRow, startRow, 2, 11); - } - - /** - * 照片模块(第26行)- 修正序号 - */ - private static void createPhotoModule(Sheet sheet, Workbook workbook, int startRow, - CellStyle headerStyle, CellStyle contentStyle) { - Row photoRow = sheet.createRow(startRow); - - Cell seqCell = photoRow.createCell(0); - seqCell.setCellValue("9"); - seqCell.setCellStyle(headerStyle); - - Cell titleCell = photoRow.createCell(1); - titleCell.setCellValue("照片"); - titleCell.setCellStyle(headerStyle); - - Cell contentCell = photoRow.createCell(2); - contentCell.setCellStyle(contentStyle); - addMergedRegionSafe(sheet, startRow, startRow, 2, 11); - } - - /** - * 填报审核模块(第26行)- 合并F-L列 - */ - private static void createApprovalModule(Sheet sheet, Workbook workbook, int startRow, - CellStyle headerStyle, CellStyle contentStyle) { - Row approvalRow = sheet.createRow(startRow); - - Cell seqCell = approvalRow.createCell(0); - seqCell.setCellValue("10"); - seqCell.setCellStyle(headerStyle); - - Cell fillLabel = approvalRow.createCell(1); - fillLabel.setCellValue("填报:"); - fillLabel.setCellStyle(headerStyle); - - Cell fillerCell = approvalRow.createCell(2); - fillerCell.setCellValue("伍雪飞"); - fillerCell.setCellStyle(contentStyle); - - Cell checkLabel = approvalRow.createCell(4); - checkLabel.setCellValue("审核:"); - checkLabel.setCellStyle(headerStyle); - - Cell checkerCell = approvalRow.createCell(5); - checkerCell.setCellValue("张等红"); - checkerCell.setCellStyle(contentStyle); - - // 合并F-L列 - addMergedRegionSafe(sheet, startRow, startRow, 5, 11); - - // 为F-L列设置空单元格和边框 - for (int i = 5; i <= 11; i++) { - Cell cell = approvalRow.getCell(i); - if (cell == null) { - cell = approvalRow.createCell(i); - cell.setCellStyle(contentStyle); - } - } - } - - /** - * 创建标题样式(支持自动换行) - */ - private static CellStyle createTitleCellStyle(Workbook workbook) { - CellStyle style = workbook.createCellStyle(); - Font font = workbook.createFont(); - font.setFontName("宋体"); - font.setFontHeightInPoints((short)16); - font.setBold(true); - style.setFont(font); - style.setAlignment(HorizontalAlignment.CENTER); - style.setVerticalAlignment(VerticalAlignment.CENTER); - style.setBorderTop(BorderStyle.THIN); - style.setBorderBottom(BorderStyle.THIN); - style.setBorderLeft(BorderStyle.THIN); - style.setBorderRight(BorderStyle.THIN); - style.setWrapText(true); // 启用自动换行 - return style; - } - - /** - * 创建表头样式(支持自动换行) - */ - private static CellStyle createHeaderCellStyle(Workbook workbook) { - CellStyle style = workbook.createCellStyle(); - Font font = workbook.createFont(); - font.setFontName("宋体"); - font.setFontHeightInPoints((short)11); - font.setBold(true); - style.setFont(font); - style.setAlignment(HorizontalAlignment.CENTER); - style.setVerticalAlignment(VerticalAlignment.CENTER); - style.setBorderTop(BorderStyle.THIN); - style.setBorderBottom(BorderStyle.THIN); - style.setBorderLeft(BorderStyle.THIN); - style.setBorderRight(BorderStyle.THIN); - style.setFillForegroundColor(IndexedColors.GREY_25_PERCENT.getIndex()); - style.setFillPattern(FillPatternType.SOLID_FOREGROUND); - style.setWrapText(true); // 启用自动换行 - return style; - } - - /** - * 创建内容样式(支持自动换行和自动调整行高) - */ - private static CellStyle createContentCellStyle(Workbook workbook) { - CellStyle style = workbook.createCellStyle(); - Font font = workbook.createFont(); - font.setFontName("宋体"); - font.setFontHeightInPoints((short)10); - style.setFont(font); - style.setAlignment(HorizontalAlignment.LEFT); - style.setVerticalAlignment(VerticalAlignment.TOP); // 改为顶部对齐,便于自动换行 - style.setBorderTop(BorderStyle.THIN); - style.setBorderBottom(BorderStyle.THIN); - style.setBorderLeft(BorderStyle.THIN); - style.setBorderRight(BorderStyle.THIN); - style.setWrapText(true); // 启用自动换行 - return style; - } - - /** - * 创建表头样式(支持自动换行) - */ - private static CellStyle createTableHeaderCellStyle(Workbook workbook) { - CellStyle style = workbook.createCellStyle(); - Font font = workbook.createFont(); - font.setFontName("宋体"); - font.setFontHeightInPoints((short)10); - font.setBold(true); - style.setFont(font); - style.setAlignment(HorizontalAlignment.CENTER); - style.setVerticalAlignment(VerticalAlignment.CENTER); - style.setBorderTop(BorderStyle.THIN); - style.setBorderBottom(BorderStyle.THIN); - style.setBorderLeft(BorderStyle.THIN); - style.setBorderRight(BorderStyle.THIN); - style.setFillForegroundColor(IndexedColors.LIGHT_GREEN.getIndex()); - style.setFillPattern(FillPatternType.SOLID_FOREGROUND); - style.setWrapText(true); // 启用自动换行 - return style; - } - - /** - * 安全添加合并区域(修复重叠检测逻辑) - */ - private static void addMergedRegionSafe(Sheet sheet, int firstRow, int lastRow, int firstCol, int lastCol) { - if (firstRow == lastRow && firstCol == lastCol) { - return; - } - - CellRangeAddress newRegion = new CellRangeAddress(firstRow, lastRow, firstCol, lastCol); - - // 检查是否与现有合并区域重叠 - List mergedRegions = sheet.getMergedRegions(); - boolean hasOverlap = false; - - for (CellRangeAddress existingRegion : mergedRegions) { - if (regionsOverlap(newRegion, existingRegion)) { - // 如果是完全相同的区域,跳过(可能是重复设置) - if (newRegion.equals(existingRegion)) { - System.out.println("跳过重复的合并区域: " + newRegion.formatAsString()); - return; - } - System.err.println("跳过重叠的合并区域: " + newRegion.formatAsString() + - " 与 " + existingRegion.formatAsString()); - hasOverlap = true; - break; - } - } - - if (!hasOverlap) { - try { - sheet.addMergedRegion(newRegion); - System.out.println("成功添加合并区域: " + newRegion.formatAsString()); - } catch (IllegalStateException e) { - System.err.println("添加合并区域失败: " + newRegion.formatAsString() + " - " + e.getMessage()); - } - } - } - - /** - * 自动调整行高以适应内容 - */ - private static void autoAdjustRowHeights(Sheet sheet) { - for (int rowNum = 0; rowNum <= sheet.getLastRowNum(); rowNum++) { - Row row = sheet.getRow(rowNum); - if (row != null) { - // 计算该行中所有单元格的最大行数 - int maxLines = 1; - for (int cellNum = 0; cellNum < row.getLastCellNum(); cellNum++) { - Cell cell = row.getCell(cellNum); - if (cell != null && cell.getStringCellValue() != null) { - String cellValue = cell.getStringCellValue(); - // 根据内容长度和列宽估算行数 - int estimatedLines = estimateLineCount(cellValue, sheet.getColumnWidth(cellNum)); - maxLines = Math.max(maxLines, estimatedLines); - } - } - - // 设置行高(每行约15点) - float rowHeight = Math.max(20f, maxLines * 15f); // 最小高度20,根据行数调整 - row.setHeightInPoints(rowHeight); - } - } - } - - /** - * 估算文本在指定列宽下的行数 - */ - private static int estimateLineCount(String text, int columnWidth) { - if (text == null || text.isEmpty()) { - return 1; - } - - // 估算每个字符的宽度(近似值) - double charWidth = 256; // Excel中字符宽度的近似值 - double availableWidth = columnWidth; - - String[] lines = text.split("\n"); - int totalLines = 0; - - for (String line : lines) { - if (line.isEmpty()) { - totalLines++; - continue; - } - - // 估算该行需要的行数 - double lineWidth = line.length() * charWidth; - int linesNeeded = (int) Math.ceil(lineWidth / availableWidth); - totalLines += Math.max(1, linesNeeded); - } - - return Math.max(1, totalLines); - } - - /** - * 创建空单元格样式(带边框) - */ - private static CellStyle createEmptyCellStyle(Workbook workbook) { - CellStyle style = workbook.createCellStyle(); - style.setBorderTop(BorderStyle.THIN); - style.setBorderBottom(BorderStyle.THIN); - style.setBorderLeft(BorderStyle.THIN); - style.setBorderRight(BorderStyle.THIN); - return style; - } - - /** - * 设置关键行的行高(移除固定行高设置,使用自动调整) - */ - private static void setKeyRowHeights(Sheet sheet) { - // 不再设置固定行高,由autoAdjustRowHeights自动调整 - // 只设置最小行高确保基本显示 - for (int i = 0; i <= sheet.getLastRowNum(); i++) { - Row row = sheet.getRow(i); - if (row != null && row.getHeightInPoints() < 20) { - row.setHeightInPoints(20); // 设置最小行高 - } - } - } - - /** - * 检查两个合并区域是否重叠 - */ - private static boolean regionsOverlap(CellRangeAddress region1, CellRangeAddress region2) { - return !(region1.getLastRow() < region2.getFirstRow() || - region1.getFirstRow() > region2.getLastRow() || - region1.getLastColumn() < region2.getFirstColumn() || - region1.getFirstColumn() > region2.getLastColumn()); - } - - /** - * 设置所有小范围的合并区域 - 修正日期合并区域 - */ - private static void setupAllSmallMergeRegions(Sheet sheet) { - // 创建必要的行 - for (int i = 0; i <= 3; i++) { - if (sheet.getRow(i) == null) { - sheet.createRow(i); - } - } - - // 按从小到大的顺序设置合并区域 - try { - // 1. 取消J3:J4和K3:L4合并,改为单独的合并区域 - sheet.addMergedRegion(new CellRangeAddress(2, 3, 9, 9)); // J3:J4合并 - sheet.addMergedRegion(new CellRangeAddress(2, 3, 10, 11)); // K3:L4合并 - System.out.println("设置小合并区域: J3:J4, K3:L4"); - - // 2. 中等范围的合并区域 - sheet.addMergedRegion(new CellRangeAddress(2, 2, 0, 1)); // A3:B3 - sheet.addMergedRegion(new CellRangeAddress(2, 2, 2, 6)); // C3:G3 - System.out.println("设置中等合并区域: A3:B3, C3:G3"); - - // 3. 较大范围的合并区域 - sheet.addMergedRegion(new CellRangeAddress(3, 3, 1, 8)); // B4:I4 - System.out.println("设置大合并区域: B4:I4"); - - } catch (IllegalStateException e) { - System.err.println("小范围合并区域设置失败: " + e.getMessage()); - } - } - - /** - * 确保所有单元格都有边框 - */ - private static void ensureAllCellsHaveBorders(Sheet sheet, Workbook workbook) { - CellStyle borderStyle = createContentCellStyle(workbook); - - // 遍历所有行和列,确保每个单元格都有边框 - for (int rowNum = 0; rowNum <= sheet.getLastRowNum(); rowNum++) { - Row row = sheet.getRow(rowNum); - if (row != null) { - for (int colNum = 0; colNum < 12; colNum++) { - Cell cell = row.getCell(colNum); - if (cell == null) { - cell = row.createCell(colNum); - cell.setCellStyle(borderStyle); - } else if (cell.getCellStyle() == null) { - cell.setCellStyle(borderStyle); - } - } - } - } - } } diff --git a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/controller/HseSafetyWeeklyReportController.java b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/controller/HseSafetyWeeklyReportController.java index 95e5237b..0effa230 100644 --- a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/controller/HseSafetyWeeklyReportController.java +++ b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/controller/HseSafetyWeeklyReportController.java @@ -115,4 +115,13 @@ public class HseSafetyWeeklyReportController extends BaseController { @PathVariable Long id, HttpServletRequest request, HttpServletResponse response) { safetyWeeklyReportService.singleFileUploads(id, request, response); } + + /** + * 生成模板 + */ +// @GetMapping("/generateTemplate") +// public R generateTemplate() { +// return R.ok(safetyWeeklyReportService.testExcel()); +// } + } diff --git a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/HseSafetyWeeklyReport.java b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/HseSafetyWeeklyReport.java index d261ebfc..a38bd98a 100644 --- a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/HseSafetyWeeklyReport.java +++ b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/HseSafetyWeeklyReport.java @@ -54,6 +54,11 @@ public class HseSafetyWeeklyReport extends BaseEntity { */ private String path; + /** + * excel文件ID + */ + private Long excelId; + /** * 备注 */ diff --git a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/dto/safetyweeklyreport/HseSafetyWeeklyReportCreateReq.java b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/dto/safetyweeklyreport/HseSafetyWeeklyReportCreateReq.java index 97dd1dca..7639dca3 100644 --- a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/dto/safetyweeklyreport/HseSafetyWeeklyReportCreateReq.java +++ b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/dto/safetyweeklyreport/HseSafetyWeeklyReportCreateReq.java @@ -41,6 +41,11 @@ public class HseSafetyWeeklyReportCreateReq implements Serializable { */ private String path; + /** + * excel文件ID + */ + private Long excelId; + /** * 备注 */ diff --git a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/vo/safetyweeklyreport/HseSafetyWeeklyReportVo.java b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/vo/safetyweeklyreport/HseSafetyWeeklyReportVo.java index 4cc57035..9e3a03f3 100644 --- a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/vo/safetyweeklyreport/HseSafetyWeeklyReportVo.java +++ b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/domain/vo/safetyweeklyreport/HseSafetyWeeklyReportVo.java @@ -72,6 +72,11 @@ public class HseSafetyWeeklyReportVo implements Serializable { */ private String filePath; + /** + * excel文件ID + */ + private Long excelId; + /** * 文件后缀 */ diff --git a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/service/IHseSafetyWeeklyReportService.java b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/service/IHseSafetyWeeklyReportService.java index 14e3ae43..e6b57bbd 100644 --- a/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/service/IHseSafetyWeeklyReportService.java +++ b/xinnengyuan/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/safety/service/IHseSafetyWeeklyReportService.java @@ -13,6 +13,7 @@ import org.dromara.safety.domain.dto.safetyweeklyreport.HseSafetyWeeklyReportQue import org.dromara.safety.domain.dto.safetyweeklyreport.HseSafetyWeeklyReportUpdateReq; import org.dromara.safety.domain.vo.safetyweeklyreport.HseSafetyWeeklyReportVo; +import java.io.File; import java.util.Collection; import java.util.List; @@ -106,4 +107,10 @@ public interface IHseSafetyWeeklyReportService extends IService 7) { + jkCell.setCellValue(progressData[i][7]); // 第8个元素是下周计划完成数据 + } + jkCell.setCellStyle(contentStyle); + addMergedRegionSafe(sheet, startRow + 1 + i, startRow + 1 + i, 9, 10); + + // 设置L列(备注)- 使用数据数组的第9个元素 + Cell lCell = row.createCell(11); // L列 + if (progressData[i].length > 8) { + lCell.setCellValue(progressData[i][8]); // 第9个元素是备注数据 + } + lCell.setCellStyle(contentStyle); + } + + // 设置合并区域 + try { + // A11:A18合并(序号6) + sheet.addMergedRegion(new CellRangeAddress(startRow, startRow + 7, 0, 0)); + // B11:B18合并(标题) + sheet.addMergedRegion(new CellRangeAddress(startRow, startRow + 7, 1, 1)); + // D12:D15合并(光伏区) + sheet.addMergedRegion(new CellRangeAddress(startRow + 1, startRow + 4, 3, 3)); + // D16:D18合并(线路工程) + sheet.addMergedRegion(new CellRangeAddress(startRow + 5, startRow + 7, 3, 3)); + // L12:L18合并(备注) + sheet.addMergedRegion(new CellRangeAddress(startRow + 1, startRow + 7, 11, 11)); + } catch (IllegalStateException e) { + System.err.println("施工进度表合并区域设置失败: " + e.getMessage()); + } + } + + /** + * 设备材料表格(第19-23行)- 修正数据赋值问题 + */ + private void createEquipmentMaterialTable(Sheet sheet, Workbook workbook, int startRow, + CellStyle headerStyle, CellStyle contentStyle, + CellStyle tableHeaderStyle) { + // 表头行(第19行) + Row headerRow = sheet.createRow(startRow); + + // A19与A20:A23合并,内容为7 + Cell a19Cell = headerRow.createCell(0); + a19Cell.setCellValue("7"); + a19Cell.setCellStyle(headerStyle); + + // B19与B20:B23合并,内容为:主要设备材料到货情况(列出主要材料即可) + Cell b19Cell = headerRow.createCell(1); + b19Cell.setCellValue("主要设备材料到货情况(列出主要材料即可)"); + b19Cell.setCellStyle(headerStyle); + + // C19内容为:设备材料名称 + Cell c19Cell = headerRow.createCell(2); + c19Cell.setCellValue("设备材料名称"); + c19Cell.setCellStyle(tableHeaderStyle); + + // 其他表头 - 从D列开始 + String[] headers = {"", "单位", "设计数量", "本周到货量", "累计到货量", "累计到货率"}; + for (int i = 0; i < headers.length; i++) { + Cell cell = headerRow.createCell(i + 3); // D列开始 + cell.setCellValue(headers[i]); + cell.setCellStyle(tableHeaderStyle); + } + + // J19:K19合并,内容为:计划到货日期 + Cell j19Cell = headerRow.createCell(9); + j19Cell.setCellValue("计划到货日期"); + j19Cell.setCellStyle(tableHeaderStyle); + addMergedRegionSafe(sheet, startRow, startRow, 9, 10); + + // L19内容为:备注,背景颜色与左边保持一致 + Cell l19Cell = headerRow.createCell(11); + l19Cell.setCellValue("备注"); + l19Cell.setCellStyle(tableHeaderStyle); + + // 数据行 - 从第20行开始(共4行数据)- 修正数据位置和赋值 + String[][] materialData = { + {"檩条、斜撑", "", "根", "131728", "3752", "106745", "81.0%", "", ""}, + {"立杆", "", "根", "133841", "5549", "53372", "39.9%", "", ""}, + {"光伏组件", "", "块", "576548", "25880", "177360", "30.8%", "", ""}, + {"预埋件", "", "套", "164728", "0", "113000", "68.6%", "", ""} + }; + + for (int i = 0; i < materialData.length; i++) { + Row row = sheet.createRow(startRow + 1 + i); + row.setHeightInPoints(20); + + // A列和B列不设置内容(在合并区域中) + + // 从C列开始设置数据(C-I列) + for (int j = 0; j < 7; j++) { // 只设置前7列数据(C-I列) + Cell cell = row.createCell(j + 2); // C列开始 + if (j < materialData[i].length) { + cell.setCellValue(materialData[i][j]); + } + cell.setCellStyle(contentStyle); + } + + // 设置J,K列(计划到货日期)- 使用数据数组的第8个元素 + Cell jkCell = row.createCell(9); // J列 + if (materialData[i].length > 7) { + jkCell.setCellValue(materialData[i][7]); // 第8个元素是计划到货日期数据 + } + jkCell.setCellStyle(contentStyle); + addMergedRegionSafe(sheet, startRow + 1 + i, startRow + 1 + i, 9, 10); + + // 设置L列(备注)- 使用数据数组的第9个元素 + Cell lCell = row.createCell(11); // L列 + if (materialData[i].length > 8) { + lCell.setCellValue(materialData[i][8]); // 第9个元素是备注数据 + } + lCell.setCellStyle(contentStyle); + } + + // 设置合并区域 + try { + // A19:A23合并(序号7) + sheet.addMergedRegion(new CellRangeAddress(startRow, startRow + 4, 0, 0)); + // B19:B23合并(标题) + sheet.addMergedRegion(new CellRangeAddress(startRow, startRow + 4, 1, 1)); + // L20:L23合并(备注) + sheet.addMergedRegion(new CellRangeAddress(startRow + 1, startRow + 4, 11, 11)); + } catch (IllegalStateException e) { + System.err.println("设备材料表合并区域设置失败: " + e.getMessage()); + } + } + + /** + * 修正其他相关模块的行号引用 + */ + private void createProblemsModule(Sheet sheet, Workbook workbook, int startRow, + CellStyle headerStyle, CellStyle contentStyle) { + Row problemsRow = sheet.createRow(startRow); + + Cell seqCell = problemsRow.createCell(0); + seqCell.setCellValue("8"); + seqCell.setCellStyle(headerStyle); + + Cell titleCell = problemsRow.createCell(1); + titleCell.setCellValue("存在问题及需要协调的事项"); + titleCell.setCellStyle(headerStyle); + + Cell contentCell = problemsRow.createCell(2); + contentCell.setCellValue("1、场区围栏选型问题一直未能确定,班组迟迟不能采购;\n" + + "2、道路青赔费用本月需支付20万、外苏三户村名青赔增加费用30万需支付;\n" + + "3、管理人员工资8、9两月需支付;\n" + + "4、班组应付款项未能及时支付,造成班组材料采购都成问题。"); + contentCell.setCellStyle(contentStyle); + addMergedRegionSafe(sheet, startRow, startRow, 2, 11); + } + + /** + * 照片模块(第26行)- 修正序号 + */ + private void createPhotoModule(Sheet sheet, Workbook workbook, int startRow, + CellStyle headerStyle, CellStyle contentStyle) { + Row photoRow = sheet.createRow(startRow); + + Cell seqCell = photoRow.createCell(0); + seqCell.setCellValue("9"); + seqCell.setCellStyle(headerStyle); + + Cell titleCell = photoRow.createCell(1); + titleCell.setCellValue("照片"); + titleCell.setCellStyle(headerStyle); + + Cell contentCell = photoRow.createCell(2); + contentCell.setCellStyle(contentStyle); + addMergedRegionSafe(sheet, startRow, startRow, 2, 11); + } + + /** + * 填报审核模块(第26行)- 合并F-L列 + */ + private void createApprovalModule(Sheet sheet, Workbook workbook, int startRow, + CellStyle headerStyle, CellStyle contentStyle) { + Row approvalRow = sheet.createRow(startRow); + + Cell seqCell = approvalRow.createCell(0); + seqCell.setCellValue("10"); + seqCell.setCellStyle(headerStyle); + + Cell fillLabel = approvalRow.createCell(1); + fillLabel.setCellValue("填报:"); + fillLabel.setCellStyle(headerStyle); + + Cell fillerCell = approvalRow.createCell(2); + fillerCell.setCellValue("XXX"); + fillerCell.setCellStyle(contentStyle); + + Cell checkLabel = approvalRow.createCell(4); + checkLabel.setCellValue("审核:"); + checkLabel.setCellStyle(headerStyle); + + Cell checkerCell = approvalRow.createCell(5); + checkerCell.setCellValue("XXX"); + checkerCell.setCellStyle(contentStyle); + + // 合并F-L列 + addMergedRegionSafe(sheet, startRow, startRow, 5, 11); + + // 为F-L列设置空单元格和边框 + for (int i = 5; i <= 11; i++) { + Cell cell = approvalRow.getCell(i); + if (cell == null) { + cell = approvalRow.createCell(i); + cell.setCellStyle(contentStyle); + } + } + } + + /** + * 创建标题样式(支持自动换行) + */ + private CellStyle createTitleCellStyle(Workbook workbook) { + CellStyle style = workbook.createCellStyle(); + Font font = workbook.createFont(); + font.setFontName("宋体"); + font.setFontHeightInPoints((short)16); + font.setBold(true); + style.setFont(font); + style.setAlignment(HorizontalAlignment.CENTER); + style.setVerticalAlignment(VerticalAlignment.CENTER); + style.setBorderTop(BorderStyle.THIN); + style.setBorderBottom(BorderStyle.THIN); + style.setBorderLeft(BorderStyle.THIN); + style.setBorderRight(BorderStyle.THIN); + style.setWrapText(true); // 启用自动换行 + return style; + } + + /** + * 创建表头样式(支持自动换行) + */ + private CellStyle createHeaderCellStyle(Workbook workbook) { + CellStyle style = workbook.createCellStyle(); + Font font = workbook.createFont(); + font.setFontName("宋体"); + font.setFontHeightInPoints((short)11); + font.setBold(true); + style.setFont(font); + style.setAlignment(HorizontalAlignment.CENTER); + style.setVerticalAlignment(VerticalAlignment.CENTER); + style.setBorderTop(BorderStyle.THIN); + style.setBorderBottom(BorderStyle.THIN); + style.setBorderLeft(BorderStyle.THIN); + style.setBorderRight(BorderStyle.THIN); + style.setFillForegroundColor(IndexedColors.GREY_25_PERCENT.getIndex()); + style.setFillPattern(FillPatternType.SOLID_FOREGROUND); + style.setWrapText(true); // 启用自动换行 + return style; + } + + /** + * 创建内容样式(支持自动换行和自动调整行高) + */ + private CellStyle createContentCellStyle(Workbook workbook) { + CellStyle style = workbook.createCellStyle(); + Font font = workbook.createFont(); + font.setFontName("宋体"); + font.setFontHeightInPoints((short)10); + style.setFont(font); + style.setAlignment(HorizontalAlignment.LEFT); + style.setVerticalAlignment(VerticalAlignment.TOP); // 改为顶部对齐,便于自动换行 + style.setBorderTop(BorderStyle.THIN); + style.setBorderBottom(BorderStyle.THIN); + style.setBorderLeft(BorderStyle.THIN); + style.setBorderRight(BorderStyle.THIN); + style.setWrapText(true); // 启用自动换行 + return style; + } + + /** + * 创建表头样式(支持自动换行) + */ + private CellStyle createTableHeaderCellStyle(Workbook workbook) { + CellStyle style = workbook.createCellStyle(); + Font font = workbook.createFont(); + font.setFontName("宋体"); + font.setFontHeightInPoints((short)10); + font.setBold(true); + style.setFont(font); + style.setAlignment(HorizontalAlignment.CENTER); + style.setVerticalAlignment(VerticalAlignment.CENTER); + style.setBorderTop(BorderStyle.THIN); + style.setBorderBottom(BorderStyle.THIN); + style.setBorderLeft(BorderStyle.THIN); + style.setBorderRight(BorderStyle.THIN); + style.setFillForegroundColor(IndexedColors.LIGHT_GREEN.getIndex()); + style.setFillPattern(FillPatternType.SOLID_FOREGROUND); + style.setWrapText(true); // 启用自动换行 + return style; + } + + /** + * 安全添加合并区域(修复重叠检测逻辑) + */ + private void addMergedRegionSafe(Sheet sheet, int firstRow, int lastRow, int firstCol, int lastCol) { + if (firstRow == lastRow && firstCol == lastCol) { + return; + } + + CellRangeAddress newRegion = new CellRangeAddress(firstRow, lastRow, firstCol, lastCol); + + // 检查是否与现有合并区域重叠 + List mergedRegions = sheet.getMergedRegions(); + boolean hasOverlap = false; + + for (CellRangeAddress existingRegion : mergedRegions) { + if (regionsOverlap(newRegion, existingRegion)) { + // 如果是完全相同的区域,跳过(可能是重复设置) + if (newRegion.equals(existingRegion)) { + System.out.println("跳过重复的合并区域: " + newRegion.formatAsString()); + return; + } + System.err.println("跳过重叠的合并区域: " + newRegion.formatAsString() + + " 与 " + existingRegion.formatAsString()); + hasOverlap = true; + break; + } + } + + if (!hasOverlap) { + try { + sheet.addMergedRegion(newRegion); + System.out.println("成功添加合并区域: " + newRegion.formatAsString()); + } catch (IllegalStateException e) { + System.err.println("添加合并区域失败: " + newRegion.formatAsString() + " - " + e.getMessage()); + } + } + } + + /** + * 自动调整行高以适应内容 + */ + private void autoAdjustRowHeights(Sheet sheet) { + for (int rowNum = 0; rowNum <= sheet.getLastRowNum(); rowNum++) { + Row row = sheet.getRow(rowNum); + if (row != null) { + // 计算该行中所有单元格的最大行数 + int maxLines = 1; + for (int cellNum = 0; cellNum < row.getLastCellNum(); cellNum++) { + Cell cell = row.getCell(cellNum); + if (cell != null) { + String cellValue = getCellValueAsString(cell); + if (cellValue != null && !cellValue.isEmpty()) { + // 根据内容长度和列宽估算行数 + int estimatedLines = estimateLineCount(cellValue, sheet.getColumnWidth(cellNum)); + maxLines = Math.max(maxLines, estimatedLines); + } + } + } + + // 设置行高(每行约15点) + float rowHeight = Math.max(20f, maxLines * 15f); // 最小高度20,根据行数调整 + row.setHeightInPoints(rowHeight); + } + } + } + + /** + * 估算文本在指定列宽下的行数 + */ + private int estimateLineCount(String text, int columnWidth) { + if (text == null || text.isEmpty()) { + return 1; + } + + // 估算每个字符的宽度(近似值) + double charWidth = 256; // Excel中字符宽度的近似值 + double availableWidth = columnWidth; + + String[] lines = text.split("\n"); + int totalLines = 0; + + for (String line : lines) { + if (line.isEmpty()) { + totalLines++; + continue; + } + + // 估算该行需要的行数 + double lineWidth = line.length() * charWidth; + int linesNeeded = (int) Math.ceil(lineWidth / availableWidth); + totalLines += Math.max(1, linesNeeded); + } + + return Math.max(1, totalLines); + } + + /** + * 创建空单元格样式(带边框) + */ + private CellStyle createEmptyCellStyle(Workbook workbook) { + CellStyle style = workbook.createCellStyle(); + style.setBorderTop(BorderStyle.THIN); + style.setBorderBottom(BorderStyle.THIN); + style.setBorderLeft(BorderStyle.THIN); + style.setBorderRight(BorderStyle.THIN); + return style; + } + + /** + * 设置关键行的行高(移除固定行高设置,使用自动调整) + */ + private static void setKeyRowHeights(Sheet sheet) { + // 不再设置固定行高,由autoAdjustRowHeights自动调整 + // 只设置最小行高确保基本显示 + for (int i = 0; i <= sheet.getLastRowNum(); i++) { + Row row = sheet.getRow(i); + if (row != null && row.getHeightInPoints() < 20) { + row.setHeightInPoints(20); // 设置最小行高 + } + } + } + + /** + * 检查两个合并区域是否重叠 + */ + private boolean regionsOverlap(CellRangeAddress region1, CellRangeAddress region2) { + return !(region1.getLastRow() < region2.getFirstRow() || + region1.getFirstRow() > region2.getLastRow() || + region1.getLastColumn() < region2.getFirstColumn() || + region1.getFirstColumn() > region2.getLastColumn()); + } + + /** + * 设置所有小范围的合并区域 - 修正日期合并区域 + */ + private void setupAllSmallMergeRegions(Sheet sheet) { + // 创建必要的行 + for (int i = 0; i <= 3; i++) { + if (sheet.getRow(i) == null) { + sheet.createRow(i); + } + } + + // 按从小到大的顺序设置合并区域 + try { + // 1. 取消J3:J4和K3:L4合并,改为单独的合并区域 + sheet.addMergedRegion(new CellRangeAddress(2, 3, 9, 9)); // J3:J4合并 + sheet.addMergedRegion(new CellRangeAddress(2, 3, 10, 11)); // K3:L4合并 + System.out.println("设置小合并区域: J3:J4, K3:L4"); + + // 2. 中等范围的合并区域 + sheet.addMergedRegion(new CellRangeAddress(2, 2, 0, 1)); // A3:B3 + sheet.addMergedRegion(new CellRangeAddress(2, 2, 2, 6)); // C3:G3 + System.out.println("设置中等合并区域: A3:B3, C3:G3"); + + // 3. 较大范围的合并区域 + sheet.addMergedRegion(new CellRangeAddress(3, 3, 1, 8)); // B4:I4 + System.out.println("设置大合并区域: B4:I4"); + + } catch (IllegalStateException e) { + System.err.println("小范围合并区域设置失败: " + e.getMessage()); + } + } + + /** + * 确保所有单元格都有边框 + */ + private void ensureAllCellsHaveBorders(Sheet sheet, Workbook workbook) { + CellStyle borderStyle = createContentCellStyle(workbook); + + // 遍历所有行和列,确保每个单元格都有边框 + for (int rowNum = 0; rowNum <= sheet.getLastRowNum(); rowNum++) { + Row row = sheet.getRow(rowNum); + if (row != null) { + for (int colNum = 0; colNum < 12; colNum++) { + Cell cell = row.getCell(colNum); + if (cell == null) { + cell = row.createCell(colNum); + cell.setCellStyle(borderStyle); + } else if (cell.getCellStyle() == null) { + cell.setCellStyle(borderStyle); + } + } + } + } + } + + /** + * 安全获取单元格的字符串值 + */ + private String getCellValueAsString(Cell cell) { + if (cell == null) { + return ""; + } + + switch (cell.getCellType()) { + case STRING: + return cell.getStringCellValue(); + case NUMERIC: + if (org.apache.poi.ss.usermodel.DateUtil.isCellDateFormatted(cell)) { + return cell.getDateCellValue().toString(); + } else { + // 对于数值,转换为字符串(避免科学计数法) + double numericValue = cell.getNumericCellValue(); + if (numericValue == Math.floor(numericValue)) { + // 如果是整数 + return String.valueOf((long) numericValue); + } else { + // 如果是小数,保留2位 + return String.format("%.2f", numericValue); + } + } + case BOOLEAN: + return String.valueOf(cell.getBooleanCellValue()); + case FORMULA: + try { + return cell.getStringCellValue(); + } catch (Exception e) { + try { + return String.valueOf(cell.getNumericCellValue()); + } catch (Exception ex) { + return cell.getCellFormula(); + } + } + case BLANK: + return ""; + default: + return ""; + } + } + }