Generate PDF from Javascript using jsPDF

We show lot of data in our web applications, it will be awesome if we quickly download specific part of PDF rather than printing it. It will be easy to share for different stakeholders and also for focussed meetings. In web application development, download to PDF means, we need to develop backend api specifically and then link it in frontend which takes longer development cylce. Instead it would be really great, if there is way to download what we see in the user interface quickly with few lines of Javascript, similar to export options in word processing application.
jsPDF is a library written in Javascript. It helps to convert frontend html content, image, charts or a tabular data to directly export to pdf. It also provides advanced support of adding watermark, embedding fonts, adding forms, encryption and password protection also. It is licensed under MIT. It has very good documentation.
Setup:
In this blog, we will see how jsPDF can be used with plain html, which will be webpacked to have the download option in the frontend page. Create a npm project by using npm init, then install jsPdf, html2canvas. Also supporting dependenceis like webpack, webpack-cli and html-webpack-plugin. In the JsPDF documentation, they have given ways for integrating jsPdf with Angular, Vue and React.
npm install jsPdf --save
npm install html2canvas
You can also load it via CDN
<script src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/2.5.0/jspdf.umd.min.js"></script>
Create PDF with text content
To load the jsPDF, use require jspdf and get the jsPDF class. Then create a instance of the object, will create a pdf object reference.
const { jsPDF } = require("jspdf");
const doc = new jsPDF();
Now we can write the text using text() method. Pass the text with x and y co-ordinates to write the text into the pdf object.
doc.text("jsPdf Tutorial - Sample PDF", 10, 10);
To save the PDF, pass the output file name as argument to save method.
doc.save("sampletutorial.pdf");
Creating the pdf from the client, we can hook it, on click of the button or on click of the URL.
<button id="downloadpdf">Download</button>
function downloadContent() {
const { jsPDF } = require("jspdf");
doc.text("jsPdf Tutorial - Sample PDF", 10, 10);
doc.save("sampletutorial.pdf");
}
Add a link to the PDF content
Now lets add a text with hyperlink in the pdf object. It can be done with textWithLink() method which takes the text, origin and the url. So when click on the text it will redirect to the URL. We can change the color of the text by changing the text color of the pdf object to blue, so it appears as a hyperlink text.
doc.setTextColor("0645AD");
doc.textWithLink("Hyper link text: FindBestOpenSource", 10, 25, {
url: "https://www.findbestopensource.com/",
});
HTML content to PDF
Generate the html content to PDF object can be done, by using html() method. Below is the HTML content element which has header, paragraph text and numbering list. It is done by html plugin which is seamlessly integrated with the jsPdf library, which works by just using the method.
<div id="content">
<h2>H2 Header</h2>
<p>It is a paragraph text</p>
<ul style="padding-left: 10px;"><span>Sample numbering list</span>
<li>First item</li>
<li>Second item</li>
<li>Third item</li>
</ul>
</div
Now get the HTML DOM element and provide it to html() method. This will convert all the html element in the same way how it renders in browser and adds as a content to PDF instance. In the callback function, pdf document object comes as arugment which has the html content converted in it. Now we just need to save the content to PDF.
let element = document.getElementById("content");
doc.html(element, {
margin: 30,
callback: function (doc) {
doc.save("sampletutorial.pdf");
}
});
Create Scatter Chart:
We can create the simple chart on the canvas element by plotting the context ellipse and fill with different x and y coordinates with plain javascript.
function createChart() {
const canvas = document.getElementById("myCanvas");
canvas.style.background = "floralwhite";
const ctx = canvas.getContext("2d");
canvas.height = canvas.width;
ctx.transform(1, 0, 0, -1, 0, canvas.height)
const xArray = [50,60,70,80,90,100,110,120,130,140,150];
const yArray = [7,8,8,9,9,9,10,11,14,14,15];
ctx.fillStyle = "red";
for (let i = 0; i < xArray.length-1; i++) {
let x = xArray[i]*400/150;
let y = yArray[i]*400/15;
ctx.beginPath();
ctx.ellipse(x, y, 3, 3, 0, 0, Math.PI * 2);
ctx.fill();
}
}
Now get the canvas element, then directly do the doc.addImage(canvas) but background will have dark background. To get the floral white background of the chart, it is better to use html2canvas method which will convert the exact chart element with the background into a canvas html element, which can be added as image to the pdf object with expected format and co-ordinates.
const canvas = document.getElementById("myCanvas");
const canvaselement = await html2canvas(canvas, {useCORS: true, allowTaint: true});
doc.addImage(canvaselement, 'png', 10, 130);
Insert Pages to the PDF:
Now if we want to put the content in a new page, it can be done using insertPage method with the page number.
doc.insertPage(2);
This example has been made as webpack project, it will generate the assets in dist folder with index.html. If we open, it looks like the below html page. This project is available in the github.
By clicking, download PDF, it downloads the PDF content with html content and chart objects.
References:
https://parall.ax/products/jspdf
https://github.com/parallax/jsPDF