Reputation: 659
I have googled enough for a whole one day, and searched StackOverflow to find a solution for changing the font in pdf exports of dataTables. However, I didn't run into a solution. When I export the table into pdf script fonts are something undecipherable. Just look at the picture below. It shows two columns from my table.
Both dataTables forum and pdfMaker documentations are vague. Can anyone please help me out of the problem. I need to specify a font for pdfMaker extension of datatables. The following is what vfs_fonts.js looks like:
this.pdfMake = this.pdfMake || {}; this.pdfMake.vfs = {
pdfMake.fonts = {
Vazir: {
normal: 'Vazir-FD.ttf',
bold: 'Vazir-FD.ttf',
italics: 'Vazir-FD.ttf',
bolditalics: 'Vazir-FD.ttf'
}
};
}
The following is also my buttons block of my datatables:
buttons: [
{ extend: 'pdfHtml5', exportOptions:
{ columns: [0, 1, 2, 3, 4, 5, 6] },
customize: function (doc) {
doc.defaultStyle.font = Vazir},
},
]
Note that in the above block of code, when I add 'customize' block, the pdfMaker button won't prepare any pdf reports; without it, it works, however, the fonts are undecipherable. Thanks in advance.
Upvotes: 5
Views: 4839
Reputation: 21918
Here is a solution.
The HTML is as follows:
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Export to PDF</title>
<script src="https://code.jquery.com/jquery-3.3.1.min.js"></script>
<script src="https://cdn.datatables.net/1.10.20/js/jquery.dataTables.min.js"></script>
<link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/1.10.20/css/jquery.dataTables.min.css">
<link rel="stylesheet" type="text/css" href="https://datatables.net/media/css/site-examples.css">
<!-- buttons -->
<link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/buttons/1.6.1/css/buttons.dataTables.min.css">
<script src="https://code.jquery.com/jquery-3.3.1.js"></script>
<script src="https://cdn.datatables.net/1.10.20/js/jquery.dataTables.min.js"></script>
<script src="https://cdn.datatables.net/buttons/1.6.1/js/dataTables.buttons.min.js"></script>
<script src="https://cdn.datatables.net/buttons/1.6.1/js/buttons.flash.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jszip/3.1.3/jszip.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/pdfmake/0.1.53/pdfmake.min.js"></script>
<!--
<script src="https://cdnjs.cloudflare.com/ajax/libs/pdfmake/0.1.53/vfs_fonts.js"></script>
Build a custom local version of the vfs_fonts.js file, containing whatever fonts you need. The
structure of the file is this:
this.pdfMake = this.pdfMake || {}; this.pdfMake.vfs = {
"arial.ttf": "AAEAA...MYXRu",
"another_one.ttf": "XXXX...XXXX"
};
Replace the "AAEAA...MYXRu" with the base64-encoded string of your font file.
You can use this site to generate the string: https://dataurl.sveinbjorn.org/#dataurlmaker
-->
<script src="vfs_fonts.js"></script>
<script src="https://cdn.datatables.net/buttons/1.6.1/js/buttons.html5.min.js"></script>
<script src="https://cdn.datatables.net/buttons/1.6.1/js/buttons.print.min.js"></script>
</head>
<body>
<div style="margin: 20px;">
<table id="example" class="display nowrap dataTable cell-border" style="width:100%">
<thead>
<tr>
<th>Name</th>
<th>Data</th>
</tr>
</thead>
<tbody>
<tr>
<td>Adélaïde Nixon</td>
<td><font face="verdana">الفبای فارسی ۱۲۳۴</font></td>
</tr>
</tbody>
<tfoot>
<tr>
<th>Name</th>
<th>Data</th>
</tr>
</tfoot>
</table>
</div>
<script type="text/javascript">
$(document).ready(function() {
$('#example').DataTable({
dom: 'Bfrtip',
buttons: [{
extend: 'pdf',
customize: function ( doc ) {
processDoc(doc);
}
}]
});
});
function processDoc(doc) {
//
// https://pdfmake.github.io/docs/fonts/custom-fonts-client-side/
//
// Update pdfmake's global font list, using the fonts available in
// the customized vfs_fonts.js file (do NOT remove the Roboto default):
pdfMake.fonts = {
Roboto: {
normal: 'Roboto-Regular.ttf',
bold: 'Roboto-Medium.ttf',
italics: 'Roboto-Italic.ttf',
bolditalics: 'Roboto-MediumItalic.ttf'
},
arial: {
normal: 'arial.ttf',
bold: 'arial.ttf',
italics: 'arial.ttf',
bolditalics: 'arial.ttf'
}
};
// modify the PDF to use a different default font:
doc.defaultStyle.font = "arial";
var i = 1;
}
</script>
</body>
The above HTML produces the following web page:
When you click on the "Save as PDF" button, the PDF document looks like this:
As explained here, pdfMake uses the Roboto font by default. This font does not support Persian characters/script. To work around this, I changed the default font to Arial, which does provide support for Persian characters/script.
Please see the additional notes at the end regarding the use of Arial - another font may be more appropriate to avoid licensing issues.
To make this change I took the following steps:
I generated a new vfs_fonts.js
file, containing the contents of an arial TTF file. I also refer to this new local vfs_fonts.js
file, instead of the Cloudflare version.
The vfs_fonts.js
file has the following structure:
this.pdfMake = this.pdfMake || {}; this.pdfMake.vfs = {
"arial.ttf": "AAEAA...MYXRu",
"another_one.ttf": "XXXX...XXXX"
};
Each of the "AAEAA...MYXRu
strings is the base64-encoded representation of the related font file.
To generate the string for your TTF file, you can use the utilities provided by pdfmake (see below), or you can use any base64 encoder. One example is dataurlmaker.
Paste the (very long) string generated by dataurlmaker into your vfs_fonts.js
file. Do NOT include any preamble provided by dataurlmaker ("data:application/octet-stream;base64,"). Include only the base64 string itself.
Alternatively...
Using the tools provided by pdfmake:
To generate this new vfs_fonts.js
file, I followed the relevant instructions on this page.
(a) I already had npm installed.
(b) I ran npm install pdfmake
(c) I changed to the pdfmake installation directory:
C:\Users\<myUserID>\node_modules\pdfmake\
(d) I created the examples/fonts
subdirectory in my pdfMake
directory.
(e) I copied my Windows arial.ttf
file into this new fonts
directory.
(f) I ran npm install
(from the pdfMake directory) to ensure all prerequisites modules were installed.
(g) I installed gulp using npm install gulp --global
(h) I ran gulp buildFonts
to create a new build/vfs_fonts.js
.
(i) I included this new build/vfs_fonts.js
file in my web page code (as shown above).
After taking these steps, I was able to generate a PDF using the Arial font.
Update
Please read the comments provided by @anotherfred for some important notes:
Regarding the specific use of Arial (emphasis is mine):
Note that Arial's licence may forbid this. Fonts like Noto Sans are free international fonts but you have to carefully choose the version to get the languages you want.
You can use online tools such as Google Fonts and Font Squirrel to find fonts which match your language & character/glyph requirements.
Regarding how to reference your chosen font file(s):
Also, to avoid having to set the default font in datatables options, you can just name your key in
pdfMake.fonts
Roboto (whatever ttf files you actually use in it) and it will be used automatically.
It would be great if the following could be usd out-of-the-box in a future version of DataTables (with an upgraded version of pdfmake)
You can also use a font url instead of vfs_fonts, but this requires a newer version of pdfMake than datatables suggest.
Upvotes: 8