Перейти к основному содержимому

HTML в PDF с помощью OpenPDF

· 5 мин. чтения

1. Обзор

В этом кратком руководстве мы рассмотрим использование OpenPDF в Java для программного преобразования файлов HTML в форматы PDF .

2. ОпенПДФ

OpenPDF — это бесплатная библиотека Java для создания и редактирования PDF-файлов под лицензиями LGPL и MPL. Это форк программы iText. Фактически, до версии 5 код для создания PDF с помощью OpenPDF был почти идентичен API iText. Это хорошо поддерживаемое решение для создания PDF-файлов на Java.

3. Преобразование с помощью летающей тарелки

Flying Saucer — это библиотека Java, которая позволяет нам отображать правильно сформированный XML (или XHTML) с помощью CSS 2.1 для стиля и форматирования, генерируя вывод в PDF, изображения и поворотные панели.

3.1. Зависимости Maven

Начнем с зависимостей Maven:

<dependency>
<groupId>org.jsoup</groupId>
<artifactId>jsoup</artifactId>
<version>1.13.1</version>
</dependency>
<dependency>
<groupId>org.xhtmlrenderer</groupId>
<artifactId>flying-saucer-pdf-openpdf</artifactId>
<version>9.1.20</version>
</dependency>

Мы будем использовать библиотеку jsoup для разбора HTML-файлов, входных потоков, URL-адресов и даже строк. Он предлагает возможности обхода DOM (объектная модель документа), CSS и jQuery-подобные селекторы для извлечения данных из HTML.

Библиотека fly-saucer-pdf-openpdf принимает XML-представление файлов HTML в качестве входных данных, применяет форматирование и стили CSS и выводит PDF.

3.2. HTML в PDF

В этом руководстве мы постараемся охватить простые случаи, с которыми вы можете столкнуться при преобразовании HTML в PDF, такие как изображения в HTML и стили, с использованием Flying Saucer и OpenPDF. Мы также обсудим, как можно настроить код для приема внешних стилей, изображений и шрифтов.

Давайте взглянем на наш пример HTML-кода:

<html>
<head>
<style>
.center_div {
border: 1px solid gray;
margin-left: auto;
margin-right: auto;
width: 90%;
background-color: #d0f0f6;
text-align: left;
padding: 8px;
}
</style>
<link href="style.css" rel="stylesheet">
</head>
<body>
<div class="center_div">
<h1>Hello ForEach!</h1>
<img src="Java_logo.png">
<div class="myclass">
<p>This is the tutorial to convert html to pdf.</p>
</div>
</div>
</body>
</html>

Чтобы преобразовать HTML в PDF, мы сначала прочитаем файл HTML из определенного места:

File inputHTML = new File(HTML);

В качестве следующего шага мы будем использовать jsoup для преобразования вышеуказанного HTML-файла в документ jsoup для визуализации XHTML. ``

Ниже приведен вывод XHTML:

Document document = Jsoup.parse(inputHTML, "UTF-8");
document.outputSettings().syntax(Document.OutputSettings.Syntax.xml);
return document;

Теперь, в качестве последнего шага, давайте создадим PDF-файл из XHTML-документа, созданного на предыдущем шаге. ITextRenderer возьмет этот документ XHTML и создаст выходной файл PDF. Обратите внимание, что мы заключаем наш код в блок try-with-resources , чтобы обеспечить закрытие выходного потока : ``

try (OutputStream outputStream = new FileOutputStream(outputPdf)) {
ITextRenderer renderer = new ITextRenderer();
SharedContext sharedContext = renderer.getSharedContext();
sharedContext.setPrint(true);
sharedContext.setInteractive(false);
renderer.setDocumentFromString(xhtml.html());
renderer.layout();
renderer.createPDF(outputStream);
}

3.3. Настройка внешнего стиля

Мы можем зарегистрировать дополнительные шрифты, используемые во входном документе HTML, в ITextRenderer , чтобы он мог включать их при создании PDF:

renderer.getFontResolver().addFont(getClass().getClassLoader().getResource("fonts/PRISTINA.ttf").toString(), true);

ITextRenderer может потребоваться зарегистрировать относительные URL-адреса для доступа к внешним стилям:

