Renderizar una página de PDF a PNG o JPG
Renderiza una página a un data URL PNG o JPG, con escala configurable. Solo navegador (usa canvas).
import * as pdfjsLib from "pdfjs-dist";
import workerUrl from "pdfjs-dist/build/pdf.worker.min.mjs?url";
pdfjsLib.GlobalWorkerOptions.workerSrc = workerUrl;
// pageNumber is 1-based; scale controls the resolution (2 is roughly high quality).
export async function renderPdfPageToImage(
file: File,
pageNumber: number,
scale = 2,
format: "png" | "jpeg" = "png",
quality = 0.92,
): Promise<string> {
const data = new Uint8Array(await file.arrayBuffer());
const pdf = await pdfjsLib.getDocument({ data }).promise;
const page = await pdf.getPage(pageNumber);
const viewport = page.getViewport({ scale });
const canvas = document.createElement("canvas");
const context = canvas.getContext("2d");
if (!context) {
throw new Error("Couldn't get the canvas 2D context.");
}
canvas.width = Math.ceil(viewport.width);
canvas.height = Math.ceil(viewport.height);
await page.render({ canvas, canvasContext: context, viewport }).promise;
await pdf.destroy();
return canvas.toDataURL(format === "jpeg" ? "image/jpeg" : "image/png", format === "jpeg" ? quality : undefined);
}pdfjs-distNotas de uso
- La config de worker de arriba es para Vite (import con ?url).
- Alternativa con bundler genérico (sin Vite): GlobalWorkerOptions.workerPort = new Worker(new URL('pdfjs-dist/build/pdf.worker.min.mjs', import.meta.url), { type: 'module' }).
- Alternativa CDN: GlobalWorkerOptions.workerSrc = 'https://cdnjs.cloudflare.com/ajax/libs/pdf.js/<VERSION>/pdf.worker.min.mjs'.
- Para varias páginas, iterá de 1 a pdf.numPages.
Limitaciones
- Solo navegador: depende de document.createElement('canvas'); no corre en Node sin polyfills.
- Un scale alto sube la resolución y el costo: con páginas grandes puede consumir mucha memoria.
- El empaquetado multipágina en ZIP (con jszip) queda como extensión fuera de este snippet.
- La versión del worker debe coincidir con la versión de pdfjs-dist instalada.