diff --git a/README.md b/README.md index 6a5b184..0280ba8 100644 --- a/README.md +++ b/README.md @@ -248,4 +248,17 @@ EasyPoi导出实例 for (int i = 0; i < result.getList().size(); i++) { System.out.println(ReflectionToStringBuilder.toString(result.getList().get(i))); } -``` +``` + +9.Excel 导出的ForEach **Angelia**的需求 可以到处更加复杂的模板Excel了 + + foreach提供两个语法写法 + + 1.createRow的 + foreach||entitylist{{accountType projectName approvedAmount amountApplied}} + foreach开头,|| 后面是map的key,{{这个里面是各个属性值}} + 2.不createRow的,如果row不够了还是会create,但是首先会用现成的 + !foreach||entitylist{{accountType projectName approvedAmount amountApplied}} + !foreach开头,|| 后面是map的key,{{这个里面是各个属性值}} + + demo是TemplateForEachTest diff --git a/easypoi-base/src/main/java/org/jeecgframework/poi/excel/export/template/ExcelExportOfTemplateUtil.java b/easypoi-base/src/main/java/org/jeecgframework/poi/excel/export/template/ExcelExportOfTemplateUtil.java index 2e0d90a..615d5d5 100644 --- a/easypoi-base/src/main/java/org/jeecgframework/poi/excel/export/template/ExcelExportOfTemplateUtil.java +++ b/easypoi-base/src/main/java/org/jeecgframework/poi/excel/export/template/ExcelExportOfTemplateUtil.java @@ -5,9 +5,11 @@ import java.util.ArrayList; import java.util.Arrays; import java.util.Collection; import java.util.HashMap; +import java.util.HashSet; import java.util.Iterator; import java.util.List; import java.util.Map; +import java.util.Set; import org.apache.commons.lang.StringUtils; import org.apache.poi.ss.usermodel.Cell; @@ -38,7 +40,12 @@ import org.slf4j.LoggerFactory; */ public final class ExcelExportOfTemplateUtil extends ExcelExportBase { - private static final Logger LOGGER = LoggerFactory.getLogger(ExcelExportOfTemplateUtil.class); + private static final Logger LOGGER = LoggerFactory + .getLogger(ExcelExportOfTemplateUtil.class); + /** + * 缓存temp 的for each创建的cell ,跳过这个cell的模板语法查找,提高效率 + */ + private Set tempCreateCellSet = new HashSet(); /** * 往Sheet 填充正常数据,根据表头信息 使用导入的部分逻辑,坐对象映射 @@ -242,12 +249,16 @@ public final class ExcelExportOfTemplateUtil extends ExcelExportBase { } private void parseTemplate(Sheet sheet, Map map) throws Exception { - Iterator rows = sheet.rowIterator(); - Row row; - while (rows.hasNext()) { - row = rows.next(); + Row row = null; + int index = 0; + while (index <= sheet.getLastRowNum()) { + row = sheet.getRow(index++); for (int i = row.getFirstCellNum(); i < row.getLastCellNum(); i++) { - setValueForCellByMap(row.getCell(i), map); + if (!tempCreateCellSet.contains(row.getRowNum() + "_" + + row.getCell(i).getColumnIndex())) { + System.out.println(row.getCell(i).getStringCellValue()); + setValueForCellByMap(row.getCell(i), map); + } } } } @@ -265,7 +276,7 @@ public final class ExcelExportOfTemplateUtil extends ExcelExportBase { } catch (Exception e) { return; } - if (oldString != null && oldString.indexOf("{{") != -1) { + if (oldString != null && oldString.indexOf("{{") != -1 && !oldString.contains("foreach||")) { // setp 2. 判断是否含有解析函数 String params; while (oldString.indexOf("{{") != -1) { @@ -275,6 +286,103 @@ public final class ExcelExportOfTemplateUtil extends ExcelExportBase { } cell.setCellValue(oldString); } + //判断foreach 这种方法 + if (oldString != null + && (oldString.trim().startsWith("foreach||") || oldString.trim().startsWith( + "!foreach||"))) { + addListDataToExcel(cell, map, oldString.trim()); + } + } + + /** + * 利用foreach循环输出数据 + * @param cell + * @param map + * @param oldString + * @throws Exception + */ + private void addListDataToExcel(Cell cell, Map map, String name) + throws Exception { + boolean isCreate = !name.startsWith("!"); + Collection datas = (Collection) map.get(name.substring(name.indexOf("||") + 2, + name.indexOf("{{"))); + List columns = getAllDataColumns(cell, name); + if (datas == null) { + return; + } + Iterator its = datas.iterator(); + Row row; + int rowIndex = cell.getRow().getRowNum() + 1; + //处理当前行 + if (its.hasNext()) { + Object t = its.next(); + setForEeachCellValue(isCreate, cell.getRow(), cell.getColumnIndex(), t, columns); + } + while (its.hasNext()) { + Object t = its.next(); + if (isCreate) { + row = cell.getRow().getSheet().createRow(rowIndex++); + } else { + row = cell.getRow().getSheet().getRow(rowIndex++); + if (row == null) { + row = cell.getRow().getSheet().createRow(rowIndex - 1); + } + } + setForEeachCellValue(isCreate, row, cell.getColumnIndex(), t, columns); + } + } + + private void setForEeachCellValue(boolean isCreate, Row row, int columnIndex, Object t, + List columns) throws Exception { + for (int i = 0, max = columnIndex + columns.size(); i < max; i++) { + if (row.getCell(i) == null) + row.createCell(i); + } + for (int i = 0, max = columns.size(); i < max; i++) { + String val = getValueDoWhile(t, columns.get(i).split("\\."), 0); + row.getCell(i + columnIndex).setCellValue(val); + tempCreateCellSet.add(row.getRowNum() + "_" + (i + columnIndex)); + } + + } + + /** + * 获取迭代的数据的值 + * @param cell + * @param name + * @return + */ + private List getAllDataColumns(Cell cell, String name) { + List columns = new ArrayList(); + if (name.contains("}}")) { + columns.add(name.substring(name.indexOf("{{") + 2, name.indexOf("}}")).trim()); + cell.setCellValue(""); + return columns; + } + columns.add(name.substring(name.indexOf("{{") + 2).trim()); + int index = cell.getColumnIndex(); + Cell tempCell; + while (true) { + tempCell = cell.getRow().getCell(++index); + String cellStringString; + try {//不允许为空 + cellStringString = tempCell.getStringCellValue(); + if (StringUtils.isBlank(cellStringString)) { + throw new RuntimeException(); + } + } catch (Exception e) { + throw new ExcelExportException("for each 当中存在空字符串,请检查模板"); + } + cell.setCellValue(""); + if (cellStringString.contains("}}")) { + columns.add(cellStringString.trim().replace("}}", "")); + break; + } else { + columns.add(cellStringString.trim()); + } + + } + return columns; } /** diff --git a/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/doc/foreach.xlsx b/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/doc/foreach.xlsx new file mode 100644 index 0000000..09a895e Binary files /dev/null and b/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/doc/foreach.xlsx differ diff --git a/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/template/TemplateExcelExportTest.java b/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/template/TemplateExcelExportTest.java index 98f613a..59a1488 100644 --- a/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/template/TemplateExcelExportTest.java +++ b/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/template/TemplateExcelExportTest.java @@ -29,7 +29,7 @@ public class TemplateExcelExportTest { @Test public void test() throws Exception { TemplateExportParams params = new TemplateExportParams( - "org/jeecgframework/poi/excel/doc/专项支出用款申请书.xls"); + "org/jeecgframework/poi/test/excel/doc/专项支出用款申请书.xls"); params.setHeadingStartRow(3); params.setHeadingRows(2); params.setStyle(ExcelExportStylerColorImpl.class); diff --git a/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/template/TemplateForEachTest.java b/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/template/TemplateForEachTest.java new file mode 100644 index 0000000..8d765b8 --- /dev/null +++ b/easypoi-test/src/main/java/org/jeecgframework/poi/test/excel/template/TemplateForEachTest.java @@ -0,0 +1,64 @@ +package org.jeecgframework.poi.test.excel.template; + +import java.io.File; +import java.io.FileOutputStream; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import org.apache.poi.ss.usermodel.Workbook; +import org.jeecgframework.poi.excel.ExcelExportUtil; +import org.jeecgframework.poi.excel.entity.TemplateExportParams; +import org.jeecgframework.poi.excel.export.styler.ExcelExportStylerColorImpl; +import org.jeecgframework.poi.test.entity.temp.BudgetAccountsEntity; +import org.jeecgframework.poi.test.entity.temp.PayeeEntity; +import org.jeecgframework.poi.test.entity.temp.TemplateExcelExportEntity; +import org.junit.Test; + +import com.google.common.collect.Lists; + +public class TemplateForEachTest { + + @Test + public void test() throws Exception { + TemplateExportParams params = new TemplateExportParams( + "org/jeecgframework/poi/test/excel/doc/foreach.xlsx"); + Map map = new HashMap(); + List list = new ArrayList(); + + for (int i = 0; i < 4; i++) { + TemplateExcelExportEntity entity = new TemplateExcelExportEntity(); + entity.setIndex(i + 1 + ""); + entity.setAccountType("开源项目"); + entity.setProjectName("EasyPoi " + i + "期"); + entity.setAmountApplied(i * 10000 + ""); + entity.setApprovedAmount((i + 1) * 10000 - 100 + ""); + list.add(entity); + } + map.put("entitylist", list); + List> mapList = new ArrayList>(); + for (int i = 0; i < 4; i++) { + Map testMap = new HashMap(); + + testMap.put("id", i); + testMap.put("name", "小明" + i); + testMap.put("sex", "man"); + mapList.add(testMap); + } + map.put("maplist", mapList); + Workbook workbook = ExcelExportUtil.exportExcel(params, map); + File savefile = new File("d:/"); + if (!savefile.exists()) { + savefile.mkdirs(); + } + FileOutputStream fos = new FileOutputStream("d:/foreach.xlsx"); + workbook.write(fos); + fos.close(); + workbook = ExcelExportUtil.exportExcel(params, map); + fos = new FileOutputStream("d:/foreach2.xlsx"); + workbook.write(fos); + fos.close(); + } + +}