npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

vue-ofd-viewer

v0.0.2

Published

vue-ofd-viewer - OFD document viewer for Vue 2 and Vue 3 with customizable toolbar

Readme

vue-ofd-viewer


📋 项目概述

vue-ofd-viewer 是一个功能完整、高度可定制的 OFD(Open Fixed-layout Document)文档查看器组件,专为 Vue.js 应用程序设计。该组件提供了企业级的文档查看解决方案,支持 Vue 2.6+ 和 Vue 3.x 双版本,具备完整的 TypeScript 类型支持。

🏗️ 技术架构

┌─────────────────────────────────────────────────────────────┐
│                    vue-ofd-viewer                           │
├─────────────────────────────────────────────────────────────┤
│  ┌─────────────┐  ┌─────────────┐  ┌─────────────────────┐  │
│  │   OfdView   │  │  Thumbnail  │  │      Toolbar        │  │
│  │  (主组件)   │  │   Panel     │  │  (工具栏组件)       │  │
│  └──────┬──────┘  └──────┬──────┘  └──────────┬──────────┘  │
│         │                │                    │              │
│  ┌──────┴────────────────┴────────────────────┴──────────┐  │
│  │                    Core Engine                         │  │
│  │  ┌────────────┐  ┌────────────┐  ┌────────────────┐   │  │
│  │  │ OFD Parser │  │  Renderer  │  │  Signature     │   │  │
│  │  │ (解析器)   │  │  (渲染器)  │  │  Verifier      │   │  │
│  │  └────────────┘  └────────────┘  └────────────────┘   │  │
│  └───────────────────────────────────────────────────────┘  │
│  ┌───────────────────────────────────────────────────────┐  │
│  │                    Composables                         │  │
│  │  ┌────────────┐  ┌────────────┐  ┌────────────────┐   │  │
│  │  │ useConfig  │  │  vue-demi  │  │  Mosaic        │   │  │
│  │  │ (配置管理) │  │ (兼容层)   │  │  (马赛克工具)  │   │  │
│  │  └────────────┘  └────────────┘  └────────────────┘   │  │
│  └───────────────────────────────────────────────────────┘  │
└─────────────────────────────────────────────────────────────┘

🔧 技术栈

| 类别 | 技术 | |------|------| | 框架 | Vue 2.6+ / Vue 3.x (via vue-demi) | | 语言 | TypeScript 5.5+ | | 构建 | Vite 5.x | | OFD解析 | ofd-xml-parser | | 加密算法 | sm-crypto (国密算法) | | 签名验证 | jsrsasign |


✨ 特性

核心功能

  • 📄 OFD 文档渲染 - 高保真渲染 OFD 文档,支持复杂排版
  • 🔍 缩放控制 - 多级缩放,支持自适应、实际大小、百分比等多种模式
  • 📐 缩略图面板 - 快速导航,支持打印页面选择
  • 🖨️ 打印支持 - 支持全部打印、选择页面打印
  • 📥 下载功能 - 一键下载 OFD 文档
  • 🔐 签章验证 - 查看数字签章信息,验证文档完整性
  • 🔲 马赛克工具 - 敏感信息遮罩处理

开发体验

  • 🎨 高度可定制 - 工具栏按钮、样式、布局全面可配置
  • 📦 开箱即用 - 零配置即可使用,所有功能默认启用
  • 🔒 类型安全 - 完整的 TypeScript 类型定义
  • 🌐 双版本支持 - 同时支持 Vue 2 和 Vue 3
  • 📱 响应式设计 - 适配各种屏幕尺寸

📦 安装

环境要求

| 依赖 | 版本要求 | |------|---------| | Node.js | >= 16.0.0 | | Vue | ^2.6.14 或 ^3.0.0 |

安装命令

# npm
npm install vue-ofd-viewer

# yarn
yarn add vue-ofd-viewer

# pnpm
pnpm add vue-ofd-viewer

Vue 2 额外依赖

