Linux上的PDFBox 2.0.17字体

时间:2019-12-04 04:12:11

标签: java pdfbox

我正在将PDF文档中的页面转换为字节,然后从中构造图像。

在Windows上,图像构造良好。在Linux上,图片上的字母看起来很脏(彼此重叠)

在日志(weblogic)中,我看到以下内容指示Linux上缺少所需的字体。

<Dec 3, 2019 11:06:35 PM EST> <Warning> <org.apache.pdfbox.pdmodel.font.PDType1Font> <BEA-000000> <Using fallback font LiberationSans for Helvetica-Bold>
<Dec 3, 2019 11:06:35 PM EST> <Warning> <org.apache.pdfbox.pdmodel.font.PDType1Font> <BEA-000000> <Using fallback font LiberationSans for Times-Roman>
<Dec 3, 2019 11:06:35 PM EST> <Warning> <org.apache.pdfbox.pdmodel.font.PDType1Font> <BEA-000000> <Using fallback font LiberationSans for Times-Bold>
<Dec 3, 2019 11:06:35 PM EST> <Warning> <org.apache.pdfbox.pdmodel.font.PDType1Font> <BEA-000000> <Using fallback font LiberationSans for Times-Italic>
<Dec 3, 2019 11:06:35 PM EST> <Warning> <org.apache.pdfbox.pdmodel.font.PDType1Font> <BEA-000000> <Using fallback font LiberationSans for Helvetica>

如何在Linux上提供缺少的字体?我看到有关在2之前的版本中使用属性文件(PDFBox_External_Fonts.properties)的引用。在pdfbox版本2.0.17上我能做什么?我找不到有关如何进行操作的任何文档。

3 个答案:

答案 0 :(得分:2)

我专门为可能与 OP 有相同问题但在 Microsoft-Azure 上的 Linux WebApps 安装上使用 PdfBox 的利益而写这篇文章。我还提供了@user1187958 和@Lux 的答案中未提供的更多信息 - 我很感激,因为他们帮助我解决了我的问题。

正如@user1187958 上面所说,可以将字体安装在 PDFBox 搜索的目录之一中(通过以下代码)

package org.apache.fontbox.util.autodetect;

public class UnixFontDirFinder extends NativeFontDirFinder
{
    protected String[] getSearchableDirectories() {
        return new String[] { System.getProperty("user.home") + "/.fonts", "/usr/local/fonts", "/usr/local/share/fonts", "/usr/share/fonts", "/usr/X11R6/lib/X11/fonts"};
    }
}

然而,问题是所有这些目录(据我所知)在服务器重启期间都被 Azure 删除了。事实上,您显然需要重启服务器才能让 PDFBox 注册字体已上传。所以我所做的 - 尽管我认为有更好的方法 - 是从 PDFBox.jar 中提取 org.apache.fontbox.util.autodetect.UnixFontDirFinder,反编译它,添加我自己的目录(按照下面的代码提取),然后将其插入回.jar

 package org.apache.fontbox.util.autodetect;

public class UnixFontDirFinder extends NativeFontDirFinder
{
    protected String[] getSearchableDirectories() {
        return new String[] { System.getProperty("user.home") + "/.fonts", "/usr/local/fonts", "/usr/local/share/fonts", "/usr/share/fonts", "/usr/X11R6/lib/X11/fonts" 
,"/home/site/wwwroot/webapps/myapp/fonts"};
    }
}

上传新的 .jar 后,我将必需的字体上传到目录 /home/site/wwwroot/webapps/myapp/fonts,重新启动服务器,它工作了。

请注意,根据 org.apache.fontbox.util.autodetect.FileFinder.java 中的以下代码,上传的字体必须是以下格式之一:.ttf、.otf、.pfb、.ttc:

private boolean checkFontfile(final File file) {
        final String name = file.getName().toLowerCase(Locale.US);
        return (name.endsWith(".ttf") || name.endsWith(".otf") || name.endsWith(".pfb") || name.endsWith(".ttc")) && !name.startsWith("fonts.");
    }

C:/Windows/Fonts 目录上传 TTF 文件是可行的,但需要检查此类操作的合法性。

答案 1 :(得分:1)

PDFBox users mailing list的蒂尔曼·豪舍(Tilman Hausherr)伸出了援手。

将所需的字体复制到{home} /。fonts文件夹有助于解决我的问题。 PDFBox代码在以下目录中查找字体。

protected String[] getSearchableDirectories()
{
     return new String[] { System.getProperty("user.home") + "/.fonts", // user
             "/usr/local/fonts", // local
             "/usr/local/share/fonts", // local shared
             "/usr/share/fonts", // system
             "/usr/X11R6/lib/X11/fonts" // X
     };
 }

答案 2 :(得分:1)

Linux:org.apache.fontbox.util.autodetect.UnixFontDirFinder.java
Windows:org.apache.fontbox.util.autodetect.WindowsFontsDirFinder.Java
PDFBox通过上述类加载系统字体。您可以检查来源。
解决方案1:您可以将缺少的字体添加到任何Dir中,然后在上述类中添加find Dir。 解决方案2:作为蒂尔曼·豪舍(Tilman Hausher)的解决方案。

另一件事:当PDFBox首次加载系统中的所有字体时。然后创建一个名为.pdfbox.cache的文件。如果要PDFBox重新加载字体或加载新添加的字体,则需要先删除该文件。请让我知道是否有任何问题。