|
|
|
@ -7,9 +7,15 @@ import com.alibaba.excel.write.metadata.holder.WriteWorkbookHolder;
|
|
|
|
|
import lombok.Data;
|
|
|
|
|
import org.apache.poi.ss.usermodel.*;
|
|
|
|
|
import org.apache.poi.ss.util.CellRangeAddressList;
|
|
|
|
|
import org.apache.poi.xssf.usermodel.XSSFDataValidation;
|
|
|
|
|
|
|
|
|
|
import java.util.Map;
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* 实现easyExcel的接口, 下拉框注解处理程序
|
|
|
|
|
*
|
|
|
|
|
* @author lx
|
|
|
|
|
*/
|
|
|
|
|
@Data
|
|
|
|
|
public class ExcelSelectorDataWriteHandler implements SheetWriteHandler {
|
|
|
|
|
|
|
|
|
@ -18,36 +24,75 @@ public class ExcelSelectorDataWriteHandler implements SheetWriteHandler {
|
|
|
|
|
@Override
|
|
|
|
|
public void afterSheetCreate(WriteWorkbookHolder writeWorkbookHolder, WriteSheetHolder writeSheetHolder) {
|
|
|
|
|
Sheet sheet = writeSheetHolder.getSheet();
|
|
|
|
|
Workbook workbook = sheet.getWorkbook();
|
|
|
|
|
DataValidationHelper helper = sheet.getDataValidationHelper();
|
|
|
|
|
if (CollUtil.isEmpty(selectedMap)) {
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
selectedMap.forEach((k, v) -> {
|
|
|
|
|
String[] deptList = v.getSelectorData();
|
|
|
|
|
int startRow = v.getStartRow();
|
|
|
|
|
int endRow = v.getEndRow();
|
|
|
|
|
String hiddenName = "hidden"+k;
|
|
|
|
|
//1.创建隐藏的sheet页。 起个名字吧!叫"hidden"!
|
|
|
|
|
Sheet hidden = sheet.getWorkbook().createSheet(hiddenName);
|
|
|
|
|
//2.循环赋值(为了防止下拉框的行数与隐藏域的行数相对应,将隐藏域加到结束行之后)
|
|
|
|
|
for (int i = 0, length = deptList.length; i < length; i++) {
|
|
|
|
|
hidden.createRow(endRow + i).createCell(k).setCellValue(deptList[i]);
|
|
|
|
|
}
|
|
|
|
|
Name category1Name = sheet.getWorkbook().createName();
|
|
|
|
|
category1Name.setNameName(hiddenName);
|
|
|
|
|
//3 A1:A代表隐藏域创建第N列createCell(N)时。以A1列开始A行数据获取下拉数组
|
|
|
|
|
category1Name.setRefersToFormula(hiddenName + "!A1:A" + (deptList.length + endRow));
|
|
|
|
|
//
|
|
|
|
|
// 下拉 首行 末行 首列 末列
|
|
|
|
|
CellRangeAddressList list = new CellRangeAddressList(startRow, endRow, k, k);
|
|
|
|
|
// 下拉值
|
|
|
|
|
DataValidationConstraint constraint = helper.createExplicitListConstraint(v.getSelectorData());
|
|
|
|
|
DataValidation validation = helper.createValidation(constraint, list);
|
|
|
|
|
validation.setErrorStyle(DataValidation.ErrorStyle.STOP);
|
|
|
|
|
validation.setShowErrorBox(true);
|
|
|
|
|
validation.setSuppressDropDownArrow(true);
|
|
|
|
|
validation.createErrorBox("提示", "请输入下拉选项中的内容");
|
|
|
|
|
sheet.addValidationData(validation);
|
|
|
|
|
// shortSelectData(sheet, helper, k, v);
|
|
|
|
|
longSelectData(sheet, workbook, helper, k, v);
|
|
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* 下拉框数据量比较大时候用
|
|
|
|
|
* @param sheet
|
|
|
|
|
* @param workbook
|
|
|
|
|
* @param helper
|
|
|
|
|
* @param k
|
|
|
|
|
* @param v
|
|
|
|
|
*/
|
|
|
|
|
private void longSelectData(Sheet sheet, Workbook workbook, DataValidationHelper helper, Integer k, ExcelSelectorResolve v) {
|
|
|
|
|
String[] deptList = v.getSelectorData();
|
|
|
|
|
int startRow = v.getStartRow();
|
|
|
|
|
int endRow = v.getEndRow();
|
|
|
|
|
// 起个名字吧!叫"hidden"!
|
|
|
|
|
String hiddenName = "hidden" + k;
|
|
|
|
|
//1.创建隐藏的sheet页。
|
|
|
|
|
Sheet hidden = workbook.createSheet(hiddenName);
|
|
|
|
|
//2.循环赋值(为了防止下拉框的行数与隐藏域的行数相对应,将隐藏域加到结束行之后)
|
|
|
|
|
for (int i = 0, length = deptList.length; i < length; i++) {
|
|
|
|
|
hidden.createRow(endRow + i).createCell(k).setCellValue(deptList[i]);
|
|
|
|
|
}
|
|
|
|
|
Name category1Name = workbook.createName();
|
|
|
|
|
category1Name.setNameName(hiddenName);
|
|
|
|
|
//3 A1:A代表隐藏域创建第N列createCell(N)时。以A1列开始A行数据获取下拉数组
|
|
|
|
|
category1Name.setRefersToFormula(hiddenName + "!A1:A" + (deptList.length + endRow));
|
|
|
|
|
|
|
|
|
|
DataValidationConstraint constraint = helper.createFormulaListConstraint(hiddenName);
|
|
|
|
|
CellRangeAddressList addressList = new CellRangeAddressList(startRow, endRow, k, k);
|
|
|
|
|
DataValidation dataValidation = helper.createValidation(constraint, addressList);
|
|
|
|
|
if (dataValidation instanceof XSSFDataValidation) {
|
|
|
|
|
// 数据校验
|
|
|
|
|
dataValidation.setSuppressDropDownArrow(true);
|
|
|
|
|
dataValidation.setShowErrorBox(true);
|
|
|
|
|
} else {
|
|
|
|
|
dataValidation.setSuppressDropDownArrow(false);
|
|
|
|
|
}
|
|
|
|
|
// 作用在目标sheet上
|
|
|
|
|
sheet.addValidationData(dataValidation);
|
|
|
|
|
// 设置hiddenSheet隐藏
|
|
|
|
|
workbook.setSheetHidden(k + 1, true);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* 下拉框数据量较少的时候用
|
|
|
|
|
* @param sheet
|
|
|
|
|
* @param helper
|
|
|
|
|
* @param k
|
|
|
|
|
* @param v
|
|
|
|
|
*/
|
|
|
|
|
private void shortSelectData(Sheet sheet, DataValidationHelper helper, Integer k, ExcelSelectorResolve v) {
|
|
|
|
|
// 下拉 首行 末行 首列 末列
|
|
|
|
|
CellRangeAddressList list = new CellRangeAddressList(v.getStartRow(), v.getEndRow(), k, k);
|
|
|
|
|
// 下拉值
|
|
|
|
|
DataValidationConstraint constraint = helper.createExplicitListConstraint(v.getSelectorData());
|
|
|
|
|
DataValidation validation = helper.createValidation(constraint, list);
|
|
|
|
|
validation.setErrorStyle(DataValidation.ErrorStyle.STOP);
|
|
|
|
|
validation.setShowErrorBox(true);
|
|
|
|
|
validation.setSuppressDropDownArrow(true);
|
|
|
|
|
validation.createErrorBox("提示", "请输入下拉选项中的内容");
|
|
|
|
|
sheet.addValidationData(validation);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|