如果您使用 Vue 2,需要额外安装 Composition API 插件:

npm install @vue/composition-api

🚀 快速开始

Vue 3 项目

1. 全局注册

// main.ts
import { createApp } from "vue";
import App from "./App.vue";
import VueOfdViewer from "vue-ofd-viewer";
import "vue-ofd-viewer/style.css";

const app = createApp(App);
app.use(VueOfdViewer);
app.mount("#app");

2. 组件使用

<template>
  <div class="document-container">
    <OfdView
      :ofdLink="documentUrl"
      :config="viewerConfig"
      @ready="handleReady"
      @pageChange="handlePageChange"
    />
  </div>
</template>

<script setup lang="ts">
import { ref } from "vue";
import { createOfdViewerConfig, type OfdViewerExpose } from "vue-ofd-viewer";

const documentUrl = ref("/documents/sample.ofd");

const viewerConfig = createOfdViewerConfig({
  toolbar: {
    buttons: {
      print: { key: "print", visible: true },
      download: { key: "download", visible: true },
    },
    defaultScale: 5, // 默认 100%
  },
  thumbnailPanel: {
    visible: true,
    width: 200,
  },
});

const handleReady = (instance: OfdViewerExpose) => {
  console.log("文档加载完成,共", instance.pageCount, "页");
};

const handlePageChange = (page: number) => {
  console.log("当前页:", page);
};
</script>

<style scoped>
.document-container {
  width: 100%;
  height: 100vh;
}
</style>

Vue 2 项目

1. 全局注册

// main.js
import Vue from "vue";
import VueCompositionAPI from "@vue/composition-api";
import VueOfdViewer from "vue-ofd-viewer";
import "vue-ofd-viewer/style.css";

Vue.use(VueCompositionAPI);
Vue.use(VueOfdViewer);

new Vue({
  render: (h) => h(App),
}).$mount("#app");

2. 组件使用

<template>
  <div class="document-container">
    <OfdView
      :ofdLink="documentUrl"
      :config="viewerConfig"
      @ready="handleReady"
    />
  </div>
</template>

<script>
import { createOfdViewerConfig } from "vue-ofd-viewer";

export default {
  name: "DocumentViewer",
  data() {
    return {
      documentUrl: "/documents/sample.ofd",
      viewerConfig: createOfdViewerConfig({
        toolbar: {
          defaultScale: 5,
        },
      }),
    };
  },
  methods: {
    handleReady(instance) {
      console.log("文档加载完成,共", instance.pageCount, "页");
    },
  },
};
</script>

📖 API 文档

组件 Props

OfdView Props

| 属性名 | 类型 | 默认值 | 说明 | |--------|------|--------|------| | ofdLink | string | - | OFD 文档 URL 地址 | | showOpenFileButton | boolean | true | 是否显示打开文件按钮 | | config | OfdViewerConfig | - | 查看器配置对象 | | sealClick | (sealInfo: IOfdSignatureInfo) => void | - | 签章点击回调 |

配置类型定义

OfdViewerConfig

interface OfdViewerConfig {
  toolbar?: ToolbarConfig | false;      // 工具栏配置,false 表示隐藏
  thumbnailPanel?: ThumbnailPanelConfig | false;  // 缩略图面板配置
  showOpenFileButton?: boolean;          // 是否显示打开文件按钮
  showLoading?: boolean;                 // 是否显示加载动画
  loadingText?: string;                  // 加载提示文字
}

ToolbarConfig

interface ToolbarConfig {
  visible?: boolean;                     // 是否显示工具栏
  buttons?: Partial<Record<ToolbarButtonKey, ToolbarButtonConfig | false>>;
  scaleList?: ScaleOption[];             // 自定义缩放选项
  defaultScale?: number;                 // 默认缩放值
}

interface ToolbarButtonConfig {
  key: ToolbarButtonKey;                 // 按钮唯一标识
  visible?: boolean;                     // 是否显示
  title?: string;                        // 提示文字
  order?: number;                        // 排序权重
}

