使用itext生成word格式的报表(by quqi99)
作者:张华 发表于:2008-06-27 ( http://blog.csdn.net/quqi99 )
版权声明:可以任意转载,转载时请务必以超链接形式标明文章原始出处和作者信息及本版权声明。
package gnsclient.util; import gnsclient.views.TreeNode; import java.awt.Color; import java.io.FileOutputStream; import java.util.ArrayList; import java.util.Date; import java.util.HashMap; import java.util.List; import java.util.Map; import com.lowagie.text.Cell; import com.lowagie.text.Chunk; import com.lowagie.text.Document; import com.lowagie.text.Font; import com.lowagie.text.PageSize; import com.lowagie.text.Phrase; import com.lowagie.text.Rectangle; import com.lowagie.text.Table; import com.lowagie.text.pdf.BaseFont; import com.lowagie.text.pdf.PRAcroForm; import com.lowagie.text.pdf.PdfCopy; import com.lowagie.text.pdf.PdfImportedPage; import com.lowagie.text.pdf.PdfReader; import com.lowagie.text.pdf.SimpleBookmark; import com.lowagie.text.rtf.RtfWriter2; /** ** @作者 张华 ** @时间 2008-6-26 上午10:22:17 ** @描述 报表 目前报表只支持演出部门、剧种、网站来源三级结构 * 注意建第三级网站来源一级分类时请保证它与Parser中站点的内容一致 * http://hi.baidu.com/lion98/blog/item/a25352666dad1f24aa184c0d.html * http://jinghua.javaeye.com/blog/112027 * http://ivanl.javaeye.com/blog/56780 * http://itextdocs.lowagie.com/tutorial/ * http://blog.csdn.net/mxd306/archive/2007/07/24/1704613.aspx * http://hi.baidu.com/df1019/blog/item/9a0acd11aa66c7c2a6ef3f01.html * http://blog.csdn.net/wangphoenix/archive/2004/08/10/70573.aspx * http://hi.baidu.com/df1019/blog/item/1aef26d78bab26d9a044df00.html 值得一看 * * 尚未实现表格单元格设置高度 **/ public class ReportTable { /**生成报表,目前报表只支持演出部门、剧种、网站来源三级结构 * @param outfile * @param deptNodes 演出部门列表,若传进来为null,则默认为所有的演出部门生成报表 */ public static void creatReportTable(String outfile,TreeNode[] deptNodes) throws Exception{ Rectangle rectPageSize = new Rectangle(PageSize.A4.rotate()); // 定义A4页面大小 //rectPageSize.setBackgroundColor(new java.awt.Color(0xFF, 0xFF, 0xDE)); //左右上下边距分别是2.54,2.54,3.2,3.4,单位:厘米。换算为:3.2/2.54=1.25英寸,1.25*72=90个点 //Document document = new Document(rectPageSize,72,72,90,96); //其余4个参数,设置了页面的4个边距 Document document = new Document(rectPageSize,1,1,1,1); //其余4个参数,设置了页面的4个边距 try{ //增加中文支持 BaseFont bfChinese = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED); Font bold4Font = new Font(bfChinese, 14, Font.BOLD); //4号黑体 Font bold5Font = new Font(bfChinese, 10, Font.BOLD); //5号黑体 Font boldSmall5Font = new Font(bfChinese, 9, Font.BOLD); //小5黑体 Font small5Font = new Font(bfChinese, 9, Font.NORMAL); //小5普通体 //PdfWriter.getInstance(document, new FileOutputStream("e://Helloworld.PDF")); RtfWriter2.getInstance(document,new FileOutputStream(outfile)); document.addCreationDate(); document.addProducer(); document.open(); document.setPageSize(rectPageSize); //设置表格 int deep = TreeNode.getMaxDeep(); //目前只让报表支持演出部门、剧种、网站来源三级结构 if(deep!=0 && deep==4){ deep = deep - 2; //根结点不要,去掉后面的按网络媒体分类 //第一行头 float[] widths = {50f, 300f, 220f, 220f, 220f, 220f, 220f,220f,220f,220f,130f,130f};//设置表格的每一列的宽度 Table table = new Table(10 + deep); table.setWidths(widths); table.setBorderWidth(1); table.setPadding(0); table.setSpacing(0); Cell cell = null; Phrase phrase = new Phrase(); Chunk titleChunk = new Chunk("网络媒体舆情监测记录", bold4Font); //titleChunk.setBackground(new Color(0xFF, 0xFF, 0x00)); phrase.add(titleChunk); Chunk riquChunk = new Chunk(" 日期 ", new Font(bfChinese, 14, Font.NORMAL)); phrase.add(riquChunk); Map<String,Date> map = DateUtil.getDateMap(); String temp =DateUtil.dateToString(map.get("FRIDAY")) + "—" + DateUtil.dateToString(map.get("THURSDAY")); Chunk timeChunk = new Chunk(temp, new Font(bfChinese, 14, Font.UNDERLINE)); phrase.add(timeChunk); cell = new Cell(phrase); cell.setHeader(true); cell.setColspan(10 + deep); cell.setHorizontalAlignment(1); table.addCell(cell); //第二行头 Chunk chunk = new Chunk("项目", bold5Font); cell = new Cell(chunk); cell.setColspan(2); cell.setHorizontalAlignment(1); cell.setBackgroundColor(new Color(192, 192, 192)); //设置灰色 table.addCell(cell); chunk = new Chunk("网络媒体", bold5Font); cell = new Cell(chunk); cell.setHorizontalAlignment(1); cell.setBackgroundColor(new Color(192, 192, 192)); table.addCell(cell); chunk = new Chunk("周五/n" + DateUtil.dateToString(map.get("FRIDAY")),bold5Font); cell = new Cell(chunk); cell.setHorizontalAlignment(1); cell.setBackgroundColor(new Color(192, 192, 192)); table.addCell(cell); chunk = new Chunk("周六/n" + DateUtil.dateToString(map.get("SATURDAY")),bold5Font); cell = new Cell(chunk); cell.setHorizontalAlignment(1); cell.setBackgroundColor(new Color(192, 192, 192)); table.addCell(cell); chunk = new Chunk("周日/n" + DateUtil.dateToString(map.get("SUNDAY")), bold5Font); cell = new Cell(chunk); cell.setHorizontalAlignment(1); cell.setBackgroundColor(new Color(192, 192, 192)); table.addCell(cell); chunk = new Chunk("周一/n" + DateUtil.dateToString(map.get("MONDAY")), bold5Font); cell = new Cell(chunk); cell.setHorizontalAlignment(1); cell.setBackgroundColor(new Color(192, 192, 192)); table.addCell(cell); chunk = new Chunk("周二/n" + DateUtil.dateToString(map.get("TUESDAY")), bold5Font); cell = new Cell(chunk); cell.setBackgroundColor(new Color(192, 192, 192)); table.addCell(cell); cell.setHorizontalAlignment(1); chunk = new Chunk("周三/n" + DateUtil.dateToString(map.get("WEDNESDAY")), bold5Font); cell = new Cell(chunk); table.addCell(cell); cell.setHorizontalAlignment(1); cell.setBackgroundColor(new Color(192, 192, 192)); chunk = new Chunk("周四/n" + DateUtil.dateToString(map.get("THURSDAY")), bold5Font); cell = new Cell(chunk); table.addCell(cell); cell.setHorizontalAlignment(1); cell.setBackgroundColor(new Color(192, 192, 192)); chunk = new Chunk("总数",bold5Font); cell = new Cell(chunk); cell.setColspan(2); cell.setHorizontalAlignment(1); cell.setBackgroundColor(new Color(192, 192, 192)); table.addCell(cell); //头结束 table.endHeaders(); //正文表格开始 if(deptNodes==null || deptNodes.length==0) deptNodes = TreeNode.loadChild(0); //默认生取得根结点下的所有子结点 if(deptNodes!=null && deptNodes.length>0){ int rootCount=0; for(int i=0;i<deptNodes.length;i++){ TreeNode deptNode = deptNodes[i]; //得到该结点下的所有子孙结点。目前只支持演出部门、剧种、网站来源三级结构 int lineNum = 0; TreeNode[] projectNodes = TreeNode.loadChild(deptNode.getTreeid()); if(projectNodes!=null && projectNodes.length>0){ for(int j=0;j<projectNodes.length;j++){ int count = TreeNode.getChildCount(projectNodes[j].getTreeid()); lineNum += count; } } //构建演出部门这一列 chunk = new Chunk(deptNode.getName(),boldSmall5Font); cell = new Cell(chunk); cell.setRowspan(lineNum); //这种跨行可能:生成跨页的的表格的时候,总是会出现单元格截断的问题 int a = cell.getRotation(); cell.rotate(); table.addCell(cell); //开始从剧种这一级往后构建 if(projectNodes!=null && projectNodes.length>0){ for(int j=0;j<projectNodes.length;j++){ TreeNode projectNode = projectNodes[j]; //剧种 TreeNode[] siteNodes = TreeNode.loadChild(projectNode.getTreeid()); int siteLineNum = 0; if(siteNodes!=null) siteLineNum = siteNodes.length; //构建剧种这一列 chunk = new Chunk(projectNode.getName(),boldSmall5Font); cell = new Cell(chunk); cell.setRowspan(siteLineNum); cell.setVerticalAlignment(1); table.addCell(cell); //开始构建剧种这一级往后的 int allCount = 0; for(int k=0;k<siteNodes.length;k++){ TreeNode siteNode = siteNodes[k]; //网站来源 //构建网站来源这一列 chunk = new Chunk(siteNode.getName(),small5Font); cell = new Cell(chunk); table.addCell(cell); int count = 0; //周五 HashMap[] hm = TreeNode.loadNodeByCidAndDate(map.get("FRIDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0){ //只将第一个的来源列上了 count += hm.length; chunk = new Chunk(hm.length + "(" + hm[0].get("src") + ")",small5Font); if(hm.length>1) chunk = new Chunk(hm.length + "(" + hm[0].get("src") + "...)",small5Font); }else{ chunk = new Chunk(" ",small5Font); } cell = new Cell(chunk); cell.setHorizontalAlignment(1); table.addCell(cell); //周六 hm = TreeNode.loadNodeByCidAndDate(map.get("SATURDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0){ //只将第一个的来源列上了 count += hm.length; chunk = new Chunk(hm.length + "(" + hm[0].get("src") + ")",small5Font); if(hm.length>1) chunk = new Chunk(hm.length + "(" + hm[0].get("src") + "...)",small5Font); }else{ chunk = new Chunk(" ",small5Font); } cell = new Cell(chunk); cell.setHorizontalAlignment(1); table.addCell(cell); //周日 hm = TreeNode.loadNodeByCidAndDate(map.get("SUNDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0){ //只将第一个的来源列上了 count += hm.length; chunk = new Chunk(hm.length + "(" + hm[0].get("src") + ")",small5Font); if(hm.length>1) chunk = new Chunk(hm.length + "(" + hm[0].get("src") + "...)",small5Font); }else{ chunk = new Chunk(" ",small5Font); } cell = new Cell(chunk); cell.setHorizontalAlignment(1); table.addCell(cell); //周一 hm = TreeNode.loadNodeByCidAndDate(map.get("MONDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0){ //只将第一个的来源列上了 count += hm.length; chunk = new Chunk(hm.length + "(" + hm[0].get("src") + ")",small5Font); if(hm.length>1) chunk = new Chunk(hm.length + "(" + hm[0].get("src") + "...)",small5Font); }else{ chunk = new Chunk(" ",small5Font); } cell = new Cell(chunk); cell.setHorizontalAlignment(1); table.addCell(cell); //周二 hm = TreeNode.loadNodeByCidAndDate(map.get("TUESDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0){ //只将第一个的来源列上了 count += hm.length; chunk = new Chunk(hm.length + "(" + hm[0].get("src") + ")",small5Font); if(hm.length>1) chunk = new Chunk(hm.length + "(" + hm[0].get("src") + "...)",small5Font); }else{ chunk = new Chunk(" ",small5Font); } cell = new Cell(chunk); cell.setHorizontalAlignment(1); table.addCell(cell); //周三 hm = TreeNode.loadNodeByCidAndDate(map.get("WEDNESDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0){ //只将第一个的来源列上了 count += hm.length; chunk = new Chunk(hm.length + "(" + hm[0].get("src") + ")",small5Font); if(hm.length>1) chunk = new Chunk(hm.length + "(" + hm[0].get("src") + "...)",small5Font); }else{ chunk = new Chunk(" ",small5Font); } cell = new Cell(chunk); cell.setHorizontalAlignment(1); table.addCell(cell); //周四 hm = TreeNode.loadNodeByCidAndDate(map.get("THURSDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0){ //只将第一个的来源列上了 count += hm.length; chunk = new Chunk(hm.length + "(" + hm[0].get("src") + ")",small5Font); if(hm.length>1) chunk = new Chunk(hm.length + "(" + hm[0].get("src") + "...)",small5Font); }else{ chunk = new Chunk(" ",small5Font); } cell = new Cell(chunk); cell.setHorizontalAlignment(1); table.addCell(cell); //一个项目下一个站点下周五到周四的总数 if(count>0) chunk = new Chunk(count + "",small5Font); else chunk = new Chunk("未发",small5Font); cell = new Cell(chunk); cell.setHorizontalAlignment(1); table.addCell(cell); //一个项目周五到周四的总数 if(k==0){ //只生成一次 for(int n=0;n<siteNodes.length;n++){ //重新统计 siteNode = siteNodes[n]; hm = TreeNode.loadNodeByCidAndDate(map.get("FRIDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0) allCount += hm.length; hm = TreeNode.loadNodeByCidAndDate(map.get("SATURDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0) allCount += hm.length; hm = TreeNode.loadNodeByCidAndDate(map.get("SUNDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0) allCount += hm.length; hm = TreeNode.loadNodeByCidAndDate(map.get("MONDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0) allCount += hm.length; hm = TreeNode.loadNodeByCidAndDate(map.get("TUESDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0) allCount += hm.length; hm = TreeNode.loadNodeByCidAndDate(map.get("WEDNESDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0) allCount += hm.length; hm = TreeNode.loadNodeByCidAndDate(map.get("THURSDAY"),siteNode.getTreeid(),siteNode.getName()); if(hm!=null && hm.length>0) allCount += hm.length; } chunk = new Chunk(allCount + "",small5Font); cell = new Cell(chunk); cell.setRowspan(siteLineNum); cell.setHorizontalAlignment(1); table.addCell(cell); rootCount += allCount; } } } } } //最后汇总 chunk = new Chunk("总数",bold5Font); cell = new Cell(chunk); cell.setColspan(deep); cell.setHorizontalAlignment(1); table.addCell(cell); chunk = new Chunk(rootCount + "",small5Font); cell = new Cell(chunk); cell.setColspan(10); cell.setHorizontalAlignment(1); table.addCell(cell); } document.add(table); } }catch (Exception e) { e.printStackTrace(); throw new Exception(e.getMessage()); } finally{ if(document!=null){ document.close(); } } } public static void mergePdf(String[] args, String finalFile) { try { int pageOffset = 0; ArrayList master = new ArrayList(); int f = 0; String outFile = finalFile; Document document = null; PdfCopy writer = null; while (f < args.length) { // we create a reader for a certain document PdfReader reader = new PdfReader(args[f]); reader.consolidateNamedDestinations(); // we retrieve the total number of pages int n = reader.getNumberOfPages(); List bookmarks = SimpleBookmark.getBookmark(reader); if (bookmarks != null) { if (pageOffset != 0) SimpleBookmark.shiftPageNumbers(bookmarks, pageOffset, null); master.addAll(bookmarks); } pageOffset += n; if (f == 0) { // step 1: creation of a document-object document = new Document(reader.getPageSizeWithRotation(1)); // step 2: we create a writer that listens to the document writer = new PdfCopy(document, new FileOutputStream(outFile)); // step 3: we open the document document.open(); } // step 4: we add content PdfImportedPage page; for (int i = 0; i < n; ) { ++i; page = writer.getImportedPage(reader, i); writer.addPage(page); } PRAcroForm form = reader.getAcroForm(); if (form != null) writer.copyAcroForm(reader); f++; } if (!master.isEmpty()) writer.setOutlines(master); // step 5: we close the document document.close(); } catch(Exception e) { e.printStackTrace(); } } /** * @param args */ public static void main(String[] args) { try { ReportTable.creatReportTable("e://HelloWorld.doc",null); } catch (Exception e) { e.printStackTrace(); } } }