Wednesday, June 17, 2020

AngularJS exporting to PDF utilising pdfmake.js library.

The pdfmake.js library can be installed using bower cd to your angular directory and run this code to get the latest version of pdfmake.js.

bower install pdfmake

This can also be downloaded from github here. Now include the library into your angularJS index.html file.

<!doctype html>
<html lang='en'>
<head>
<meta charset='utf-8'>
<title>AngularJS export to pdf example.</title>
<script src='pdfmake/build/pdfmake.min.js'></script>
<script src='pdfmake/build/vfs_fonts.js'></script>
</head>
<body>

Next create a link in a view to call a $scope function.

<a href=”#” ng-click=”downloadPDF()”></a>

Now create a $scope method $scope.downloadPDF within a controller which is executed by our view. This method will contain the guts of our export logic.

$scope.downloadPDF = function() {
});

Lets create a header and footer for our PDF. Within our $scope.downloadPDF method

var docDefinition = {
header: function() {
return [
{
style: 'table',
margin: [62,35,62,35],
table: {
widths: ['*', '*'],
headerRows: 0,
body: [
[
{text: 'Booking Summary', style: 'topHeader', alignment: 'left'},
{
'base64-image-string-goes-here',
width: 150,
alignment: 'right'
}
]
]
},
layout: 'noBorders'
}
]
},
footer: function(currentPage, pageCount) {
return [
{text: currentPage.toString() + ' of ' + pageCount, alignment: 'center', style: 'footer'}
]
},
content: [],
pageSize: 'A4',
pageMargins: [62,80,62,80],
styles: {
topHeader: {
fontSize: 20,
bold: true,
margin: [0, 6, 0, 30],
alignment: 'left'
},
table: {
fontSize: 8,
alignment: 'left',
color: 'black',
margin: [0, 5, 0, 15]
},
header: {
fontSize: 16,
bold: true,
margin: [0, 10, 0, 15],
alignment: 'left'
},
footer: {
fontSize: 8,
margin: [0, 25, 0, 17],
alignment: 'center'
}
}
};
pdfMake.createPdf(docDefinition).download();
};

The docDefinition object is how we describe our PDF for pdfmake.js to render. The header consists of a table with two columns. The column widths are auto sized using the asterisk symbol. By appending another width to this list we are instructing pdfmake.js to size our new column.

widths: ['*', '*']

The content which is defined as a table can be found within the body array. The left table column contains the text ‘Title’, its linked to the style reference ‘topHeader’. The right table column embeds a base64 image string into the object. We generate the base64 string via this online tool then copy and paste the generated base64 string ‘base64-image-string-goes-here’ into our object. We want this table to have no borders otherwise pdfmake.js would draw a black border for our cells and table. The footer function draws the current page against the total number of pages at the bottom of the PDF. Notice we attach styling for the footer using the ‘footer’ selector within the styles object. More about creating styles can be found here.

content: [
{
style: 'topTable',
table: {
widths: ['*','*', '*', '*'],
heights: [18],
headerRows: 1,
body: [
[
{text: $scope.title+' '+$scope.firstName+' '+$scope.surname,
style: 'tableHeader', colSpan: 4}, {}, {}, {}
],
[
{text: 'Type:', style: 'tableLabel'}, {text: 'Flight'},
{text: 'Verified:', style: 'tableLabel'}, {text: 'Yes'}
],
[
{text: 'Status ID:', style: 'tableLabel'}, {text: $scope.statusid},
{text: 'Supplier ID:', style: 'tableLabel'}, {text: $scope.supplierid}
],
[
{text: 'Session ID:', style: 'tableLabel'}, {text: $scope..sessionid},
{text: 'Booking ID:', style: 'tableLabel'}, {text: $scope.bookingid}
],
[
{text: 'Departing:', style: 'tableLabel'}, {text: $scope.date },
{text: 'Passengers:', style: 'tableLabel'}, {text: $scope.passengers'}
]
]
},
layout: {
paddingLeft: function(i, node) { return 8; },
paddingRight: function(i, node) { return 8; },
paddingTop: function(i, node) { return 6; },
paddingBottom: function(i, node) { return 6; },
fillColor: function (i, node) {
return (i % 2 === 0) ? '#F5F5F5' : null;
}
}
}
]

Above in our content object we instruct pdfmake.js to draw a table consisting of four columns. The column widths are set to auto defined by the asterisks symbol. We want to display the table header as one row so a colspan of 4 is set. This table will be bordered by default so we just need to attach some padding for each of the table cells. We also want to create a zebra effect for each of the table rows which is defined in our fillColor function.

Incorporating font-awesome into the PDF.

First we need to convert our font-awesome font file into a base64 encoded string by using this tool. Navigate to bower_components/pdfmake/build/vjs_fonts.js, paste the encoded font-awesome.ttf base64 string into the vjs_fonts.js file. I have removed the strings from this code snippet because they are pretty large as you will find out!

this.pdfMake = this.pdfMake || {};this.pdfMake.vfs = {
"Roboto-Italic.ttf": "paste-roboto-base64-string-here",
"Roboto-Medium.ttf": "paste-roboto-base64-string-here",
"Roboto-MediumItalic.ttf": "paste-roboto-base64-string-here",
"Roboto-Regular.ttf": "paste-roboto-base64-string-here",
"FontAwesome.ttf": "paste-font-awesome-base64-string-here"
};
this.pdfMake.fonts = {
Roboto: {
italics : 'Roboto-Italic.ttf',
normal : 'Roboto-Regular.ttf',
bold : 'Roboto-Medium.ttf',
mediumitalics : 'Roboto-MediumItalic.ttf'
},
FontAwesome: {
normal : 'FontAwesome.ttf',
bold : 'FontAwesome.ttf',
italics : 'FontAwesome.ttf',
bolditalics: 'FontAwesome.ttf'
}
};

No comments:

Post a Comment

Free hosting web sites and features -2024

  Interesting  summary about hosting and their offers. I still host my web site https://talash.azurewebsites.net with zero cost on Azure as ...