Rendering multiple pages of pdf to single Canvas using pdf.js and ImageData

DareDev picture DareDev · Nov 6, 2013 · Viewed 8.9k times · Source

I am trying to render pdf onto the single canvas, I referred to the below link to implement the same.

Visit: Render .pdf to single Canvas using pdf.js and ImageData

var pdf = null;

    PDFJS.disableWorker = true;
    var pages = new Array();
   var canvas = document.getElementById('the-canvas');
    var context = canvas.getContext('2d');
    var scale = 1.5;
    var canvasWidth = 0;
    var canvasHeight = 0;
    var pageStarts = new Array();
    pageStarts[0] = 0;


    PDFJS.getDocument(url).then(function getPdfHelloWorld(_pdf) {
        debugger;
        pdf = _pdf;
        //Render all the pages on a single canvas
        for (var pNum = 1; pNum <= pdf.numPages; pNum++) {
            pdf.getPage(pNum).then(function getPage(page) {
                var viewport = page.getViewport(scale);
                canvas.width = viewport.width;
                canvas.height = viewport.height;
                page.render({ canvasContext: context, viewport: viewport });
                pages[pNum - 1] = context.getImageData(0, 0, canvas.width, canvas.height);
                canvasHeight += canvas.height;
                pageStarts[i] = pageStarts[i - 1] + canvas.height;


            });
        }

        canvas.width = canvasWidth;
        canvas.height = canvasHeight;

        for (var i = 0; i < pages.length; i++) {
            context.putImageData(pages[i], 0, pageStarts[i]);
        }
    });

I see space is created to render the page where as pdf is not displayed.

any help would greatly appreceated. Thanks.

Answer

Chris Porter picture Chris Porter · Jan 22, 2014

Your code to store the pageStarts references "i" as if it was an iterator index, but it is in a for statement using pNum. I'm surprised that this code doesn't throw errors in the console pointing you to the possible solution. You should change:

canvasHeight += canvas.height;
pageStarts[i] = pageStarts[i - 1] + canvas.height;

to something like:

pageStarts[pNum - 1] = canvasHeight;
canvasHeight += canvas.height;

Notice that I reorganized the canvasHeight calculation until after you've grabbed the "last" value. This will allow you to determine the correct starting height for the current page image data without having to use the pageStart for the previous iteration.

This is an untested solution since you didn't post the rest of the code, but it should lead you towards your solution.