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

如何在Vite+React项目中为react-pdf Viewer添加PDF高亮批注

实现react-pdf-viewer的本地永久高亮批注功能

要在Vite+React项目里用react-pdf-viewer实现无需数据库的永久高亮,你需要正确配置highlight插件并在本地存储高亮数据(组件状态+localStorage)。以下是修改后的完整方案:

核心修改点

  • 导入并初始化highlightPlugin,绑定高亮数据的读写逻辑
  • 用组件状态存储高亮内容,结合localStorage实现页面刷新后高亮不丢失
  • 将highlight插件加入Viewer的插件列表,启用高亮交互

修改后的完整代码

import React, { useState, useEffect } from "react";
import { Worker, Viewer } from "@react-pdf-viewer/core";
import { ExcelRenderer, OutTable } from "react-excel-renderer";
import { defaultLayoutPlugin } from "@react-pdf-viewer/default-layout";
import { highlightPlugin } from "@react-pdf-viewer/highlight"; // 新增导入highlight插件
import "@react-pdf-viewer/highlight/lib/styles/index.css";
import "@react-pdf-viewer/core/lib/styles/index.css";
import "@react-pdf-viewer/default-layout/lib/styles/index.css";
import { backendBaseUrl } from "../config";

function DocumentDrawer({ isOpen, toggle, viewFile }) {
  const newPdfPlugin = defaultLayoutPlugin();
  const [fileType, setFileType] = useState(null);
  const [excelData, setExcelData] = useState(null);
  // 存储当前PDF的高亮数据,初始值从localStorage读取或为空数组
  const [highlights, setHighlights] = useState([]);

  // 初始化highlight插件,绑定数据更新逻辑
  const highlightPluginInstance = highlightPlugin({
    highlights,
    onHighlightChange: (newHighlights) => {
      setHighlights(newHighlights);
      // 按文件名存储高亮,确保不同PDF的高亮独立保存
      localStorage.setItem(`pdf-highlights-${viewFile}`, JSON.stringify(newHighlights));
    },
  });

  // 切换PDF文件时,加载对应文件的历史高亮
  useEffect(() => {
    if (!viewFile) return;
    const savedHighlights = localStorage.getItem(`pdf-highlights-${viewFile}`);
    setHighlights(savedHighlights ? JSON.parse(savedHighlights) : []);
  }, [viewFile]);

  // 补充文件类型识别逻辑(原代码未实现,确保能正确区分PDF/Excel)
  useEffect(() => {
    if (viewFile) {
      const ext = viewFile.split('.').pop().toLowerCase();
      setFileType(ext === 'pdf' ? 'pdf' : 'excel');
      // 处理Excel文件渲染
      if (ext === 'excel') {
        ExcelRenderer(`${backendBaseUrl}/api/documents/${viewFile}`, (err, resp) => {
          if (err) console.error(err);
          else setExcelData(resp);
        });
      }
    }
  }, [viewFile]);

  return (
    <div className={`sidebar_content_viewer ${isOpen ? "open" : ""}`}>
      <button className="btn ms-5 btn-primary close-button" onClick={toggle}>
        Close
      </button>
      <div className="slider_inner_contentview">
        <div className="file_container">
          {fileType === "pdf" && (
            <Worker workerUrl="https://unpkg.com/pdfjs-dist@3.9.179/build/pdf.worker.min.js">
              <Viewer
                fileUrl={`${backendBaseUrl}/api/documents/${viewFile}`}
                plugins={[newPdfPlugin, highlightPluginInstance]} // 启用highlight插件
                defaultScale={1.2}
                preload={true}
              />
            </Worker>
          )}
          {/* 渲染Excel文件 */}
          {fileType === "excel" && excelData && (
            <OutTable data={excelData} columns={excelData.headers} />
          )}
        </div>
      </div>
    </div>
  );
}

export default DocumentDrawer;

关键说明

  1. 高亮持久化:用户添加/删除高亮时,onHighlightChange会同步更新组件状态并将数据存入localStorage,刷新页面或切换回同一PDF时会自动加载历史高亮
  2. 插件生效条件:必须将highlightPluginInstance加入Viewer的plugins数组,否则高亮交互和样式都不会生效
  3. 文件隔离:通过pdf-highlights-${viewFile}作为localStorage的键,保证不同PDF的高亮数据不会互相覆盖

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.10 00:01:00