package com.ruoyi.project.pssr.controller; import com.deepoove.poi.XWPFTemplate; import com.deepoove.poi.data.*; import com.deepoove.poi.data.style.Style; import com.deepoove.poi.data.style.TableStyle; import com.ruoyi.common.utils.DateUtils; import com.ruoyi.common.utils.file.FileUploadUtils; import com.ruoyi.common.utils.file.FileUtils; import com.ruoyi.framework.aspectj.lang.annotation.Log; import com.ruoyi.framework.aspectj.lang.enums.BusinessType; import com.ruoyi.framework.config.RuoYiConfig; import com.ruoyi.framework.web.controller.BaseController; import com.ruoyi.framework.web.domain.AjaxResult; import com.ruoyi.framework.web.page.TableDataInfo; import com.ruoyi.project.officeConvert.OfficeConvertController; import com.ruoyi.project.pssr.domain.TPssrAboveall; import com.ruoyi.project.pssr.domain.TPssrApprove; import com.ruoyi.project.pssr.domain.TPssrSubcontent; import com.ruoyi.project.pssr.mapper.TPssrSubcontentMapper; import com.ruoyi.project.pssr.service.ITPssrAboveallService; import com.ruoyi.project.pssr.service.ITPssrApproveService; import com.ruoyi.project.pssr.service.ITPssrSubcontentService; import com.ruoyi.project.system.domain.SysUser; import com.ruoyi.project.system.service.impl.SysUserServiceImpl; import io.jsonwebtoken.lang.Assert; import org.activiti.engine.HistoryService; import org.activiti.engine.RuntimeService; import org.activiti.engine.TaskService; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.security.access.prepost.PreAuthorize; import org.springframework.web.bind.annotation.*; import javax.annotation.Resource; import java.io.File; import java.io.IOException; import java.io.InputStream; import java.time.LocalDateTime; import java.time.format.DateTimeFormatter; import java.util.HashMap; import java.util.List; import java.util.Map; /** * 开车条件确认Controller * * @author ssy * @date 2024-09-18 */ @RestController @RequestMapping("/pssr/subcontent") public class TPssrSubcontentController extends BaseController { @Resource private TPssrSubcontentMapper tPssrSubcontentMapper; @Autowired private ITPssrSubcontentService tPssrSubcontentService; @Autowired private ITPssrAboveallService tPssrAboveallService; @Autowired private ITPssrApproveService tPssrApproveService; @Autowired private SysUserServiceImpl sysUserService; @Autowired private TPssrApproveController tPssrApproveController; @Autowired private RuntimeService runtimeService; @Autowired private HistoryService historyService; @Autowired private TaskService taskService; @Resource private OfficeConvertController officeConvertController; /** * 查询开车条件确认列表 */ @PreAuthorize("@ss.hasPermi('pssr:subcontent:list')") @GetMapping("/list") public TableDataInfo list(TPssrSubcontent tPssrSubcontent) { if (tPssrSubcontent.getTaskType() != null && tPssrSubcontent.getTaskType() == 1) { Long userId = getUserId(); TPssrAboveall aboveall = tPssrAboveallService.selectTPssrAboveallById(tPssrSubcontent.getAboveallId()); if (userId.equals(aboveall.getPlantMgr())) { tPssrSubcontent.setDeptUnit("Production"); } else if (userId.equals(aboveall.getCtmMgr())) { tPssrSubcontent.setDeptUnit("CTM"); } else if (userId.equals(aboveall.getCtaMgr())) { tPssrSubcontent.setDeptUnit("CTA"); } } startPage(); List list = tPssrSubcontentService.selectTPssrSubcontentList(tPssrSubcontent); return getDataTable(list); } /** * 导出开车条件确认列表 */ @PreAuthorize("@ss.hasPermi('pssr:subcontent:export')") @Log(title = "开车条件确认", businessType = BusinessType.EXPORT) @GetMapping("/export") public AjaxResult export(TPssrSubcontent tPssrSubcontent) throws IOException { List list = tPssrSubcontentService.selectTPssrSubcontentList(tPssrSubcontent); // ExcelUtil util = new ExcelUtil(TPssrSubcontent.class); // return util.exportExcel(list, "subcontent"); //渲染文本 Map params = getWordData(list, tPssrSubcontent.getAboveallId()); // 模板路径 String templatePath = "static/word/pssr/pssrConfirm.docx"; // 生成word的路径 String fileDir = RuoYiConfig.getProfile() + "/" + "pssr"; // 生成word的文件名称 String time = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd_HH-mm-ss")); String fileName = time + tPssrSubcontent.getAboveallId() + "_" + DateUtils.getDate() + ".docx"; String wordPath = createWord(templatePath, fileDir, fileName, params, "pssr"); return AjaxResult.success(officeConvertController.wordTransPdf(wordPath)); } public Map getWordData(List list, Long aboveallId) { TPssrApprove approve = null; TPssrAboveall aboveall = tPssrAboveallService.selectTPssrAboveallById(aboveallId); Map params = new HashMap<>(); TableRenderData tableRenderData = new TableRenderData(); TableStyle tableStyle = new TableStyle(); tableStyle.setWidth("100%"); tableStyle.setColWidths(new int[]{10, 13, 47, 10, 10, 10}); tableRenderData.setTableStyle(tableStyle); // 创建表头行 RowRenderData row1 = Rows.of("部门", "项目", "内容", "确认人", "确认时间", "备注").center().textBold().rowExactHeight(1.1f).create(); tableRenderData.addRow(row1); int plant = 0, ctm = 0, cta = 0, count = 1; PictureRenderData plantMgr = null; for (int i = 0; i < list.size(); i++) { TPssrSubcontent subcontent = list.get(i); // 获取审批信息 if (approve == null) { approve = tPssrApproveService.selectTPssrApproveByAboveallId(subcontent.getAboveallId()); } // 创建数据行 RowRenderData row = Rows.of(subcontent.getDeptUnit(), subcontent.getItem(), subcontent.getContent(), subcontent.getApproveStatus() == 2 ? "" : "", // 如果需要确认人签名图片,这里空着 DateUtils.dateTime(subcontent.getConfirmationDate()), subcontent.getRemarks()).verticalCenter().rowExactHeight(1.1f).create(); // 如果确认状态为2,插入确认人签名图片 if (subcontent.getApproveStatus() == 2) { SysUser sysUser = sysUserService.selectUserById(Long.valueOf(subcontent.getConfirm())); if (sysUser != null) { row.getCells().set(3, new CellRenderData().addParagraph(new ParagraphRenderData().addPicture(Pictures.ofLocal(FileUtils.fileName(sysUser.getSignUrl())).size(120, 40).create()))); } } tableRenderData.addRow(row); // 判断所属部门是否相同,记录索引 if (subcontent.getDeptUnit().equals("Production")) plant = count; if (subcontent.getDeptUnit().equals("CTM")) ctm = count; if (subcontent.getDeptUnit().equals("CTA")) cta = count; // 判断是否为最后一条或部门是否不相同 if (i < list.size() - 1 && subcontent.getDeptUnit().equals(list.get(i + 1).getDeptUnit())) { count++; } else { count++; //根据当前数据所属部门添加经理审批行 RowRenderData signRow = Rows.of("", "装置经理确认: 日期:", "", "", "", "").verticalCenter().textBold().rowExactHeight(1.1f).create(); if (subcontent.getDeptUnit().equals("Production")) { plant = count; signRow = Rows.of("", "装置经理确认: 日期:", "", "", "", "").verticalCenter().textBold().rowExactHeight(1.1f).create(); } if (subcontent.getDeptUnit().equals("CTM")) { ctm = count + 1; signRow = Rows.of("", "CTM 经理确认: 日期:", "", "", "", "").verticalCenter().textBold().rowExactHeight(1.1f).create(); } if (subcontent.getDeptUnit().equals("CTA")) { if (ctm == 0) { cta = count + 1; } else { cta = count + 2; } signRow = Rows.of("", "CTA 经理确认: 日期:", "", "", "", "").verticalCenter().textBold().rowExactHeight(1.1f).create(); } // 添加经理审批签字数据 if (approve != null) { SysUser sysUser = null; //根据当前所属部门查询部门经理 if (subcontent.getDeptUnit().equals("Production")) { sysUser = sysUserService.selectUserById(Long.valueOf(aboveall.getPlantMgr())); plantMgr = Pictures.ofLocal(FileUtils.fileName(sysUser.getSignUrl())).size(110, 30).create(); } if (subcontent.getDeptUnit().equals("CTM")) { sysUser = sysUserService.selectUserById(Long.valueOf(aboveall.getCtmMgr())); } if (subcontent.getDeptUnit().equals("CTA")) { sysUser = sysUserService.selectUserById(Long.valueOf(aboveall.getCtaMgr())); } if (sysUser != null) { //经理签字图片 PictureRenderData mgr = Pictures.ofLocal(FileUtils.fileName(sysUser.getSignUrl())).size(110, 30).create(); //空数据列,为了后面合并 TextRenderData text = Texts.of("").create(); CellRenderData cell = new CellRenderData(); cell.addParagraph(new ParagraphRenderData().addText(text)); //数据列,该列内容为经理签字和日期 CellRenderData cell2 = new CellRenderData(); if (subcontent.getDeptUnit().equals("Production")) cell2.addParagraph(new ParagraphRenderData().addText(Texts.of("装置经理确认:").create()).addPicture(mgr).addText(" 日期:" + DateUtils.dateTime(aboveall.getConfirmationDate()))); if (subcontent.getDeptUnit().equals("CTM")) cell2.addParagraph(new ParagraphRenderData().addText(Texts.of("CTM 经理确认:").create()).addPicture(mgr).addText(" 日期:" + DateUtils.dateTime(aboveall.getConfirmationDate()))); if (subcontent.getDeptUnit().equals("CTA")) cell2.addParagraph(new ParagraphRenderData().addText(Texts.of("CTA 经理确认:").create()).addPicture(mgr).addText(" 日期:" + DateUtils.dateTime(aboveall.getConfirmationDate()))); signRow = Rows.of(cell, cell2, cell, cell, cell, cell).verticalCenter().textBold().rowExactHeight(1.1f).create(); } } tableRenderData.addRow(signRow); } } // 设置第一列加粗样式 Style boldStyle = new Style(); boldStyle.setBold(true); // 遍历每一行,将第一列的文字加粗 for (RowRenderData row : tableRenderData.getRows()) { // 获取第一列 CellRenderData firstColumn = row.getCells().get(0); // 直接使用现有内容并应用加粗样式 String text = firstColumn.getParagraphs().get(0).getContents().get(0).toString(); // 获取第一列的文本内容 // 使用 Cells.of 创建带加粗样式的新单元格 firstColumn = Cells.of(Texts.of(text).style(boldStyle).create()).center().create(); // 将加粗后的单元格重新放回第一列 row.getCells().set(0, firstColumn); } // 合并第一列和每个部门的最后一行 MergeCellRule.MergeCellRuleBuilder rule = MergeCellRule.builder(); if (plant > 0 && ctm > 0 && cta > 0) { rule.map(MergeCellRule.Grid.of(1, 0), MergeCellRule.Grid.of(plant, 0)) .map(MergeCellRule.Grid.of(plant, 1), MergeCellRule.Grid.of(plant, 5)) .map(MergeCellRule.Grid.of(plant + 1, 0), MergeCellRule.Grid.of(ctm, 0)) .map(MergeCellRule.Grid.of(ctm, 1), MergeCellRule.Grid.of(ctm, 5)) .map(MergeCellRule.Grid.of(ctm + 1, 0), MergeCellRule.Grid.of(cta, 0)) .map(MergeCellRule.Grid.of(cta, 1), MergeCellRule.Grid.of(cta, 5)); } else if (plant > 0 && ctm > 0 && cta == 0) { rule.map(MergeCellRule.Grid.of(1, 0), MergeCellRule.Grid.of(plant, 0)) .map(MergeCellRule.Grid.of(plant, 1), MergeCellRule.Grid.of(plant, 5)) .map(MergeCellRule.Grid.of(plant + 1, 0), MergeCellRule.Grid.of(ctm, 0)) .map(MergeCellRule.Grid.of(ctm, 1), MergeCellRule.Grid.of(ctm, 5)); } else if (plant > 0 && ctm == 0 && cta > 0) { rule.map(MergeCellRule.Grid.of(1, 0), MergeCellRule.Grid.of(plant, 0)) .map(MergeCellRule.Grid.of(plant, 1), MergeCellRule.Grid.of(plant, 5)) .map(MergeCellRule.Grid.of(plant + 1, 0), MergeCellRule.Grid.of(cta, 0)) .map(MergeCellRule.Grid.of(cta, 1), MergeCellRule.Grid.of(cta, 5)); } else if (plant == 0 && ctm > 0 && cta > 0) { rule.map(MergeCellRule.Grid.of(1, 0), MergeCellRule.Grid.of(ctm - 1, 0)) .map(MergeCellRule.Grid.of(ctm - 1, 1), MergeCellRule.Grid.of(ctm - 1, 5)) .map(MergeCellRule.Grid.of(ctm + 1, 0), MergeCellRule.Grid.of(cta, 0)) .map(MergeCellRule.Grid.of(cta, 1), MergeCellRule.Grid.of(cta, 5)); } else if (plant > 0 && ctm == 0 && cta == 0) { rule.map(MergeCellRule.Grid.of(1, 0), MergeCellRule.Grid.of(plant, 0)) .map(MergeCellRule.Grid.of(plant, 1), MergeCellRule.Grid.of(plant, 5)); } else if (plant == 0 && ctm > 0 && cta == 0) { rule.map(MergeCellRule.Grid.of(1, 0), MergeCellRule.Grid.of(ctm - 1, 0)) .map(MergeCellRule.Grid.of(ctm - 1, 1), MergeCellRule.Grid.of(ctm - 1, 5)); } else if (plant == 0 && ctm == 0 && cta > 0) { rule.map(MergeCellRule.Grid.of(1, 0), MergeCellRule.Grid.of(cta - 2, 0)) .map(MergeCellRule.Grid.of(cta - 2, 1), MergeCellRule.Grid.of(cta - 2, 5)); } tableRenderData.setMergeRule(rule.build()); // 准备表格数据和其他参数 params.put("unit", aboveall.getUnit()); params.put("region", aboveall.getRegion()); params.put("subcontent", tableRenderData); params.put("plantMgr", plantMgr); params.put("confirmDate", DateUtils.dateTime(aboveall.getConfirmationDate())); return params; } private String createWord(String templatePath, String fileDir, String fileName, Map paramMap, String directory) throws IOException { Assert.notNull(templatePath, "word模板文件路径不能为空"); Assert.notNull(fileDir, "生成的文件存放地址不能为空"); Assert.notNull(fileName, "生成的文件名不能为空"); File dir = new File(fileDir); if (!dir.exists()) { logger.info("目录不存在,创建文件夹{}!", fileDir); dir.mkdirs(); } fileName = fileName.replaceAll("/", "_"); //替换文件中敏感字段 logger.info("目录文件{}!", fileName); String filePath = fileDir + "/" + fileName; logger.info("目录{}!", filePath); logger.info("模板{}!", templatePath); // 读取模板渲染参数 InputStream is = getClass().getClassLoader().getResourceAsStream(templatePath); XWPFTemplate template = XWPFTemplate.compile(is).render(paramMap); try { // 将模板参数写入路径 template.writeToFile(filePath); template.close(); is.close(); } catch (Exception e) { logger.error("生成word异常{}", e.getMessage()); e.printStackTrace(); } String pathFileName = FileUploadUtils.getPathFileName(RuoYiConfig.getFilePath("/" + directory), fileName); return pathFileName; } /** * 获取开车条件确认详细信息 */ @PreAuthorize("@ss.hasPermi('pssr:subcontent:query')") @GetMapping(value = "/{id}") public AjaxResult getInfo(@PathVariable("id") Long id) { return AjaxResult.success(tPssrSubcontentService.selectTPssrSubcontentById(id)); } /** * 新增开车条件确认 */ @PreAuthorize("@ss.hasPermi('pssr:subcontent:add')") @Log(title = "开车条件确认", businessType = BusinessType.INSERT) @PostMapping public AjaxResult add(@RequestBody TPssrSubcontent tPssrSubcontent) { return toAjax(tPssrSubcontentService.insertTPssrSubcontent(tPssrSubcontent)); } /** * 修改开车条件确认 */ @PreAuthorize("@ss.hasPermi('pssr:subcontent:edit')") @Log(title = "开车条件确认", businessType = BusinessType.UPDATE) @PutMapping public AjaxResult edit(@RequestBody TPssrSubcontent tPssrSubcontent) { return toAjax(tPssrSubcontentService.updateTPssrSubcontent(tPssrSubcontent)); } /** * 删除开车条件确认 */ @PreAuthorize("@ss.hasPermi('pssr:subcontent:remove')") @Log(title = "开车条件确认", businessType = BusinessType.DELETE) @DeleteMapping("/{ids}") public AjaxResult remove(@PathVariable Long[] ids) { return toAjax(tPssrSubcontentService.deleteTPssrSubcontentByIds(ids)); } /** * 修改开车条件确认 */ @PreAuthorize("@ss.hasPermi('pssr:subcontent:edit')") @Log(title = "开车条件确认", businessType = BusinessType.UPDATE) @PutMapping("/turnDownSubcontent") public AjaxResult turnDownSubcontent(@RequestBody TPssrSubcontent tPssrSubcontent) { if (tPssrSubcontent.getIds() != null && tPssrSubcontent.getIds().size() > 0) { for (Long id : tPssrSubcontent.getIds()) { tPssrApproveController.doApprove(id); } TPssrAboveall aboveall = new TPssrAboveall(); aboveall.setId(tPssrSubcontent.getAboveallId()); aboveall.setApproveStatus(0L); tPssrAboveallService.updateTPssrAboveall(aboveall); TPssrApprove approve = tPssrApproveService.selectTPssrApproveByAboveallId(tPssrSubcontent.getAboveallId()); try { runtimeService.deleteProcessInstance(approve.getProcessId(), "pssrMgrConfirm"); historyService.deleteHistoricProcessInstance(approve.getProcessId()); } catch (Exception e) { logger.info("无运行时流程"); } return AjaxResult.success(); } return AjaxResult.error("请选择需要执行的流程"); } }