Silent Print an Embedded PDF

Silent print an embedded PDF

You are not going to be able to print silently with plain old JavaScript. How would you like your printer to start printing out 100000000 pages of all black. Not a good thing. If you want to print silently and have it work for Internet Explorer only, there are ActiveX controls out there that can do it. This requires higher security settings for your page and for your users to really trust your site.

Print PDF directly from JavaScript

Based on comments below, it no longer works in modern browsers
This question demonstrates an approach that might be helpful to you: Silent print an embedded PDF

It uses the <embed> tag to embed the PDF in the document:

<embed
type="application/pdf"
src="path_to_pdf_document.pdf"
id="pdfDocument"
width="100%"
height="100%" />

Then you call the .print() method on the element in Javascript when the PDF is loaded:

function printDocument(documentId) {
var doc = document.getElementById(documentId);

//Wait until PDF is ready to print
if (typeof doc.print === 'undefined') {
setTimeout(function(){printDocument(documentId);}, 1000);
} else {
doc.print();
}
}

You could place the embed in a hidden iframe and print it from there, giving you a seamless experience.

Print embedded PDF from browser with Javascript, HTML5, AngularJS

Also answered here: Print Pdf from javascript embed tag

I'm going to post what I learned here after a lot of research for anyone in the future who might find this.

PDF's are displayed differently based on browser, browser version, browser configuration, and Operating System. There are a lot of variables so I'll talk about the most common situations here.

  • On all browsers I was unable to call any sort of print() method through Javascript, I was only able to use PdfActions. The OPENACTION would call print. I embedded these into the PDF using iText.

  • Chrome uses Adobe's viewer, which doesn't give access to any sort of print() method but does execute PdfActions embedded in the PDF. So you can embed an 'OpenAction' in a PDF and have the PDF call print whenever it's opened from any application that looks at those actions.

  • Firefox (above a certain version, all recent versions though) uses the Adobe viewer in Windows, which also recognizes PdfActions. However, in OSX it loses support for the Adobe viewer and switches to the baked in Firefox viewer (pdf.js). Which does not support PdfActions.

  • IE: I didn't really test much on IE. Mostly because I gave up on printing PDF's from Javascript after Firefox didn't work on OSX (a req. for me).

My PDF's were being generated by a server that I control so I ended up making service changes in my server and adding a get PNG service that generated a PNG based on the same markup that the PDF generation uses. Browsers handle images much better than PDFs, which I knew going in, but hoped that I would just be able to re-use the PDF generation service since it's used elsewhere in my code.

It doesn't answer the question, but it's all the information I have. My suggestion to anyone who might find this in the future: ditch PDF if possible in this case and go simpler. Otherwise, please update this question if you know how to call print() through Javascript in FF preview pdf viewer in OSX.

-Phil

Chrome extensions for silent print?

Finally I reached an acceptable solution for this problem, as I couldn't find it out there, but read to many post with the same issue I will leave my solution here.

So first you need to add your printer to the Google Cloud Print and then you will need to add a proyect to the Google Developers Console

Then add this script and any time you need to print something execute the print() function. This method will print the document indicated in the content

The application will ask for your permission once to manage your printers.

function auth() {  gapi.auth.authorize({    'client_id': 'YOUR_GOOGLE_API_CLIENT_ID',    'scope': 'https://www.googleapis.com/auth/cloudprint',    'immediate': true  });
}
function print() { var xhr = new XMLHttpRequest(); var q = new FormData() q.append('xsrf', gapi.auth.getToken().access_token); q.append('printerid', 'YOUR_GOOGLE_CLOUD_PRINTER_ID'); q.append('jobid', ''); q.append('title', 'silentPrintTest'); q.append('contentType', 'url'); q.append('content',"http://www.pdf995.com/samples/pdf.pdf"); q.append('ticket', '{ "version": "1.0", "print": {}}');

xhr.open('POST', 'https://www.google.com/cloudprint/submit'); xhr.setRequestHeader('Authorization', 'Bearer ' + gapi.auth.getToken().access_token); xhr.onload = function () { try { var r = JSON.parse(xhr.responseText); console.log(r.message) } catch (e) { console.log(xhr.responseText) } }
xhr.send(q)
}
window.addEventListener('load', auth);
<script src="https://apis.google.com/js/client.js"></script>

Print a pdf without visually opening it

UPDATE: This link details an elegant solution that involves editing the page properties for the first page and adding an action on Page Open. Works across all browsers (as browsers will execute the JavaScript placed in the actions section). Requires Adobe Acrobat Pro.


It seems 2016 brings no new advancements to the printing problem. Had a similar issue and to make the printing cross-browser I solved it using PDF.JS but had to make a one-liner addition to the source (they ask you to build upon it in anyways).

The idea:

  • Download the pre-built stable release from https://mozilla.github.io/pdf.js/getting_started/#download and add the "build" and "web" folders to the project.
  • The viewer.html file is what renders out PDFs with a rich interface and contains print functionality. I added a link in that file to my own JavaScript that simply triggers window.print() after a delay.

The link added to viewer:

    <script src="viewer.js"></script>
<!-- this autoPrint.js was added below viewer.js -->
<script src="autoPrint.js"></script>
</head>

The autoPrint.js javascript:

(function () {
function printWhenReady() {
if (PDFViewerApplication.initialized) {
window.print();
}
else {
window.setTimeout(printWhenReady, 3000);
}
};

printWhenReady();
})();
  • I could then put calls to viewer.html?file= in the src of an iframe and hide it. Had to use visibility, not display styles because of Firefox:

    <iframe src="web/viewer.html?file=abcde.pdf" style="visibility: hidden">

The result: the print dialog showed after a short delay with the PDF being hidden from the user.

Tested in Chrome, IE, Firefox.

CefGlue silent printing to PDF

You'd need to merge this patch and recompile cef from source; Besides, you might have to add some glue logic to CefGlue. I tested the patch myself (on C++ API) and it worked fine.

EDITED: the patch will be merged in trunk.

If you only need to print some pages (specially if these pages are under your control), you will do just fine. However if you need (as I did at the time) to print almost anything, you'll probably face the fact that some web pages don't render anything useful to the print view. Also, even those well-behaved diverge significantly from what you see on the screen - and that's not a CEF behavior, as even google chrome showed the same issues. In my application this was a no-go so I dropped printing and started capturing the screen (and implemented saving that to a pdf using a pdf library in C++), but perhaps your application isn't as demanding as mine was. Cheers!



Related Topics



Leave a reply



Submit