feat(12-01): PreviewModal component with react-pdf Document/Page
- 'use client' component accepting ArrayBuffer prop and onClose callback - Configures pdfjs worker independently from PdfViewer module - Imports AnnotationLayer.css and TextLayer.css - Prev/Next page navigation with disabled states - Fixed overlay (rgba black 70%) with white inner container
This commit is contained in:
@@ -0,0 +1,79 @@
|
||||
'use client';
|
||||
import { useState } from 'react';
|
||||
import { Document, Page, pdfjs } from 'react-pdf';
|
||||
import 'react-pdf/dist/Page/AnnotationLayer.css';
|
||||
import 'react-pdf/dist/Page/TextLayer.css';
|
||||
|
||||
// Worker setup — configured independently from PdfViewer (separate module)
|
||||
pdfjs.GlobalWorkerOptions.workerSrc = new URL(
|
||||
'pdfjs-dist/build/pdf.worker.min.mjs',
|
||||
import.meta.url,
|
||||
).toString();
|
||||
|
||||
interface PreviewModalProps {
|
||||
pdfBytes: ArrayBuffer;
|
||||
onClose: () => void;
|
||||
}
|
||||
|
||||
export function PreviewModal({ pdfBytes, onClose }: PreviewModalProps) {
|
||||
const [numPages, setNumPages] = useState(0);
|
||||
const [pageNumber, setPageNumber] = useState(1);
|
||||
|
||||
return (
|
||||
<div
|
||||
style={{
|
||||
position: 'fixed',
|
||||
inset: 0,
|
||||
background: 'rgba(0,0,0,0.7)',
|
||||
zIndex: 50,
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
}}
|
||||
>
|
||||
<div
|
||||
style={{
|
||||
background: 'white',
|
||||
maxWidth: '900px',
|
||||
width: '90vw',
|
||||
maxHeight: '90vh',
|
||||
overflowY: 'auto',
|
||||
padding: '16px',
|
||||
}}
|
||||
>
|
||||
{/* Navigation controls */}
|
||||
<div className="flex items-center gap-3 text-sm mb-4">
|
||||
<button
|
||||
onClick={() => setPageNumber(p => Math.max(1, p - 1))}
|
||||
disabled={pageNumber <= 1}
|
||||
className="px-3 py-1 border rounded disabled:opacity-40 hover:bg-gray-100"
|
||||
>
|
||||
Prev
|
||||
</button>
|
||||
<span>{pageNumber} / {numPages || '?'}</span>
|
||||
<button
|
||||
onClick={() => setPageNumber(p => Math.min(numPages, p + 1))}
|
||||
disabled={pageNumber >= numPages}
|
||||
className="px-3 py-1 border rounded disabled:opacity-40 hover:bg-gray-100"
|
||||
>
|
||||
Next
|
||||
</button>
|
||||
<button
|
||||
onClick={onClose}
|
||||
className="ml-auto px-3 py-1 border rounded hover:bg-gray-100"
|
||||
>
|
||||
Close
|
||||
</button>
|
||||
</div>
|
||||
|
||||
{/* PDF renderer */}
|
||||
<Document
|
||||
file={pdfBytes}
|
||||
onLoadSuccess={({ numPages }) => setNumPages(numPages)}
|
||||
>
|
||||
<Page pageNumber={pageNumber} />
|
||||
</Document>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user