You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

jsPDF使用output()时自定义TTF字体与PNG图片异常求助

问题分析与解决方案

核心问题根源

  1. 二进制PDF数据传输损坏:直接将doc.output()的结果通过JSON.stringify传输,会破坏PDF的二进制结构,导致后端生成的文件异常。
  2. 自定义字体未嵌入PDF:注册字体时未开启嵌入选项,仅在客户端环境可用,未写入最终PDF文件。
  3. 图片异步加载未处理:使用DOM Image对象加载图片时,未等待加载完成就执行addImage,导致图片数据未被嵌入PDF。

分步解决方案

1. 修复PDF二进制传输问题

放弃JSON传输,改用FormData发送Blob格式的PDF,避免二进制数据被转义:

客户端修改printAPI函数

async function printAPI(pdfBlob, printer, labelName, paper, quantity) {
    const formData = new FormData();
    formData.append('doc', pdfBlob, 'label.pdf');
    formData.append('printer', printer);
    formData.append('labelName', labelName);
    formData.append('paper', paper);
    formData.append('quantity', quantity);

    await fetch('http://127.0.0.1:3000/api/printer/print-label', {
        method: 'POST',
        body: formData
    });
}

生成PDF时转成Blob调用

// 替换原printAPI调用代码
const pdfBuffer = doc.output('arraybuffer');
const pdfBlob = new Blob([pdfBuffer], { type: 'application/pdf' });
printAPI(pdfBlob, printer, 'lbl_' + part.replace('.',''), this.paper, quantity);

后端接收处理(用multer简化文件上传)

const multer = require('multer');
const upload = multer({ dest: uploadDirectory });

app.post('/api/printer/print-label', upload.single('doc'), (req, res) => {
    const targetPath = `${uploadDirectory}/lbl_${req.body.labelName}.pdf`;
    fs.rename(req.file.path, targetPath, (err) => {
        err ? res.sendStatus(500) : res.sendStatus(200);
    });
});

2. 确保自定义字体嵌入PDF

注册字体时必须添加embed参数,将字体数据写入PDF:

// 补充字体注册代码(需提前将TTF转成base64)
doc.addFileToVFS('fre3of9x.ttf', '你的字体base64编码内容');
doc.addFont('fre3of9x.ttf', 'fre3of9x', 'normal', 'embed'); // 关键是embed选项

3. 修复图片嵌入问题

等待图片加载完成后再添加到PDF,或直接使用base64格式嵌入:

方案一:异步加载图片

function loadImage(src) {
    return new Promise((resolve, reject) => {
        const img = new Image();
        img.onload = () => resolve(img);
        img.onerror = reject;
        img.src = src;
    });
}

// 生成PDF的函数改为异步
async function generateLabelPDF() {
    const img = await loadImage('/assets/bag.png');
    const doc = new jsPDF(); // 此处补充你的doc初始化逻辑

    doc.addImage(img,'png',this.width-2-18.54,0,18.54,5);
    // 后续文本、条形码生成逻辑...
}

方案二:直接使用base64图片

将bag.png转成base64字符串(可通过在线工具转换),直接嵌入代码:

const bagImgBase64 = 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAA...';
doc.addImage(bagImgBase64,'png',this.width-2-18.54,0,18.54,5);

内容的提问来源于stack exchange,提问作者jam0

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.20 20:14:51