Tags: __exception, api, document, essentials, exception, following, java, pdf, print, printing
Printing a PDF document using Java 1.4 Printing API
On Java Studio » Java Essentials
10,807 words with 15 Comments; publish: Mon, 04 Feb 2008 23:08:00 GMT; (15078.13, « »)
Hi,
When I tried to print a PDF document using JAVA 1.4 Printing API, I got the following exception.
__
Exception in thread "main" sun.print.PrintJobFlavorException: invalid flavor
at sun.print.Win32PrintJob.print(Win32PrintJob.java:290)
at Printing.main(Printing.java:40)
__
I am able to print the same PDF document using Acrobat reader.
Is PDF format not supported in JAVA 1.4 printing API? or is something wrong in my code?
here is the sample JAVA program that I was using
import javax.print.*;
import javax.print.attribute.*;
import java.io.*;
public class Printing {
public static void main(String args[]) throws Exception {
String filename = args[0];
PrintRequestAttributeSet pras =
new HashPrintRequestAttributeSet();
DocFlavor flavor = DocFlavor.INPUT_STREAM.PDF;
PrintService defaultService =
PrintServiceLookup.lookupDefaultPrintService();
DocPrintJob job = defaultService.createPrintJob();
FileInputStream fis = new FileInputStream(filename);
DocAttributeSet das = new HashDocAttributeSet();
Doc doc = new SimpleDoc(fis, flavor, das);
job.print(doc, pras);
Thread.sleep(10000);
System.exit(0);
}
}
Thank you
Sumana
http://javaessentials.developerfaqs.com/q_java-essentials_56211.html
All Comments
Leave a comment...
- 15 Comments

I was able to recreate your problem, getting the same error message. I was trying to print a plain text file. However, you can try this. It worked for me.
Change DocFlavor.INPUT_STREAM.PDF to
DocFlavor.INPUT_STREAM.AUTOSENSE
On the same subject, for all the other readers, is there a way to bring up the print dialog to choose from all suitable printers using the Print Service? I don't know if this works the same as in the Printable Interface.
#1; Thu, 05 Jul 2007 21:23:00 GMT

I tried a quick test of your solution with JBuilder8, java version 1.4.1-b21, Windows NT4 svc pack 6a, HP IIIP printer.
It did avoid the error and send something to the printer, but it was hash.
Would you describe some more about your setup where you were able to print a PDF? Is there a JDK update needed? Or perhaps a more modern printer/driver?
-Thanks
#2; Thu, 05 Jul 2007 21:23:00 GMT

> I was able to recreate your problem, getting the same
> error message. I was trying to print a plain text
> file. However, you can try this. It worked for me.
>
> Change DocFlavor.INPUT_STREAM.PDF to
> DocFlavor.INPUT_STREAM.AUTOSENSE
>
> On the same subject, for all the other readers, is
> there a way to bring up the print dialog to choose
> from all suitable printers using the Print Service? I
> don't know if this works the same as in the Printable
> Interface.
It printed with AUTOSENSE ... but not the PDF document just the PDF file bytes ("%PDF-1.2 ..."), so several dozen sheets wasted ... ;-)
any other hint?
#3; Thu, 05 Jul 2007 21:23:00 GMT

This is one of Sun's nasty little "gotchas" in java. While they included a PDF flavor in javax.print, there's still no PDF renderer, so printing PDF is not yet supported. When will it be? Oh, probably about the same time the promised update to the Windows version of javax.comm comes out...
If you are lucky enough to be running on *nix with a recent implementation of GhostScript, you can use the POSTSCRIPT or AUTOSENSE flavor, since gs will directly print PDF.
Under Windoze, if you are printing to a newer PostScript3 printer, you can do the same. However, most printers under Windoze will just print garbage.
The usual solution for Windoze is to exec Adobe Reader with command line arguments.
#4; Thu, 05 Jul 2007 21:23:00 GMT

