PDFbox 找不到字体:/Helv

PDFbox Could not find font: /Helv

我尝试向现有 PDF 文件添加表单域,但出现以下错误 PDFbox Could not find font: /Helv

我在 Java 中的代码具有以下视图:

        PDDocument pdf = PDDocument.load(inputStream);
        PDDocumentCatalog docCatalog = pdf.getDocumentCatalog();
        PDAcroForm acroForm = docCatalog.getAcroForm();
        PDPage page = pdf.getPage(0);

        PDTextField textBox = new PDTextField(acroForm);
        textBox.setPartialName("SampleField");
        acroForm.getFields().add(textBox);
        PDAnnotationWidget widget = textBox.getWidgets().get(0);
        PDRectangle rect = new PDRectangle(0, 0, 0, 0);
        widget.setRectangle(rect);
        widget.setPage(page);
        widget.setAppearance(acroForm.getFields().get(0).getWidgets().get(0).getAppearance());

        widget.setPrinted(false);

        page.getAnnotations().add(widget);

        acroForm.refreshAppearances();
        acroForm.flatten();
        pdf.save(outputStream);
        pdf.close();

您知道为什么会出现异常吗?

有栈顶跟踪

java.io.IOException: Could not find font: /Helv
at org.apache.pdfbox.pdmodel.interactive.form.PDDefaultAppearanceString.processSetFont(PDDefaultAppearanceString.java:179)
at org.apache.pdfbox.pdmodel.interactive.form.PDDefaultAppearanceString.processOperator(PDDefaultAppearanceString.java:132)
at org.apache.pdfbox.pdmodel.interactive.form.PDDefaultAppearanceString.processAppearanceStringOperators(PDDefaultAppearanceString.java:108)
at org.apache.pdfbox.pdmodel.interactive.form.PDDefaultAppearanceString.<init>(PDDefaultAppearanceString.java:86)
at org.apache.pdfbox.pdmodel.interactive.form.PDVariableText.getDefaultAppearanceString(PDVariableText.java:93)
at org.apache.pdfbox.pdmodel.interactive.form.AppearanceGeneratorHelper.<init>(AppearanceGeneratorHelper.java:100)
at org.apache.pdfbox.pdmodel.interactive.form.PDTextField.constructAppearances(PDTextField.java:262)
at org.apache.pdfbox.pdmodel.interactive.form.PDAcroForm.refreshAppearances(PDAcroForm.java:368)
at com.workjam.service.impl.PDFService.fillForm(PDFService.java:85)

这是 PDF 的 link:https://drive.google.com/file/d/0B2--NSDOiujoR3hOZFYteUl2UE0/view?usp=sharing

您的新文本字段没有默认外观,因此 PDFBox 为您制作了一个 (/Helv 0 Tf 0 g)。

解决方案 1:从您正在使用的字段中获取它(这不适用于每个 PDF,因为您做出了几个假设,即有一个字段并且它是一个文本字段)

textBox.setDefaultAppearance(((PDTextField)acroForm.getFields().get(0)).getDefaultAppearance());

方案二:初始化默认资源:

PDResources resources = new PDResources();
resources.put(COSName.getPDFName("Helv"), PDType1Font.HELVETICA);
acroForm.setDefaultResources(resources);

另请参阅源代码下载中的 CreateSimpleForm.java 示例。

更新:这已在 2.0.8 中修复,请参阅问题 PDFBOX-3943

原因是您和源 PDF 没有为文本字段提供默认外观,而 PDFBox 提供的默认外观无关紧要。

默认外观

根据规范,每个包含可变文本的字段(例如您的文本字段)必须具有 DA 默认外观值:

DA string (Required; inheritable) The default appearance string containing a sequence of valid page-content graphics or text state operators that define such properties as the field’s text size and colour.

(ISO 32000-1, Table 222 – Additional entries common to all fields containing variable text)

除了字段树中的父字段外,DA值也可以继承自AcroForm字典:

DA string (Optional) A document-wide default value for the DA attribute of variable text fields (see 12.7.3.3, “Variable Text”).

(ISO 32000-1, Table 218 – Entries in the interactive form dictionary)

在您的 PDF 中

您没有提供默认外观,并且您的 PDF 在 AcroForm 词典中没有默认外观。

因此,严格来说,在您调用acroForm.refreshAppearances()的那一刻,它是无效的。因此 PDFBox 可能会因为缺少信息而拒绝该调用。

不过,它的工作方式不同,因为 PDFBox 为某些 AcroForm 字典条目提供默认值,特别是

final String adobeDefaultAppearanceString = "/Helv 0 Tf 0 g ";

// DA entry is required
if (getDefaultAppearance().length() == 0)
{
    setDefaultAppearance(adobeDefaultAppearanceString);
}

不幸的是,PDFBox 不能确保此处使用的字体 Helv 存在于默认资源中,除非它们也完全丢失。

解决方案

刚看到Tilman在这里也写了一个回答。您可以在那里找到问题的解决方案。