interface ScaleOption {
  value: number;                         // 缩放值
  label: string;                         // 显示标签
}

ThumbnailPanelConfig

interface ThumbnailPanelConfig {
  visible?: boolean;                     // 是否显示
  width?: number;                        // 面板宽度 (px)
  position?: "left" | "right";           // 显示位置
  showPageNumber?: boolean;              // 是否显示页码
  showPrintSelect?: boolean;             // 是否显示打印选择图标
}

工具栏按钮键值

| Key | 功能 | 说明 | |-----|------|------| | openFile | 打开文件 | 打开本地 OFD 文件 | | firstPage | 首页 | 跳转到第一页 | | prePage | 上一页 | 向前翻页 | | pageInput | 页码输入 | 显示当前页码,支持跳转 | | nextPage | 下一页 | 向后翻页 | | lastPage | 末页 | 跳转到最后一页 | | zoomOut | 缩小 | 缩小文档 | | zoomSelect | 缩放选择 | 下拉选择缩放比例 | | zoomIn | 放大 | 放大文档 | | thumbnail | 缩略图 | 切换缩略图面板 | | fullScreen | 全屏 | 切换全屏模式 | | print | 打印 | 打印文档 | | download | 下载 | 下载 OFD 文件 | | sealInfo | 签章信息 | 查看签章详情 | | mosaic | 马赛克 | 马赛克绘制工具 |

暴露方法

通过 ref 可以访问以下方法:

interface OfdViewerExpose {
  // 页面导航
  firstPage(): void;
  prePage(): void;
  nextPage(): void;
  lastPage(): void;
  gotoPage(page: number): void;

  // 缩放控制
  zoomIn(): Promise<void>;
  zoomOut(): Promise<void>;
  setScale(scale: number): Promise<void>;

  // 文件操作
  openFile(file: File | string): Promise<void>;
  print(): void;
  download(): void;

  // UI 控制
  toggleThumbnail(): void;
  toggleFullScreen(): void;
  enableMosaic(): void;

  // 数据获取
  readonly pageIndex: number;
  readonly pageCount: number;
  readonly loading: boolean;
  getSeals(): ISeal[];
  getPrintList(): Set<number>;
  clearPrintList(): void;
}

方法使用示例

<template>
  <div>
    <OfdView ref="ofdRef" :ofdLink="documentUrl" />
    <div class="controls">
      <button @click="handlePrint">打印</button>
      <button @click="handleZoomIn">放大</button>
      <button @click="handleGotoPage(10)">跳转到第10页</button>
    </div>
  </div>
</template>

<script setup lang="ts">
import { ref } from "vue";
import type { OfdViewerExpose } from "vue-ofd-viewer";

const ofdRef = ref<OfdViewerExpose>();

const handlePrint = () => {
  ofdRef.value?.print();
};

const handleZoomIn = () => {
  ofdRef.value?.zoomIn();
};

const handleGotoPage = (page: number) => {
  ofdRef.value?.gotoPage(page);
};
</script>

事件

| 事件名 | 参数 | 说明 | |--------|------|------| | ready | OfdViewerExpose | 文档加载完成 | | pageChange | number | 页码变化 | | scaleChange | number | 缩放比例变化 |


🎨 高级配置

自定义工具栏

const config = createOfdViewerConfig({
  toolbar: {
    // 隐藏特定按钮
    buttons: {
      print: false,           // 隐藏打印按钮
      download: false,        // 隐藏下载按钮
      mosaic: {               // 自定义按钮配置
        key: "mosaic",
        visible: true,
        title: "敏感信息遮罩",
      },
    },
    // 自定义缩放选项
    scaleList: [
      { value: 0, label: "自适应" },
      { value: 5, label: "100%" },
      { value: 7.5, label: "150%" },
      { value: 10, label: "200%" },
    ],
    // 默认缩放比例
    defaultScale: 5,
  },
});

自定义缩略图面板

