前端实现PDF导出与Office文件在线预览方案汇总

作者:百宝袋

时间:2026-10-31

浏览:441

本文梳理了前端实现PDF文件导出及Office文档在线预览的主流技术方案。涵盖pdfmake、jsPDF、html2pdf等纯前端PDF生成库的使用场景与对比,详解利用pdf.js进行PDF渲染、docx-preview处理Word文档、exceljs结合handsontable展示Excel数据,以及SheetJS和PPTXjs处理电子表格与演示文稿的方法,并补充了基于微软和谷歌API的通用预览接口。

文章目录

本系列文章聚焦于JavaScript文件导出技术,本期重点探讨如何在浏览器端直接生成PDF文件,以及如何实现Office格式文档的在线预览。当前前端生态中,相关技术已趋于成熟,存在多种稳定可用的技术库,下文将逐一介绍这些方案。

纯前端导出PDF方案

此处不重复造轮子,主要介绍几种流行的纯前端PDF导出库,开发者可根据具体业务场景选择合适工具。

1、pdfmake

项目地址:github.com/bpampuch/pdfmake

该库支持中文显示,并具备部分自适应布局能力,但需额外引入字体库以支持多语言排版。

//npm 或者cdn引入文件
// 引入字体库
pdfmake.addFonts(Roboto);
// 创建文档流
let docDefinition={}
var pdf = pdfmake.createPdf(docDefinition);
pdf.write('pdfs/absolute.pdf').then(() => {
	console.log(new Date() - now);
}, err => {
	console.error(err);
});

此方案适用于对排版精美度要求不高的文档流生成场景,操作简便,但不支持在线预览,仅适用于直接下载PDF文件的场景。

2、jsPDF

项目地址:

github.com/parallax/jsPDF

该库使用门槛较低,官方推荐结合html2canvas使用,通过html2canvas将HTML页面转换为图片后再嵌入PDF。

// webpack.config.js
module.exports = {
  // ...
  externals: {
    // only define the dependencies you are NOT using as externals!
    canvg: "canvg",
    html2canvas: "html2canvas",
    dompurify: "dompurify"
  }
};

使用方式简单直观

// 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");

支持自定义引入字体文件

const doc = new jsPDF();

const myFont = ... // load the *.ttf font file as binary string

// add the font to jsPDF
doc.addFileToVFS("MyFont.ttf", myFont);
doc.addFont("MyFont.ttf", "MyFont", "normal");
doc.setFont("MyFont");

3、html2pdf

该库可直接将HTML内容导出为PDF,项目地址:github.com/eKoopmans/html2pdf.js

适合排版较为复杂的场景,实现所见即所得的导出效果。若需同时实现预览与导出功能,此方案较为合适。

Office文件在线预览

对于PDF文件的在线预览,通常采用pdf.js库。

首先通过npm安装依赖:npm i pdfjs-dist

需配置PDFJS.GlobalWorkerOptions.workerSrc指向正确的worker文件路径。

调用PDFJS.getDocument方法处理PDF数据,该方法返回一个包含文档信息的对象pdfDoc。

利用pdfDoc.getPage方法单独获取指定页码(如第1页)的数据对象。

创建一个DOM元素,并设置其为canvas画布属性,用于接收渲染内容。

调用page.render方法,将页面数据渲染至上述画布元素中。

HTML结构示例:

<div class="showContent" id="canvasWrap"></div>

JavaScript逻辑示例:

import pdfjsLib from 'pdfjs-dist'
import pdfwprker from 'pdfjs-dist/build/pdf.worker.js'
// let pdfPath = 'http://cdn.mozilla.net/pdfjs/tracemonkey.pdf'

 pdfjsLib.GlobalWorkerOptions.workerSrc = pdfwprker
  const wrapBox = document.getElementById('canvasWrap')