String baseUrl = FileSystems.getDefault()
.getPath("src/main/resources/")
.toUri().toURL().toString();
renderer.setDocumentFromString(xhtml, baseUrl);

Мы можем настроить атрибуты, связанные с изображением, реализуя ReplacedElementFactory :

public ReplacedElement createReplacedElement(LayoutContext lc, BlockBox box, UserAgentCallback uac, int cssWidth, int cssHeight) {
Element e = box.getElement();
String nodeName = e.getNodeName();
if (nodeName.equals("img")) {
String imagePath = e.getAttribute("src");
try {
InputStream input = new FileInputStream("src/main/resources/"+imagePath);
byte[] bytes = IOUtils.toByteArray(input);
Image image = Image.getInstance(bytes);
FSImage fsImage = new ITextFSImage(image);
if (cssWidth != -1 || cssHeight != -1) {
fsImage.scale(cssWidth, cssHeight);
} else {
fsImage.scale(2000, 1000);
}
return new ITextImageElement(fsImage);
} catch (Exception e1) {
e1.printStackTrace();
}
}
return null;
}

Примечание. Приведенный выше код добавляет префикс базового пути к пути к изображению и устанавливает размер изображения по умолчанию, если он не указан.

Затем мы можем добавить пользовательский ReplacedElementFactory в SharedContext :

sharedContext.setReplacedElementFactory(new CustomElementFactoryImpl());

4. Преобразование с использованием открытого HTML

Open HTML to PDF — это библиотека Java, которая выводит правильно сформированный XML/XHTML (и даже немного HTML5) в PDF или изображения с использованием CSS 2.1 (и более поздних стандартов) для компоновки и форматирования.

4.1. Зависимости Maven

В дополнение к библиотеке jsoup , показанной выше, нам нужно добавить пару библиотек Open HTML to PDF в наш файл pom.xml :

<dependency>
<groupId>com.openhtmltopdf</groupId>
<artifactId>openhtmltopdf-core</artifactId>
<version>1.0.6</version>
</dependency>
<dependency>
<groupId>com.openhtmltopdf</groupId>
<artifactId>openhtmltopdf-pdfbox</artifactId>
<version>1.0.6</version>
</dependency>

Библиотека openhtmltopdf-core визуализирует правильно сформированный XML/XHTML, а openhtmltopdf-pdfbox создает документ PDF из визуализированного представления XHTML.

4.2. HTML в PDF

В этой программе для преобразования HTML в PDF с помощью Open HTML мы будем использовать тот же HTML, упомянутый в разделе 3.2. Сначала мы преобразуем файл HTML в документ jsoup , как показано в предыдущем примере. ``

На последнем шаге, чтобы создать PDF-файл из XHTML-документа, PdfRendererBuilder возьмет этот XHTML-документ и создаст PDF-файл в качестве выходного файла . Опять же, мы используем try-with-resources , чтобы обернуть нашу логику: ``

try (OutputStream os = new FileOutputStream(outputPdf)) {
PdfRendererBuilder builder = new PdfRendererBuilder();
builder.withUri(outputPdf);
builder.toStream(os);
builder.withW3cDocument(new W3CDom().fromJsoup(doc), "/");
builder.run();
}

4.3. Настройка внешнего стиля

Мы можем зарегистрировать дополнительные шрифты, используемые во входном документе HTML, в PdfRendererBuilder , чтобы он мог включить их в PDF:

builder.useFont(new File(getClass().getClassLoader().getResource("fonts/PRISTINA.ttf").getFile()), "PRISTINA");

Библиотеке PdfRendererBuilder также может потребоваться зарегистрировать относительные URL-адреса для доступа к внешним стилям, как в нашем предыдущем примере:

String baseUrl = FileSystems.getDefault()
.getPath("src/main/resources/")
.toUri().toURL().toString();
builder.withW3cDocument(new W3CDom().fromJsoup(doc), baseUrl);

5. Вывод

В этой статье мы узнали, как конвертировать HTML в PDF с помощью Flying Saucer и Open HTML. Мы также обсудили, как мы можем зарегистрировать внешние шрифты, стили и настройки.

Как обычно, все примеры кода, используемые в этом руководстве, доступны на GitHub .