Fix horizontal PDF scale

This commit is contained in:
Richard Roberson 2025-01-26 14:38:16 -07:00
parent a1136be580
commit 816690360e
2 changed files with 21 additions and 21 deletions

View file

@ -1,10 +1,9 @@
'use client';
import { RefObject, useCallback } from 'react';
import { RefObject, useCallback, useState, useEffect, useRef } from 'react';
import { Document, Page } from 'react-pdf';
import 'react-pdf/dist/Page/AnnotationLayer.css';
import 'react-pdf/dist/Page/TextLayer.css';
import { useState, useEffect, useRef } from 'react';
import { PDFSkeleton } from './PDFSkeleton';
import { useTTS } from '@/contexts/TTSContext';
import { usePDF } from '@/contexts/PDFContext';
@ -109,13 +108,25 @@ export function PDFViewer({ zoomLevel }: PDFViewerProps) {
};
}, [currDocText, currentSentence, highlightPattern, clearHighlights]);
// Add scale calculation function
const calculateScale = useCallback((pageWidth = 595): number => {
// Add page dimensions state
const [pageWidth, setPageWidth] = useState<number>(595); // default A4 width
const [pageHeight, setPageHeight] = useState<number>(842); // default A4 height
// Modify scale calculation function to handle orientation
const calculateScale = useCallback((width = pageWidth, height = pageHeight): number => {
const margin = 24; // 24px padding on each side
const containerHeight = window.innerHeight - 100; // approximate visible height
const targetWidth = containerWidth - margin;
const baseScale = targetWidth / pageWidth;
const targetHeight = containerHeight - margin;
// Calculate scales based on both dimensions
const scaleByWidth = targetWidth / width;
const scaleByHeight = targetHeight / height;
// Use the smaller scale to ensure the page fits both dimensions
const baseScale = Math.min(scaleByWidth, scaleByHeight);
return baseScale * (zoomLevel / 100);
}, [containerWidth, zoomLevel]);
}, [containerWidth, zoomLevel, pageWidth, pageHeight]);
// Add resize observer effect
useEffect(() => {
@ -152,6 +163,10 @@ export function PDFViewer({ zoomLevel }: PDFViewerProps) {
renderTextLayer={true}
className="shadow-lg"
scale={calculateScale()}
onLoadSuccess={(page) => {
setPageWidth(page.originalWidth);
setPageHeight(page.originalHeight);
}}
/>
</div>
</div>

View file

@ -39,7 +39,6 @@ interface PDFContextType {
getDocument: (id: string) => Promise<PDFDocument | undefined>;
removeDocument: (id: string) => Promise<void>;
isLoading: boolean;
error: string | null;
extractTextFromPDF: (pdfURL: string, currDocPage: number) => Promise<string>;
highlightPattern: (text: string, pattern: string, containerRef: React.RefObject<HTMLDivElement>) => void;
clearHighlights: () => void;
@ -65,7 +64,6 @@ const PDFContext = createContext<PDFContextType | undefined>(undefined);
export function PDFProvider({ children }: { children: ReactNode }) {
const [documents, setDocuments] = useState<PDFDocument[]>([]);
const [isLoading, setIsLoading] = useState(true);
const [error, setError] = useState<string | null>(null);
const { isDBReady } = useConfig();
const {
@ -86,12 +84,10 @@ export function PDFProvider({ children }: { children: ReactNode }) {
if (!isDBReady) return;
try {
setError(null);
const docs = await indexedDBService.getAllDocuments();
setDocuments(docs);
} catch (error) {
console.error('Failed to load documents:', error);
setError('Failed to load documents. Please try again.');
} finally {
setIsLoading(false);
}
@ -102,7 +98,6 @@ export function PDFProvider({ children }: { children: ReactNode }) {
// Add a new document to IndexedDB
const addDocument = useCallback(async (file: File): Promise<string> => {
setError(null);
const id = uuidv4();
const newDoc: PDFDocument = {
id,
@ -118,32 +113,27 @@ export function PDFProvider({ children }: { children: ReactNode }) {
return id;
} catch (error) {
console.error('Failed to add document:', error);
setError('Failed to save the document. Please try again.');
throw error;
}
}, []);
// Get a document by ID from IndexedDB
const getDocument = useCallback(async (id: string): Promise<PDFDocument | undefined> => {
setError(null);
try {
return await indexedDBService.getDocument(id);
} catch (error) {
console.error('Failed to get document:', error);
setError('Failed to retrieve the document. Please try again.');
return undefined;
}
}, []);
// Remove a document by ID from IndexedDB
const removeDocument = useCallback(async (id: string): Promise<void> => {
setError(null);
try {
await indexedDBService.removeDocument(id);
setDocuments((prev) => prev.filter((doc) => doc.id !== id));
} catch (error) {
console.error('Failed to remove document:', error);
setError('Failed to remove the document. Please try again.');
throw error;
}
}, []);
@ -241,7 +231,6 @@ export function PDFProvider({ children }: { children: ReactNode }) {
setTTSText(text);
} catch (error) {
console.error('Error loading PDF text:', error);
setError('Failed to extract PDF text');
}
}, [currDocURL, currDocPage, extractTextFromPDF, setTTSText]);
@ -254,7 +243,6 @@ export function PDFProvider({ children }: { children: ReactNode }) {
// Set curr document
const setCurrentDocument = useCallback(async (id: string): Promise<void> => {
setError(null);
try {
const doc = await getDocument(id);
if (doc) {
@ -265,7 +253,6 @@ export function PDFProvider({ children }: { children: ReactNode }) {
}
} catch (error) {
console.error('Failed to get document URL:', error);
setError('Failed to retrieve the document. Please try again.');
}
}, [getDocument]);
@ -463,7 +450,6 @@ export function PDFProvider({ children }: { children: ReactNode }) {
getDocument,
removeDocument,
isLoading,
error,
extractTextFromPDF,
highlightPattern,
clearHighlights,
@ -483,7 +469,6 @@ export function PDFProvider({ children }: { children: ReactNode }) {
getDocument,
removeDocument,
isLoading,
error,
extractTextFromPDF,
highlightPattern,
clearHighlights,