HTML5+JavaScript读取DOCX 文档完整内容

HTML5+JavaScript读取DOCX 文档完整内容

HTML5 本身只提供文件读取能力,不懂 DOCX 格式,但可以通过第三方 JavaScript 库,在纯前端环境下读取和解析 Word 文档的完整内容。

核心原理:两步走

读文件:利用 HTML5 的 FileReader API 将用户选择的 .docx 文件读取为 ArrayBuffer(二进制数据缓冲区)。

做解析:将 ArrayBuffer 传给 JavaScript 库,由它完成解压、XML解析、语义映射和最终的 HTML 渲染。

常用方案

Mammoth.js库:把 DOCX 转成 HTML 或纯文本,保留基础样式(标题、列表、加粗等),适合展示。

docx-preview.js库:尽量还原原始排版(分页、字体、表格),效果与Office打开几乎一致,适合预览。

需注意,这两个库主要处理文档正文部分。mammoth.js 对页眉页脚的支持有限,而 docx-preview.js库 则支持得更好,能近乎完美地渲染它们

JSZip .js库,解压 DOCX 这个 ZIP 容器,取出里面的 XML 和图片。

下面给出docx-preview 比较完整的示例

先看效果图:

docx-preview 的工作流程:

.注意:JSZip必须在docx-preview之前加载,否则会报错。

JSZip 在 docx-preview 中的作用

DOCX 文件本质就是一个 ZIP 压缩包。把任何.docx改成.zip解压后,你会看到类似这样的结构:

这里JSZip 和 docx-preview库用CDN (Content Delivery Network 中文:内容分发网络)引入。

示例代码:

html 复制代码
<!DOCTYPE html>
<html lang="zh-CN">
<head>
  <meta charset="UTF-8">
  <title>DOCX 预览</title>
  <style>
    body { margin: 0; font-family: sans-serif; }
    #toolbar {
      padding: 10px; background: #f5f5f5;
      border-bottom: 1px solid #ddd;
    }
    #container {
      padding: 20px;
      background: #e8e8e8;
      min-height: calc(100vh - 60px);
    }
    /* docx-preview 会在容器内生成 .docx-wrapper */
    .docx-wrapper {
      background: gray;
      padding: 30px;
      display: flex;
      flex-flow: column;
      align-items: center;
    }
    .docx-wrapper > section.docx {
      background: white;
      box-shadow: 0 0 10px rgba(0,0,0,0.5);
      margin-bottom: 30px;
    }
  </style>
</head>
<body>
  <div id="toolbar">
    <input type="file" id="fileInput" accept=".docx">
    <span id="status"></span>
  </div>
  <div id="container"></div>

  <!-- 依赖:JSZip 必须先加载 -->
  <script src="https://unpkg.com/jszip/dist/jszip.min.js"></script>
  <script src="https://unpkg.com/docx-preview/dist/docx-preview.js"></script>

  <script>
    const fileInput = document.getElementById('fileInput');
    const container = document.getElementById('container');
    const status = document.getElementById('status');

    fileInput.addEventListener('change', async (e) => {
      const file = e.target.files[0];
      if (!file) return;

      status.textContent = '正在解析...';
      container.innerHTML = '';

      try {
        await docx.renderAsync(file, container, null, {
          className: 'docx',           // 生成元素的类名前缀
          inWrapper: true,             // 是否包一层 wrapper
          ignoreWidth: false,          // 是否忽略页面宽度
          ignoreHeight: false,         // 是否忽略页面高度
          ignoreFonts: false,          // 是否忽略字体
          breakPages: true,            // 分页渲染
          ignoreLastRenderedPageBreak: true,
          experimental: false,         // 实验性功能
          trimXmlDeclaration: true,
          useBase64URL: false,         // 图片是否用 base64
          renderHeaders: true,         // 渲染页眉
          renderFooters: true,         // 渲染页脚
          renderFootnotes: true,       // 渲染脚注
          renderEndnotes: true,        // 渲染尾注
          renderComments: false,       // 渲染批注
          debug: false
        });
        status.textContent = '解析完成 ✓';
      } catch (err) {
        console.error(err);
        status.textContent = '解析失败:' + err.message;
      }
    });
  </script>
</body>
</html>
相关推荐
IT_陈寒33 分钟前
SpringBoot自动装配坑了我一天,原来问题出在这
前端·人工智能·后端
索西引擎1 小时前
【React】key 属性:协调算法中的元素标识机制与最佳实践
前端·javascript·react.js
只会cv的前端攻城狮2 小时前
动态组件架构设计:从配置到事件驱动全链路解析
前端·vue.js
飞天狗2 小时前
Next.js 16 App Router 实战:服务端组件与流式渲染
前端·next.js
OpenTiny社区2 小时前
TinyEngine 2.11版本发布:AI 进一步融入画布,Vue 工程可一键转DSL
前端·vue.js·github
小雪_Snow2 小时前
JavaScript 中的三种常用事件
开发语言·前端·javascript
Hyyy2 小时前
Electron-Vite是什么,和Vite有什么区别
前端·面试
蓝胖子酱2 小时前
在 Electron 中用 electron-store 实现加密存储与自定义格式文件
前端·javascript·数据库
虚焦像素_2 小时前
海康 Web 插件版接入指南:用法与注意事项
前端
虚焦像素_3 小时前
海康 Web 无插件版接入指南:用法与注意事项
前端