Java PDF操作指南:iText与PDFBox实战对比 1. Java操作PDF的常见场景与工具选型PDF作为跨平台文档格式在企业级应用中有着广泛的使用场景。Java开发者经常需要处理PDF文档的生成、编辑和内容提取等需求。从发票生成、报表导出到合同签署PDF操作几乎成为Java后台开发的标配技能。目前主流的Java PDF操作库主要有以下几个iText功能最全面的开源库支持PDF生成、编辑、加密等全套操作AGPL/commercial双协议Apache PDFBoxApache旗下的开源项目专注PDF内容提取和基础操作OpenPDFiText分支版本LGPL协议更友好Flying Saucer适合HTML转PDF场景JasperReports报表工具内置PDF导出功能对于数据写入场景iText和PDFBox是最常用的选择。iText在生成复杂PDF时更具优势而PDFBox在已有PDF修改方面更轻量。我们以iText 7为例进行演示这是目前最新的商业友好版本。2. 基础环境准备与依赖配置2.1 Maven依赖配置使用iText 7需要添加以下依赖到pom.xmldependency groupIdcom.itextpdf/groupId artifactIditext7-core/artifactId version7.2.5/version typepom/type /dependency如果需要处理中文等亚洲字符还需添加额外的字体模块dependency groupIdcom.itextpdf/groupId artifactIdfont-asian/artifactId version7.2.5/version /dependency2.2 字体资源准备处理中文内容时必须明确指定支持中文的字体。推荐将字体文件(.ttf)放在resources/fonts目录下。常用开源字体如思源黑体(Source Han Sans)阿里巴巴普惠体文泉驿系列字体注意直接使用系统字体可能导致部署环境缺少对应字体而出错建议将字体文件随项目一起打包。3. 基础文本写入实现3.1 创建PDF文档基础框架以下是创建PDF并写入文本的最小实现import com.itextpdf.kernel.pdf.PdfDocument; import com.itextpdf.kernel.pdf.PdfWriter; import com.itextpdf.layout.Document; import com.itextpdf.layout.element.Paragraph; public class BasicPdfWriter { public static void main(String[] args) throws Exception { // 1. 创建PdfWriter指向输出文件 PdfWriter writer new PdfWriter(output.pdf); // 2. 创建PdfDocument对象 PdfDocument pdf new PdfDocument(writer); // 3. 创建Document对象用于添加内容 Document document new Document(pdf); // 4. 添加段落内容 document.add(new Paragraph(Hello PDF World!)); // 5. 关闭文档 document.close(); } }3.2 中文内容处理处理中文需要特别注意字体设置// 加载字体(假设resources/fonts下有SourceHanSans.ttf) PdfFont font PdfFontFactory.createFont( fonts/SourceHanSans.ttf, PdfEncodings.IDENTITY_H, true); // 创建支持中文的段落 Paragraph p new Paragraph(这是一个中文段落) .setFont(font) .setFontSize(14); document.add(p);3.3 文本样式控制iText提供了丰富的文本样式控制Paragraph styledText new Paragraph() .add(new Text(加粗文本).setBold()) .add( ) .add(new Text(斜体文本).setItalic()) .add( ) .add(new Text(红色文本).setFontColor(Color.RED)) .add( ) .add(new Text(带背景色).setBackgroundColor(Color.YELLOW)) .setFont(font) .setFontSize(12);4. 高级数据写入技巧4.1 表格数据写入表格是数据展示的常见形式iText表格操作示例// 创建3列表格 Table table new Table(new float[]{1, 2, 1}); // 添加表头 table.addHeaderCell(new Cell().add(new Paragraph(ID).setBold())); table.addHeaderCell(new Cell().add(new Paragraph(商品名称).setBold())); table.addHeaderCell(new Cell().add(new Paragraph(价格).setBold())); // 添加数据行 for(Product product : productList) { table.addCell(new Cell().add(new Paragraph(product.getId()))); table.addCell(new Cell().add(new Paragraph(product.getName()))); table.addCell(new Cell().add(new Paragraph(product.getPrice()))); } // 设置表格宽度占页面80% table.setWidth(UnitValue.createPercentValue(80)); // 添加到文档 document.add(table);4.2 列表数据展示有序列表和无序列表的实现// 无序列表 List list new List() .setSymbolIndent(12) .setListSymbol(•) .setFont(font); list.add(列表项1); list.add(列表项2); document.add(list); // 有序列表 List numberedList new List(ListNumberingType.DECIMAL); numberedList.add(第一项); numberedList.add(第二项); document.add(numberedList);4.3 图片插入处理插入图片到PDF的完整流程// 加载图片(假设在resources/images下) ImageData imageData ImageDataFactory.create(images/logo.png); Image image new Image(imageData); // 设置图片属性 image.setAutoScale(true); // 自动缩放 image.setHorizontalAlignment(HorizontalAlignment.CENTER); // 居中 // 添加到文档 document.add(image);提示处理大图片时建议先压缩避免PDF体积过大。iText支持JPEG、PNG、BMP等多种格式。5. 页面布局与样式控制5.1 页面大小与边距创建文档时指定页面属性// 自定义页面大小(A4竖版) PageSize pageSize PageSize.A4; Document document new Document(pdfDoc, pageSize); // 设置页边距(上下左右) document.setMargins(50, 30, 50, 30);5.2 分页与页眉页脚添加页眉页脚的实现方式// 总页数 int totalPages pdfDoc.getNumberOfPages(); // 为每页添加页脚 for (int i 1; i totalPages; i) { PdfPage page pdfDoc.getPage(i); Rectangle pageSize page.getPageSize(); // 在页面底部创建Canvas Canvas canvas new Canvas(page, pageSize); float y 20; // 距离底部20单位 // 添加页脚文本 canvas.showTextAligned( new Paragraph(String.format(第 %d 页/共 %d 页, i, totalPages)) .setFontSize(10), pageSize.getWidth() / 2, y, TextAlignment.CENTER); canvas.close(); }5.3 多栏布局创建类似报纸的多栏布局// 创建两栏布局 ColumnDocumentRenderer renderer new ColumnDocumentRenderer( document, new float[]{250, 250} // 两栏宽度 ); document.setRenderer(renderer); // 添加内容时会自动分栏 document.add(new Paragraph(第一栏内容...)); document.add(new Paragraph(第二栏内容...));6. 常见问题排查6.1 中文乱码问题中文显示异常通常由以下原因导致未正确设置支持中文的字体字体编码未使用PdfEncodings.IDENTITY_H字体文件路径错误或未打包到最终jar中解决方案// 确保使用以下方式加载字体 PdfFont font PdfFontFactory.createFont( fonts/YourChineseFont.ttf, PdfEncodings.IDENTITY_H, true);6.2 内存泄漏问题iText操作PDF时需要及时关闭资源try (PdfWriter writer new PdfWriter(outputPath); PdfDocument pdf new PdfDocument(writer); Document doc new Document(pdf)) { // 操作文档 } catch (Exception e) { e.printStackTrace(); }6.3 性能优化建议处理大批量数据时使用PdfWriter.setSmartMode(true)启用智能模式对于大型表格考虑分页显示图片使用适当压缩质量复用字体等资源对象7. 实际应用案例7.1 生成销售报表典型销售报表生成流程public void generateSalesReport(ListSaleRecord records, String outputPath) throws IOException { // 初始化文档 PdfWriter writer new PdfWriter(outputPath); PdfDocument pdf new PdfDocument(writer); Document document new Document(pdf, PageSize.A4.rotate()); // 横向A4 // 添加标题 document.add(new Paragraph(月度销售报表) .setFont(titleFont) .setFontSize(18) .setTextAlignment(TextAlignment.CENTER)); // 添加生成日期 document.add(new Paragraph(生成日期: LocalDate.now()) .setFont(bodyFont) .setFontSize(10)); // 创建表格 Table table new Table(new float[]{1, 3, 2, 2, 2}); table.setWidth(UnitValue.createPercentValue(100)); // 添加表头 addTableHeader(table); // 添加数据行 for (SaleRecord record : records) { addTableRow(table, record); } // 添加表格到文档 document.add(table); // 添加统计信息 addSummary(document); document.close(); }7.2 合同文档生成合同生成的关键要点使用固定格式模板关键字段高亮显示添加数字签名区域设置文档权限// 合同关键信息高亮示例 Paragraph contractItem new Paragraph() .add(甲方: ) .add(new Text(partyA).setUnderline()) .add( 乙方: ) .add(new Text(partyB).setUnderline()); document.add(contractItem); // 添加签名区域 Table signatureTable new Table(2); signatureTable.addCell(new Cell().add(new Paragraph(甲方签字:))); signatureTable.addCell(new Cell().add(new Paragraph(乙方签字:))); signatureTable.addCell(new Cell().setHeight(50)); // 留空签字处 signatureTable.addCell(new Cell().setHeight(50)); document.add(signatureTable);8. 扩展功能实现8.1 PDF加密与权限控制设置文档打开密码和权限WriterProperties props new WriterProperties() .setStandardEncryption( userPass.getBytes(), // 用户密码 ownerPass.getBytes(), // 所有者密码 EncryptionConstants.ALLOW_PRINTING, // 允许打印 EncryptionConstants.ENCRYPTION_AES_256 // 加密强度 ); PdfWriter writer new PdfWriter(outputPath, props);8.2 添加条形码/二维码使用Barcode4J集成生成条形码// 生成二维码 BarcodeQRCode qrCode new BarcodeQRCode(https://example.com); Image qrCodeImage new Image(qrCode.createFormXObject(pdf)); document.add(qrCodeImage);8.3 动态水印添加为PDF添加文字水印for (int i 1; i pdf.getNumberOfPages(); i) { PdfPage page pdf.getPage(i); PdfCanvas canvas new PdfCanvas(page.newContentStreamBefore(), page.getResources(), pdf); // 设置水印样式 canvas.saveState() .setFillColor(Color.LIGHT_GRAY) .setFontAndSize(font, 40) .beginText(); // 在页面中心添加旋转文字 canvas.showTextAligned(CONFIDENTIAL, page.getPageSize().getWidth() / 2, page.getPageSize().getHeight() / 2, i, TextAlignment.CENTER, VerticalAlignment.MIDDLE, 45); canvas.restoreState(); }9. 最佳实践与性能优化9.1 对象复用提升性能避免重复创建相同资源// 在文档级别共享字体等资源 PdfFont sharedFont PdfFontFactory.createFont(...); Style sharedStyle new Style() .setFont(sharedFont) .setFontSize(12); // 在多个段落中复用 Paragraph p1 new Paragraph(段落1).addStyle(sharedStyle); Paragraph p2 new Paragraph(段落2).addStyle(sharedStyle);9.2 大文档分块处理处理大型PDF时的内存管理// 启用智能模式减少内存占用 writer.setSmartMode(true); // 定期释放资源 if(docCounter % 100 0) { document.flush(); System.gc(); }9.3 错误处理与日志记录完善的错误处理机制try { // PDF操作代码 } catch (PdfException e) { logger.error(PDF处理错误: {}, e.getMessage()); throw new BusinessException(PDF生成失败, e); } catch (IOException e) { logger.error(IO异常: {}, e.getMessage()); throw new BusinessException(文件操作失败, e); } finally { // 确保资源释放 IOUtils.closeQuietly(document); IOUtils.closeQuietly(pdf); IOUtils.closeQuietly(writer); }10. 替代方案比较10.1 iText vs PDFBox特性iTextPDFBox生成PDF功能强大API丰富基础功能完善修改PDF支持但较复杂简单直接中文支持需要额外配置字体同左性能中等较高许可协议AGPL/CommercialApache 2.0学习曲线较陡峭较平缓10.2 HTML转PDF方案对于已有HTML内容的情况Flying Saucer Thymeleaf/Freemarker// 使用模板引擎渲染HTML String htmlContent templateEngine.process(template, context); // 转换为PDF OutputStream os new FileOutputStream(output.pdf); ITextRenderer renderer new ITextRenderer(); renderer.setDocumentFromString(htmlContent); renderer.layout(); renderer.createPDF(os); os.close();OpenHTMLToPDF更现代的替代方案10.3 云端PDF生成服务对于无服务器环境需求AWS TextractGoogle Document AI阿里云智能媒体服务这些服务提供REST API接口适合分布式系统集成但需要考虑网络延迟和成本因素。

相关新闻

最新新闻

ngx_output_chain_get_buf

ngx_output_chain_get_buf

1 定义 ngx_output_chain_get_buf 函数 定义在 src/core/ngx_output_chain.cstatic ngx_int_t ngx_output_chain_get_buf(ngx_output_chain_ctx_t *ctx, off_t bsize) {size_t size;ngx_buf_t *b, *in;ngx_uint_t recycled;in ctx->in->buf;size ctx->buf…

2026/7/20 0:18:02
互联网大厂常见Java面试题及答案汇总(2026持续更新)

互联网大厂常见Java面试题及答案汇总(2026持续更新)

金九银十即将来袭,又是一个跳槽的好季节,准备跳槽的同学都摩拳擦掌准备大面好几场,今天为大家准备了互联网面试必备的 1 到 5 年 Java 面试者都需要掌握的面试题,分别 JVM,并发编程,MySQL,Tomca…

2026/7/20 0:18:02
Copilot数据模型训练数据构成真相(92.3%代码+5.1%自然语言+2.6%隐式意图信号)

Copilot数据模型训练数据构成真相(92.3%代码+5.1%自然语言+2.6%隐式意图信号)

更多请点击: https://kaifayun.com 第一章:Copilot数据模型训练数据构成真相(92.3%代码5.1%自然语言2.6%隐式意图信号) GitHub Copilot 的核心能力并非来自通用大语言模型的简单迁移,而是深度扎根于其训练数据的特异性…

2026/7/20 0:13:02
【AI 2026落地实战白皮书】:全球首批商用大模型API接口清单+性能基准测试数据(仅限Q1释放)

【AI 2026落地实战白皮书】:全球首批商用大模型API接口清单+性能基准测试数据(仅限Q1释放)

更多请点击: https://kaifayun.com 第一章:AI 2026年全球商用大模型落地元年总览 2026年标志着人工智能从实验室验证与行业试点正式迈入规模化商用阶段。全球范围内,超73%的《财富》500强企业已将大模型深度集成至核心业务流,涵盖…

2026/7/20 0:13:02
python数据可视化技巧的100个练习 -- 31. 类别数据的点图

python数据可视化技巧的100个练习 -- 31. 类别数据的点图

重要性★★★☆☆ 难度★★☆☆☆ 你是一家零售公司的数据分析师。你的经理要求你可视化最近产品发布的客户满意度评级分布。评级是分类的,范围从“非常不满意”到“非常满意”。创建一个点图以显示每个评级类别的频率。使用 Python 进行数据处理和可视化。在代码中生成输入…

2026/7/20 0:13:02
智能体走进物理世界,千里科技携舱驾协同成果亮相WAIC 2026

智能体走进物理世界,千里科技携舱驾协同成果亮相WAIC 2026

在2026世界人工智能大会(WAIC 2026)举办期间,千里科技董事长、阶跃星辰董事长印奇作为特邀嘉宾出席大会开幕式并在大会主论坛(上午场)发表主题演讲《当智能体进入物理世界》。在印奇看来,"智能体"…

2026/7/20 0:13:02

月新闻