this.renderPdfs(wrapBox,pdfPath )

  //渲染函数
    async renderPdfs(element, url) {
    //  console.log(url,"psfurl")
      const loadingTask = pdfjsLib.getDocument(url)
      const pdfDocument = await loadingTask.promise
      // console.log(pdfDocument, 'pdf')
      for (let i = 1; i <= pdfDocument.numPages; i++) {
        const canvas = document.createElement('canvas')
        // 动态创建canvas
        element.appendChild(canvas);
        (async function(n) {
          const pdfPage = await pdfDocument.getPage(n)
          // Display page on the existing canvas with 100% scale.
          const viewport = pdfPage.getViewport(1.5)
          canvas.id = `theCanvas${n}`
          canvas.width = viewport.width
          canvas.height = viewport.height
          var ctx = canvas.getContext('2d')
          var renderTask = pdfPage.render({
            canvasContext: ctx,
            viewport: viewport
          })
          return renderTask.promise
        })(i)
      }
    }

DOCX文件前端预览实现

首先安装依赖:npm i docx-preview

引入库中提供的renderAsync方法。

将包含文档内容的blob数据流传入该方法,即可在页面上渲染Word文档。

import { defaultOptions, renderAsync } from "docx-preview";
renderAsync(buffer, document.getElementById("container"), null,
options: {
       className: string = "docx", // 默认和文档样式类的类名/前缀
       inWrapper: boolean = true, // 启用围绕文档内容渲染包装器
       ignoreWidth: boolean = false, // 禁止页面渲染宽度
       ignoreHeight: boolean = false, // 禁止页面渲染高度
       ignoreFonts: boolean = false, // 禁止字体渲染
       breakPages: boolean = true, // 在分页符上启用分页
       ignoreLastRenderedPageBreak: boolean = true,//禁用lastRenderedPageBreak元素的分页
       experimental: boolean = false, //启用实验性功能(制表符停止计算)
       trimXmlDeclaration: boolean = true, //如果为真,xml声明将在解析之前从xml文档中删除
       debug: boolean = false, // 启用额外的日志记录
   }
);

Excel文件前端预览实现

参考exceljs库:github.com/exceljs/exceljs

需同时下载exceljs和handsontable两个库。

利用exceljs读取文件数据。

通过workbook.getWorksheet方法获取每个工作表的数据,并将其处理为二维数组格式。

通过settings属性传入配置参数及处理好的二维数组数据至组件,渲染出Excel样式界面,从而实现预览功能。

// 加载excel的数据
(new ExcelJS.Workbook().xlsx.load(buffer)).then(workbook=>{
   // 获取excel的第一页的数据
   const ws = workbook.getWorksheet(1);
   // 获取每一行的数据
   const data = ws.getRows(1, ws.actualRowCount);
 })
 
 
// 渲染页面
hotSettings = {
   language: "zh-CN",
   readOnly: true,
   data: this.data,
   cell: this.cell,
   mergeCells: this.merge,
   colHeaders: true,
   rowHeaders: true,
   height: "calc(100vh - 107px)",
   // contextMenu: true,
   // manualRowMove: true,
   // 关闭外部点击取消选中时间的行为
   outsideClickDeselects: false,
   // fillHandle: {
   //   direction: 'vertical',
   //   autoInsertRow: true
   // },
   // afterSelectionEnd: this.afterSelectionEnd,
   // bindRowsWithHeaders: 'strict',
   licenseKey: "non-commercial-and-evaluation"
}

Excel预览的另一种方案可采用github.com/SheetJS/sheetjs库。

该方案支持Node.js环境或纯客户端运行,纯客户端React使用案例如下:

参考demo:github.com/SheetJS/sheetjs/tree/master/demos/react

PPTX文件前端预览实现

项目地址:github.com/meshesha/PPTXjs

该库依赖jquery和jszip,若项目中不希望引入jquery,可自行改造代码以适配使用。

另一种通用且便捷的方式是将PPT文件转换为PDF格式,随后通过PDF预览组件进行展示。

小结

除上述纯前端技术方案外,微软和谷歌也提供了在线预览API,其预览效果更佳且实现更简单。

谷歌在线预览接口地址:https://docs.google.com/viewer?url=预览文档地址

微软预览接口地址:

https://view.officeapps.live.com/op/view.aspx?src=预览文档指定地址

至此,关于JavaScript实现PDF文件导出和在线预览功能的介绍已完成,更多相关JavaScript PDF导出内容可参考本站往期文章或继续浏览后续文章,感谢支持。

实用工具推荐

电子包浆

绿化、压缩、噪点和虚拟水印,自由调节做旧程度。

使用 ›
图片压缩

选择画质和输出格式,预览压缩前后的大小。

使用 ›
相关文章