最近项目需要根据客户填写的信息,依照模板生成一个pdf文件。
要是格式是固定的类型,可以使用Adobe Acrobat DC将模板的pdf文件转化成可以编辑的类型,然后根据编辑时候取的变量名字一一将数据插入。
首先需要导入itextpdf的jar包。
// 模板路径
String templatePath = "E:/test.pdf";
// 生成的新文件路径
String newPDFPath = "E:/ceshi.pdf";
PdfReader reader;
FileOutputStream out;
ByteArrayOutputStream bos;
PdfStamper stamper;
try {
BaseFont bf = BaseFont.createFont("C:/Windows/Fonts/SIMYOU.TTF",BaseFont.IDENTITY_H,BaseFont.NOT_EMBEDDED); //设置中文字体
Font font = new Font(bf, 12, Font.NORMAL);
out = new FileOutputStream(newPDFPath);// 输出流
reader = new PdfReader(templatePath);// 读取pdf模板
bos = new ByteArrayOutputStream();
stamper = new PdfStamper(reader, bos);
AcroFields form = stamper.getAcroFields(); //获取表单
String[] str = { "2017-05-10", "12345678", "LC123456", "2017-05-10", "深圳XXXXX有限公司", "4567890132","深圳市XXXX室", "34267687","123344","深圳市XXXXX室"};
int i = 0;
java.util.Iterator<String> it = form.getFields().keySet().iterator();
//赋值
while (it.hasNext()) {
String name = it.next().toString();
form.setFieldProperty(name, "textfont", bf, null);
form.setField(name, str[i++]);
}
stamper.setFormFlattening(true);// 如果为false那么生成的PDF文件还能编辑,一定要设为true
stamper.close();
Document doc = new Document();
PdfCopy copy = new PdfCopy(doc, out);
doc.open();
PdfImportedPage importPage = copy.getImportedPage(new PdfReader(bos.toByteArray()), 1);
copy.addPage(importPage);
doc.close();
} catch (IOException e) {
e.printStackTrace();
} catch (DocumentException e) {
e.printStackTrace();
}
但是因为要根据用户输入的信息,动态的生成一个对应的表格。所以最后就直接按照模板生成了一个新的pdf。
这个主要就是使用段落、表格进行布局,中间拼接一些数据就OK了。(最后做出来的文件不是很好看,还是要在字体和布局上进行修改)
//实例化文档对象
Document document = new Document(PageSize.A4, 50, 50, 50, 50);
//设置中文字体
BaseFont bfChinese =
BaseFont.createFont("C:/Windows/Fonts/simhei.ttf",BaseFont.IDENTITY_H, BaseFont.NOT_EMBEDDED);
//字体
Font titleChinese = new Font(bfChinese, 18, Font.BOLD);
Font secondtitleChinese = new Font(bfChinese, 14, Font.BOLD);
Font fontChinese = new Font(bfChinese, 12, Font.NORMAL);
//创建PdfWriter对象
PdfWriter writer = PdfWriter.getInstance(document,new FileOutputStream("C:\\ITextTest.pdf"));
document.open();
Paragraph title=new Paragraph("主标题",titleChinese);
title.setAlignment(Element.ALIGN_CENTER);
Paragraph title2=new Paragraph("(副标题)",fontChinese);
title2.setAlignment(Element.ALIGN_CENTER);
//设置段落间距
title2.setSpacingAfter(30);
document.add(title);
document.add(title2);
String str="正文一类的东西。。。。。。。。";
Paragraph content=new Paragraph(str,fontChinese);
//首行缩进
content.setFirstLineIndent(20);
//设置行间距
content.setLeading(20);
content.setSpacingAfter(30);
document.add(content);
Paragraph title3=new Paragraph("供应商应收账款转让清单",secondtitleChinese);
title3.setAlignment(Element.ALIGN_CENTER);
document.add(title3);
//表格编号和日期
Paragraph id=new Paragraph();
Chunk chunk=new Chunk(" 编号:ABCDEFGH",fontChinese);
Chunk chunk2=new Chunk(" 日期:2017年6月29日",fontChinese);
id.add(chunk);
id.add(chunk2);
id.setSpacingAfter(5);
document.add(id);
// 建立一个pdf表格
float[] widths = {25f, 30f, 35f, 25f, 25f, 25f, 30f, 30f};
PdfPTable table = new PdfPTable(widths);
PdfPCell cell = null;
//第一行
cell = new PdfPCell(new Paragraph("供应商",fontChinese));
cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
table.addCell(cell);
cell = new PdfPCell(new Paragraph("发票号",fontChinese));
cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
table.addCell(cell);
cell = new PdfPCell(new Paragraph("币别",fontChinese));
cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
table.addCell(cell);
cell = new PdfPCell(new Paragraph("发票日",fontChinese));
cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
table.addCell(cell);
cell = new PdfPCell(new Paragraph("发票票面金额",fontChinese));
cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
table.addCell(cell);
cell = new PdfPCell(new Paragraph("供应商应收账款金额(承诺付款金额)",fontChinese));
cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
table.addCell(cell);
cell = new PdfPCell(new Paragraph("承诺付款日",fontChinese));
cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
table.addCell(cell);
cell = new PdfPCell(new Paragraph("备注",fontChinese));
cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
table.addCell(cell);
//往表格内部填充数据,必须填充为列数的整数倍的单元格,没有则填充空
String[] danju=new String[]{"1","2","3","4","5","6","7","8"};
for (int i = 0; i <danju.length; i++) {
table.addCell(new Paragraph(danju[i],fontChinese));
}
table.addCell(new Paragraph("合计",fontChinese));
table.addCell("");
table.addCell("");
table.addCell("");
table.addCell("");
table.addCell("");
table.addCell("");
table.addCell("");
document.add(table);
//签名
PdfPTable table2=new PdfPTable(2);
table2.setSpacingBefore(30);
PdfPCell sgin1 = new PdfPCell(new Paragraph("XX企业电子签名:",fontChinese));
sgin1.setBorder(0);
PdfPCell sgin2 = new PdfPCell(new Paragraph("XX平台电子签名:",fontChinese));
sgin2.setBorder(0);
table2.addCell(sgin1);
table2.addCell(sgin2);
PdfPCell image=new PdfPCell(new Paragraph("签名区域",fontChinese));
image.setFixedHeight(50);
image.setBorder(0);
table2.addCell(image);
table2.addCell(image);
Chunk underline = new Chunk("2017");
underline.setUnderline(0.1f, -1f);
Chunk underline2 = new Chunk("6");
underline2.setUnderline(0.1f, -1f);
Chunk underline3 = new Chunk("29");
underline3.setUnderline(0.1f, -1f);
Paragraph date=new Paragraph();
date.add(underline);
date.add(new Chunk("年",fontChinese));
date.add(underline2);
date.add(new Chunk("月",fontChinese));
date.add(underline3);
date.add(new Chunk("日",fontChinese));
PdfPCell date1 = new PdfPCell(date);
date1.setBorder(0);
date1.setHorizontalAlignment(Element.ALIGN_CENTER);
table2.addCell(date1);
table2.addCell(date1);
document.add(table2);
document.close();
还是觉得这个方法不太好,有多少个模板就要写多少个,不能直接利用模板。