2.4 KiB
2.4 KiB
Exporting PDF Pages as PNG Images
When you need to export every page of a jsPDF document as individual PNG images (e.g., for sharing in chat, embedding in emails, or image-only workflows):
Installation
npm install pdfjs-dist
Worker Setup (main.tsx or entry point)
import * as pdfjsLib from 'pdfjs-dist';
pdfjsLib.GlobalWorkerOptions.workerSrc = new URL(
'pdfjs-dist/build/pdf.worker.min.mjs',
import.meta.url,
).toString();
Implementation Pattern
The function accepts EITHER a jsPDF instance OR a Blob (from a function that returns doc.output('blob')):
export async function downloadPdfAsImages(
pdfInput: jsPDF | Blob,
customerName: string,
): Promise<void> {
// 1. Get raw PDF bytes
let arrayBuffer: ArrayBuffer;
if (pdfInput instanceof Blob) {
arrayBuffer = await pdfInput.arrayBuffer();
} else {
arrayBuffer = pdfInput.output('arraybuffer');
}
// 2. Load into pdfjs
const pdf = await pdfjsLib.getDocument({ data: arrayBuffer }).promise;
// 3. Render each page to canvas, then trigger download
for (let pageNum = 1; pageNum <= pdf.numPages; pageNum++) {
const page = await pdf.getPage(pageNum);
const viewport = page.getViewport({ scale: 2 }); // 2x = Retina
const canvas = document.createElement('canvas');
canvas.width = viewport.width;
canvas.height = viewport.height;
const ctx = canvas.getContext('2d')!;
await page.render({ canvasContext: ctx, viewport }).promise;
const blob = await new Promise<Blob>((resolve) => {
canvas.toBlob((b) => resolve(b!), 'image/png');
});
const url = URL.createObjectURL(blob);
const a = document.createElement('a');
a.href = url;
a.download = `${customerName.replace(/\s+/g, '_')}_Page${pageNum}.png`;
document.body.appendChild(a);
a.click();
document.body.removeChild(a);
URL.revokeObjectURL(url);
page.cleanup();
}
}
Key Details
- Scale:
getViewport({ scale: 2 })= 144 DPI. Use 1 for smaller files, 3-4 for print quality. - Blob path: If you have a function that already builds the PDF and returns
doc.output('blob'), pass the blob directly — you don't need access to the jsPDF instance. - Browser download: Each page triggers its own download. Browsers batch them into the download bar.
- Memory:
URL.revokeObjectURL()andpage.cleanup()prevent leaks with many pages. - Dependency:
pdfjs-distadds ~2MB to the bundle (worker + core).