PDFmake - 在VFS上找不到字体文件



我有以下代码用于测试PDFmake。 我在字体文件的位置有问题。我看到的文档似乎表明,在拉入vfs_fonts文件后,我应该能够看到它们。然而,对我来说并非如此。

function createPdf(assessmentId: string): string {
const pdfMake = require('pdfmake/build/pdfmake.js');
const pdfFonts = require('pdfmake/build/vfs_fonts.js');
pdfMake.vfs = pdfFonts.pdfMake.vfs;
//required font setup, requires that you link to the fonts shipped with npm
const fontDescriptors = {
Roboto: {
normal: 'Roboto-Regular.ttf',
bold: 'Roboto-Medium.ttf',
italics: 'Roboto-Italic.ttf',
bolditalics: 'Roboto-Italic.ttf',
}
};
const termpaper = new PdfLayout();
const docDefinition = termpaper.layout
const printer = new Printer(fontDescriptors);
//get a reference to the PdfKit instance, which is a streaming interface
const pdfDoc = printer.createPdfKitDocument(docDefinition);
return "pdflocation";
}

当此代码执行时,我收到此错误。

错误:

ENOENT:没有这样的文件或目录,打开"机器人介质.ttf" 错误(本机) at Object.fs.openSync (fs.js:642:18) at Object.fs.readFileSync (fs.js:510:33) at Object.fontkit.openSync (/user_code/node_modules/pdfmake/node_modules/fontkit/index.js:43:19) at Function.PDFFont.open (/user_code/node_modules/pdfmake/node_modules/pdfkit/js/font.js:14:24) at PDFDocument.font (/user_code/node_modules/pdfmake/node_modules/pdfkit/js/mixins/fonts.js:39:28) at FontProvider.provideFont (/user_code/node_modules/pdfmake/src/fontProvider.js:49:58) at/user_code/node_modules/pdfmake/src/textTools.js:258:27 at Array.forEach (native) at measure (/user_code/node_modules/pdfmake/src/textTools.js:240:13)

我需要做什么才能正确找到这些字体文件?

我也为此苦苦挣扎。我找到的解决方案是在我的项目中实际包含字体文件。列出的文件位于项目根目录的"fonts"文件夹中,我的代码通过 uri 引用它们:

const fonts = {
Roboto: {
normal: 'fonts/Roboto-Regular.ttf',
bold: 'fonts/Roboto-Medium.ttf',
italics: 'fonts/Roboto-Italic.ttf',
bolditalics: 'fonts/Roboto-MediumItalic.ttf'
}
};

我从这里下载了字体文件。

希望这有帮助。

你也可以这样使用,在我的例子中,我的字体、控制器、工作区目录中的帮助程序目录。

const path = require('path'); // path is give you a working directory path.resolve() and you can give your font file path.
const fontDescriptors = {
Roboto: {
normal: path.resolve('./fonts/Roboto-Regular.ttf'),
bold: path.resolve('./fonts/Roboto-Medium.ttf'),
italics: path.resolve('./fonts/Roboto-Italic.ttf'),
bolditalics: path.resolve('./fonts/Roboto-MediumItalic.ttf')
}
}

曾经遇到过类似的问题,您需要给出字体的确切位置。

它还在字体之前标记了通知。

/

/必需的字体设置,要求您链接到 npm 附带的字体


尝试以下各项的完整目录路径:

normal: '/Exampledir/pdfmake/Roboto-Regular.ttf',
bold: 'Roboto-Medium.ttf',
italics: 'Roboto-Italic.ttf',
bolditalics: 'Roboto-Italic.ttf',

