提交 f8ddcb09 authored 作者: douxy's avatar douxy

增加店内执行计划导出/入功能: 1.修改某些格式要求;2.修改序号列类名描述;3.增加样式描述,适配经销商编号,经销商编号不按照数字处理

上级 d15e37ea
......@@ -99,13 +99,13 @@ public class NormalDisplayExportStrategyImpl implements IExportApExcelStrategy {
actualHangingStripQuantityForm.setValidationErrorMsg("挂条数量形式必须输入“执行与计划一致”或“执行与计划不一致”!");
actualHangingStripQuantityForm.setConditionalStyling(true);
column.add(new ExportColumnConfig("sadId", "序号", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("sadId", "程序编号-请忽略", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("salesMonth", "计划月份", "YYYY-MM", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("regionName", "销售大区", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("districtName", "销售战区", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("dealerCode", "经销商代码", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("dealerCode", "经销商代码", "@", ExcelStyleUtils.ExcelStyle.CHANGE_TEXT_STYLE));
column.add(new ExportColumnConfig("dealerName", "经销商名称", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("storeCode", "门店编码", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("storeCode", "门店编码", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("storeName", "门店名称", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("lineName", "系统名称", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
column.add(new ExportColumnConfig("plannedMainShelfType", "主货架形式(计划)", "", ExcelStyleUtils.ExcelStyle.UNMODIFIABLE));
......@@ -150,39 +150,4 @@ public class NormalDisplayExportStrategyImpl implements IExportApExcelStrategy {
return EXPORT_FILE_NAME_PREFIX;
}
/* *//**
* 判断登录人权限
* 判断是否存在人客关系,存在:根据负责经销商查询数据;不存在:判断是否是销售部人员。是:根据部门查询;不是:返回全部数据
*//*
private void checkPermission(SalesApRequest salesApRequest) {
LoginUser loginUser = SecurityUtils.getLoginUser();
String ancestors = loginUser.getSysUser().getDept().getAncestors();
List<SysRole> roles = loginUser.getSysUser().getRoles();
// 不是区域销售部的人员,可以查看所有
if (!ancestors.contains(constantValue.deptYX) && roles.stream().filter(role -> RoleConstants.OPERATION_CENTER_AP_MANAGER.equals(role.getRoleKey())).findFirst().isPresent()) {
return;
}
// 是区域销售部的人员:1、销售查看人客关系;2、大区TM查看当前部门下所有数据
// 判断是否是大区TM
String empNo = loginUser.getUsername();
Optional<SysRole> first = roles.stream().filter(role -> RoleConstants.DISTRICT_AP_MANAGER.equals(role.getRoleKey())).findFirst();
if (first.isPresent()) {
ArrayList<String> deptNames = new ArrayList<>();
deptNames.add(loginUser.getSysUser().getDept().getDeptName());
if ("000889".equals(empNo)){
deptNames.add("北京特区");
}
return;
}
// 不是大区TM,判断是否是销售人员(人客关系)
List<String> dealerCodes = qinceMarketEmployeeService.checkPermission(empNo);
if (dealerCodes.isEmpty()) {
throw new CheckedException(ECode.QC_MARKET_EMP_ERROR);
}
// salesApRequest.setNickName(loginUser.getNickName());
salesApRequest.setDealerCodes(dealerCodes);
}*/
}
......@@ -23,8 +23,12 @@ public class ExcelStyleUtils {
LIGHT_GREY_BG,
//默认
DEFAULT_STYLE,
//红色
RED_STYLE,
HEADER_STYLE
//表头
HEADER_STYLE,
//修改数字列为文本样式
CHANGE_TEXT_STYLE
}
/**
......@@ -90,6 +94,13 @@ public class ExcelStyleUtils {
cellStyle.setFillForegroundColor(IndexedColors.GREY_25_PERCENT.getIndex());
cellStyle.setLocked(false);
break;
case CHANGE_TEXT_STYLE:
cellStyle.setFillForegroundColor(IndexedColors.GREY_25_PERCENT.getIndex());
cellStyle.setDataFormat(workbook.getCreationHelper().createDataFormat().getFormat("@"));
cellStyle.setLocked(true);
font.setBold(true);
cellStyle.setFont(font);
break;
// 默认
case DEFAULT_STYLE:
default:
......
......@@ -7,7 +7,6 @@ import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.poi.ss.usermodel.*;
import org.apache.poi.ss.util.CellRangeAddressList;
import org.apache.poi.xssf.streaming.SXSSFSheet;
import org.apache.poi.xssf.streaming.SXSSFWorkbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.slf4j.Logger;
......@@ -23,7 +22,6 @@ import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.concurrent.ConcurrentHashMap;
import java.util.regex.Pattern;
/**
* @Author: DouXinYu
......@@ -53,7 +51,7 @@ public class ExcelUtils {
}
// 1. 设置响应头(解决中文乱码、指定文件类型)
String fileName = String.format("%s_%s.xlsx", fileNamePrefix, new SimpleDateFormat("yyyyMMdd-HH:mm:ss").format(new Date()));
String fileName = String.format("%s_%s.xlsx", fileNamePrefix, new SimpleDateFormat("yyyyMMdd").format(new Date()));
// URLEncoder编码兼容所有浏览器
String encodedFileName = URLEncoder.encode(fileName, String.valueOf(StandardCharsets.UTF_8));
......@@ -113,8 +111,6 @@ public class ExcelUtils {
// 处理需要验证的列
for (int i = 0; i < exportColumnConfigList.size(); i++) {
ExportColumnConfig config = exportColumnConfigList.get(i);
// 给列配置数据验证(策略自定义的规则)
ExcelStyleUtils.addColumnDataValidation(sheet, i, config);
// 给列配置只读验证
if (isColumnProtected(config)) {
// 为该列所有数据行添加只读验证
......@@ -122,11 +118,6 @@ public class ExcelUtils {
addReadOnlyValidation(sheet, i, 1, dataList.size());
}
}
// 自适应所有列宽
// autoSizeAllColumns(sheet, exportColumnConfigList.size(),dataList.size());
workbook.write(outputStream);
return outputStream.toByteArray();
} finally {
......@@ -144,7 +135,6 @@ public class ExcelUtils {
}
/**
* 创建工作簿
*
......@@ -196,8 +186,13 @@ public class ExcelUtils {
}
// 为表头行添加只读验证(防止用户修改表头)
for (int i = 0; i < exportColumnConfigList.size(); i++) {
// 只保护第0行(表头行)
addReadOnlyValidation(sheet, i, 0, 0);
ExportColumnConfig exportColumnConfig = exportColumnConfigList.get(i);
if (exportColumnConfig.getValidationPromptTitle() != null && exportColumnConfig.getValidationPromptMsg() != null){
addHeaderPromptValidation(sheet, i, exportColumnConfig);
}
// 只保护第0行(表头行)
addReadOnlyValidation(sheet, i, 0, 0);
}
}
......@@ -265,6 +260,42 @@ public class ExcelUtils {
}
/**
* 添加表头提示
*
* @param sheet 工作表
* @param columnIndex 列索引
* @param config 表头配置
*/
private static void addHeaderPromptValidation(Sheet sheet, int columnIndex, ExportColumnConfig config) {
DataValidationHelper helper = sheet.getDataValidationHelper();
// 创建总是为真的约束
DataValidationConstraint constraint = helper.createCustomConstraint("FALSE");
// 仅对表头行(第0行)应用
CellRangeAddressList addressList = new CellRangeAddressList(0, 0, columnIndex, columnIndex);
DataValidation validation = helper.createValidation(constraint, addressList);
// 设置提示信息
validation.setShowPromptBox(true);
validation.createPromptBox(config.getValidationPromptTitle(), config.getValidationPromptMsg());
validation.setShowErrorBox(true);
validation.createErrorBox("禁止修改", "单元格内容禁止修改!");
validation.setErrorStyle(DataValidation.ErrorStyle.STOP);
validation.setEmptyCellAllowed(false);
validation.setSuppressDropDownArrow(false);
sheet.addValidationData(validation);
}
/**
* 根据字段名获取字段值
*
* @param fieldName 字段名
* @param data 数据对象
* @return 字段值
*/
private static Object getFieldValueByOgnl(String fieldName, Object data) {
// 避免空指针访问
if (data == null || fieldName == null || fieldName.trim().isEmpty()) {
......@@ -293,6 +324,12 @@ public class ExcelUtils {
return;
}
// 特殊处理:如果格式为 "@" 或者字段名包含某些关键词,则强制作为文本处理
if ("@".equals(format)) {
cell.setCellValue(value.toString());
return;
}
// 1. 日期类型
if (value instanceof Date) {
if (format != null && !format.isEmpty()) {
......@@ -326,6 +363,7 @@ public class ExcelUtils {
/**
* 计算文本宽度(支持换行)
*
* @param text 文本内容
* @return 宽度值
*/
......@@ -344,37 +382,6 @@ public class ExcelUtils {
return maxLineLength * 256 + 1000;
}
/**
* 根据表头内容自动调整所有列的宽度
* @param sheet 工作表
* @param columnCount 列数
* @param dataRowCount 数据行数(未使用)
*/
private static void autoSizeAllColumns(Sheet sheet, int columnCount, int dataRowCount) {
// 对于SXSSFSheet,先跟踪所有列以便自动调整大小
if (sheet instanceof SXSSFSheet) {
SXSSFSheet sxssfSheet = (SXSSFSheet) sheet;
for (int i = 0; i < columnCount; i++) {
sxssfSheet.trackColumnForAutoSizing(i);
}
}
// 基于表头内容自动调整每列宽度
for (int i = 0; i < columnCount; i++) {
try {
sheet.autoSizeColumn(i);
// 添加适量的缓冲确保内容显示完整
int currentWidth = sheet.getColumnWidth(i);
sheet.setColumnWidth(i, Math.min(currentWidth + 800, 255 * 256));
} catch (Exception e) {
sheet.setColumnWidth(i, 20 * 256);
logger.warn("Failed to auto-size column {}: {}", i, e.getMessage());
}
}
}
/**
* 缓存样式避免内存溢出
......@@ -406,19 +413,32 @@ public class ExcelUtils {
return "";
}
// 替换中文括号及其内容为换行形式
String result = originalText.replaceAll("((.*?))", "\n$1");
// 替换英文括号及其内容为换行形式
result = result.replaceAll("\\((.*?)\\)", "\n$1");
String result ;
if (originalText.contains("(") && originalText.contains(")")) {
// 中文括号替换为换行
result = originalText.replaceAll("((.*?))", "\n$1");
} else if (originalText.contains("(") && originalText.contains(")")){
// 英文括号替换为换行
result = originalText.replaceAll("\\((.*?)\\)", "\n$1");
}else if (originalText.contains("-")){
// 横线替换为换行(内容)
result = originalText.replaceAll("-(.+)", "\n($1)");
}else if (originalText.contains("_")){
result = originalText.replaceAll("_(.+)", "\n($1)");
}else {
result = originalText;
}
return result;
}
/**
* 为特定单元格区域添加只读数据验证
*
* @param sheet 工作表
* @param sheet 工作表
* @param columnIndex 列索引
* @param startRow 起始行
* @param endRow 结束行
* @param startRow 起始行
* @param endRow 结束行
*/
private static void addReadOnlyValidation(Sheet sheet, int columnIndex, int startRow, int endRow) {
DataValidationHelper helper = sheet.getDataValidationHelper();
......@@ -445,7 +465,7 @@ public class ExcelUtils {
* @return 是否需要保护
*/
private static boolean isColumnProtected(ExportColumnConfig config) {
return config.getStyle() == ExcelStyleUtils.ExcelStyle.UNMODIFIABLE;
return config.getStyle() == ExcelStyleUtils.ExcelStyle.UNMODIFIABLE || config.getStyle() == ExcelStyleUtils.ExcelStyle.CHANGE_TEXT_STYLE;
}
}
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论