合并代码
This commit is contained in:
@@ -3,19 +3,14 @@
|
||||
* 显示文档内容和评查点高亮
|
||||
*/
|
||||
import { useState, useEffect, useRef, ChangeEvent } from 'react';
|
||||
import { pdfjs } from 'react-pdf';
|
||||
import { DOCUMENT_URL } from '~/api/axios-client';
|
||||
import { CollaboraViewer, type CollaboraViewerHandle } from '~/components/collabora/CollaboraViewer';
|
||||
import { requestPageInfo, customGotoPage } from '~/components/collabora/lib';
|
||||
import { PdfPreview } from './previewComponents/PdfPreview';
|
||||
|
||||
// 设置worker路径为public目录下的worker文件
|
||||
pdfjs.GlobalWorkerOptions.workerSrc = '/pdf.worker.js';
|
||||
|
||||
// 导入统一的ReviewPoint类型
|
||||
import { type ReviewPoint } from './';
|
||||
import { toastService } from '../ui/Toast';
|
||||
|
||||
// 直接从ReviewPointsList导入类型,避免循环依赖
|
||||
import { type ReviewPoint } from './ReviewPointsList';
|
||||
|
||||
// 定义文档内容类型
|
||||
interface FileContent {
|
||||
title: string;
|
||||
@@ -68,34 +63,24 @@ export function FilePreview({ fileContent, activeReviewPointResultId, targetPage
|
||||
const isDocx = fileExtension === 'docx';
|
||||
const isPdf = fileExtension === 'pdf';
|
||||
|
||||
// 如果是PDF文件,直接使用PdfPreview组件
|
||||
if (isPdf && real_path) {
|
||||
// console.log('fileContent', fileContent)
|
||||
// console.log('activeReviewPointResultId', activeReviewPointResultId)
|
||||
const pageOffset = fileContent.ocrResult?.__meta?.page_offset || 0;
|
||||
return (
|
||||
<PdfPreview
|
||||
filePath={real_path}
|
||||
targetPage={targetPage}
|
||||
charPositions={charPositions}
|
||||
isStructuredView={isStructuredView}
|
||||
activeReviewPointResultId={activeReviewPointResultId}
|
||||
pageOffset={pageOffset}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
// DOCX 和其他文件类型继续使用原有逻辑
|
||||
// ✅ 将所有hooks移到条件return之前,确保遵守React Hooks规则
|
||||
// Refs
|
||||
const contentRef = useRef<HTMLDivElement>(null);
|
||||
const collaboraViewerRef = useRef<CollaboraViewerHandle>(null);
|
||||
const prevTargetPageRef = useRef<number | undefined>(undefined);
|
||||
const lastMousePosRef = useRef({ x: 0, y: 0 });
|
||||
|
||||
// States
|
||||
const [numPages, setNumPages] = useState<number | null>(null);
|
||||
const [pageInputValue, setPageInputValue] = useState<string>('');
|
||||
const [dragMode, setDragMode] = useState(false);
|
||||
const [isDragging, setIsDragging] = useState(false);
|
||||
const [dragCursor, setDragCursor] = useState('default');
|
||||
|
||||
// ✅ 将所有useEffect移到条件return之前
|
||||
// DOCX 页数获取: 使用 requestPageInfo 方法
|
||||
useEffect(() => {
|
||||
if (!isDocx) return;
|
||||
|
||||
// console.log('[FilePreview] DOCX 文档加载,尝试获取页数');
|
||||
if (!isDocx || isPdf) return; // PDF文件不需要执行
|
||||
|
||||
let intervalCleared = false;
|
||||
|
||||
@@ -108,7 +93,6 @@ export function FilePreview({ fileContent, activeReviewPointResultId, targetPage
|
||||
return;
|
||||
}
|
||||
|
||||
// console.log('[FilePreview] Collabora 已就绪,尝试获取页数');
|
||||
clearInterval(checkInterval);
|
||||
intervalCleared = true;
|
||||
|
||||
@@ -132,13 +116,97 @@ export function FilePreview({ fileContent, activeReviewPointResultId, targetPage
|
||||
return () => {
|
||||
clearInterval(checkInterval);
|
||||
};
|
||||
}, [isDocx]);
|
||||
}, [isDocx, isPdf]);
|
||||
|
||||
// 拖拽状态管理(仅用于 DOCX)
|
||||
const [dragMode, setDragMode] = useState(false);
|
||||
const [isDragging, setIsDragging] = useState(false);
|
||||
const [dragCursor, setDragCursor] = useState('default');
|
||||
const lastMousePosRef = useRef({ x: 0, y: 0 });
|
||||
// 监听鼠标离开窗口事件
|
||||
useEffect(() => {
|
||||
if (isPdf) return; // PDF不需要拖拽功能
|
||||
|
||||
const handleMouseLeave = () => {
|
||||
if (dragMode && isDragging) {
|
||||
setIsDragging(false);
|
||||
setDragCursor('grab');
|
||||
}
|
||||
};
|
||||
|
||||
const handleMouseUp = () => {
|
||||
if (!dragMode) return;
|
||||
setIsDragging(false);
|
||||
setDragCursor('grab');
|
||||
};
|
||||
|
||||
document.addEventListener('mouseleave', handleMouseLeave);
|
||||
document.addEventListener('mouseup', handleMouseUp as EventListener);
|
||||
|
||||
return () => {
|
||||
document.removeEventListener('mouseleave', handleMouseLeave);
|
||||
document.removeEventListener('mouseup', handleMouseUp as EventListener);
|
||||
};
|
||||
}, [isDragging, dragMode, isPdf]);
|
||||
|
||||
// 处理页面跳转
|
||||
useEffect(() => {
|
||||
if (isPdf) return; // PDF由PdfPreview处理
|
||||
|
||||
// 如果有目标页码,并且与上次相同,提示用户
|
||||
if(targetPage && numPages && targetPage <= numPages && targetPage === prevTargetPageRef.current){
|
||||
// toastService.success(`已跳转至目标页码`);
|
||||
}
|
||||
// 如果有目标页码,并且与上次不同或activeReviewPointId变化了,则执行跳转
|
||||
if (targetPage && numPages && targetPage <= numPages) {
|
||||
prevTargetPageRef.current = targetPage;
|
||||
let newTargetPage = targetPage;
|
||||
|
||||
// 页码偏移量
|
||||
try {
|
||||
// 安全地访问ocrResult
|
||||
if (fileContent.ocrResult && fileContent.ocrResult.__meta && fileContent.ocrResult.__meta.page_offset) {
|
||||
// 可以根据需要使用page_offset调整目标页面
|
||||
newTargetPage = targetPage + fileContent.ocrResult.__meta.page_offset;
|
||||
}
|
||||
} catch (error) {
|
||||
console.error("访问ocrResult时出错:", error);
|
||||
toastService.error("访问ocrResult时出错:" + (error instanceof Error ? error.message : '未知错误'));
|
||||
}
|
||||
|
||||
const pageElementId = `page-${newTargetPage}${isStructuredView ? '-structured' : ''}`;
|
||||
|
||||
const pageElement = document.getElementById(pageElementId);
|
||||
if (pageElement) {
|
||||
pageElement.scrollIntoView({ behavior: 'smooth', block: 'start' });
|
||||
} else {
|
||||
console.warn(`未找到页面元素: ${pageElementId}`);
|
||||
}
|
||||
}
|
||||
}, [targetPage, numPages, fileContent, activeReviewPointResultId, isStructuredView, isPdf]);
|
||||
|
||||
// 调试日志
|
||||
console.log('[FilePreview] 组件渲染', {
|
||||
real_path,
|
||||
fileExtension,
|
||||
isDocx,
|
||||
isPdf,
|
||||
hasPath: !!fileContent.path,
|
||||
hasTemplatePath: !!fileContent.template_contract_path
|
||||
});
|
||||
|
||||
// 如果是PDF文件,直接使用PdfPreview组件
|
||||
if (isPdf && real_path) {
|
||||
console.log('[FilePreview] 渲染PDF预览', { real_path, targetPage, charPositions });
|
||||
const pageOffset = fileContent.ocrResult?.__meta?.page_offset || 0;
|
||||
return (
|
||||
<PdfPreview
|
||||
filePath={real_path}
|
||||
targetPage={targetPage}
|
||||
charPositions={charPositions}
|
||||
isStructuredView={isStructuredView}
|
||||
activeReviewPointResultId={activeReviewPointResultId}
|
||||
pageOffset={pageOffset}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
// DOCX 和其他文件类型继续使用原有逻辑
|
||||
|
||||
// 放大文档(仅用于 DOCX)
|
||||
const handleZoomIn = () => {
|
||||
@@ -209,66 +277,7 @@ export function FilePreview({ fileContent, activeReviewPointResultId, targetPage
|
||||
setIsDragging(false);
|
||||
setDragCursor('grab');
|
||||
};
|
||||
|
||||
// 监听鼠标离开窗口事件
|
||||
useEffect(() => {
|
||||
const handleMouseLeave = () => {
|
||||
if (dragMode && isDragging) {
|
||||
setIsDragging(false);
|
||||
setDragCursor('grab');
|
||||
}
|
||||
};
|
||||
|
||||
document.addEventListener('mouseleave', handleMouseLeave);
|
||||
document.addEventListener('mouseup', handleMouseUp as EventListener);
|
||||
|
||||
return () => {
|
||||
document.removeEventListener('mouseleave', handleMouseLeave);
|
||||
document.removeEventListener('mouseup', handleMouseUp as EventListener);
|
||||
};
|
||||
}, [isDragging, dragMode]);
|
||||
|
||||
// 处理页面跳转
|
||||
const prevTargetPageRef = useRef<number | undefined>(undefined);
|
||||
useEffect(() => {
|
||||
// 调试信息:记录组件状态
|
||||
// console.log(`FilePreview更新 - isStructuredView:${isStructuredView}, targetPage:${targetPage}, activeReviewPointResultId:${activeReviewPointResultId}, numPages:${numPages}`);
|
||||
|
||||
// 如果有目标页码,并且与上次相同,提示用户
|
||||
if(targetPage && numPages && targetPage <= numPages && targetPage === prevTargetPageRef.current){
|
||||
// toastService.success(`已跳转至目标页码`);
|
||||
}
|
||||
// 如果有目标页码,并且与上次不同或activeReviewPointId变化了,则执行跳转
|
||||
if (targetPage && numPages && targetPage <= numPages) {
|
||||
// if (targetPage && numPages && targetPage <= numPages && (targetPage !== prevTargetPageRef.current || activeReviewPointResultId)) {
|
||||
prevTargetPageRef.current = targetPage;
|
||||
let newTargetPage = targetPage;
|
||||
|
||||
// 页码偏移量
|
||||
try {
|
||||
// 安全地访问ocrResult
|
||||
if (fileContent.ocrResult && fileContent.ocrResult.__meta && fileContent.ocrResult.__meta.page_offset) {
|
||||
// 可以根据需要使用page_offset调整目标页面
|
||||
newTargetPage = targetPage + fileContent.ocrResult.__meta.page_offset;
|
||||
}
|
||||
} catch (error) {
|
||||
console.error("访问ocrResult时出错:", error);
|
||||
toastService.error("访问ocrResult时出错:" + (error instanceof Error ? error.message : '未知错误'));
|
||||
}
|
||||
|
||||
const pageElementId = `page-${newTargetPage}${isStructuredView ? '-structured' : ''}`;
|
||||
// console.log(`尝试跳转到元素ID: ${pageElementId}`);
|
||||
|
||||
const pageElement = document.getElementById(pageElementId);
|
||||
if (pageElement) {
|
||||
// console.log(`跳转到第${newTargetPage}页,对应评查点结果ID: ${activeReviewPointResultId}`);
|
||||
pageElement.scrollIntoView({ behavior: 'smooth', block: 'start' });
|
||||
} else {
|
||||
console.warn(`未找到页面元素: ${pageElementId}`);
|
||||
}
|
||||
}
|
||||
}, [targetPage, numPages, fileContent, activeReviewPointResultId, isStructuredView]);
|
||||
|
||||
|
||||
// 获取评查点对应的样式类
|
||||
// const getHighlightClass = (status: string) => {
|
||||
// switch (status) {
|
||||
|
||||
Reference in New Issue
Block a user