- So, is there a PDF renderer for the Windows J2SE available? (There has to be, otherwise Sun can't claim to support/offer a PDF flavor.) #5; Thu, 05 Jul 2007 21:23:00 GMT

- Read the last paragraph:http://www-106.ibm.com/developerworks/java/library/j-mer0322/% #6; Thu, 05 Jul 2007 21:23:00 GMT

> So, is there a PDF renderer for the Windows J2SE
> available? (There has to be, otherwise Sun can't claim
> to support/offer a PDF flavor.)
Nope, sorry.
Here's an alternative approach to printing PDF (an other) files on Windoze:
http://forum.planetpdf.com/wb/default.asp?action=9&read=37301&fid=3#98958
#7; Thu, 05 Jul 2007 21:23:00 GMT

Here's a pure Java solution (that works!):
http://www.mycgiserver.com/~zhouwu/pdf/readme.html
The caveats are:
- prints only to the default printer
- requires a properties file located in the home directory
my workaround for the last:
/**
* Print a PDF file to the default printer (might consume lots of memory!).
*
* <b>Required:</b>
* <ul>
* <li>a file "acrobat.properties" needs to be in the working directory. The content is:
<table align="center" bgcolor="#E0E0E0" border=1 cellpadding="10" cellspacing="0"><tr><td><pre style="margin-top:0; margin-bottom:0">
#com.adobe.acrobat.Viewer Properties
#Wed Oct 29 20:34:05 PST 2003
com.adobe.acrobat.AcceptedLicAgreement=true
com.adobe.acrobat.Fax_Fine_Mode=true
com.adobe.acrobat.Find\:FindAll=false
com.adobe.acrobat.Find\:FindBackwards=false
com.adobe.acrobat.Find\:FindWholeWord=false
com.adobe.acrobat.Find\:MatchCase=false
com.adobe.acrobat.Open_Dialog_Directory=C\:\\temp\\
com.adobe.acrobat.Open_Dialog_File=itext.pdf
com.adobe.acrobat.Print_Method_Known=true
com.adobe.acrobat.Shrink_To_Fit=false
com.adobe.acrobat.SitePreferencesURL=file\://localhost/C\:/pdf/acrobat-site.properties
com.adobe.acrobat.Use_Print_Server=false
com.adobe.acrobat.util.fontDirectories=C\:\\Winnt\\Fonts
com.adobe.acrobat.util.fontIgnoreExtensions=.fon;.pfm;.ini;.lst;.txt;.doc;.ttmap;.z;.enc;.dir;.afm;.f3b;.pfa;.spd;.ps;.bepf;.map;.alias;.scale;.all;.upr
</pre></td></tr></table>
* <li>The JAR files PDFPrinter.jar, acrobat.jar and MRJToolkitStubs.zip in the CLASSPATH.
* </ul>
*
* Note: the file "acrobat.properties" is expected to be in the user's home directory. As this is not always feasible,
* the system property "user.home" is mapped to "user.dir" for the time of execution.
*
* .javaessentials.developerfaqs.com.param fileName Name of PDF file to print.
* .javaessentials.developerfaqs.com.throws Exception on error.
* .javaessentials.developerfaqs.com.see <a href="/app/links/?link=http://www.mycgiserver.com/~zhouwu/pdf/readme.html">PDF Server (Silent) Printing</a>
*/
public void printPDF(String fileName) throws Exception {
String oldHome = System.getProperty("user.home");
System.setProperty("user.home", System.getProperty("user.dir"));
PDFPrinter vi = new PDFPrinter();
vi.activate();
vi.setDocumentInputStream(new FileInputStream(fileName));
vi.printAll();
System.setProperty("user.home", oldHome);
}//printPDF()
I just need the following additional files in my CLASSPATH: PDFPrinter.jar, acrobat.jar and MRJToolkitStubs.zip. Despite the note at the site above that "printing quality is not very good", i can't agree: the print quality is quite good. Not perfect, but acceptable for most uses.
(Tested on Windows 2000 SP4, J2SE 1.4.2_03, hp laserjet 2300dn)
#8; Thu, 05 Jul 2007 21:23:00 GMT

- > Here's a pure Java solution (that works!):> Since it relies on an outdated, unsupported Adobe library, it isn't likely that it will work on all PDF files. Have you tried printing the latest (1.5) version PDF files? #9; Thu, 05 Jul 2007 21:23:00 GMT

- Nope, but on several PDF files we use/generate here. And all worked well, so far. #10; Thu, 05 Jul 2007 21:23:00 GMT

But it seems the best solution so far (concerning output accuracy) is to first convert the PDF to PS (e.g. with pdftops.exe from the windows xpdf release) and then use the general java print api to print the PostScript file:
/**
* Print content of an input stream to the default system printer.
*
* .javaessentials.developerfaqs.com.param inputStream Input stream to print (e.g. new FileInputStream("Hello.ps")).
* .javaessentials.developerfaqs.com.throws PrintException on error.
*/
public void print(InputStream inputStream) throws PrintException {
PrintService printService = PrintServiceLookup.lookupDefaultPrintService();
Doc doc = new SimpleDoc(inputStream, DocFlavor.INPUT_STREAM.AUTOSENSE, null);
PrintRequestAttributeSet attributes = new HashPrintRequestAttributeSet();
attributes.add(MediaSizeName.ISO_A4);
attributes.add(new Copies(1));
print(printService, doc, attributes);
}//print()
#11; Thu, 05 Jul 2007 21:23:00 GMT

forgot the second method:
/**
* Print a document to a printer.
*
* .javaessentials.developerfaqs.com.param printService Printer to use.
* .javaessentials.developerfaqs.com.param doc Document to print.
* .javaessentials.developerfaqs.com.param attributes Print attributes.
* .javaessentials.developerfaqs.com.throws PrintException on error.
*/
public void print(PrintService printService, Doc doc, PrintRequestAttributeSet attributes) throws PrintException {
if (printService != null) {
DocPrintJob docPrintJob = printService.createPrintJob();
docPrintJob.print(doc, attributes);
}
}//print()
#12; Thu, 05 Jul 2007 21:23:00 GMT

- How to print a PDF document residing on iSeries using Java 1.4 Printing API?Does JDK 1.4 print services support PDF?thanks. #13; Thu, 05 Jul 2007 21:23:00 GMT

- Just wondering if you have found a solution to this problem. I'm trying to do the same thing but I get the problems that everyone else is posting. That is; invalid flavor for pdf flavor. #14; Thu, 05 Jul 2007 21:23:00 GMT

- I'm not sure what the answer is using the Java Print API but there is an open source api for manipulating PDF's through java called Itexthttp://www.lowagie.com/iText/This is working for me, check it out.Chris#15; Wed, 18 Jul 2007 11:27:00 GMT