import { Box, Typography } from '@mui/material'; import React, { useState, useEffect, useContext } from 'react'; import ToolContent from '@components/ToolContent'; import { ToolComponentProps } from '@tools/defineTool'; import { compressPdf } from './service'; import { InitialValuesType, CompressionLevel } from './types'; import ToolPdfInput from '@components/input/ToolPdfInput'; import { GetGroupsType } from '@components/options/ToolOptions'; import ToolFileResult from '@components/result/ToolFileResult'; import SimpleRadio from '@components/options/SimpleRadio'; import { CardExampleType } from '@components/examples/ToolExamples'; import { PDFDocument } from 'pdf-lib'; import { CustomSnackBarContext } from '../../../../contexts/CustomSnackBarContext'; import { useTranslation } from 'react-i18next'; const initialValues: InitialValuesType = { compressionLevel: 'low' }; const exampleCards: CardExampleType[] = [ { title: 'Low Compression', description: 'Minimal quality loss with slight file size reduction', sampleText: '', sampleResult: '', sampleOptions: { compressionLevel: 'low' } }, { title: 'Medium Compression', description: 'Balance between file size and quality', sampleText: '', sampleResult: '', sampleOptions: { compressionLevel: 'medium' } }, { title: 'High Compression', description: 'Maximum file size reduction with some quality loss', sampleText: '', sampleResult: '', sampleOptions: { compressionLevel: 'high' } } ]; export default function CompressPdf({ title, longDescription }: ToolComponentProps) { const { t } = useTranslation('pdf'); const [input, setInput] = useState(null); const [result, setResult] = useState(null); const [resultSize, setResultSize] = useState(''); const [isProcessing, setIsProcessing] = useState(false); const [fileInfo, setFileInfo] = useState<{ size: string; pages: number; } | null>(null); const { showSnackBar } = useContext(CustomSnackBarContext); // Get the PDF info when a file is uploaded useEffect(() => { const getPdfInfo = async () => { if (!input) { setFileInfo(null); return; } try { const arrayBuffer = await input.arrayBuffer(); const pdf = await PDFDocument.load(arrayBuffer); const pages = pdf.getPageCount(); const size = formatFileSize(input.size); setFileInfo({ size, pages }); } catch (error) { console.error('Error getting PDF info:', error); setFileInfo(null); showSnackBar(t('compressPdf.errorReadingPdf'), 'error'); } }; getPdfInfo(); }, [input]); const formatFileSize = (bytes: number): string => { if (bytes === 0) return '0 Bytes'; const k = 1024; const sizes = ['Bytes', 'KB', 'MB', 'GB']; const i = Math.floor(Math.log(bytes) / Math.log(k)); return parseFloat((bytes / Math.pow(k, i)).toFixed(2)) + ' ' + sizes[i]; }; const compute = async (values: InitialValuesType, input: File | null) => { if (!input) return; try { setIsProcessing(true); const compressedPdf = await compressPdf(input, values); setResult(compressedPdf); // Log compression results const compressionRatio = (compressedPdf.size / input.size) * 100; console.log(`Compression Ratio: ${compressionRatio.toFixed(2)}%`); setResultSize(formatFileSize(compressedPdf.size)); } catch (error) { console.error('Error compressing PDF:', error); showSnackBar( t('compressPdf.errorCompressingPdf', { error: error instanceof Error ? error.message : String(error) }), 'error' ); setResult(null); } finally { setIsProcessing(false); } }; const compressionOptions: { value: CompressionLevel; label: string; description: string; }[] = [ { value: 'low', label: t('compressPdf.lowCompression'), description: t('compressPdf.lowCompressionDescription') }, { value: 'medium', label: t('compressPdf.mediumCompression'), description: t('compressPdf.mediumCompressionDescription') }, { value: 'high', label: t('compressPdf.highCompression'), description: t('compressPdf.highCompressionDescription') } ]; return ( } resultComponent={ } getGroups={({ values, updateField }) => [ { title: t('compressPdf.compressionSettings'), component: ( {t('compressPdf.compressionLevel')} {compressionOptions.map((option) => ( { updateField('compressionLevel', option.value); }} /> ))} {fileInfo && ( {t('compressPdf.fileSize')}:{' '} {fileInfo.size} {t('compressPdf.pages')}: {fileInfo.pages} {resultSize && ( {t('compressPdf.compressedFileSize')}:{' '} {resultSize} )} )} ) } ]} /> ); }