const config = createOfdViewerConfig({
  thumbnailPanel: {
    visible: true,
    width: 250,
    position: "right",
    showPageNumber: true,
    showPrintSelect: true,
  },
});

隐藏工具栏

const config = createOfdViewerConfig({
  toolbar: false,  // 完全隐藏工具栏
});

📁 项目结构

vue-ofd-viewer/
├── src/
│   ├── components/           # Vue 组件
│   │   ├── OfdView.vue       # 主组件
│   │   ├── common/           # 通用组件
│   │   │   ├── Dialog.vue
│   │   │   ├── ThumbnailPanel.vue
│   │   │   └── FullScreenLoading.vue
│   │   └── toolbar/          # 工具栏组件
│   │       ├── ToolbarButton.vue
│   │       ├── ToolbarPage.vue
│   │       └── ToolbarZoom.vue
│   ├── composables/          # 组合式函数
│   │   └── useConfig.ts      # 配置管理
│   ├── compat/               # Vue 兼容层
│   │   └── index.ts          # vue-demi 封装
│   ├── core/                 # 核心引擎
│   │   ├── ofd/              # OFD 解析与渲染
│   │   └── jbig2/            # 图像解码
│   ├── types/                # TypeScript 类型
│   │   ├── config.ts         # 配置类型
│   │   └── ofd.ts            # OFD 类型
│   ├── utils/                # 工具函数
│   │   ├── helpers.ts        # 辅助函数
│   │   └── mosaic.ts         # 马赛克工具
│   └── index.ts              # 入口文件
├── dist/                     # 构建产物
│   ├── vue-ofd-viewer.es.js  # ES Module
│   ├── vue-ofd-viewer.umd.js # UMD 格式
│   ├── style.css             # 样式文件
│   └── index.d.ts            # 类型声明
└── package.json

🔧 开发指南

本地开发

# 克隆项目
git clone https://gitee.com/usin_cc/vue-ofd-viewer.git

# 安装依赖
npm install

# 启动开发服务器
npm run dev

# 类型检查
npm run type-check

# 构建库
npm run build:lib

发布流程

# 1. 更新版本号
npm version patch/minor/major

# 2. 构建
npm run build:lib

# 3. 发布
npm publish

❓ 常见问题

Q1: Vue 2 项目中组件无法正常工作?

A: 确保已安装 @vue/composition-api 插件并在入口文件中注册:

import VueCompositionAPI from "@vue/composition-api";
Vue.use(VueCompositionAPI);

Q2: 如何处理跨域问题?

A: OFD 文件需要通过 HTTP 服务提供,确保服务器配置了正确的 CORS 头:

Access-Control-Allow-Origin: *
Access-Control-Allow-Methods: GET

Q3: 打印时页面显示不完整?

A: 这通常是因为文档未完全加载。请确保在 ready 事件触发后再调用打印功能。

Q4: 如何自定义按钮样式?

A: 可以通过 CSS 变量覆盖默认样式:

:root {
  --ofd-toolbar-bg: #f5f5f5;
  --ofd-toolbar-icon-color: #333;
  --ofd-toolbar-icon-hover-color: #409eff;
}

Q5: 支持 SSR 吗?

A: 当前版本不支持服务端渲染 (SSR),请在客户端渲染环境中使用。


🤝 贡献指南

我们欢迎所有形式的贡献!

贡献流程

  1. Fork 本仓库
  2. 创建特性分支 (git checkout -b feature/AmazingFeature)
  3. 提交更改 (git commit -m 'Add some AmazingFeature')
  4. 推送到分支 (git push origin feature/AmazingFeature)
  5. 提交 Pull Request

代码规范

  • 使用 TypeScript 编写代码
  • 遵循 ESLint 规则
  • 编写单元测试
  • 更新相关文档

📄 许可证

本项目基于 MIT 许可证开源。


📞 联系方式


🙏 致谢

  • ofd.js - OFD 解析核心
  • vue-demi - Vue 双版本兼容方案
  • 所有贡献者和用户