1

I have the below HTML:

<template>
    <lightning-button onclick={generateData} label="Generate PDF"></lightning-button>

<iframe id="pdfFrame" src="/resource/pdfjs/web/viewer.html" width="100%" height="100%" class="pdfFrame"
    onload={generateData}></iframe>
</template>

JS:

import { LightningElement } from 'lwc';
import { loadScript } from "lightning/platformResourceLoader";
import JSPDF from '@salesforce/resourceUrl/jspdf';
import getContacts from '@salesforce/apex/PdfGenerator.getContactsController';

export default class JspdfDemo extends LightningElement {
    contactList = [];
    headers = this.createHeaders([
        "Id",
        "FirstName",
        "LastName"
    ]);

    renderedCallback() {
        Promise.all([
            loadScript(this, JSPDF)
        ]);
    }

    generatePdf() {
        const { jsPDF } = window.jspdf;
        const doc = new jsPDF({
            encryption: {
                userPassword: "user",
                ownerPassword: "owner",
                userPermissions: ["print", "modify", "copy", "annot-forms"]
                // try changing the user permissions granted
            }
        });

        doc.text("Hi I'm Matt", 20, 20);
        doc.table(30, 30, this.contactList, this.headers, { autosize: true });
        doc.save("demo.pdf");
    }

    generateData() {
        getContacts().then(result => {
            this.contactList = result;
            this.generatePdf();
        });
    }

    createHeaders(keys) {
        var result = [];
        for (var i = 0; i < keys.length; i += 1) {
            result.push({
                id: keys[i],
                name: keys[i],
                prompt: keys[i],
                width: 65,
                align: "center",
                padding: 0
            });
        }
        return result;
    }
}

This is the JS PDF librarythat I am using as a static resource:

After clicking the button it successfully downloads the PDF file.

But instead of downloading the file, I need to display the PDF file using iframe on salesforce I created iFrame tag in the HTML and tried below JS

this.template.querySelector('iframe').contentWindow.postMessage(this.pdfData, window.location.origin);

I tried passing blob or base64 as below

this.pdfData = doc.output('blob);

or

this.pdfData = new Blob([doc.output('blob')], { type: 'application/pdf' });

or

this.pdfData = doc.output('datauristring');

But the above did not work as expected, and also the generate PDF button doesn't work on salesforce 1 mobile app, can someone please suggest how to display the PDF on salesforce on both mobile and desktop view instead of downloading it. The other solution I am thinking of is saving this PDF to a content document and then use the content document to display the PDF file, but it would be a lot better if the iframe solution works so that we can eliminate server-side call.

Update:

I am not able to save the file to the content document also I have created another thread for that Saving PDF file to content document saves as black pages

screenshot of the page:

enter image description here

7
  • Can you check with this similar implementation? May 4 '21 at 8:50
  • Thank you for your comment, this is about showing the PDF file from the content document on the browser but in my case, I have to generate the file and then display it on the iframe.
    – gs650x
    May 4 '21 at 8:52
  • In that case this post could provide more insight on showing the pdf in same tab or opening in a new tab. For iframe,I still suspect whether it would be possible or not. May 4 '21 at 9:48
  • Thank you so much for your kind help here but none of the solutions suggested in the above forum worked so I am going with the content document approach, could you please take a look into this salesforce.stackexchange.com/questions/342163/… thread where it is not saving the file properly.
    – gs650x
    May 4 '21 at 11:01
  • @gs650x I am currently working on showing pdf in lwc but in my case I am getting base64data for pdf file and I M showing it in iFrame using pdfjs library. I am on phone but I will link my question and answer in sometime. I had hard time only with postMessage as lwc wasnt able to find the iframe. May 4 '21 at 12:38
1

Update your postMessage in iframe to below,

this.template.querySelector('iframe').contentWindow.postMessage(this.pdfData, window.location.origin);

for me Origin fixed the issue in iframe.

9
  • thank you for your answer, but unfortunately, this is not working.
    – gs650x
    May 4 '21 at 13:18
  • is your pdfjs loading a pdf viewer? that would be a big one as atleast the pdf viewer should be able to load if the library has been imported correctly. May 4 '21 at 13:20
  • yes it is loading, adding a screenshot to the question.
    – gs650x
    May 4 '21 at 13:22
  • did you try to console pdfData, is it correct base64 format string? May 4 '21 at 13:24
  • can you see if that same base64 you are generating is able to generate PDF here May 4 '21 at 13:25

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.