【问题标题】:How to use TTF font with PDFBox AcroForm and then flatten document?如何在 PDFBox AcroForm 中使用 TTF 字体然后展平文档?
【发布时间】:2021-12-22 06:01:43
【问题描述】:

我一直在尝试使用 LibreOffice Writer 7.2.2.2 制作可填写的 PDF 文件。文档如下所示: 垂直线右侧的所有字段都是表单文本框,每个字段都有自己的名称(tbxOrderId、tbxFullName...)。每个文本框都使用 SF Pro Text Light 作为字体。只有右下角的 (tbxTotal) - Total €123.00Oswald Regular。当我使用 LibreOffice Writer 填写这些字段时,文档看起来还不错。

下面是我的导出设置。我选择Archive PDF A-2b 是为了将字体嵌入到文档中。

这是我对导出的 PDF 文件运行 pdffonts 时的输出。

但是,当我运行以下仅更改 tbxOrderIdtbxTotal 值的代码时,输​​出的 PDF 文档缺少这些字体。

public class Start {
    public static void main(String[] args) {
        try {
            PDDocument pDDocument = PDDocument.load(new File("/media/stoyank/Elements/Java/tmp/Receipt.pdf"));
            PDAcroForm pDAcroForm = pDDocument.getDocumentCatalog().getAcroForm();

            PDField field = pDAcroForm.getField("tbxOrderId");
            field.setValue("192753");
            field = pDAcroForm.getField("tbxTotal");
            field.setValue("Total: €192.00");

            pDAcroForm.flatten();
            pDDocument.save("/media/stoyank/Elements/Java/tmp/output.pdf");
            pDDocument.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

这是输出文档的样子:

我尝试通过参考this Stackoverflow question手动添加字体,但仍然没有成功:

PDDocument pDDocument = PDDocument.load(new File("/media/stoyank/Elements/Java/tmp/Receipt.pdf"));
PDAcroForm pDAcroForm = pDDocument.getDocumentCatalog().getAcroForm();

InputStream font_file = ClassLoader.getSystemResourceAsStream("Oswald-Regular.ttf");
PDType0Font font = PDType0Font.load(pDDocument, font_file, false);
if (font_file != null) font_file.close();

PDResources resources = pDAcroForm.getDefaultResources();
if (resources == null) resources = new PDResources();

resources.put(COSName.getPDFName("Oswald-Regular"), font);
pDAcroForm.setDefaultResources(resources);
pDAcroForm.refreshAppearances();

PDField field = pDAcroForm.getField("tbxOrderId");
field.setValue("192753");
field = pDAcroForm.getField("tbxTotal");
field.setValue("Total: €192.00");

pDAcroForm.flatten();
pDDocument.save("/media/stoyank/Elements/Java/tmp/output.pdf");
pDDocument.close();

在我写入这些文本框字段后,我想展平文档。

这是我的文件夹结构:

系统:Ubuntu 20.04

另外,here is a link 到我然后导出为 PDF 和导出的 PDF 的 ODT 文件。

【问题讨论】:

  • 我认为您还需要调用 setDefaultAppearance 以便它使用新的(非子集)字体。请参阅CreateSimpleFormWithEmbeddedFont.java 示例。请注意,字体名称不是“Oswald-Regular”,它是您从 resources.add() 得到的。 (不是 resources.put())
  • @TilmanHausherr 检查了CreateSimpleFormWithEmbeddedFont.java 文件并应用了所有内容。仍然没有成功。输出是乱码。我也收到WARNING: Using fallback font LiberationSans for CID-keyed TrueType font Oswald-Regular。这是代码:pastebin.com/51huv5Jm
  • @TilmanHausherr 在 GitHub 上发布了该项目。这是链接:github.com/stoyanK7/pdfbox-stackoverflow-question

标签: java pdfbox truetype pdf-form acrofields


【解决方案1】:

您的文件没有正确的字段外观流,这是创建 PDF 的软件的错误。尽早致电pDAcroForm.refreshAppearances();

pastebin 中的代码很好(它基于CreateSimpleFormWithEmbeddedFont.java 示例),只是你应该保留默认资源,不要以空资源开头。所以你的代码应该是这样的:

pDAcroForm.refreshAppearances();

PDType0Font formFont = PDType0Font.load(pDDocument, ...input stream..., false);

PDResources resources = pDAcroForm.getDefaultResources();
if (resources == null)
{
    resources = new PDResources();
    pDAcroForm.setDefaultResources(resources);
}

final String fontName = resources.add(formFont).getName();

// Acrobat sets the font size on the form level to be
// auto sized as default. This is done by setting the font size to '0'
String defaultAppearanceString = "/" + fontName + " 0 Tf 0 g";

PDTextField field = (PDTextField) (pDAcroForm.getField("tbxTotal"));
field.setDefaultAppearance(defaultAppearanceString);
field.setValue("Total: €192.00");

【讨论】:

  • 即使听从了您的建议,仍然会胡言乱语:imgur.com/a/JkaZXwD。代码:pastebin.com/TAJiHRTU
  • 您可以尝试从文件中加载字体吗?这可能是资源过滤问题。 (我没用资源)我的结果文件在这里:filedropper.com/6PRv1DY0 上传你的结果文件,或者用PDFDebugger查看文件看看有没有区别。
  • 尝试使用 new File() 从文件中加载它。但是,当使用 File 类型作为第二个参数时,方法 PDType0Font.load() 不能接受第三个参数。仍然,同样的结果 - github.com/stoyanK7/pdfbox-stackoverflow-question/blob/main/tmp/…
  • 我使用了 FileInputStream 所以支持第三个参数。在您的文件中,由于某种原因没有嵌入字体。您的代码运行时是否有任何日志消息?
  • 也使用了FileInputStream。结果相同。我得到的唯一日志消息是Nov 14, 2021 6:32:24 PM org.apache.pdfbox.pdmodel.font.PDCIDFontType2 <init> WARNING: Using fallback font LiberationSans for CID-keyed TrueType font Oswald-Regular。它重复 4 次。
猜你喜欢
  • 2013-12-29
  • 1970-01-01
  • 2018-11-10
  • 2013-05-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-10-08
相关资源
最近更新 更多