或者有/缺少
const pdfFonts = require("pdfmake/

例如。
const pdfFonts = require("/pdfmake/

它就是这么简单,因为错误表明它无法从该位置找到字体,使用简单的 cd ./然后是 cd/pdfmake/等和 ls 过度检查该位置。比较配置文件,应该让它工作。

您可以通过简单的 3 个步骤很好地使用自定义字体:

要使用自定义字体,需要 3 个步骤:

  • 创建包含字体的vfs_fonts.js
  • 定义字体系列
  • 更改文档定义对象中的字体系列

1.创建包含字体的vfs_fonts.js

将字体复制到 myProject/fonts/目录

运行 grunt dump_dir(如果您想更改基目录或为dump_dir任务添加替代配置.js您可以更新 Gruntfile)

在网页上使用新版本/vfs_fonts.js

顺便说一句 - 上述操作从myProject/fonts/(不仅是字体)转储所有文件,这意味着您可以将图像放在那里,运行grunt dump_dir并在doc-definition-object中按名称引用它们

阿拉伯数字。定义字体系列

在调用pdfMake.createPdf(docDefinition)之前,请将pdfMake.fonts设置为以下对象:

{
yourFontName: {
normal: 'fontFile.ttf',
bold: 'fontFile2.ttf',
italics: 'fontFile3.ttf',
bolditalics: 'fontFile4.ttf'
},
anotherFontName: {
(...)
}
}

键是稍后可以在文档定义中使用的字体系列名称

每个字体系列定义 4 个属性:普通、粗体、斜体和粗斜体,指的是适当的文件(默认情况下,这些是相对于myProject/fonts/的文件路径)

默认情况下,pdfMake 使用以下结构:

{
Roboto: {
normal: 'Roboto-Regular.ttf',
bold: 'Roboto-Medium.ttf',
italics: 'Roboto-Italic.ttf',
bolditalics: 'Roboto-Italic.ttf'
}
};

3.更改文档定义对象中的字体系列

目前pdfmake使用"Roboto"作为默认姓氏,因此为了使用您的字体,您应该更改它。最简单的方法是在 defaultStyle 中全局执行此操作

var docDefinition = {
content: (...),
defaultStyle: {
font: 'yourFontName'
}
}

所以,理想情况下,我建议你下载所有你想要的字体文件并将其放在一个文件夹中,比如myProject/fonts/,然后尝试在你的代码中引用相同的文件。正确的代码片段如下所示:

const fontDescriptors = {
Roboto: {
normal: 'myProject/fonts/Roboto-Regular.ttf',
bold: 'myProject/fonts/Roboto-Medium.ttf',
italics: 'myProject/fonts/Roboto-Italic.ttf',
bolditalics: 'myProject/fonts/Roboto-Italic.ttf',
}
};

希望这能解决您的问题。如有疑问,请随时提出疑问。

此错误主要发生在您使用 webpack 时。我们正在使用 webpack,并通过使用 webpack 导入加载器将其填充到窗口来解决此问题,如下所示:

var fonts = require('imports?this=>window!pdfmake/build/vfs_fonts.js');

修复:

function createPdf(assessmentId: string): string {
const pdfMake = require('pdfmake/build/pdfmake.js');
const pdfFonts = require('pdfmake/build/vfs_fonts.js');// this line will give an error if you are working with webpack . 

变量字体 = require('imports?this=>window!pdfmake/build/vfs_fonts.js');使用此行来修复它

pdfMake.vfs = pdfFonts.pdfMake.vfs;
//required font setup, requires that you link to the fonts shipped with npm
const fontDescriptors = {
Roboto: {
normal: 'Roboto-Regular.ttf',
bold: 'Roboto-Medium.ttf',
italics: 'Roboto-Italic.ttf',
bolditalics: 'Roboto-Italic.ttf',
}
};
const termpaper = new PdfLayout();
const docDefinition = termpaper.layout
const printer = new Printer(fontDescriptors);
//get a reference to the PdfKit instance, which is a streaming interface
const pdfDoc = printer.createPdfKitDocument(docDefinition);
return "pdflocation";
}

希望这对其他人有帮助!

我正在使用 React 和 datatables.net。这是对我有用的:

import React from 'react';
import $ from 'jquery';
import 'datatables.net-bs';
import 'datatables.net-buttons-bs';
import 'datatables.net-responsive-bs';
import 'datatables.net-buttons/js/buttons.colVis.js';
import 'datatables.net-buttons/js/buttons.flash.js';
import 'jszip';
import pdfMake from 'pdfmake/build/pdfmake';
import pdfFonts from 'pdfmake/build/vfs_fonts';
import 'datatables.net-buttons/js/buttons.html5.js';
import 'datatables.net-buttons/js/buttons.print.js';
import 'bootstrap/dist/css/bootstrap.min.css';
import 'datatables.net-bs/css/dataTables.bootstrap.css';
$.DataTable = require('datatables.net');
pdfMake.vfs = pdfFonts.pdfMake.vfs; // This line solved the Roboto errors
require("datatables.net-buttons/js/buttons.colVis.js"); // Column visibility
require("datatables.net-buttons/js/buttons.html5.js"); // HTML 5 file export
require("datatables.net-buttons/js/buttons.flash.js"); // Flash file export
require("datatables.net-buttons/js/buttons.print.js"); // Print view button

我最近遇到了这个问题。我尝试按照他们的文档上的步骤进行操作,但我发现了与您相同的错误。我的字体已成功添加到node_modules的子目录中。我的错误是当我运行命令gulp buildFonts时,它没有在vfs_fonts.js文件中添加准备好的字体。

事实证明,我们必须将字体准确地放在examples/fonts子目录中。或者,您可以重新配置 gulpfile.js以便将默认子目录更改为要放置字体的子目录。

希望这有帮助。

对于那些将 React (TypeScript) 与 Vite 一起使用并最终来到这里的人,我设法为此找到了一个非常简单的解决方案。

PDFMake Docs说你应该按如下方式导入库:

import * as pdfMake from 'pdfmake/build/pdfmake';
import * as pdfFonts from 'pdfmake/build/vfs_fonts';
(pdfMake as any).vfs = pdfFonts.pdfMake.vfs;

这在开发中工作正常,但是在构建应用程序时,"pdfFonts.pdfMake"变得未定义。所以它不起作用。

所以我分析了生产版本,看到构建包含这样的部分,其中包含字体对象

globalThis.pdfMake = globalThis.pdfMake || {};
globalThis.pdfMake.vfs = {
"Roboto-Italic.ttf": "AAEAAAARAQAABAAQR0RFRqWLoiAAAdT4AA=...",
"Roboto-Medium.ttf": "AAEAAAARAQAABAAQR0RFRqWLoiAAAb9IAA...",
"Roboto-MediumItalic.ttf": "AAEAAAARAQAABAAQR0RFRqWLoiAAAd==....",
"Roboto-Regular.ttf": "AAEAAAARAQAABAAQR0RFRqWLoiAAAb8IAAACWA=....",
};

由于字体已经存在,因此我们可以使用它们来解决问题:

import * as pdfMake from 'pdfmake/build/pdfmake';
import * as pdfFonts from 'pdfmake/build/vfs_fonts';
(pdfMake as any).vfs =
pdfFonts && pdfFonts.pdfMake ? pdfFonts.pdfMake.vfs : globalThis.pdfMake.vfs;

现在,这将适用于开发阶段和生产构建,没有任何问题。

function createPdf(assessmentId: string): string {
const pdfMake = require("pdfmake/build/pdfmake.js");
const pdfFonts = require("pdfmake/build/vfs_fonts.js");
pdfMake.vfs = pdfFonts.pdfMake.vfs;
const projectId = "crds-wayfinder-int";
const philstorage = new gcs({
projectId: projectId
});
// required font setup, requires that you link to the fonts shipped with npm
const termpaper = new PdfLayout();
const docDefinition = termpaper.layout;
// get a reference to the PdfKit instance, which is a streaming interface
const pdfDoc = pdfMake.createPdf(docDefinition);
pdfDoc.getBuffer((buffer: any) => {
console.log('buffer: ', buffer);
});
console.log('pdfDoc: ', pdfDoc);
return "pdflocation";
}

对于电子(带有电子生成器的 @vue-CLI),这最终对我有用:

yarn add pdfmake

然后在 js/coffeescript 代码中:

import pdfMake from 'pdfmake/build/pdfmake.min.js'
import pdfFonts from 'pdfmake/build/vfs_fonts.js'
# this did the trick:
pdfMake.vfs = pdfFonts.pdfMake.vfs

希望对您有所帮助!

最新更新