1. 引入itextpdf 依赖
<dependency>
<groupId>com.itextpdf</groupId>
<artifactId>itextpdf</artifactId>
<version>5.5.13.3</version>
</dependency>
2. 创建文档对象、写入实例并将内容写入二进制流,打开文档写入内容
// 创建文档对象
Document document = new Document();
ByteArrayOutputStream baos = new ByteArrayOutputStream();
// 创建 PDF 写入器实例
PdfWriter.getInstance(document, baos);
// 打开文档
document.open();
3. itextpdf不支持中文,需要下载支持中文字库的.ttf的矢量字库,这里以simsun.ttf来做演示。字库下载需要去github。
输入的字符,通常是Unicode编码,通过Unicode编码来查找字符映射表,从而找到对应的矢量字库中的字模,itextpdf内置的字体没有对应的中文字模,导致问题就是输入了中文,最后显示的确是什么都没有,结果就是没有找到对应的字模。
// 加载支持中文的字体
BaseFont baseFont = BaseFont.createFont("E:\\FontSimsun-master\\SimSun.ttf", BaseFont.IDENTITY_H, BaseFont.EMBEDDED);
Font font = new Font(baseFont, 15, Font.BOLD);
4. 段落编写
如果段落需要作为标题:
Font.PLAIN
: 默认的普通字体样式(不加粗、不倾斜)。
Font.BOLD
: 粗体样式。
Font.ITALIC
: 斜体样式。
Font.BOLD + Font.ITALIC
: 粗体和斜体的组合样式。
// 设置标题字体 baseFont本地字体 20字体大小 Font.BOLD字体加粗
Font titleFont = new Font(baseFont, 20, Font.BOLD);
Paragraph title = new Paragraph("我只是一个标题", titleFont);
// 居中对齐
title.setAlignment(Element.ALIGN_CENTER);
// 设置标题和表格或者段落的距离
title.setSpacingAfter(1);
//将标题添加进文档内
document.add(title);
如果段落需要作为内容:
Font textFont = new Font(baseFont, 16, Font.PLAIN);
// 添加内容
String content1 = "我只是内容";
Paragraph paragraph1 = new Paragraph(content, textFont);
// 设置段落间距
paragraph1.setSpacingBefore(20);
// 首行缩进
paragraph1.setFirstLineIndent(30);
// 内容添加至文档
document.add(paragraph1);
5. 表格编写
Font font = new Font(baseFont, 15, Font.BOLD);
// 创建表格对象 4是4列
PdfPTable table = new PdfPTable(4);
PdfPCell header1 = new PdfPCell(new Phrase("卖方城市", font));
header1.setHorizontalAlignment(Element.ALIGN_CENTER);
table.addCell(header1);
PdfPCell header2 = new PdfPCell(new Phrase("合同项数", font));
header2.setHorizontalAlignment(Element.ALIGN_CENTER);
table.addCell(header2);
PdfPCell header3 = new PdfPCell(new Phrase("合同成交总金额(亿元)", font));
header3.setHorizontalAlignment(Element.ALIGN_CENTER);
table.addCell(header3);
PdfPCell header4 = new PdfPCell(new Phrase("技术交易额(亿元)", font));
header4.setHorizontalAlignment(Element.ALIGN_CENTER);
table.addCell(header4);
//根据业务获取数据
List<Map<String, Object>> listMaps = xxService.listMaps(queryWrapper);
String[][] data = new String[listMaps.size()][4];
......
// 将合计行添加到数据中
data = Arrays.copyOf(data, data.length + 1);
data[data.length - 1] = totalRow;
for (String[] row : data) {
for (String cell : row) {
PdfPCell cellElement = new PdfPCell(new Phrase(cell, font));
cellElement.setHorizontalAlignment(Element.ALIGN_CENTER);
table.addCell(cellElement);
}
}
// 添加表格到文档
document.add(table);
// 如果有多个表格 并且每个表格占一页,在此处插入新页
document.newPage();
6. 关闭文档并将文档写入响应。
文档一定要关闭否则导不出来。
// 关闭文档
document.close();
response.setContentType("application/pdf");
response.setHeader("Content-Disposition", "attachment; filename=xx.pdf");
response.setContentLength(baos.size());
baos.writeTo(response.getOutputStream());
response.flushBuffer();