Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Generating a pdf that preserves styling of the HTML page with jsPDF

I'm trying to create a button that will start the automatic download of a PDF of the page as it looks with the sass styling. However, everything I try ends up with the styling messed up.

Here is the page (this is a testing site with several different content types)

http://gobrandgotests.wpengine.com/preview-pdf/

But the PDF comes out looking like this:

enter image description here

I'm pulling jspdf.debug.js and have the following HTML button+script in my page:

<div id="bypass"> <!-- keeps button from showing in PDF -->
    <button id="pdf-new" style="margin: 50px;"><a href="javascript:demoFromHTML()" class="button" style="color: black;">Generate PDF</a></button>
</div>

<script>
    function demoFromHTML() {
        var pdf = new jsPDF('p', 'pt', 'letter');
        // source can be HTML-formatted string, or a reference
        // to an actual DOM element from which the text will be scraped.
        source = $('#content')[0];

        // we support special element handlers. Register them with jQuery-style 
        // ID selector for either ID or node name. ("#iAmID", "div", "span" etc.)
        // There is no support for any other type of selectors 
        // (class, of compound) at this time.
        specialElementHandlers = {
            // element with id of "bypass" - jQuery style selector
            '#bypass': function (element, renderer) {
                // true = "handled elsewhere, bypass text extraction"
                return true
            }
        };
        margins = {
            top: 80,
            bottom: 60,
            left: 40,
            width: 522
        };
        // all coords and widths are in jsPDF instance's declared units
        // 'inches' in this case
        pdf.fromHTML(
        source, // HTML string or DOM elem ref.
        margins.left, // x coord
        margins.top, { // y coord
            'width': margins.width, // max width of content on PDF
            'elementHandlers': specialElementHandlers
        },

        function (dispose) {
            // dispose: object with X, Y of the last line add to the PDF 
            //          this allow the insertion of new lines after html
            pdf.save('Test.pdf');
        }, margins);
    }
</script>

How can I make the styling stay consistent from the html to the pdf?

like image 937
Virge Assault Avatar asked Dec 01 '15 21:12

Virge Assault


People also ask

How do I export my HTML page as PDF using JavaScript?

Generate PDF using JavaScript The following example shows how to use the jsPDF library to generate PDF file using JavaScript. Specify the content in text() method of jsPDF object. Use the addPage() method to add new page to PDF. Use the save() method to generate and download PDF file.


1 Answers

I ended up getting this to work by using html2canvas along with jsPDF.

My button that hides itself from pdf with an html2canvas option:

<div data-html2canvas-ignore="true">
    <button id="pdf-new"><a href="javascript:demoFromHTML()" class="button" style="color: black;">Generate PDF</a></button>
</div>

And the script for the bottom of the html page

<script>
    function demoFromHTML() {
        var pdf = new jsPDF('p', 'pt', 'letter');
        var options = {
            background: '#fff' //background is transparent if you don't set it, which turns it black for some reason.
        };
        pdf.addHTML($('#content')[0], options, function () {
                pdf.save('Test.pdf');
        });
    }
</script>

Also in html2canvas.js I changed:

_html2canvas.Util.isTransparent = function(backgroundColor) {
  return (backgroundColor === "transparent" || backgroundColor === "rgba(0, 0, 0, 0)");
};

to this, in order to avoid that transparent-to-black background

_html2canvas.Util.isTransparent = function(backgroundColor) {
  return (backgroundColor === "transparent" || backgroundColor === "rgba(0, 0, 0, 0)" || backgroundColor === undefined);
};

Hope that helps someone!

like image 130
Virge Assault Avatar answered Nov 15 '22 10:11

Virge Assault