PDF笔记(二):Itext 实际项目案例
来源:互联网 发布:什么是栅格数据 编辑:程序博客网 时间:2024/06/06 03:29
一、PDF打印的思路:
(一)、输出生成: PDFPractise.java
package pdf.practise;import java.io.FileOutputStream;import java.io.IOException;import com.itextpdf.text.BaseColor;import com.itextpdf.text.Chunk;import com.itextpdf.text.Document;import com.itextpdf.text.DocumentException;import com.itextpdf.text.Element;import com.itextpdf.text.Font;import com.itextpdf.text.Image;import com.itextpdf.text.PageSize;import com.itextpdf.text.Paragraph;import com.itextpdf.text.Phrase;import com.itextpdf.text.Rectangle;import com.itextpdf.text.pdf.BaseFont;import com.itextpdf.text.pdf.PdfPCell;import com.itextpdf.text.pdf.PdfPTable;import com.itextpdf.text.pdf.PdfWriter;/** * * @Title: 单纯输出PDF报表 * @Description: * @Copyright: Copyright (c) 2014 * @Company: SinoSoft * * @author: ShaoMin * @version: 1.0 * @CreateDate:Nov 5, 2014 */public class PDFPractise { /** * @author ShaoMin * @param args */ public static void main(String[] args) { PDFPractise tPDFPractise = new PDFPractise(); try { tPDFPractise.createPdfFile(); // tPDFPractise.createPDFFile(); } catch (Exception e) { e.printStackTrace(); } } /** * 创建PDF * * @author ShaoMin * @throws Exception */ public void createPdfFile() throws Exception { Document doc = new Document(); FileOutputStream out = new FileOutputStream("temp/pdf/practisePdfFile.pdf"); PdfWriter.getInstance(doc, out); doc.open(); BaseFont bfChinese = BaseFont.createFont("STSongStd-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED); Font titleFont = new Font(bfChinese, 16, Font.BOLD);// 标题 Font tableTitleFont = new Font(bfChinese, 12, Font.BOLD);// 表格标题 Font conyentFont = new Font(bfChinese, 12, Font.NORMAL);// 内容 Paragraph title = new Paragraph("受理材料收取凭证", titleFont); title.setAlignment(Rectangle.ALIGN_CENTER);// 居中 doc.add(title); StringBuffer strBuff = new StringBuffer(); strBuff.append("兹收到客户 " + "SAM-SHO"); strBuff.append("(先生/女士)提交的保单号为 " + "123456789009876"); strBuff.append(" 的申请材料,共 " + " 2 " + " 张保单。"); Paragraph content = new Paragraph(strBuff.toString(), conyentFont); content.setAlignment(Rectangle.ALIGN_JUSTIFIED); content.setFirstLineIndent(15f);// 首行缩进 content.setSpacingBefore(30f);// 上留白 doc.add(content); String cont2 = "申请保全项目 " + " CM-退保"; content = new Paragraph(cont2, conyentFont); content.setAlignment(Rectangle.ALIGN_JUSTIFIED); content.setFirstLineIndent(15f);// 首行缩进 content.setSpacingBefore(15f);// 上留白 doc.add(content); String cont3 = "所提供材料明细如下:"; content = new Paragraph(cont3, conyentFont); content.setAlignment(Rectangle.ALIGN_JUSTIFIED); content.setFirstLineIndent(15f);// 首行缩进 content.setSpacingBefore(15f);// 上留白 content.setSpacingAfter(15f);// 下留白 doc.add(content); // 表格的处理是难点,特别是表格的跨行跨列 // 可以使用跨行也可以使用表格嵌套 int tCol = 5; PdfPTable table = new PdfPTable(tCol); table.setHorizontalAlignment(Element.ALIGN_LEFT); table.setTotalWidth(500f); table.setWidths(new float[] { 0.4f, 0.25f, 0.25f, 0.25f, 0.25f }); table.setWidthPercentage(100); table.setLockedWidth(true); String strTableTitle = "申请材料名称"; Paragraph tableTitle = new Paragraph(strTableTitle, tableTitleFont); PdfPCell cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 cell.setRowspan(2);// 跨2行 table.addCell(cell); strTableTitle = "申请材料类型"; tableTitle = new Paragraph(strTableTitle, tableTitleFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 cell.setColspan(2);// 跨2列 table.addCell(cell); strTableTitle = "收取页数/份数"; tableTitle = new Paragraph(strTableTitle, tableTitleFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 cell.setRowspan(2);// 跨2行 table.addCell(cell); strTableTitle = "备注"; tableTitle = new Paragraph(strTableTitle, tableTitleFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 cell.setRowspan(2);// 跨2行 table.addCell(cell); // 这边属于第二行的表格 // 思路上,这点很关键 strTableTitle = "原件"; tableTitle = new Paragraph(strTableTitle, tableTitleFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 table.addCell(cell); strTableTitle = "复印件"; tableTitle = new Paragraph(strTableTitle, tableTitleFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 table.addCell(cell); String[] arrTitle = { "保险合同", "保险合同收据或发票", "保单贷款申请书", "保全变更申请书", "被保险人变更清单", "健康及财务告知", "授权委托书", "投保人身份证件", "被保险人身份证件", "身故受益人身份证件", "受托人身份证件", "投保人账号", "被保险人/监护人账号 ", "生存证明", "关系证明 ", "其他受理材料 " }; int tRow = arrTitle.length; for (int i = 0; i < tRow; i++) { for (int j = 0; j < tCol; j++) { if (j == 0) { // 左侧标题 strTableTitle = arrTitle[i]; tableTitle = new Paragraph(strTableTitle, conyentFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_LEFT);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 table.addCell(cell); } else { strTableTitle = i + "--" + j; tableTitle = new Paragraph(strTableTitle, conyentFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 table.addCell(cell); } } } table.setSpacingAfter(15f);// 下留白 doc.add(table); // 所有的都要指定中文,不然显示不出来 // Phrase没有位置的操作,但是空格会被保留 // 也可以使用表格处理,隐藏边框即可 Phrase tPhrase = new Phrase(" 申请人: " + " " + " " + "保全试算金额:", conyentFont); Paragraph tParagraph = new Paragraph(tPhrase); doc.add(tParagraph); // 尾部表格处理 PdfPTable footTable = new PdfPTable(2); footTable.setTotalWidth(760f); footTable.setWidths(new float[] { 4.6f, 1f }); footTable.setHorizontalAlignment(Element.ALIGN_LEFT); strTableTitle = " 申请日期:"; tableTitle = new Paragraph(strTableTitle, conyentFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_LEFT);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 cell.setBorderWidth(0); footTable.addCell(cell); strTableTitle = "受理人:"; tableTitle = new Paragraph(strTableTitle, conyentFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_LEFT);// 水平居中 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 cell.setBorderWidth(0); footTable.addCell(cell); strTableTitle = " 申请人电话:"; tableTitle = new Paragraph(strTableTitle, conyentFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_LEFT);// cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 cell.setBorderWidth(0); footTable.addCell(cell); strTableTitle = "受理日期:"; tableTitle = new Paragraph(strTableTitle, conyentFont); cell = new PdfPCell(tableTitle); cell.setHorizontalAlignment(Element.ALIGN_LEFT);// cell.setVerticalAlignment(Element.ALIGN_MIDDLE);// 垂直居中 cell.setBorderWidth(0); footTable.addCell(cell); doc.add(footTable); tParagraph = new Paragraph(); Chunk tChunk = new Chunk(" 说明: ",conyentFont); tParagraph.add(tChunk); tChunk = new Chunk(" ",conyentFont); tChunk.setUnderline(0.1f, -2f); tParagraph.add(tChunk); tChunk = new Chunk(" ",conyentFont); tChunk.setUnderline(0.1f, -2f); tParagraph.add(tChunk); tChunk = new Chunk(" ",conyentFont); tChunk.setUnderline(0.1f, -2f); tParagraph.add(tChunk); tParagraph.setLeading(30f); tChunk = new Chunk(" ",conyentFont); tChunk.setUnderline(0.1f, -2f); tParagraph.add(tChunk); tChunk = new Chunk(" ",conyentFont); tChunk.setUnderline(0.1f, -2f); tParagraph.add(tChunk); doc.add(tParagraph); doc.close(); System.out.println("结束....."); } /** * * @author ShaoMin * */ public void createPDFFile() { Document document = new Document(PageSize.A4, 80, 79, 20, 45); // A4纸大小,// // 左、右、上、下 try { // 中文处理 BaseFont bfChinese = BaseFont.createFont("STSongStd-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED); Font FontChinese = new Font(bfChinese, 14, Font.COURIER); // 其他所有文字字体 Font BoldChinese = new Font(bfChinese, 14, Font.BOLD); // 粗体 Font titleChinese = new Font(bfChinese, 20, Font.BOLD); // 模板抬头的字体 Font moneyFontChinese = new Font(bfChinese, 8, Font.COURIER); // 币种和租金金额的小一号字体 Font subBoldFontChinese = new Font(bfChinese, 8, Font.BOLD); // 币种和租金金额的小一号字体 // 使用PDFWriter进行写文件操作 PdfWriter.getInstance(document, new FileOutputStream("temp/pdf/pdfFile.pdf")); document.open(); // 打开文档 // ------------开始写数据------------------- Paragraph title = new Paragraph("起租通知书", titleChinese);// 抬头 title.setAlignment(Element.ALIGN_CENTER); // 居中设置 title.setLeading(1f);// 设置行间距//设置上面空白宽度 document.add(title); title = new Paragraph("致:XXX公司", BoldChinese);// 抬头 title.setSpacingBefore(25f);// 设置上面空白宽度 document.add(title); title = new Paragraph(" 贵我双方签署的编号为 XXX有关起租条件已满足,现将租赁合同项下相关租赁要素明示如下:", FontChinese); title.setLeading(22f);// 设置行间距 document.add(title); float[] widths = { 10f, 25f, 30f, 30f };// 设置表格的列宽和列数 默认是4列 PdfPTable table = new PdfPTable(widths);// 建立一个pdf表格 table.setSpacingBefore(20f);// 设置表格上面空白宽度 table.setTotalWidth(500);// 设置表格的宽度 table.setWidthPercentage(100);// 设置表格宽度为%100 // table.getDefaultCell().setBorder(0);//设置表格默认为无边框 String[] tempValue = { "1", "2011-07-07", "2222元", "233元", "2014-12-22", "3000元", "9999元" }; // 租金期次列表 int rowCount = 1; // 行计数器 PdfPCell cell = null; // ---表头 cell = new PdfPCell(new Paragraph("期次", subBoldFontChinese));// 描述 cell.setFixedHeight(20); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 设置内容水平居中显示 cell.setVerticalAlignment(Element.ALIGN_MIDDLE); // 设置垂直居中 table.addCell(cell); cell = new PdfPCell(new Paragraph("租金日", subBoldFontChinese));// 描述 cell.setFixedHeight(20); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 设置内容水平居中显示 cell.setVerticalAlignment(Element.ALIGN_MIDDLE); // 设置垂直居中 table.addCell(cell); cell = new PdfPCell(new Paragraph("各期租金金额", subBoldFontChinese));// 描述 cell.setFixedHeight(20); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 设置内容水平居中显示 cell.setVerticalAlignment(Element.ALIGN_MIDDLE); // 设置垂直居中 table.addCell(cell); cell = new PdfPCell(new Paragraph("各期租金后\n剩余租金", subBoldFontChinese));// 描述 cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 设置内容水平居中显示 cell.setVerticalAlignment(Element.ALIGN_MIDDLE); // 设置垂直居中 cell.setFixedHeight(20); table.addCell(cell); for (int j = 1; j < tempValue.length; j++) { if (j % 2 == 1) { // 第一列 日期 cell = new PdfPCell(new Paragraph(rowCount + "", moneyFontChinese));// 描述 cell.setFixedHeight(20); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 设置内容水平居中显示 cell.setVerticalAlignment(Element.ALIGN_MIDDLE); // 设置垂直居中 table.addCell(cell); rowCount++; } cell = new PdfPCell(new Paragraph(tempValue[j], moneyFontChinese));// 描述 cell.setFixedHeight(20); cell.setHorizontalAlignment(Element.ALIGN_CENTER);// 设置内容水平居中显示 cell.setVerticalAlignment(Element.ALIGN_MIDDLE); // 设置垂直居中 table.addCell(cell); } document.add(table); title = new Paragraph(" 租金总额:XXX", FontChinese); title.setLeading(22f);// 设置行间距 document.add(title); title = new Paragraph(" 特此通知!", FontChinese); title.setLeading(22f);// 设置行间距 document.add(title); // -------此处增加图片和日期,因为图片会遇到跨页的问题,图片跨页,图片下方的日期就会脱离图片下方会放到上一页。 // 所以必须用表格加以固定的技巧来实现 float[] widthes = { 50f };// 设置表格的列宽和列数 PdfPTable hiddenTable = new PdfPTable(widthes);// 建立一个pdf表格 hiddenTable.setSpacingBefore(11f); // 设置表格上空间 hiddenTable.setTotalWidth(500);// 设置表格的宽度 hiddenTable.setWidthPercentage(100);// 设置表格宽度为%100 hiddenTable.getDefaultCell().disableBorderSide(1); hiddenTable.getDefaultCell().disableBorderSide(2); hiddenTable.getDefaultCell().disableBorderSide(4); hiddenTable.getDefaultCell().disableBorderSide(8); Image upgif = Image.getInstance("source/imag/bage.png"); upgif.scalePercent(7.5f);// 设置缩放的百分比%7.5 upgif.setAlignment(Element.ALIGN_RIGHT); cell = new PdfPCell(new Paragraph("", FontChinese));// 描述 cell.setHorizontalAlignment(Element.ALIGN_RIGHT);// 设置内容水平居中显示 cell.addElement(upgif); cell.setPaddingTop(0f); // 设置内容靠上位置 cell.setPaddingBottom(0f); cell.setPaddingRight(20f); cell.setBorder(Rectangle.NO_BORDER);// 设置单元格无边框 hiddenTable.addCell(cell); cell = new PdfPCell(new Paragraph("XX 年 XX 月 XX 日 ", FontChinese));// 金额 cell.setHorizontalAlignment(Element.ALIGN_RIGHT);// 设置内容水平居中显示 cell.setPaddingTop(0f); cell.setPaddingRight(20f); cell.setBorder(Rectangle.NO_BORDER); hiddenTable.addCell(cell); document.add(hiddenTable); System.out.println("拼装起租通知书结束..."); document.close(); } catch (DocumentException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } /** * 支持中文 * * @return */ public Font getChineseFont() { BaseFont bfChinese; Font fontChinese = null; try { bfChinese = BaseFont.createFont("STSongStd-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED); // fontChinese = new Font(bfChinese, 12, Font.NORMAL); fontChinese = new Font(bfChinese, 12, Font.NORMAL, BaseColor.BLUE); } catch (DocumentException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } return fontChinese; }}
(二)、使用模板 : PdfTempletePractise.java
package pdf.practise;import java.io.FileOutputStream;import java.io.IOException;import java.util.ArrayList;import java.util.HashMap;import java.util.List;import java.util.Map;import com.itextpdf.text.BaseColor;import com.itextpdf.text.DocumentException;import com.itextpdf.text.Element;import com.itextpdf.text.Font;import com.itextpdf.text.Paragraph;import com.itextpdf.text.pdf.AcroFields;import com.itextpdf.text.pdf.AcroFields.Item;import com.itextpdf.text.pdf.BaseFont;import com.itextpdf.text.pdf.PdfContentByte;import com.itextpdf.text.pdf.PdfPCell;import com.itextpdf.text.pdf.PdfPTable;import com.itextpdf.text.pdf.PdfReader;import com.itextpdf.text.pdf.PdfStamper;/** * * @Title: 模板报表制作 * @Description: * @Copyright: Copyright (c) 2014 * @Company: SinoSoft * * @author: ShaoMin * @version: 1.0 * @CreateDate:Nov 5, 2014 */public class PdfTempletePractise { protected PdfStamper mPdfStamper = null;// pdf解析器 // 定义动态表的各类数据 private final int TABLE_COLNUM = 4;// 整个表格列数 private final float TABLE_WIDTH = 369.7f;// 整个表格宽度 private final float ROW_HEIGHT = 19.19f;// 单元格高度 private final float XPOS = 174.52f;// 整个表格 X坐标 private final float YPOS = 569.18f; // 整个表格 Y坐标 private final float[] ROW_WIDTHS = { 0.2565f, 0.25f, 0.25f, 0.245f };// 单元格宽度 /** * @author ShaoMin * @param args */ public static void main(String[] args) { PdfTempletePractise tPdfTemplete = new PdfTempletePractise(); Map<String, String> mMapDatas = new HashMap<String, String>(); mMapDatas.put("PdfResultFile", "temp/pdf/templetePdfFile.pdf");// 生成的文件路径 mMapDatas.put("PdfTemplateFile", "source/pdf/templete/EdorAcceptResource.pdf");// 获取模板路径 mMapDatas.put("CustomerName", "SAM-SHO");// 客户姓名 mMapDatas.put("ContNo", "123456789098765");// 合同号 mMapDatas.put("ContCount", "1");// 保单个数 mMapDatas.put("EdorType", "CT-退保");// 保全类型 mMapDatas.put("GetMoney", "999.99");// 保全失算金额 mMapDatas.put("AcceptName", "人寿保险");// 受理人 mMapDatas.put("AcceptDate", "2014-14-1");// 受理日期 tPdfTemplete.fillTempleteDates(mMapDatas);// 表单域数据 List<String[]> tableLists = new ArrayList<String[]>(); for (int i = 0; i < 16; i++) { String[] arrStr = new String[4]; arrStr[0] = i + "--" + 0; arrStr[1] = i + "--" + 1; arrStr[2] = i + "--" + 2; arrStr[3] = i + "--" + 3; tableLists.add(arrStr); } tPdfTemplete.createTable(tableLists); System.out.println("完成........."); } /** * 填充模板数据,表单域数据 * * @author ShaoMin * @param map */ @SuppressWarnings("unchecked") protected boolean fillTempleteDates(Map<String, String> map) { String tPdfResultFile = map.get("PdfResultFile");// 生成的文件路径 String tPdfTemplateFile = map.get("PdfTemplateFile");// 获取模板路径 FileOutputStream fos = null; PdfReader reader = null; try { fos = new FileOutputStream(tPdfResultFile);// 需要生成PDF reader = new PdfReader(tPdfTemplateFile);// 模板 mPdfStamper = new PdfStamper(reader, fos);// 解析 AcroFields form = mPdfStamper.getAcroFields();// 获取到模板上预定义的参数域 // 获取模板中定义的变量 Map<String, Item> acroFieldMap = form.getFields(); for (Map.Entry<String, Item> entry : acroFieldMap.entrySet()) { // 获得块名 String fieldName = entry.getKey(); String fieldValue = map.get(fieldName);// 通过名字,获取传入的参数值 if (!"".equals(fieldValue)) { // 为模板中的变量赋值 form.setField(fieldName, fieldValue); System.out.println(fieldName + "," + fieldValue); } } // 模板中的变量赋值之后不能编辑 mPdfStamper.setFormFlattening(true); reader.close();// 阅读器关闭,解析器暂时不关闭,因为创建动态表格还需要使用 } catch (Exception e) { e.printStackTrace(); return false; } finally { if (reader != null) { reader.close(); } } return true; } /** * 创建表格 * * @author ShaoMin * @param resultList * @return */ protected boolean createTable(List<String[]> resultList) { PdfPTable table = new PdfPTable(TABLE_COLNUM);// 创建表格 PdfPCell cell = null; try { for (String[] tResults : resultList) { for (int i = 0; i < tResults.length; i++) { // 创建单元格,并置上值 Paragraph para = new Paragraph(tResults[i], getChineseFont()); para.setAlignment(Element.ALIGN_CENTER); cell = new PdfPCell(para); // cell.setBorderWidth(0)//边框 cell.setFixedHeight(ROW_HEIGHT);// 单元格高度 cell.setHorizontalAlignment(Element.ALIGN_CENTER);//水平位置 cell.setVerticalAlignment(Element.ALIGN_MIDDLE);//垂直位置 table.addCell(cell);// 单元格加入动态表格 } } table.setWidths(ROW_WIDTHS);// 设置每个单元格的宽度,是比例关系 table.setTotalWidth(TABLE_WIDTH);// 总宽度 PdfContentByte tContent = mPdfStamper.getOverContent(1);// 获取模板的层次 table.writeSelectedRows(0, -1, 0, -1, XPOS, YPOS, tContent);// 把表格写入模板的固定位置(0行-最后一行| 0列-最后一列) mPdfStamper.close();// 关闭解析器 } catch (DocumentException e) { e.printStackTrace(); return false; } catch (IOException e) { e.printStackTrace(); return false; } finally { try { if (mPdfStamper != null) { mPdfStamper.close();// 关闭解析器 } } catch (DocumentException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } return true; } /** * 支持中文 * * @return */ public Font getChineseFont() { BaseFont bfChinese; Font fontChinese = null; try { bfChinese = BaseFont.createFont("STSongStd-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED); // fontChinese = new Font(bfChinese, 12, Font.NORMAL); fontChinese = new Font(bfChinese, 12, Font.NORMAL, BaseColor.BLUE); } catch (DocumentException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } return fontChinese; }}
二、PDF打印设计:
1、核心:
1)模板方法设计模式:Template Method设计
2)抽象类的使用
2、实现
1)打印抽象类:AbstractPDFPrintBL.java
2)实例,受理凭证打印: EdorAcceptPDFPrintBL.java
3)实际使用的过程中需要传递List和map容器的数据。表格数据放入List,其他数据放入Map。
3、代码如下:
1)抽象类如下:
package com.sinosoft.lis.agentprint;import java.io.File;/** * @Title: PDF打印公共类 * @Description:其他PDF打印类,都可以继承本类,例如受理凭证打印类:EdorAcceptPDFPrintBL * @Copyright: Copyright (c) 2014 * @Company: * * @author: ShaoMin * @version: 1.0 * @CreateDate:Oct 27, 2014 */public abstract class AbstractPDFPrintBL { protected Logger logger = Logger.getLogger(getClass()); protected CErrors mErrors = new CErrors(); /** 存放动态表格的数据 */ protected List<String[]> lists = new ArrayList<String[]>(); /** 用于存放要填充的模板数据 */ protected Map<String, String> map = new HashMap<String, String>(); protected PdfStamper mPdfStamper = null;// pdf解析器 /** * 传输数据的公共方法 */ public boolean submitData() { // 获取数据 if (!getInput()) { return false; } // 数据校验 if (!checkDatas()) { return false; } // 打印处理 if (!dealData()) { return false; } return true; } /** * 获取必要的数据 * * @author ShaoMin * @return */ protected abstract boolean getInput(); /** * 数据校验 * * @author ShaoMin * @return */ protected abstract boolean checkDatas(); /** * 业务处理 * * @author ShaoMin * @return */ private boolean dealData() { // 删除临时文件 this.deleteTempFile(); // 填充模板数据 if (!fillTempleteDates(map)) { try { if (mPdfStamper != null) { mPdfStamper.close(); } } catch (DocumentException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } return false; } // 写入动态数据创建表格 if (lists != null && !lists.isEmpty()) { if (!createTable(lists)) { return false; } } // 不使用模板,直接输出PDF if(!createPdfFile()){ return false; } return true; } /** * 不使用模板,直接输出PDF(可以输出文本和表格) * @author ShaoMin * @return */ protected boolean createPdfFile() { return true; } /** * 生成pdf的动态表格,子类可以重写实现复杂逻辑 * 没有表格输出,在构造函数时,传入空的集合即可。 * 如Collections.EMPTY_LIST,不建议直接传null * @author ShaoMin * @param resultList * @return * @throws Exception */ protected abstract boolean createTable(List<String[]> resultList); /** * 支持汉字 */ protected BaseFont getBaseFont() { BaseFont tBaseFont = null; try { tBaseFont = BaseFont.createFont("STSongStd-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED); } catch (Exception e) { e.printStackTrace(); return null; } return tBaseFont; } /** * 删除临时文件 * @author ShaoMin * @param filePath * @return */ private boolean deleteTempFile() { String tPdfResultFile = map.get("PdfResultFile"); File tFile = new File(tPdfResultFile); if (tFile.exists() && tFile.isFile()) { tFile.delete(); } return true; } /** * 填充模板数据,子类可以重写实现复杂逻辑 * @author ShaoMin * @param map */ @SuppressWarnings("unchecked") protected boolean fillTempleteDates(Map<String, String> map) { String tPdfResultFile = map.get("PdfResultFile");// 生成的文件路径 String tPdfTemplateFile = map.get("PdfTemplateFile");// 获取模板路径 FileOutputStream fos = null; PdfReader reader = null; try { fos = new FileOutputStream(tPdfResultFile);// 需要生成PDF reader = new PdfReader(tPdfTemplateFile);// 模板 mPdfStamper = new PdfStamper(reader, fos);// 解析 AcroFields form = mPdfStamper.getAcroFields();// 获取到模板上预定义的参数域 // 获取模板中定义的变量 Map<String, Item> acroFieldMap = form.getFields(); for (Map.Entry<String, Item> entry : acroFieldMap.entrySet()) { // 获得块名 String fieldName = entry.getKey(); String fieldValue = map.get(fieldName);// 通过名字,获取传入的参数值 if (!"".equals(fieldValue)) { // 为模板中的变量赋值 form.setField(fieldName, fieldValue); System.out.println(fieldName + "," + fieldValue); } } // 模板中的变量赋值之后不能编辑 mPdfStamper.setFormFlattening(true); reader.close();// 阅读器关闭,解析器暂时不关闭,因为创建动态表格还需要使用 } catch (Exception e) { e.printStackTrace(); return false; } finally { if (reader != null) { reader.close(); } } return true; } /** * 判断字符串是否为空 * @param str 字符串 * @return boolean */ protected boolean isEmpty(String str) { if (str == null || "".equals(str)) { return true; } return false; } /** * 判断字符串不为空 * @param str 字符串 * @return boolean */ protected boolean isNotEmpty(String str) { return !isEmpty(str); } public void setLists(ArrayList<String[]> lists) { this.lists = lists; } public void setMap(Map<String, String> map) { this.map = map; }}
package com.sinosoft.lis.agentprint;import java.io.IOException;/** * * @Title: 受理凭证打印类 * @Description: * @Copyright: Copyright (c) 2014 * @Company: * * @author: SAM * @version: 1.0 * @CreateDate:2014-5-27 */public class EdorAcceptPDFPrintBL extends AbstractPDFPrintBL { // 定义动态表的各类数据 private final int TABLE_COLNUM = 4;// 整个表格列数 private final float TABLE_WIDTH = 369.7f;// 整个表格宽度 private final float ROW_HEIGHT = 19.19f;// 单元格高度 private final float XPOS = 174.52f;// 整个表格 X坐标 private final float YPOS = 569.18f; // 整个表格 Y坐标// private final int TABLE_BORDER = 120;// 表格的边框 private final float FONT_SIZE = 8f;// 字体的大小 private final float[] ROW_WIDTHS = {0.2565f, 0.25f, 0.25f, 0.245f};//单元格宽度 // 私有构造方法 private EdorAcceptPDFPrintBL() { } private EdorAcceptPDFPrintBL(Map<String, String> map, List<String[]> lists) { this.map = map; this.lists = lists; } public static EdorAcceptPDFPrintBL getIntance() { return new EdorAcceptPDFPrintBL(); } /** * 私有静态工厂方法,取代构造方法使用 * 如不需要动态表格的打印,这边lists参数可以传入空的集合 * 如Collections.EMPTY_LIST,不建议直接传null * @author ShaoMin * @param map * @param lists * @return */ public static EdorAcceptPDFPrintBL getIntanceByColection(Map<String, String> map, List<String[]> lists) { return new EdorAcceptPDFPrintBL(map, lists); } @Override public boolean checkDatas() { if (map == null || map.isEmpty()) { mErrors.addOneError("数据传输失败"); return false; } if (lists == null || lists.isEmpty()) { mErrors.addOneError("数据传输失败"); return false; } return true; } @Override protected boolean getInput() { return true; } @Override protected boolean createTable(List<String[]> resultList) { PdfContentByte tContent = mPdfStamper.getOverContent(1);//获取模板的层次 PdfPTable table = new PdfPTable(TABLE_COLNUM); PdfPCell cell = null; try { //设置中文字体 BaseFont bfChinese = this.getBaseFont(); Font subBoldFontChinese = new Font(bfChinese, FONT_SIZE, Font.NORMAL); for (String[] tResults : resultList) { for (int i = 0; i < tResults.length; i++) { //创建单元格,并置上值 Paragraph para = new Paragraph(tResults[i], subBoldFontChinese); para.setAlignment(Element.ALIGN_CENTER); cell = new PdfPCell(para); // cell.setBorder(TABLE_BORDER);//边框 cell.setFixedHeight(ROW_HEIGHT);// 单元格高度 cell.setHorizontalAlignment(Element.ALIGN_CENTER); cell.setVerticalAlignment(Element.ALIGN_MIDDLE); table.addCell(cell);//单元格加入动态表格 } } table.setWidths(ROW_WIDTHS);// 设置每个单元格的宽度 table.setTotalWidth(TABLE_WIDTH);// 总宽度 table.writeSelectedRows(0, -1, 0, -1, XPOS, YPOS, tContent);//把表格写入模板的固定位置 mPdfStamper.close();//关闭解析器 } catch (DocumentException e) { e.printStackTrace(); return false; } catch (IOException e) { e.printStackTrace(); return false; } finally { try { if (mPdfStamper != null) { mPdfStamper.close();//关闭解析器 } } catch (DocumentException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } return true; } }
3)调用代码如下:
// 1- 定义必要容器mMapDatas = new HashMap<String, String>();mListDatas = new ArrayList<String[]>();// 2-封装map数据// 2-1 获取必要信息:如文件名称、保全类型名等,并封装map数据mMapDatas.put("PdfTemplateFile", "templte.pdf");// PDF模版文件mMapDatas.put("PdfResultFile", "result.psd");// 生成PDF文件mMapDatas.put("PdfTempPath", "tem/pdf");// 生成PDF临时路径mMapDatas.put("CustomerName", “Sam-SHO”);// 客户姓名mMapDatas.put("ContNo", "123456789");// 合同号mMapDatas.put("ContCount", "1");// 保单个数mMapDatas.put("EdorType", "CT-退保");// 保全类型mMapDatas.put("GetMoney", "200"));// 保全失算金额mMapDatas.put("AcceptName", "SAM");// 受理人mMapDatas.put("AcceptDate", "2014-11-07");// 受理日期// 3-封装list数据// 3-1 获取受理资料信息-// 3-2 封装list数据for (int i = 1; i <= B.size(); i++) { A a = B.get(i); String[] strArr = new String[4];// 4列数据 String tCopyFlag = a.getResourceCopyFlag(); // 0-原件;1-复印件;2-无 strArr[0] = "0".equals(tCopyFlag) ? "Y" : "";// 原件 strArr[1] = "1".equals(tCopyFlag) ? "Y" : "";// 复印件 strArr[2] = a.getResourcePages();// 份数 strArr[3] = a.getResourceDesc();// 备注 mListDatas.add(strArr);}// 4-调用打印类EdorAcceptPDFPrintBL tPdfPrint = EdorAcceptPDFPrintBL.getIntanceByColection(mMapDatas, mListDatas);if (!tPdfPrint.submitData()) {return false;}
0 0
- PDF笔记(二):Itext 实际项目案例
- PDF笔记(二):Itext 实际项目案例
- PDF笔记(二):Itext 实际项目案例
- iText制作PDF文件 学习笔记 (二)
- iText操作PDF学习(二)
- PDF笔记(一):Itext 的基础知识
- PDF笔记(三):Itext学习
- iText操作PDF之学习笔记
- Itext笔记之pdf页眉页脚
- PDF笔记(一):Itext 的基础知识
- PDF笔记(一):Itext 的基础知识
- iText:iText构造PDF文件
- itext pdf 加页眉和页脚加页数(二)
- Spring AOP实际项目中使用案例
- SpringAop在实际项目中的使用案例
- iText制作PDF文件 学习笔记 (一)
- iText制作PDF文件 学习笔记 (三)
- iText制作PDF文件 学习笔记 (四)
- 关于Chartboost的视频广告
- POJ 1351-Number of Locks(记忆化搜索)
- Monty Python_From Wikipedia
- CF - 474 - D. Flowers(dp)
- nfs: server 192.168.1.150 not responding, still trying
- PDF笔记(二):Itext 实际项目案例
- java 数字签名快捷方法
- 常见进程间的通信方式
- Zookeeper的单机安装和调试
- mybatis加Spring项目: 解决There is no getter for property named '***' in 'class java.lang.String'问题
- linux iic driver1
- 用两个栈实现一个队列,用两个队列实现一个栈,C++ STL版
- git config第三篇——git的常用配置
- UVA 10115