看官方itextPDF的文档,推荐和DEMO都使用的是iTextPDF7的版本,但是看上去是版权或者收费的,不管怎么样,还是使用5版本比较保险。不过iText5生成PDF的方式和7是完全不同的,来看下
在pom.xml中引入itextpdf的依赖,基本上5这个大版本是定格在5.5.13.2了
<dependency> <groupId>com.itextpdf</groupId> <artifactId>itextpdf</artifactId> <version>5.5.13.2</version> </dependency> <!-- HTML转PDF需要--> <dependency> <groupId>com.itextpdf.tool</groupId> <artifactId>xmlworker</artifactId> <version>5.5.13.2</version> </dependency> <!-- 解决中文字体乱码问题--> <dependency> <groupId>com.itextpdf</groupId> <artifactId>itext-asian</artifactId> <version>5.2.0</version> </dependency>
测试需要转成PDF的Html文件如下:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8" /> <title>Title</title> <style> body { font-size: 14px; } * { margin: 0; padding: 0; } .mytable {border-left:#b7cee2 solid 1px;border-top:#b7cee2 solid 1px; width:100%;border-collapse:collapse;} .mytable th, .mytable td{border-right:#b7cee2 solid 1px;border-bottom:#b7cee2 solid 1px;} .mytable .bg_gray{background:#EEEEEE;} .mytable th{text-align:center; font-size:14px; height:52px; vertical-align:middle;} .mytable th small{font-size:10px; font-weight:normal;} .mytable td{height:38px; vertical-align:middle; text-align:center;} </style> </head> <body> <div style="padding: 10px;"> <table class="mytable"> <tbody> <tr> <td class="bg_gray">8月9日 星期一</td> <td>某某功能</td> </tr> <tr> <td>8月9日 星期一</td> <td>某某功能</td> </tr> <tr> <td>8月10日 星期二</td> <td>某某功能2</td> </tr> <tr> <td>8月9日 星期一</td> <td>某某功能</td> </tr> <tr> <td>8月10日 星期二</td> <td>某某功能2</td> </tr> <tr> <td>8月9日 星期一</td> <td>某某功能</td> </tr> <tr> <td>8月10日 星期二</td> <td>某某功能2</td> </tr> <tr> <td>8月9日 星期一</td> <td>某某功能</td> </tr> <tr> <td>8月10日 星期二</td> <td>某某功能2</td> </tr> <tr> <td>8月9日 星期一</td> <td>某某功能</td> </tr> <tr> <td>8月10日 星期二</td> <td>某某功能2</td> </tr> </tbody> </table> </div> </body> </html>
我们准备使用的是itextPDF的xmlworker来解析html,所以是xhtml格式,要求比较严格的xml,所以需要标签要闭合,例如:<meta charset="UTF-8" > 这样写是会报错的,需要修改成:<meta charset="UTF-8" />
转换方法如下:
public static void main(String[] args) throws Exception { File htmlFile = new File("/Users/Terry/it/source/git/githubprojects/TestMaven/src/main/resources/sample.html"); File pdfFile = new File("/Users/Terry/Downloads/a.pdf"); convertHtmlToPDF(htmlFile, pdfFile); } /** * * @param htmlFile 原始html文件 * @param pdfFile 需要转成的PDF的路径 */ private static void convertHtmlToPDF(File htmlFile, File pdfFile) throws Exception { Document document = new Document(); // PdfWriter pdfWriter = PdfWriter.getInstance(document, new FileOutputStream(pdfFile)); document.open(); //默认中文字体支持,防止中文乱码或者不显示 FontProvider fontProvider = new FontProvider() { @Override public boolean isRegistered(String s) { return false; } private BaseFont createBaseFont(String fontDir) { try { return BaseFont.createFont(fontDir, BaseFont.IDENTITY_H, BaseFont.EMBEDDED); } catch (Exception e) { e.printStackTrace(); return null; } } @Override public Font getFont(String s, String s1, boolean b, float v, int i, BaseColor baseColor) { BaseFont bfChinese; if (style == Font.BOLD) { //如果是粗体加载粗体的字体文件 bfChinese = createBaseFont("/Users/Terry/Downloads/font/宋体-粗体.ttf"); } else { bfChinese = createBaseFont("/Users/Terry/Downloads/font/STSong.ttf"); } return new Font(bfChinese, size, style, baseColor); } }; XMLWorkerHelper worker = XMLWorkerHelper.getInstance(); worker.parseXHtml(pdfWriter, document, new FileInputStream(htmlFile), StandardCharsets.UTF_8, fontProvider); document.close(); }
如上方法转成PDF,是完美支持中文、且支持内部CSS样式的。
不过你可能还有更加特殊化的需求,例如要支持外部的字体文件、支持外部的CSS文件引入。下来来看下
- 引入外部css文件:
File cssFile = new File("/path/to/main.css"); worker.parseXHtml(pdfWriter, document, new FileInputStream(htmlFile), new FileInputStream(cssFile),StandardCharsets.UTF_8, fontProvider );
- 引入外部font文件:
XMLWorkerFontProvider outerFontProvider = new XMLWorkerFontProvider(XMLWorkerFontProvider.DONTLOOKFORFONTS); // yahei字体别名,在html使用,例如:<body style='font-family: yahei;'></body> outerFontProvider.register("/path/to/微软雅黑.ttf", "yahei"); XMLWorkerHelper worker = XMLWorkerHelper.getInstance(); worker.parseXHtml(pdfWriter, document, new FileInputStream(htmlFile), StandardCharsets.UTF_8, outerFontProvider);
文章评论