Java用POI實現根據Excel表格模板生成新的Excel並實現資料輸出
阿新 • • 發佈:2019-01-01
一、
模板excel
結果excel
二、
專案所需jar包
poi-3.11-20141221.jar
poi-examples-3.11-20141221.jar
poi-excelant-3.11-20141221.jar
poi-ooxml-3.11-20141221.jar
poi-ooxml-schemas-3.11-20141221.jar
poi-scratchpad-3.11-20141221.jar
xmlbeans-2.6.0.jar
curvesapi-1.04.jar
三、專案原始碼
controller部分
/**匯出到excel * @param * @throws Exception */ @RequestMapping(value="/excel") public ModelAndView exportExcel() throws Exception{ logBefore(logger, Jurisdiction.getUsername()+"匯出Excel到excel"); if(!Jurisdiction.buttonJurisdiction(menuUrl, "cha")){return null;} ModelAndView mv; //獲取頁面表單傳遞過來的引數 PageData pd = this.getPageData(); //dataMap作為model,存入資料 Map<String,Object> dataMap = new HashMap<>(); //儲存模板Excel路徑和生成Excel路徑 List<String> urls=new ArrayList<>(); //儲存所有heads List<String> heads=new ArrayList<>(); //儲存尾部的數值 List<String> tails=new ArrayList<>(); //獲取當前日期 Date date = new Date(); //模板Excel檔案路徑 //字尾為xls的檔案路徑 String demoUrl=ExcelController.class.getClassLoader().getResource("reportxls/ExportExcel.xls").getPath().replaceFirst("/",""); //按日期設定當前Excel表格的名字 String fileName = Tools.date2Str(date, "yyyyMMddHHmmss"); //生成Excel檔名稱 // String excelUrl=fileName+".xlsx"; //字尾為xlsx檔案的路徑 String excelUrl=fileName+".xls"; //將路徑新增到urls當中 urls.add(demoUrl); urls.add(excelUrl); //將urls路徑存入到dataMap當中,作為model傳入到檢視中 dataMap.put("urls",urls); //表格所需要的標題1 String head1="標題1"; //表格所需要的標題2 String head2="標題2"; //表格所需要的標題3 String head3="標題3"; //表格所需要的標題4 String head4="標題4"; //表格所需要的標題5 // String head5="標題5"; //存入這些標題 heads.add(head1); heads.add(head2); heads.add(head3); heads.add(head4); // heads.add(head5); //表格所需要的尾部1 String tail1="尾部1"; //存入表格所需要的尾部 tails.add(tail1); //表格所需要的尾部2 String tail2="尾部2"; //存入表格所需的尾部 tails.add(tail2); //將tails存入到dataGrip中 dataMap.put("tails",tails); //將標題存放到存入到dataGrip當中 dataMap.put("heads",heads); //獲取當前Excel表格所需要的內容 List<PageData> varOList = excelService.listAll(pd); dataMap.put("varOList",varOList); //建立需要渲染的Excel表格檢視 //進行檔案字尾型別判斷 if (demoUrl.endsWith(".xls")){ XlsExcelView erv=new XlsExcelView(); mv=new ModelAndView(erv,dataMap); }else { XlsxExcelView erv=new XlsxExcelView(); mv=new ModelAndView(erv,dataMap); } return mv; }
檢視部分
附註:對於.xlsx檔案修改一下引用類名即可public class XlsExcelView extends AbstractXlsView { @Override protected void buildExcelDocument(Map<String, Object> map, Workbook workbook, HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws Exception { //獲取當前的urls地址 List<String> urls=(List<String>)map.get("urls"); //表格所要儲存的標題 List<String> heads=(List<String>)map.get("heads"); //表格所要儲存的尾部 List<String> tails=(List<String>)map.get("tails"); //獲取查詢到的結果集 List<PageData> varOList=(List<PageData>)map.get("varOList"); //獲取主表資訊 PageData mainInfo=(PageData)map.get("mainInfo"); //建立Excel檔案的輸入流物件 FileInputStream fis=new FileInputStream(urls.get(0)); //根據模板建立Excel工作簿 workbook=new HSSFWorkbook(fis); //建立Excel檔案輸出流物件 OutputStream out=httpServletResponse.getOutputStream(); httpServletResponse.setContentType("application/octet-stream"); httpServletResponse.setHeader("Content-Disposition","attachment;filename="+urls.get(1)); //將workboo強轉成需要的HSSFBook HSSFWorkbook HSSFWorkbook=(HSSFWorkbook)workbook; //獲取建立工作簿的第一頁 HSSFSheet sheet=HSSFWorkbook.getSheetAt(0); //給指定的sheet命名 HSSFWorkbook.setSheetName(0,"dataSheet"); //初始化當前的索引,設為當前sheet的最後一行行數 int currentLastRowIndex=sheet.getLastRowNum(); //儲存當前表格的樣式 HSSFCellStyle cellStyle=HSSFWorkbook.createCellStyle(); //獲取當前工作簿的行數 int totalRows=sheet.getPhysicalNumberOfRows(); /***********************遍歷模板sheet,根據當中的設定進行賦值*******************************************************************/ for (int i=0;i<totalRows;i++){ HSSFRow row=sheet.getRow(i); int column=row.getLastCellNum(); //插入主表資訊 if (mainInfo!=null){ for (int j=0;j<mainInfo.size();j++){ HSSFCell cell=row.getCell(j)!=null?row.getCell(j):row.createCell(j); String cellValue=cell.getStringCellValue(); if (cellValue.startsWith("#")){ String str=cellValue.replace("#",""); cell.setCellValue(mainInfo.get(str).toString()); } } } for (int j=0;j<column;j++){ HSSFCell cell=row.getCell(j)!=null?row.getCell(j):row.createCell(j); String cellValue=cell.getStringCellValue(); if (cellValue.startsWith("$")){ //設定新的單元格儲存的值 cell.setCellValue(heads.get(0)); heads.remove(0); } if (cellValue.startsWith("&")){ //取出表格的樣式,作為新插入單元格的樣式 cellStyle=cell.getCellStyle(); //獲取當前要插入記錄的行數 currentLastRowIndex=i; continue; } if (cellValue.startsWith("#")){ cell.setCellValue(tails.get(0)); tails.remove(0); } } } //增加一行 int lastRow=sheet.getLastRowNum()+1; sheet.setDefaultColumnWidth(lastRow); /*************************************************************************************************************/ //在該行的進行插入(在刪除了特定行的欄位進行插入) int newRowIndex=currentLastRowIndex; //獲取模板對應的資料表字段的值 HSSFRow dataRow=sheet.getRow(currentLastRowIndex); //獲得該行對應的欄位的數量 int columnNum=dataRow.getPhysicalNumberOfCells(); //根據生成欄位的單元格數量,生成對應數量的陣列 String[] cells=new String[columnNum]; //獲取資料集欄位的名稱,依次存入到cells陣列當中 for (int i=0;i<columnNum;i++){ HSSFCell cell=dataRow.getCell(i); //去掉&符號,並將從excel表格當中獲得的值統一轉換成大寫處理 cells[i]=cell.getStringCellValue().replaceFirst("&","").toUpperCase(); } //完成資料集欄位的收集後,刪除該段 HSSFRow sprRow=sheet.getRow(currentLastRowIndex); sheet.removeRow(sprRow); /*************************插入新的行數********************************************/ //將結果集渲染到當前sheet當中 for (PageData pageData:varOList){ sheet.shiftRows(newRowIndex,newRowIndex+1,1); HSSFRow newRow=sheet.createRow(newRowIndex++); //建立需要插入的目標行,該值需要在每次完成一行記錄值插入後重新歸0 int cellIndex=0; //ic此處為cells陣列的結果集的欄位的位置 for (int i=0;i<columnNum;i++){ //從pageData當中取出目標單元格需要的值 String cellContent=pageData.get(cells[i])!=null?pageData.get(cells[i]).toString():""; //設定目標單元格的位置和型別 HSSFCell cell=newRow.createCell(cellIndex++,Cell.CELL_TYPE_STRING); //設定目標單元格的樣式 cell.setCellStyle(cellStyle); //設定目標單元格的值 cell.setCellValue(cellContent); } } /*********************************************************************************/ HSSFWorkbook.write(out); fis.close(); out.flush(); out.close(); } }