Docx4J:来自 LibreOffice 的文件在 Windows 上有伪影

Docx4J: file from LibreOffice has artifacts on windows

提问人:ks_on_v 提问时间:11/11/2023 最后编辑:ks_on_v 更新时间:11/13/2023 访问量:37

问:

我正在尝试将 .docx 文件转换为 .pdf。为此,我使用了 LibreOffice (Ubuntu) 中生成的 Docx4J 库和模板。

WordprocessingMLPackage wordprocessingMLPackage = WordprocessingMLPackage.load(docxReport);
Docx4J.toPDF(wordprocessingMLPackage, reportStream);

所有工作在 Ubuntu 上都成功。我收到了带有正确内容的 .pdf 文件。

但是,如果在 Windows 操作系统上使用 LibreOffice 中的模板运行此应用程序,我会看到如下工件:

######!
####.

与MS Word生成的文件具有相同的效果。如果在 Linux 机器上使用 Windows 中的模板运行应用程序,它将包含

######!

这里附加了来自 LibreOffice 的模板 - https://dropmefiles.com/oH88X

您知道需要设置什么才能独立于操作系统和 LibreOffice 或 MS Word 从 .docx 正确转换为 .pdf 吗?

Java DocX4J

评论

0赞 JasonPlutext 11/11/2023
在出现问题的某个地方发布一个简短的测试文档?
0赞 ks_on_v 11/11/2023
@JasonPlutext文件的链接已添加到帖子

答:

2赞 JasonPlutext 11/13/2023 #1

正如评论者所建议的那样,“#”表示您的 docx 正在使用系统上不存在的字体。

为了帮助解决这个问题,docx4j 有一个字体映射器的概念。

        // Set up font mapper (optional)
//      Mapper fontMapper = new IdentityPlusMapper();  // Only for Windows, unless you have Microsoft's fonts installed
        Mapper fontMapper = new BestMatchingMapper();  // Good for Linux (and OSX?)
        wordMLPackage.setFontMapper(fontMapper);

IdentityPlusMapper适用于Windows和使用Microsoft标准字体的文档;它假定 DOCX 中的字体名称与系统上安装的字体匹配。

BestMatchingMapper 使用 Panose 系统来选择与指定字体“接近”的字体。

您选择的字体 Mapper 只是设置了基本策略。

然后,您可以指定特定字体名称到实际存在的字体的映射。

PhysicalFont font 
        = PhysicalFonts.get("Arial Unicode MS"); // just an example
if (font!=null) {
    fontMapper.put("HelveticaNeue", font);
}

当然,您可以选择在系统上安装相关字体。在这种情况下,docx4j 可以发现它们。

或者,您可以将字体嵌入到 docx 中。