Java 将字体添加到 Apache Pdfbox?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/23118074/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-13 20:50:59  来源:igfitidea点击:

Adding fonts to Apache Pdfbox?

javapdffontspdfbox

提问by K.Niemczyk

Is there a way to add additional font styles into Apache Pdfbox?

有没有办法将其他字体样式添加到 Apache Pdfbox 中?

We're currently trying to work around printing PDFs in our system (currently being done with PDF-Renderer.) I have been looking at various alternatives (pdfbox, jpedal, jPDFPrint)

我们目前正在尝试在我们的系统中打印 PDF(目前正在使用PDF-Renderer 完成。)我一直在寻找各种替代方案(pdfboxjpedaljPDFPrint

Our hope is for a free GPL compatible library to use, and as such we're leaning towards pdfbox. I have been able to write some sample code to print out the pdf which 'works'. See below:

我们希望使用免费的 GPL 兼容库,因此我们倾向于使用 pdfbox。我已经能够编写一些示例代码来打印出“有效”的 pdf。见下文:

PDDocument doc;
try {
        doc = PDDocument.load("test.pdf");
        doc.print();
    } catch (Exception e) {
        // Come up with better thing to do on fail.
        e.printStackTrace();
    }

As I mentioned, this works but the problem I'm running into is that PdfBox doesn't seem to be recognizing the fonts used in the pdf, and as such changes the font being used. As a result the document looks very odd (spacing and character size are different and look bizarre). I routinely see the following log message, or things like it:

正如我所提到的,这有效,但我遇到的问题是 PdfBox 似乎无法识别 pdf 中使用的字体,因此更改了正在使用的字体。结果文档看起来很奇怪(间距和字符大小不同,看起来很奇怪)。我经常看到以下日志消息,或类似的内容:

Apr 16, 2014 2:56:21 PM org.apache.pdfbox.pdmodel.font.PDSimpleFont drawString WARNING: Changing font on < > from < NimbusMono > to the default font

2014 年 4 月 16 日下午 2:56:21 org.apache.pdfbox.pdmodel.font.PDSimpleFont drawString 警告:将 < > 上的字体从 < NimbusMono > 更改为默认字体

Does anyone know of a way (or a reference) on how to approach adding a new fonttype into pdfbox? Or barring that, how to change the default font type?

有没有人知道如何将新字体类型添加到 pdfbox 的方法(或参考)?或者除此之外,如何更改默认字体类型?

From what I can tell, pdfbox supports 14 standard fonts. Unfortunately NimbusMono is not one of them. Any guidance would be appreciated.

据我所知,pdfbox 支持14 种标准字体。不幸的是,NimbusMono 不是其中之一。任何指导将不胜感激。

采纳答案by Tilman Hausherr

The unreleased 2.0 version supports the rendering of embedded fonts. You can get it as a snapshot https://repository.apache.org/content/groups/snapshots/org/apache/pdfbox/or through "svn checkout http://svn.apache.org/repos/asf/pdfbox/trunk/". The API is slightly different from the 1.8.x versions and might change, the best is to look at the code examples. A quick test to see whether your file will be rendered properly is to download the "pdfbox-app" https://repository.apache.org/content/groups/snapshots/org/apache/pdfbox/pdfbox-app/2.0.0-SNAPSHOT/and then run the viewer: java -jar pdfbox-app-2.0.0-20140416.173452-273.jar PDFReader your-file-name.pdf There's also a print feature.

未发布的 2.0 版本支持嵌入字体的渲染。您可以将其作为快照 https://repository.apache.org/content/groups/snapshots/org/apache/pdfbox/或通过“svn checkout http://svn.apache.org/repos/asf/pdfbox/后备箱/”。API 与 1.8.x 版本略有不同,可能会发生变化,最好查看代码示例。查看您的文件是否会正确呈现的快速测试是下载“pdfbox-app” https://repository.apache.org/content/groups/snapshots/org/apache/pdfbox/pdfbox-app/2.0.0 -SNAPSHOT/然后运行查看器: java -jar pdfbox-app-2.0.0-20140416.173452-273.jar PDFReader your-file-name.pdf 还有一个打印功能。

Good luck!

祝你好运!

Update 2016: 2.0 release is out, download it here. If you have used the 1.8 version, read the migration guide.

2016 年更新:2.0 版本已发布,请在此处下载。如果您使用过 1.8 版本,请阅读迁移指南

回答by mttdbrd

I ran into a similar problem with PDFBox. PDFs can be printed in a straightforward way using Java's javax.print package. The following code is slightly modified from the API docs for javax.print.

我遇到了与 PDFBox 类似的问题。可以使用 Java 的 javax.print 包以简单的方式打印 PDF。以下代码从 javax.print 的 API 文档稍作修改。

DocFlavor flavor = DocFlavor.INPUT_STREAM.PDF;
PrintRequestAttributeSet aset = new HashPrintRequestAttributeSet();
aset.add(MediaSizeName.ISO_C6); //letter size
PrintService[] pservices = PrintServiceLookup.lookupPrintServices(flavor, aset);
if (pservices.length > 0) {
   DocPrintJob pj = pservices[0].createPrintJob();
   try {
       FileInputStream fis = new FileInputStream("test.pdf");
       Doc doc = new SimpleDoc(fis, flavor, null);
       pj.print(doc, aset);
   } catch (FileNotFoundException | PrintException e) {
       //do something
   }

This code assumes that the printer can accept a PDF directly but it allows you to bypass PDFBox 1.8 branch's wonky font issues.

此代码假定打印机可以直接接受 PDF,但它允许您绕过 PDFBox 1.8 分支的不稳定字体问题。

回答by Column-E

I came across this post while trying to solve the same problem. The PDFBox 2.0 API documentation isn't great at the moment.

我在尝试解决同样的问题时遇到了这篇文章。PDFBox 2.0 API 文档目前不是很好。

What you're looking for is the FontFileFinder in Fontbox. Make sure you're using the full pdfbox-app jar which includes Fontbox.

您正在寻找的是 Fontbox 中的 FontFileFinder。确保您使用的是包含 Fontbox 的完整 pdfbox-app jar。

I've only tried this on Windows but looking at the classes it seems like it supports the other main operating systems.

我只在 Windows 上尝试过这个,但看看它似乎支持其他主要操作系统的类。

Here's a simple example class I wrote that writes out a small bit of text in the bottom left corner of a PDF, using a non-standard font.

这是我编写的一个简单示例类,它使用非标准字体在 PDF 的左下角写出一小段文本。

import java.io.File;
import java.io.IOException;
import java.net.URI;
import java.util.List;

import org.apache.fontbox.util.autodetect.FontFileFinder;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;
import org.apache.pdfbox.pdmodel.PDPageContentStream;
import org.apache.pdfbox.pdmodel.font.PDType0Font;
import org.apache.pdfbox.pdmodel.font.PDType1Font;

public class TestPDFWrite {

    public static void main(String[] args) throws IOException {

        FontFileFinder fontFinder = new FontFileFinder();
        List<URI> fontURIs = fontFinder.find();

        File fontFile = null;

        for (URI uri : fontURIs) {
            File font = new File(uri);
            if (font.getName().equals("CHILLER.TTF")) {
                fontFile = font;
            }
        }

        PDDocument document = new PDDocument();
        PDPage page = new PDPage();
        document.addPage(page);

        PDPageContentStream contentStream = new PDPageContentStream(document, page);
        contentStream.beginText();

        if (fontFile != null) {
            contentStream.setFont(PDType0Font.load(document, fontFile), 12);
        } else {
            contentStream.setFont(PDType1Font.HELVETICA, 12);
        }

        contentStream.newLineAtOffset(10, 10);
        contentStream.showText("Hello World");
        contentStream.endText();
        contentStream.close();
        document.save("C:/Hello World.pdf");
        document.close();
    }
}