jsPDF 快速上手与深入实践在浏览器与 Node.js 中纯客户端生成 PDF【免费下载链接】jsPDFClient-side JavaScript PDF generation for everyone.项目地址: https://gitcode.com/gh_mirrors/js/jsPDFjsPDF 是一个纯 JavaScript 的 PDF 生成库目标是面向所有人的客户端 PDF 生成Client-side JavaScript PDF generation for everyone。本指南以仓库根目录 README.md 为主线完整覆盖安装方式、浏览器/Node.js/AMD/全局变量等模块格式的使用方法、Unicode/自定义字体集成、Node 文件读取安全策略、可选依赖管理以及 compat/advanced 双 API 模式并结合 src/jspdf.js、src/index.js、src/modules/ 等源码给出实现级佐证。读完本文你将能够在浏览器端用几行代码生成并下载 PDF在 Node 端安全地读写文件并正确接入中文字体与构建工具Webpack/Vue CLI/Angular/React。一、安装npm、yarn 与 CDN 三种方式README 推荐的安装方式是使用 npm或 yarn安装后即以依赖形式进入你的工程npm install jspdf --save # 或 yarn add jspdf如果你希望始终获取最新版本也可以通过 unpkg CDN 以script标签方式直接引入 UMD 构建产物script srchttps://unpkg.com/jspdflatest/dist/jspdf.umd.min.js/scriptdist 目录中的文件类型README 明确指出包的dist目录包含不同种类的文件仓库中的 package.json 也印证了这些入口main、module、browser、exports字段均指向dist下的不同构建jspdf.es.*.js现代 ES2015 模块格式供打包工具进行 tree-shakingjspdf.node.*.js面向 Node 运行使用文件操作而非浏览器 API 来加载/保存文件jspdf.umd.*.jsUMD 模块格式可用于 AMD 或script标签直接加载polyfills*.js面向 IE 等旧浏览器的必需 polyfill。ES 变体通过core-js引入所有必需 polyfillUMD 变体则是自包含的。从 rollup.config.js 可以确认这些产物由同一套源码src/index.js为输入经 Rollup 分别以es、cjsNode与umd三种格式构建其中es/cjs产物把 package.json 中的 dependencies 与 optionalDependencies 声明为 external不打包进产物而 UMD 产物只将可选依赖 external。通常你不需要在 import 语句中指定具体文件构建工具或 Node 会自动解析出正确文件直接import jspdf即可。二、最小用法三行代码生成并下载 PDFimport { jsPDF } from jspdf; // 默认导出为 a4 纸张、纵向portrait、单位毫米mm const doc new jsPDF(); doc.text(Hello world!, 10, 10); doc.save(a4.pdf);new jsPDF()的默认行为a4/纵向/mm在源码中有明确体现src/jspdf.js 中format format || a4、orientation缺省取pportrait、unit unit || mm共同构成了这套默认值。自定义纸张尺寸、方向与单位README 给出的官方示例演示了横版 2×4 英寸的 PDF 生成// Landscape export, 2×4 inches const doc new jsPDF({ orientation: landscape, unit: in, format: [4, 2] }); doc.text(Hello world!, 1, 1); doc.save(two-by-four.pdf);结合 src/jspdf.js 的构造器注释可以梳理出完整的可用取值orientationportrait或landscape也支持简写p/l默认 portraitunitpt点、mm、cm、in英寸、px、pc、em、ex。注意若想获得px单位下的正确缩放需要启用 hotfix即传入hotfixes: [px_scaling]format既支持预设名称a0–a10、b0–b10、c0–c10、dl、letter、government-letter、legal、junior-legal、ledger、tabloid、credit-card也支持以数值数组自定义尺寸如[595.28, 841.89]即 A4 的 pt 尺寸。自定义数组传入后由getPageFormat之外的路径直接使用见 src/jspdf.js 的_addPage处理。除上述三个常用选项外构造器还支持putOnlyUsedFonts仅把用到的字体写入 PDF、compress压缩生成的 PDF、precision元素位置精度默认 16、userUnit、hotfixes以及encryption见 src/jspdf.js。三、在 Node.js 中运行jsPDF 也可以在 Node 中直接生成并保存 PDF 文件const { jsPDF } require(jspdf); // 会自动加载 node 版本 const doc new jsPDF(); doc.text(Hello world!, 10, 10); doc.save(a4.pdf); // 将文件保存到当前工作目录之所以require(jspdf)能自动加载 Node 版本是因为 package.json 的exports字段按条件导出node环境解析到./dist/jspdf.node.min.jsbrowser环境解析到./dist/jspdf.es.min.js。Node 版本使用文件操作fs而非浏览器 API 来加载和保存文件这一实现位于 src/modules/fileloading.js。四、其他模块格式AMD 与全局变量除了 ES Module 与 CommonJSjsPDF 还支持 AMD 和全局变量两种加载方式README 给出了完整示例AMDrequire([jspdf], ({ jsPDF }) { const doc new jsPDF(); doc.text(Hello world!, 10, 10); doc.save(a4.pdf); });Globalsscript标签引入 UMD 构建后const { jsPDF } window.jspdf; const doc new jsPDF(); doc.text(Hello world!, 10, 10); doc.save(a4.pdf);仓库的 examples/basic.html 展示了 UMD 引入的实际用法先script src../dist/jspdf.umd.js加载再通过window.jspdf.jsPDF取用构造函数。这一兼容矩阵ESM/Node/AMD/Globals也正是dist中多套构建产物存在的原因并且仓库在test/deployment/下分别维护了 amd、esm、globals、typescript、webworker 等多套部署测试来保证各加载方式可用。五、安全输入清洗与 Node 文件读取权限输入清洗README 强烈建议在把用户输入传给 jsPDF 之前务必先做清洗sanitize。jsPDF 本身不承担 HTML 消毒职责凡是来自用户的字符串内容都应先经过消毒处理再写入 PDF避免注入风险。Node 下读取本地文件系统的限制当在 Node 中运行时jsPDF默认禁止读取本地文件系统。README 给出了两种放行方式安全性有强有弱方式一强烈推荐使用 Node 的权限标志由运行时强制实施访问控制node --permission --allow-fs-read... ./scripts/generate.js注意--allow-fs-read必须包含所有被 import 的 JavaScript 文件包括全部依赖否则运行时也会因权限不足而拒绝读取。方式二不推荐作为首选在脚本中设置jsPDF.allowFsReadimport { jsPDF } from jspdf; const doc new jsPDF(); doc.allowFsRead [./fonts/*, ./images/logo.png]; // 允许 ./fonts 下所有文件以及单个文件README 明确警告推荐使用 Node 标志而非allowFsRead因为标志由运行时强制执行安全性更强。从实现上看src/modules/fileloading.js 的nodeReadFilejsPDF 的读取流程是先检查是否存在process.permissionNode 权限 API或this.allowFsRead两者皆无则直接抛错随后把路径realpathSync解析为真实路径若process.permission拒绝则抛权限错误最后按allowFsRead中的模式匹配——既支持精确路径也支持以单个*结尾的前缀通配例如./assets/*匹配该目录下所有路径以./assets/开头的文件。若process.permission可用它会先被检查即使allowFsRead放行也无法绕过运行时的拒绝。可选依赖与 Webpack externalsjsPDF 的部分功能依赖可选依赖optionalDependencies见 package.json例如html方法依赖html2canvas且当传入字符串形式的 HTML 文档时还依赖dompurify。jsPDF 会在需要时动态加载它们——src/modules/html.js 的loadHtml2Canvas/loadDomPurify实现说明在 ES 构建下通过动态import()加载在 CJS/AMD 下则用require/require([...])加载并兼容全局变量globalObject[html2canvas]/globalObject[DOMPurify]已存在的情况。构建工具如 Webpack会自动为每个可选依赖生成独立 chunk。如果应用不使用这些可选依赖可以通过 externals 阻止 Webpack 生成对应 chunkREADME 给出的 webpack.config.js 示例// webpack.config.js module.exports { // ... externals: { // 只把你【没有使用】的依赖声明为 externals canvg: canvg, html2canvas: html2canvas, dompurify: dompurify } };对应不同框架的处理方式README 原述Vue CLI通过vue.config.js新项目需先创建中的 configureWebpack 或 chainWebpack 属性定义 externalsAngular使用 custom webpack builders 定义 externalsReactcreate-react-app通过react-app-rewired或 eject 方式定义 externals。TypeScript 与其他框架jsPDF 可以像任何第三方库一样被导入兼容所有主流工具链与框架并且提供 TypeScript 类型声明文件仓库中的 types/index.d.tspackage.json的types/typings字段均指向它import { jsPDF } from jspdf;Meteor 项目可以这样添加meteor add jspdf:corePolyfillsjsPDF 依赖现代浏览器 API。要在 IE 等旧浏览器中使用需要加载 polyfillimport jspdf/dist/polyfills.es.js;或者加载预打包的 polyfill 文件不推荐可能重复加载 polyfill但小型应用或快速 POC 仍可用。polyfill 产物同样由 Rollup 从 src/polyfills.js 构建见 rollup.config.js 的umdPolyfills/esPolyfills配置UMD 变体自包含所有 polyfillES 变体则通过core-js引入。六、Unicode / UTF-8 与自定义字体PDF 的 14 种标准字体仅覆盖 ASCII 码页。要输出 UTF-8 文本例如中文必须集成包含所需字形glyph的自定义字体。jsPDF 支持.ttf字体文件——如果字体不含中文等所需字形PDF 中会显示乱码所以务必确认所选字体包含目标字符集。方式一使用 fontconverter 转换工具仓库自带字体转换工具 fontconverter/fontconverter.html源码位于 fontconverter/ 目录含 FileSaver.js、filereader.js 等辅助脚本。它会将提供的 ttf 文件内容转为 base64 字符串并生成一段 js 代码文件把生成的 js 文件加入项目后即可用setFont方法书写 UTF-8 文本。方式二运行时动态加载 ttf也可以直接用fetch或XMLHttpRequest把 ttf 文件作为二进制字符串加载再注册到 PDFconst doc new jsPDF(); const myFont ... // 以二进制字符串形式加载 *.ttf 字体文件 // 把字体加入 jsPDF 的 vFS虚拟文件系统 doc.addFileToVFS(MyFont.ttf, myFont); doc.addFont(MyFont.ttf, MyFont, normal); doc.setFont(MyFont);这三个 API 的实现分别位于addFileToVFS见 src/modules/vfs.js将文件内容存入this.internal.vFS[filename]addFont见 src/jspdf.js注册字体的 PostScript 名、字体名、样式如normal与字重setFont见 src/jspdf.js切换当前活动字体内部通过getFont(fontName, fontStyle, ...)解析。字体的实际解析发生在addFont事件处理中src/modules/ttfsupport.js如果是标准字体则直接从 vFS 取 base64 内容否则要求字体已存在于 vFS否则抛出Font does not exist in vFS, import fonts or remove declaration doc.addFont(...)这样的错误提示。TTF 文件内容会被转换为Uint8Array供后续字形度量使用。七、高级功能compat 与 advanced 双 API 模式jsPDF 与 yWorks fork 合并后引入了大量新特性但部分特性是破坏性 API 变更因此提供了两种 API 模式compat 模式与 MrRio 原版 API 完全一致兼容所有插件但部分高级特性如变换矩阵、图案 pattern不可用。这是默认模式advanced 模式即 yWorks fork 的 API支持 pattern、FormObject、变换矩阵等全部高级特性。在两种模式间切换doc.advancedAPI(doc { // 你的代码 }); // 或 doc.compatAPI(doc { // 你的代码 });回调执行完毕后jsPDF 会自动切回原来的 API 模式。从 src/jspdf.js 的实现可以看到advancedAPI()内部会保存图形状态、压入一个坐标变换矩阵把用户坐标系转换到 PDF 坐标系并把默认路径操作改为n不描边compatAPI()则恢复图形状态并把默认路径操作改回S描边API.advancedAPI(body)/API.compatAPI(body)支持可选回调传入回调时执行完自动切回原模式不传回调时则只切换模式、需要手动调用对应方法切回还有API.isAdvancedAPI()用于查询当前是否处于 advanced 模式某些方法如需要变换矩阵的功能会通过advancedApiModeTrap检查若不在 advanced 模式下调用会抛出... is only available in advanced API mode. You need to call advancedAPI() first.错误。注意使用约束回调内或两次调用之间的saveGraphicsState/restoreGraphicsState调用必须配对在切回 compat 模式前beginFormObject或beginTilingPattern必须由对应方法关闭。八、演示、示例与测试仓库提供了丰富的上手资源examples/basic.html 及其同目录下的 examples/js/basic.js 等示例脚本覆盖文本、图形、字体等基础元素浏览器直接打开即可交互运行examples/vite/ 是一个完整的 Vite 工程示例含 examples/vite/package.json 与 examples/vite/main.js展示了在现代打包工具下的接入方式文档站点源码位于 docs/由 JSDoc 从源码生成配置见 jsdoc.json包含各模块addImage、annotations、html、utf8、vfs 等的 API 文档页面。构建与测试命令见 package.json 的scriptsnpm run build使用 Rollup 构建 distnpm test依次运行 Node 测试Jasmine与浏览器测试KarmaChromeHeadlessnpm run test-local可依次运行 unit、node、amd、esm、globals、typescript、webworker 全套部署测试仓库在 test/ 目录下维护了大量 specs 与参考 PDFtest/reference/*.pdf用于回归对比。九、贡献与许可jsPDF 欢迎社区贡献如果觉得缺少特性或发现 bug可以查看 CONTRIBUTING.md 了解构建与测试指引并参考 CODE_OF_CONDUCT.md。Bug 报告应遵循 README 的建议提供最小可复现示例mcve、格式化良好的代码、可运行的示例并尽量证明问题确实与 jsPDF 相关而非所用框架导致。安全问题请遵循 SECURITY.md 的披露流程。项目采用 MIT 许可LICENSE版权归 James Hall 与 yWorks GmbH 所有2010-2025 / 2015-2025允许自由使用、修改与分发。【免费下载链接】jsPDFClient-side JavaScript PDF generation for everyone.项目地址: https://gitcode.com/gh_mirrors/js/jsPDF创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考