1258 lines
47 KiB
Java
1258 lines
47 KiB
Java
/*
|
|
* Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved.
|
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
|
*
|
|
* This code is free software; you can redistribute it and/or modify it
|
|
* under the terms of the GNU General Public License version 2 only, as
|
|
* published by the Free Software Foundation. Oracle designates this
|
|
* particular file as subject to the "Classpath" exception as provided
|
|
* by Oracle in the LICENSE file that accompanied this code.
|
|
*
|
|
* This code is distributed in the hope that it will be useful, but WITHOUT
|
|
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
|
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
|
* version 2 for more details (a copy is included in the LICENSE file that
|
|
* accompanied this code).
|
|
*
|
|
* You should have received a copy of the GNU General Public License version
|
|
* 2 along with this work; if not, write to the Free Software Foundation,
|
|
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
|
*
|
|
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
|
* or visit www.oracle.com if you need additional information or have any
|
|
* questions.
|
|
*/
|
|
|
|
package sun.print;
|
|
|
|
import java.awt.Dimension;
|
|
import java.awt.Frame;
|
|
import java.awt.Graphics;
|
|
import java.awt.Graphics2D;
|
|
import java.awt.PrintJob;
|
|
import java.awt.JobAttributes;
|
|
import java.awt.JobAttributes.*;
|
|
import java.awt.PageAttributes;
|
|
import java.awt.PageAttributes.*;
|
|
|
|
import java.awt.print.PageFormat;
|
|
import java.awt.print.Paper;
|
|
import java.awt.print.Printable;
|
|
import java.awt.print.PrinterException;
|
|
import java.awt.print.PrinterJob;
|
|
|
|
import java.io.File;
|
|
import java.io.FilePermission;
|
|
import java.io.IOException;
|
|
|
|
import java.net.URI;
|
|
import java.net.URISyntaxException;
|
|
|
|
import java.util.ArrayList;
|
|
import java.util.Properties;
|
|
|
|
import javax.print.PrintService;
|
|
import javax.print.attribute.HashPrintRequestAttributeSet;
|
|
import javax.print.attribute.PrintRequestAttributeSet;
|
|
import javax.print.attribute.ResolutionSyntax;
|
|
import javax.print.attribute.Size2DSyntax;
|
|
import javax.print.attribute.standard.Chromaticity;
|
|
import javax.print.attribute.standard.Copies;
|
|
import javax.print.attribute.standard.Destination;
|
|
import javax.print.attribute.standard.DialogTypeSelection;
|
|
import javax.print.attribute.standard.JobName;
|
|
import javax.print.attribute.standard.MediaSize;
|
|
import javax.print.attribute.standard.PrintQuality;
|
|
import javax.print.attribute.standard.PrinterResolution;
|
|
import javax.print.attribute.standard.SheetCollate;
|
|
import javax.print.attribute.standard.Sides;
|
|
import javax.print.attribute.standard.Media;
|
|
import javax.print.attribute.standard.OrientationRequested;
|
|
import javax.print.attribute.standard.MediaSizeName;
|
|
import javax.print.attribute.standard.PageRanges;
|
|
|
|
import sun.print.SunPageSelection;
|
|
import sun.print.SunMinMaxPage;
|
|
|
|
/**
|
|
* A class which initiates and executes a print job using
|
|
* the underlying PrinterJob graphics conversions.
|
|
*
|
|
* @see Toolkit#getPrintJob
|
|
*
|
|
*/
|
|
public class PrintJob2D extends PrintJob implements Printable, Runnable {
|
|
|
|
private static final MediaType SIZES[] = {
|
|
MediaType.ISO_4A0, MediaType.ISO_2A0, MediaType.ISO_A0,
|
|
MediaType.ISO_A1, MediaType.ISO_A2, MediaType.ISO_A3,
|
|
MediaType.ISO_A4, MediaType.ISO_A5, MediaType.ISO_A6,
|
|
MediaType.ISO_A7, MediaType.ISO_A8, MediaType.ISO_A9,
|
|
MediaType.ISO_A10, MediaType.ISO_B0, MediaType.ISO_B1,
|
|
MediaType.ISO_B2, MediaType.ISO_B3, MediaType.ISO_B4,
|
|
MediaType.ISO_B5, MediaType.ISO_B6, MediaType.ISO_B7,
|
|
MediaType.ISO_B8, MediaType.ISO_B9, MediaType.ISO_B10,
|
|
MediaType.JIS_B0, MediaType.JIS_B1, MediaType.JIS_B2,
|
|
MediaType.JIS_B3, MediaType.JIS_B4, MediaType.JIS_B5,
|
|
MediaType.JIS_B6, MediaType.JIS_B7, MediaType.JIS_B8,
|
|
MediaType.JIS_B9, MediaType.JIS_B10, MediaType.ISO_C0,
|
|
MediaType.ISO_C1, MediaType.ISO_C2, MediaType.ISO_C3,
|
|
MediaType.ISO_C4, MediaType.ISO_C5, MediaType.ISO_C6,
|
|
MediaType.ISO_C7, MediaType.ISO_C8, MediaType.ISO_C9,
|
|
MediaType.ISO_C10, MediaType.ISO_DESIGNATED_LONG,
|
|
MediaType.EXECUTIVE, MediaType.FOLIO, MediaType.INVOICE,
|
|
MediaType.LEDGER, MediaType.NA_LETTER, MediaType.NA_LEGAL,
|
|
MediaType.QUARTO, MediaType.A, MediaType.B,
|
|
MediaType.C, MediaType.D, MediaType.E,
|
|
MediaType.NA_10X15_ENVELOPE, MediaType.NA_10X14_ENVELOPE,
|
|
MediaType.NA_10X13_ENVELOPE, MediaType.NA_9X12_ENVELOPE,
|
|
MediaType.NA_9X11_ENVELOPE, MediaType.NA_7X9_ENVELOPE,
|
|
MediaType.NA_6X9_ENVELOPE, MediaType.NA_NUMBER_9_ENVELOPE,
|
|
MediaType.NA_NUMBER_10_ENVELOPE, MediaType.NA_NUMBER_11_ENVELOPE,
|
|
MediaType.NA_NUMBER_12_ENVELOPE, MediaType.NA_NUMBER_14_ENVELOPE,
|
|
MediaType.INVITE_ENVELOPE, MediaType.ITALY_ENVELOPE,
|
|
MediaType.MONARCH_ENVELOPE, MediaType.PERSONAL_ENVELOPE
|
|
};
|
|
|
|
/* This array maps the above array to the objects used by the
|
|
* javax.print APIs
|
|
*/
|
|
private static final MediaSizeName JAVAXSIZES[] = {
|
|
null, null, MediaSizeName.ISO_A0,
|
|
MediaSizeName.ISO_A1, MediaSizeName.ISO_A2, MediaSizeName.ISO_A3,
|
|
MediaSizeName.ISO_A4, MediaSizeName.ISO_A5, MediaSizeName.ISO_A6,
|
|
MediaSizeName.ISO_A7, MediaSizeName.ISO_A8, MediaSizeName.ISO_A9,
|
|
MediaSizeName.ISO_A10, MediaSizeName.ISO_B0, MediaSizeName.ISO_B1,
|
|
MediaSizeName.ISO_B2, MediaSizeName.ISO_B3, MediaSizeName.ISO_B4,
|
|
MediaSizeName.ISO_B5, MediaSizeName.ISO_B6, MediaSizeName.ISO_B7,
|
|
MediaSizeName.ISO_B8, MediaSizeName.ISO_B9, MediaSizeName.ISO_B10,
|
|
MediaSizeName.JIS_B0, MediaSizeName.JIS_B1, MediaSizeName.JIS_B2,
|
|
MediaSizeName.JIS_B3, MediaSizeName.JIS_B4, MediaSizeName.JIS_B5,
|
|
MediaSizeName.JIS_B6, MediaSizeName.JIS_B7, MediaSizeName.JIS_B8,
|
|
MediaSizeName.JIS_B9, MediaSizeName.JIS_B10, MediaSizeName.ISO_C0,
|
|
MediaSizeName.ISO_C1, MediaSizeName.ISO_C2, MediaSizeName.ISO_C3,
|
|
MediaSizeName.ISO_C4, MediaSizeName.ISO_C5, MediaSizeName.ISO_C6,
|
|
null, null, null, null,
|
|
MediaSizeName.ISO_DESIGNATED_LONG, MediaSizeName.EXECUTIVE,
|
|
MediaSizeName.FOLIO, MediaSizeName.INVOICE, MediaSizeName.LEDGER,
|
|
MediaSizeName.NA_LETTER, MediaSizeName.NA_LEGAL,
|
|
MediaSizeName.QUARTO, MediaSizeName.A, MediaSizeName.B,
|
|
MediaSizeName.C, MediaSizeName.D, MediaSizeName.E,
|
|
MediaSizeName.NA_10X15_ENVELOPE, MediaSizeName.NA_10X14_ENVELOPE,
|
|
MediaSizeName.NA_10X13_ENVELOPE, MediaSizeName.NA_9X12_ENVELOPE,
|
|
MediaSizeName.NA_9X11_ENVELOPE, MediaSizeName.NA_7X9_ENVELOPE,
|
|
MediaSizeName.NA_6X9_ENVELOPE,
|
|
MediaSizeName.NA_NUMBER_9_ENVELOPE,
|
|
MediaSizeName.NA_NUMBER_10_ENVELOPE,
|
|
MediaSizeName.NA_NUMBER_11_ENVELOPE,
|
|
MediaSizeName.NA_NUMBER_12_ENVELOPE,
|
|
MediaSizeName.NA_NUMBER_14_ENVELOPE,
|
|
null, MediaSizeName.ITALY_ENVELOPE,
|
|
MediaSizeName.MONARCH_ENVELOPE, MediaSizeName.PERSONAL_ENVELOPE,
|
|
};
|
|
|
|
|
|
// widths and lengths in PostScript points (1/72 in.)
|
|
private static final int WIDTHS[] = {
|
|
/*iso-4a0*/ 4768, /*iso-2a0*/ 3370, /*iso-a0*/ 2384, /*iso-a1*/ 1684,
|
|
/*iso-a2*/ 1191, /*iso-a3*/ 842, /*iso-a4*/ 595, /*iso-a5*/ 420,
|
|
/*iso-a6*/ 298, /*iso-a7*/ 210, /*iso-a8*/ 147, /*iso-a9*/ 105,
|
|
/*iso-a10*/ 74, /*iso-b0*/ 2835, /*iso-b1*/ 2004, /*iso-b2*/ 1417,
|
|
/*iso-b3*/ 1001, /*iso-b4*/ 709, /*iso-b5*/ 499, /*iso-b6*/ 354,
|
|
/*iso-b7*/ 249, /*iso-b8*/ 176, /*iso-b9*/ 125, /*iso-b10*/ 88,
|
|
/*jis-b0*/ 2920, /*jis-b1*/ 2064, /*jis-b2*/ 1460, /*jis-b3*/ 1032,
|
|
/*jis-b4*/ 729, /*jis-b5*/ 516, /*jis-b6*/ 363, /*jis-b7*/ 258,
|
|
/*jis-b8*/ 181, /*jis-b9*/ 128, /*jis-b10*/ 91, /*iso-c0*/ 2599,
|
|
/*iso-c1*/ 1837, /*iso-c2*/ 1298, /*iso-c3*/ 918, /*iso-c4*/ 649,
|
|
/*iso-c5*/ 459, /*iso-c6*/ 323, /*iso-c7*/ 230, /*iso-c8*/ 162,
|
|
/*iso-c9*/ 113, /*iso-c10*/ 79, /*iso-designated-long*/ 312,
|
|
/*executive*/ 522, /*folio*/ 612, /*invoice*/ 396, /*ledger*/ 792,
|
|
/*na-letter*/ 612, /*na-legal*/ 612, /*quarto*/ 609, /*a*/ 612,
|
|
/*b*/ 792, /*c*/ 1224, /*d*/ 1584, /*e*/ 2448,
|
|
/*na-10x15-envelope*/ 720, /*na-10x14-envelope*/ 720,
|
|
/*na-10x13-envelope*/ 720, /*na-9x12-envelope*/ 648,
|
|
/*na-9x11-envelope*/ 648, /*na-7x9-envelope*/ 504,
|
|
/*na-6x9-envelope*/ 432, /*na-number-9-envelope*/ 279,
|
|
/*na-number-10-envelope*/ 297, /*na-number-11-envelope*/ 324,
|
|
/*na-number-12-envelope*/ 342, /*na-number-14-envelope*/ 360,
|
|
/*invite-envelope*/ 624, /*italy-envelope*/ 312,
|
|
/*monarch-envelope*/ 279, /*personal-envelope*/ 261
|
|
};
|
|
private static final int LENGTHS[] = {
|
|
/*iso-4a0*/ 6741, /*iso-2a0*/ 4768, /*iso-a0*/ 3370, /*iso-a1*/ 2384,
|
|
/*iso-a2*/ 1684, /*iso-a3*/ 1191, /*iso-a4*/ 842, /*iso-a5*/ 595,
|
|
/*iso-a6*/ 420, /*iso-a7*/ 298, /*iso-a8*/ 210, /*iso-a9*/ 147,
|
|
/*iso-a10*/ 105, /*iso-b0*/ 4008, /*iso-b1*/ 2835, /*iso-b2*/ 2004,
|
|
/*iso-b3*/ 1417, /*iso-b4*/ 1001, /*iso-b5*/ 729, /*iso-b6*/ 499,
|
|
/*iso-b7*/ 354, /*iso-b8*/ 249, /*iso-b9*/ 176, /*iso-b10*/ 125,
|
|
/*jis-b0*/ 4127, /*jis-b1*/ 2920, /*jis-b2*/ 2064, /*jis-b3*/ 1460,
|
|
/*jis-b4*/ 1032, /*jis-b5*/ 729, /*jis-b6*/ 516, /*jis-b7*/ 363,
|
|
/*jis-b8*/ 258, /*jis-b9*/ 181, /*jis-b10*/ 128, /*iso-c0*/ 3677,
|
|
/*iso-c1*/ 2599, /*iso-c2*/ 1837, /*iso-c3*/ 1298, /*iso-c4*/ 918,
|
|
/*iso-c5*/ 649, /*iso-c6*/ 459, /*iso-c7*/ 323, /*iso-c8*/ 230,
|
|
/*iso-c9*/ 162, /*iso-c10*/ 113, /*iso-designated-long*/ 624,
|
|
/*executive*/ 756, /*folio*/ 936, /*invoice*/ 612, /*ledger*/ 1224,
|
|
/*na-letter*/ 792, /*na-legal*/ 1008, /*quarto*/ 780, /*a*/ 792,
|
|
/*b*/ 1224, /*c*/ 1584, /*d*/ 2448, /*e*/ 3168,
|
|
/*na-10x15-envelope*/ 1080, /*na-10x14-envelope*/ 1008,
|
|
/*na-10x13-envelope*/ 936, /*na-9x12-envelope*/ 864,
|
|
/*na-9x11-envelope*/ 792, /*na-7x9-envelope*/ 648,
|
|
/*na-6x9-envelope*/ 648, /*na-number-9-envelope*/ 639,
|
|
/*na-number-10-envelope*/ 684, /*na-number-11-envelope*/ 747,
|
|
/*na-number-12-envelope*/ 792, /*na-number-14-envelope*/ 828,
|
|
/*invite-envelope*/ 624, /*italy-envelope*/ 652,
|
|
/*monarch-envelope*/ 540, /*personal-envelope*/ 468
|
|
};
|
|
|
|
|
|
private Frame frame;
|
|
private String docTitle = "";
|
|
private JobAttributes jobAttributes;
|
|
private PageAttributes pageAttributes;
|
|
private PrintRequestAttributeSet attributes;
|
|
|
|
/*
|
|
* Displays the native or cross-platform dialog and allows the
|
|
* user to update job & page attributes
|
|
*/
|
|
|
|
/**
|
|
* The PrinterJob being uses to implement the PrintJob.
|
|
*/
|
|
private PrinterJob printerJob;
|
|
|
|
/**
|
|
* The size of the page being used for the PrintJob.
|
|
*/
|
|
private PageFormat pageFormat;
|
|
|
|
/**
|
|
* The PrinterJob and the application run on different
|
|
* threads and communicate through a pair of message
|
|
* queues. This queue is the list of Graphics that
|
|
* the PrinterJob has requested rendering for, but
|
|
* for which the application has not yet called getGraphics().
|
|
* In practice the length of this message queue is always
|
|
* 0 or 1.
|
|
*/
|
|
private MessageQ graphicsToBeDrawn = new MessageQ("tobedrawn");
|
|
|
|
/**
|
|
* Used to communicate between the application's thread
|
|
* and the PrinterJob's thread this message queue holds
|
|
* the list of Graphics into which the application has
|
|
* finished drawing, but that have not yet been returned
|
|
* to the PrinterJob thread. Again, in practice, the
|
|
* length of this message queue is always 0 or 1.
|
|
*/
|
|
private MessageQ graphicsDrawn = new MessageQ("drawn");
|
|
|
|
/**
|
|
* The last Graphics returned to the application via
|
|
* getGraphics. This is the Graphics into which the
|
|
* application is currently drawing.
|
|
*/
|
|
private Graphics2D currentGraphics;
|
|
|
|
/**
|
|
* The zero based index of the page currently being rendered
|
|
* by the application.
|
|
*/
|
|
private int pageIndex = -1;
|
|
|
|
// The following Strings are maintained for backward-compatibility with
|
|
// Properties based print control.
|
|
private final static String DEST_PROP = "awt.print.destination";
|
|
private final static String PRINTER = "printer";
|
|
private final static String FILE = "file";
|
|
|
|
private final static String PRINTER_PROP = "awt.print.printer";
|
|
|
|
private final static String FILENAME_PROP = "awt.print.fileName";
|
|
|
|
private final static String NUMCOPIES_PROP = "awt.print.numCopies";
|
|
|
|
private final static String OPTIONS_PROP = "awt.print.options";
|
|
|
|
private final static String ORIENT_PROP = "awt.print.orientation";
|
|
private final static String PORTRAIT = "portrait";
|
|
private final static String LANDSCAPE = "landscape";
|
|
|
|
private final static String PAPERSIZE_PROP = "awt.print.paperSize";
|
|
private final static String LETTER = "letter";
|
|
private final static String LEGAL = "legal";
|
|
private final static String EXECUTIVE = "executive";
|
|
private final static String A4 = "a4";
|
|
|
|
private Properties props;
|
|
|
|
private String options = ""; // REMIND: needs implementation
|
|
|
|
/**
|
|
* The thread on which PrinterJob is running.
|
|
* This is different than the applications thread.
|
|
*/
|
|
private Thread printerJobThread;
|
|
|
|
public PrintJob2D(Frame frame, String doctitle,
|
|
final Properties props) {
|
|
this.props = props;
|
|
this.jobAttributes = new JobAttributes();
|
|
this.pageAttributes = new PageAttributes();
|
|
translateInputProps();
|
|
initPrintJob2D(frame, doctitle,
|
|
this.jobAttributes, this.pageAttributes);
|
|
}
|
|
|
|
public PrintJob2D(Frame frame, String doctitle,
|
|
JobAttributes jobAttributes,
|
|
PageAttributes pageAttributes) {
|
|
initPrintJob2D(frame, doctitle, jobAttributes, pageAttributes);
|
|
}
|
|
|
|
private void initPrintJob2D(Frame frame, String doctitle,
|
|
JobAttributes jobAttributes,
|
|
PageAttributes pageAttributes) {
|
|
|
|
SecurityManager security = System.getSecurityManager();
|
|
if (security != null) {
|
|
security.checkPrintJobAccess();
|
|
}
|
|
|
|
if (frame == null &&
|
|
(jobAttributes == null ||
|
|
jobAttributes.getDialog() == DialogType.NATIVE)) {
|
|
throw new NullPointerException("Frame must not be null");
|
|
}
|
|
this.frame = frame;
|
|
|
|
this.docTitle = (doctitle == null) ? "" : doctitle;
|
|
this.jobAttributes = (jobAttributes != null)
|
|
? jobAttributes : new JobAttributes();
|
|
this.pageAttributes = (pageAttributes != null)
|
|
? pageAttributes : new PageAttributes();
|
|
|
|
// Currently, we always reduce page ranges to xxx or xxx-xxx
|
|
int[][] pageRanges = this.jobAttributes.getPageRanges();
|
|
int first = pageRanges[0][0];
|
|
int last = pageRanges[pageRanges.length - 1][1];
|
|
this.jobAttributes.setPageRanges(new int[][] {
|
|
new int[] { first, last }
|
|
});
|
|
this.jobAttributes.setToPage(last);
|
|
this.jobAttributes.setFromPage(first);
|
|
|
|
|
|
// Verify that the cross feed and feed resolutions are the same
|
|
int[] res = this.pageAttributes.getPrinterResolution();
|
|
if (res[0] != res[1]) {
|
|
throw new IllegalArgumentException("Differing cross feed and feed"+
|
|
" resolutions not supported.");
|
|
}
|
|
|
|
// Verify that the app has access to the file system
|
|
DestinationType dest= this.jobAttributes.getDestination();
|
|
if (dest == DestinationType.FILE) {
|
|
throwPrintToFile();
|
|
|
|
// check if given filename is valid
|
|
String destStr = jobAttributes.getFileName();
|
|
if ((destStr != null) &&
|
|
(jobAttributes.getDialog() == JobAttributes.DialogType.NONE)) {
|
|
|
|
File f = new File(destStr);
|
|
try {
|
|
// check if this is a new file and if filename chars are valid
|
|
// createNewFile returns false if file exists
|
|
if (f.createNewFile()) {
|
|
f.delete();
|
|
}
|
|
} catch (IOException ioe) {
|
|
throw new IllegalArgumentException("Cannot write to file:"+
|
|
destStr);
|
|
} catch (SecurityException se) {
|
|
//There is already file read/write access so at this point
|
|
// only delete access is denied. Just ignore it because in
|
|
// most cases the file created in createNewFile gets overwritten
|
|
// anyway.
|
|
}
|
|
|
|
File pFile = f.getParentFile();
|
|
if ((f.exists() &&
|
|
(!f.isFile() || !f.canWrite())) ||
|
|
((pFile != null) &&
|
|
(!pFile.exists() || (pFile.exists() && !pFile.canWrite())))) {
|
|
throw new IllegalArgumentException("Cannot write to file:"+
|
|
destStr);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
public boolean printDialog() {
|
|
|
|
boolean proceedWithPrint = false;
|
|
|
|
printerJob = PrinterJob.getPrinterJob();
|
|
if (printerJob == null) {
|
|
return false;
|
|
}
|
|
DialogType d = this.jobAttributes.getDialog();
|
|
PrintService pServ = printerJob.getPrintService();
|
|
if ((pServ == null) && (d == DialogType.NONE)){
|
|
return false;
|
|
}
|
|
copyAttributes(pServ);
|
|
|
|
DefaultSelectionType select =
|
|
this.jobAttributes.getDefaultSelection();
|
|
if (select == DefaultSelectionType.RANGE) {
|
|
attributes.add(SunPageSelection.RANGE);
|
|
} else if (select == DefaultSelectionType.SELECTION) {
|
|
attributes.add(SunPageSelection.SELECTION);
|
|
} else {
|
|
attributes.add(SunPageSelection.ALL);
|
|
}
|
|
|
|
if (frame != null) {
|
|
attributes.add(new DialogOwner(frame));
|
|
}
|
|
|
|
if ( d == DialogType.NONE) {
|
|
proceedWithPrint = true;
|
|
} else {
|
|
if (d == DialogType.NATIVE) {
|
|
attributes.add(DialogTypeSelection.NATIVE);
|
|
} else { // (d == DialogType.COMMON)
|
|
attributes.add(DialogTypeSelection.COMMON);
|
|
}
|
|
if (proceedWithPrint = printerJob.printDialog(attributes)) {
|
|
if (pServ == null) {
|
|
// Windows gives an option to install a service
|
|
// when it detects there are no printers so
|
|
// we make sure we get the updated print service.
|
|
pServ = printerJob.getPrintService();
|
|
if (pServ == null) {
|
|
return false;
|
|
}
|
|
}
|
|
updateAttributes();
|
|
translateOutputProps();
|
|
}
|
|
}
|
|
|
|
if (proceedWithPrint) {
|
|
|
|
JobName jname = (JobName)attributes.get(JobName.class);
|
|
if (jname != null) {
|
|
printerJob.setJobName(jname.toString());
|
|
}
|
|
|
|
pageFormat = new PageFormat();
|
|
|
|
Media media = (Media)attributes.get(Media.class);
|
|
MediaSize mediaSize = null;
|
|
if (media != null && media instanceof MediaSizeName) {
|
|
mediaSize = MediaSize.getMediaSizeForName((MediaSizeName)media);
|
|
}
|
|
|
|
Paper p = pageFormat.getPaper();
|
|
if (mediaSize != null) {
|
|
p.setSize(mediaSize.getX(MediaSize.INCH)*72.0,
|
|
mediaSize.getY(MediaSize.INCH)*72.0);
|
|
}
|
|
|
|
if (pageAttributes.getOrigin()==OriginType.PRINTABLE) {
|
|
// AWT uses 1/4" borders by default
|
|
p.setImageableArea(18.0, 18.0,
|
|
p.getWidth()-36.0,
|
|
p.getHeight()-36.0);
|
|
} else {
|
|
p.setImageableArea(0.0,0.0,p.getWidth(),p.getHeight());
|
|
}
|
|
|
|
pageFormat.setPaper(p);
|
|
|
|
OrientationRequested orient =
|
|
(OrientationRequested)attributes.get(OrientationRequested.class);
|
|
if (orient!= null &&
|
|
orient == OrientationRequested.REVERSE_LANDSCAPE) {
|
|
pageFormat.setOrientation(PageFormat.REVERSE_LANDSCAPE);
|
|
} else if (orient == OrientationRequested.LANDSCAPE) {
|
|
pageFormat.setOrientation(PageFormat.LANDSCAPE);
|
|
} else {
|
|
pageFormat.setOrientation(PageFormat.PORTRAIT);
|
|
}
|
|
|
|
printerJob.setPrintable(this, pageFormat);
|
|
|
|
}
|
|
|
|
return proceedWithPrint;
|
|
}
|
|
|
|
private void updateAttributes() {
|
|
Copies c = (Copies)attributes.get(Copies.class);
|
|
jobAttributes.setCopies(c.getValue());
|
|
|
|
SunPageSelection sel =
|
|
(SunPageSelection)attributes.get(SunPageSelection.class);
|
|
if (sel == SunPageSelection.RANGE) {
|
|
jobAttributes.setDefaultSelection(DefaultSelectionType.RANGE);
|
|
} else if (sel == SunPageSelection.SELECTION) {
|
|
jobAttributes.setDefaultSelection(DefaultSelectionType.SELECTION);
|
|
} else {
|
|
jobAttributes.setDefaultSelection(DefaultSelectionType.ALL);
|
|
}
|
|
|
|
Destination dest = (Destination)attributes.get(Destination.class);
|
|
if (dest != null) {
|
|
jobAttributes.setDestination(DestinationType.FILE);
|
|
jobAttributes.setFileName(dest.getURI().getPath());
|
|
} else {
|
|
jobAttributes.setDestination(DestinationType.PRINTER);
|
|
}
|
|
|
|
PrintService serv = printerJob.getPrintService();
|
|
if (serv != null) {
|
|
jobAttributes.setPrinter(serv.getName());
|
|
}
|
|
|
|
PageRanges range = (PageRanges)attributes.get(PageRanges.class);
|
|
int[][] members = range.getMembers();
|
|
jobAttributes.setPageRanges(members);
|
|
|
|
SheetCollate collation =
|
|
(SheetCollate)attributes.get(SheetCollate.class);
|
|
if (collation == SheetCollate.COLLATED) {
|
|
jobAttributes.setMultipleDocumentHandling(
|
|
MultipleDocumentHandlingType.SEPARATE_DOCUMENTS_COLLATED_COPIES);
|
|
} else {
|
|
jobAttributes.setMultipleDocumentHandling(
|
|
MultipleDocumentHandlingType.SEPARATE_DOCUMENTS_UNCOLLATED_COPIES);
|
|
}
|
|
|
|
Sides sides = (Sides)attributes.get(Sides.class);
|
|
if (sides == Sides.TWO_SIDED_LONG_EDGE) {
|
|
jobAttributes.setSides(SidesType.TWO_SIDED_LONG_EDGE);
|
|
} else if (sides == Sides.TWO_SIDED_SHORT_EDGE) {
|
|
jobAttributes.setSides(SidesType.TWO_SIDED_SHORT_EDGE);
|
|
} else {
|
|
jobAttributes.setSides(SidesType.ONE_SIDED);
|
|
}
|
|
|
|
// PageAttributes
|
|
|
|
Chromaticity color =
|
|
(Chromaticity)attributes.get(Chromaticity.class);
|
|
if (color == Chromaticity.COLOR) {
|
|
pageAttributes.setColor(ColorType.COLOR);
|
|
} else {
|
|
pageAttributes.setColor(ColorType.MONOCHROME);
|
|
}
|
|
|
|
OrientationRequested orient =
|
|
(OrientationRequested)attributes.get(OrientationRequested.class);
|
|
if (orient == OrientationRequested.LANDSCAPE) {
|
|
pageAttributes.setOrientationRequested(
|
|
OrientationRequestedType.LANDSCAPE);
|
|
} else {
|
|
pageAttributes.setOrientationRequested(
|
|
OrientationRequestedType.PORTRAIT);
|
|
}
|
|
|
|
PrintQuality qual = (PrintQuality)attributes.get(PrintQuality.class);
|
|
if (qual == PrintQuality.DRAFT) {
|
|
pageAttributes.setPrintQuality(PrintQualityType.DRAFT);
|
|
} else if (qual == PrintQuality.HIGH) {
|
|
pageAttributes.setPrintQuality(PrintQualityType.HIGH);
|
|
} else { // NORMAL
|
|
pageAttributes.setPrintQuality(PrintQualityType.NORMAL);
|
|
}
|
|
|
|
Media msn = (Media)attributes.get(Media.class);
|
|
if (msn != null && msn instanceof MediaSizeName) {
|
|
MediaType mType = unMapMedia((MediaSizeName)msn);
|
|
|
|
if (mType != null) {
|
|
pageAttributes.setMedia(mType);
|
|
}
|
|
}
|
|
debugPrintAttributes(false, false);
|
|
}
|
|
|
|
private void debugPrintAttributes(boolean ja, boolean pa ) {
|
|
if (ja) {
|
|
System.out.println("new Attributes\ncopies = "+
|
|
jobAttributes.getCopies()+
|
|
"\nselection = "+
|
|
jobAttributes.getDefaultSelection()+
|
|
"\ndest "+jobAttributes.getDestination()+
|
|
"\nfile "+jobAttributes.getFileName()+
|
|
"\nfromPage "+jobAttributes.getFromPage()+
|
|
"\ntoPage "+jobAttributes.getToPage()+
|
|
"\ncollation "+
|
|
jobAttributes.getMultipleDocumentHandling()+
|
|
"\nPrinter "+jobAttributes.getPrinter()+
|
|
"\nSides2 "+jobAttributes.getSides()
|
|
);
|
|
}
|
|
|
|
if (pa) {
|
|
System.out.println("new Attributes\ncolor = "+
|
|
pageAttributes.getColor()+
|
|
"\norientation = "+
|
|
pageAttributes.getOrientationRequested()+
|
|
"\nquality "+pageAttributes.getPrintQuality()+
|
|
"\nMedia2 "+pageAttributes.getMedia()
|
|
);
|
|
}
|
|
}
|
|
|
|
|
|
/* From JobAttributes we will copy job name and duplex printing
|
|
* and destination.
|
|
* The majority of the rest of the attributes are reflected
|
|
* attributes.
|
|
*
|
|
* From PageAttributes we copy color, media size, orientation,
|
|
* origin type, resolution and print quality.
|
|
* We use the media, orientation in creating the page format, and
|
|
* the origin type to set its imageable area.
|
|
*
|
|
* REMIND: Interpretation of resolution, additional media sizes.
|
|
*/
|
|
private void copyAttributes(PrintService printServ) {
|
|
|
|
attributes = new HashPrintRequestAttributeSet();
|
|
attributes.add(new JobName(docTitle, null));
|
|
PrintService pServ = printServ;
|
|
|
|
String printerName = jobAttributes.getPrinter();
|
|
if (printerName != null && printerName != ""
|
|
&& !printerName.equals(pServ.getName())) {
|
|
|
|
// Search for the given printerName in the list of PrintServices
|
|
PrintService []services = PrinterJob.lookupPrintServices();
|
|
try {
|
|
for (int i=0; i<services.length; i++) {
|
|
if (printerName.equals(services[i].getName())) {
|
|
printerJob.setPrintService(services[i]);
|
|
pServ = services[i];
|
|
break;
|
|
}
|
|
}
|
|
} catch (PrinterException pe) {
|
|
}
|
|
}
|
|
|
|
DestinationType dest = jobAttributes.getDestination();
|
|
if (dest == DestinationType.FILE &&
|
|
pServ.isAttributeCategorySupported(Destination.class)) {
|
|
|
|
String fileName = jobAttributes.getFileName();
|
|
|
|
Destination defaultDest;
|
|
if (fileName == null && (defaultDest = (Destination)pServ.
|
|
getDefaultAttributeValue(Destination.class)) != null) {
|
|
attributes.add(defaultDest);
|
|
} else {
|
|
URI uri = null;
|
|
try {
|
|
if (fileName != null) {
|
|
if (fileName.equals("")) {
|
|
fileName = ".";
|
|
}
|
|
} else {
|
|
// defaultDest should not be null. The following code
|
|
// is only added to safeguard against a possible
|
|
// buggy implementation of a PrintService having a
|
|
// null default Destination.
|
|
fileName = "out.prn";
|
|
}
|
|
uri = (new File(fileName)).toURI();
|
|
} catch (SecurityException se) {
|
|
try {
|
|
// '\\' file separator is illegal character in opaque
|
|
// part and causes URISyntaxException, so we replace
|
|
// it with '/'
|
|
fileName = fileName.replace('\\', '/');
|
|
uri = new URI("file:"+fileName);
|
|
} catch (URISyntaxException e) {
|
|
}
|
|
}
|
|
if (uri != null) {
|
|
attributes.add(new Destination(uri));
|
|
}
|
|
}
|
|
}
|
|
attributes.add(new SunMinMaxPage(jobAttributes.getMinPage(),
|
|
jobAttributes.getMaxPage()));
|
|
SidesType sType = jobAttributes.getSides();
|
|
if (sType == SidesType.TWO_SIDED_LONG_EDGE) {
|
|
attributes.add(Sides.TWO_SIDED_LONG_EDGE);
|
|
} else if (sType == SidesType.TWO_SIDED_SHORT_EDGE) {
|
|
attributes.add(Sides.TWO_SIDED_SHORT_EDGE);
|
|
} else if (sType == SidesType.ONE_SIDED) {
|
|
attributes.add(Sides.ONE_SIDED);
|
|
}
|
|
|
|
MultipleDocumentHandlingType hType =
|
|
jobAttributes.getMultipleDocumentHandling();
|
|
if (hType ==
|
|
MultipleDocumentHandlingType.SEPARATE_DOCUMENTS_COLLATED_COPIES) {
|
|
attributes.add(SheetCollate.COLLATED);
|
|
} else {
|
|
attributes.add(SheetCollate.UNCOLLATED);
|
|
}
|
|
|
|
attributes.add(new Copies(jobAttributes.getCopies()));
|
|
|
|
attributes.add(new PageRanges(jobAttributes.getFromPage(),
|
|
jobAttributes.getToPage()));
|
|
|
|
if (pageAttributes.getColor() == ColorType.COLOR) {
|
|
attributes.add(Chromaticity.COLOR);
|
|
} else {
|
|
attributes.add(Chromaticity.MONOCHROME);
|
|
}
|
|
|
|
pageFormat = printerJob.defaultPage();
|
|
if (pageAttributes.getOrientationRequested() ==
|
|
OrientationRequestedType.LANDSCAPE) {
|
|
pageFormat.setOrientation(PageFormat.LANDSCAPE);
|
|
attributes.add(OrientationRequested.LANDSCAPE);
|
|
} else {
|
|
pageFormat.setOrientation(PageFormat.PORTRAIT);
|
|
attributes.add(OrientationRequested.PORTRAIT);
|
|
}
|
|
|
|
MediaType media = pageAttributes.getMedia();
|
|
MediaSizeName msn = mapMedia(media);
|
|
if (msn != null) {
|
|
attributes.add(msn);
|
|
}
|
|
|
|
PrintQualityType qType =
|
|
pageAttributes.getPrintQuality();
|
|
if (qType == PrintQualityType.DRAFT) {
|
|
attributes.add(PrintQuality.DRAFT);
|
|
} else if (qType == PrintQualityType.NORMAL) {
|
|
attributes.add(PrintQuality.NORMAL);
|
|
} else if (qType == PrintQualityType.HIGH) {
|
|
attributes.add(PrintQuality.HIGH);
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Gets a Graphics object that will draw to the next page.
|
|
* The page is sent to the printer when the graphics
|
|
* object is disposed. This graphics object will also implement
|
|
* the PrintGraphics interface.
|
|
* @see PrintGraphics
|
|
*/
|
|
public Graphics getGraphics() {
|
|
|
|
Graphics printGraphics = null;
|
|
|
|
synchronized (this) {
|
|
++pageIndex;
|
|
|
|
// Thread should not be created after end has been called.
|
|
// One way to detect this is if any of the graphics queue
|
|
// has been closed.
|
|
if (pageIndex == 0 && !graphicsToBeDrawn.isClosed()) {
|
|
|
|
/* We start a thread on which the PrinterJob will run.
|
|
* The PrinterJob will ask for pages on that thread
|
|
* and will use a message queue to fulfill the application's
|
|
* requests for a Graphics on the application's
|
|
* thread.
|
|
*/
|
|
|
|
startPrinterJobThread();
|
|
|
|
}
|
|
notify();
|
|
}
|
|
|
|
/* If the application has already been handed back
|
|
* a graphics then we need to put that graphics into
|
|
* the drawn queue so that the PrinterJob thread can
|
|
* return to the print system.
|
|
*/
|
|
if (currentGraphics != null) {
|
|
graphicsDrawn.append(currentGraphics);
|
|
currentGraphics = null;
|
|
}
|
|
|
|
/* We'll block here until a new graphics becomes
|
|
* available.
|
|
*/
|
|
|
|
currentGraphics = graphicsToBeDrawn.pop();
|
|
|
|
if (currentGraphics instanceof PeekGraphics) {
|
|
( (PeekGraphics) currentGraphics).setAWTDrawingOnly();
|
|
graphicsDrawn.append(currentGraphics);
|
|
currentGraphics = graphicsToBeDrawn.pop();
|
|
}
|
|
|
|
|
|
if (currentGraphics != null) {
|
|
|
|
/* In the PrintJob API, the origin is at the upper-
|
|
* left of the imageable area when using the new "printable"
|
|
* origin attribute, otherwise its the physical origin (for
|
|
* backwards compatibility. We emulate this by createing
|
|
* a PageFormat which matches and then performing the
|
|
* translate to the origin. This is a no-op if physical
|
|
* origin is specified.
|
|
*/
|
|
currentGraphics.translate(pageFormat.getImageableX(),
|
|
pageFormat.getImageableY());
|
|
|
|
/* Scale to accommodate AWT's notion of printer resolution */
|
|
double awtScale = 72.0/getPageResolutionInternal();
|
|
currentGraphics.scale(awtScale, awtScale);
|
|
|
|
/* The caller wants a Graphics instance but we do
|
|
* not want them to make 2D calls. We can't hand
|
|
* back a Graphics2D. The returned Graphics also
|
|
* needs to implement PrintGraphics, so we wrap
|
|
* the Graphics2D instance. The PrintJob API has
|
|
* the application dispose of the Graphics so
|
|
* we create a copy of the one returned by PrinterJob.
|
|
*/
|
|
printGraphics = new ProxyPrintGraphics(currentGraphics.create(),
|
|
this);
|
|
|
|
}
|
|
|
|
return printGraphics;
|
|
}
|
|
|
|
/**
|
|
* Returns the dimensions of the page in pixels.
|
|
* The resolution of the page is chosen so that it
|
|
* is similar to the screen resolution.
|
|
* Except (since 1.3) when the application specifies a resolution.
|
|
* In that case it it scaled accordingly.
|
|
*/
|
|
public Dimension getPageDimension() {
|
|
double wid, hgt, scale;
|
|
if (pageAttributes != null &&
|
|
pageAttributes.getOrigin()==OriginType.PRINTABLE) {
|
|
wid = pageFormat.getImageableWidth();
|
|
hgt = pageFormat.getImageableHeight();
|
|
} else {
|
|
wid = pageFormat.getWidth();
|
|
hgt = pageFormat.getHeight();
|
|
}
|
|
scale = getPageResolutionInternal() / 72.0;
|
|
return new Dimension((int)(wid * scale), (int)(hgt * scale));
|
|
}
|
|
|
|
private double getPageResolutionInternal() {
|
|
if (pageAttributes != null) {
|
|
int []res = pageAttributes.getPrinterResolution();
|
|
if (res[2] == 3) {
|
|
return res[0];
|
|
} else /* if (res[2] == 4) */ {
|
|
return (res[0] * 2.54);
|
|
}
|
|
} else {
|
|
return 72.0;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Returns the resolution of the page in pixels per inch.
|
|
* Note that this doesn't have to correspond to the physical
|
|
* resolution of the printer.
|
|
*/
|
|
public int getPageResolution() {
|
|
return (int)getPageResolutionInternal();
|
|
}
|
|
|
|
/**
|
|
* Returns true if the last page will be printed first.
|
|
*/
|
|
public boolean lastPageFirst() {
|
|
return false;
|
|
}
|
|
|
|
/**
|
|
* Ends the print job and does any necessary cleanup.
|
|
*/
|
|
public synchronized void end() {
|
|
|
|
/* Prevent the PrinterJob thread from appending any more
|
|
* graphics to the to-be-drawn queue
|
|
*/
|
|
graphicsToBeDrawn.close();
|
|
|
|
/* If we have a currentGraphics it was the last one returned to the
|
|
* PrintJob client. Append it to the drawn queue so that print()
|
|
* will return allowing the page to be flushed.
|
|
* This really ought to happen in dispose() but for whatever reason
|
|
* that isn't how the old PrintJob worked even though its spec
|
|
* said dispose() flushed the page.
|
|
*/
|
|
if (currentGraphics != null) {
|
|
graphicsDrawn.append(currentGraphics);
|
|
}
|
|
graphicsDrawn.closeWhenEmpty();
|
|
|
|
/* Wait for the PrinterJob.print() thread to terminate, ensuring
|
|
* that RasterPrinterJob has made its end doc call, and resources
|
|
* are released, files closed etc.
|
|
*/
|
|
if( printerJobThread != null && printerJobThread.isAlive() ){
|
|
try {
|
|
printerJobThread.join();
|
|
} catch (InterruptedException e) {
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Ends this print job once it is no longer referenced.
|
|
* @see #end
|
|
*/
|
|
public void finalize() {
|
|
end();
|
|
}
|
|
|
|
/**
|
|
* Prints the page at the specified index into the specified
|
|
* {@link Graphics} context in the specified
|
|
* format. A <code>PrinterJob</code> calls the
|
|
* <code>Printable</code> interface to request that a page be
|
|
* rendered into the context specified by
|
|
* <code>graphics</code>. The format of the page to be drawn is
|
|
* specified by <code>pageFormat</code>. The zero based index
|
|
* of the requested page is specified by <code>pageIndex</code>.
|
|
* If the requested page does not exist then this method returns
|
|
* NO_SUCH_PAGE; otherwise PAGE_EXISTS is returned.
|
|
* The <code>Graphics</code> class or subclass implements the
|
|
* {@link PrinterGraphics} interface to provide additional
|
|
* information. If the <code>Printable</code> object
|
|
* aborts the print job then it throws a {@link PrinterException}.
|
|
* @param graphics the context into which the page is drawn
|
|
* @param pageFormat the size and orientation of the page being drawn
|
|
* @param pageIndex the zero based index of the page to be drawn
|
|
* @return PAGE_EXISTS if the page is rendered successfully
|
|
* or NO_SUCH_PAGE if <code>pageIndex</code> specifies a
|
|
* non-existent page.
|
|
* @exception java.awt.print.PrinterException
|
|
* thrown when the print job is terminated.
|
|
*/
|
|
public int print(Graphics graphics, PageFormat pageFormat, int pageIndex)
|
|
throws PrinterException {
|
|
|
|
int result;
|
|
|
|
/* This method will be called by the PrinterJob on a thread other
|
|
* that the application's thread. We hold on to the graphics
|
|
* until we can rendevous with the application's thread and
|
|
* hand over the graphics. The application then does all the
|
|
* drawing. When the application is done drawing we rendevous
|
|
* again with the PrinterJob thread and release the Graphics
|
|
* so that it knows we are done.
|
|
*/
|
|
|
|
/* Add the graphics to the message queue of graphics to
|
|
* be rendered. This is really a one slot queue. The
|
|
* application's thread will come along and remove the
|
|
* graphics from the queue when the app asks for a graphics.
|
|
*/
|
|
graphicsToBeDrawn.append( (Graphics2D) graphics);
|
|
|
|
/* We now wait for the app's thread to finish drawing on
|
|
* the Graphics. This thread will sleep until the application
|
|
* release the graphics by placing it in the graphics drawn
|
|
* message queue. If the application signals that it is
|
|
* finished drawing the entire document then we'll get null
|
|
* returned when we try and pop a finished graphic.
|
|
*/
|
|
if (graphicsDrawn.pop() != null) {
|
|
result = PAGE_EXISTS;
|
|
} else {
|
|
result = NO_SUCH_PAGE;
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
private void startPrinterJobThread() {
|
|
|
|
printerJobThread = new Thread(this, "printerJobThread");
|
|
printerJobThread.start();
|
|
}
|
|
|
|
|
|
public void run() {
|
|
|
|
try {
|
|
printerJob.print(attributes);
|
|
} catch (PrinterException e) {
|
|
//REMIND: need to store this away and not rethrow it.
|
|
}
|
|
|
|
/* Close the message queues so that nobody is stuck
|
|
* waiting for one.
|
|
*/
|
|
graphicsToBeDrawn.closeWhenEmpty();
|
|
graphicsDrawn.close();
|
|
}
|
|
|
|
private class MessageQ {
|
|
|
|
private String qid="noname";
|
|
|
|
private ArrayList queue = new ArrayList();
|
|
|
|
MessageQ(String id) {
|
|
qid = id;
|
|
}
|
|
|
|
synchronized void closeWhenEmpty() {
|
|
|
|
while (queue != null && queue.size() > 0) {
|
|
try {
|
|
wait(1000);
|
|
} catch (InterruptedException e) {
|
|
// do nothing.
|
|
}
|
|
}
|
|
|
|
queue = null;
|
|
notifyAll();
|
|
}
|
|
|
|
synchronized void close() {
|
|
queue = null;
|
|
notifyAll();
|
|
}
|
|
|
|
synchronized boolean append(Graphics2D g) {
|
|
|
|
boolean queued = false;
|
|
|
|
if (queue != null) {
|
|
queue.add(g);
|
|
queued = true;
|
|
notify();
|
|
}
|
|
|
|
return queued;
|
|
}
|
|
|
|
synchronized Graphics2D pop() {
|
|
Graphics2D g = null;
|
|
|
|
while (g == null && queue != null) {
|
|
|
|
if (queue.size() > 0) {
|
|
g = (Graphics2D) queue.remove(0);
|
|
notify();
|
|
|
|
} else {
|
|
try {
|
|
wait(2000);
|
|
} catch (InterruptedException e) {
|
|
// do nothing.
|
|
}
|
|
}
|
|
}
|
|
|
|
return g;
|
|
}
|
|
|
|
synchronized boolean isClosed() {
|
|
return queue == null;
|
|
}
|
|
|
|
}
|
|
|
|
|
|
private static int[] getSize(MediaType mType) {
|
|
int []dim = new int[2];
|
|
dim[0] = 612;
|
|
dim[1] = 792;
|
|
|
|
for (int i=0; i < SIZES.length; i++) {
|
|
if (SIZES[i] == mType) {
|
|
dim[0] = WIDTHS[i];
|
|
dim[1] = LENGTHS[i];
|
|
break;
|
|
}
|
|
}
|
|
return dim;
|
|
}
|
|
|
|
public static MediaSizeName mapMedia(MediaType mType) {
|
|
MediaSizeName media = null;
|
|
|
|
// JAVAXSIZES.length and SIZES.length must be equal!
|
|
// Attempt to recover by getting the smaller size.
|
|
int length = Math.min(SIZES.length, JAVAXSIZES.length);
|
|
|
|
for (int i=0; i < length; i++) {
|
|
if (SIZES[i] == mType) {
|
|
if ((JAVAXSIZES[i] != null) &&
|
|
MediaSize.getMediaSizeForName(JAVAXSIZES[i]) != null) {
|
|
media = JAVAXSIZES[i];
|
|
break;
|
|
} else {
|
|
/* create Custom Media */
|
|
media = new CustomMediaSizeName(SIZES[i].toString());
|
|
|
|
float w = (float)Math.rint(WIDTHS[i] / 72.0);
|
|
float h = (float)Math.rint(LENGTHS[i] / 72.0);
|
|
if (w > 0.0 && h > 0.0) {
|
|
// add new created MediaSize to our static map
|
|
// so it will be found when we call findMedia
|
|
new MediaSize(w, h, Size2DSyntax.INCH, media);
|
|
}
|
|
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
return media;
|
|
}
|
|
|
|
|
|
public static MediaType unMapMedia(MediaSizeName mSize) {
|
|
MediaType media = null;
|
|
|
|
// JAVAXSIZES.length and SIZES.length must be equal!
|
|
// Attempt to recover by getting the smaller size.
|
|
int length = Math.min(SIZES.length, JAVAXSIZES.length);
|
|
|
|
for (int i=0; i < length; i++) {
|
|
if (JAVAXSIZES[i] == mSize) {
|
|
if (SIZES[i] != null) {
|
|
media = SIZES[i];
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
return media;
|
|
}
|
|
|
|
private void translateInputProps() {
|
|
if (props == null) {
|
|
return;
|
|
}
|
|
|
|
String str;
|
|
|
|
str = props.getProperty(DEST_PROP);
|
|
if (str != null) {
|
|
if (str.equals(PRINTER)) {
|
|
jobAttributes.setDestination(DestinationType.PRINTER);
|
|
} else if (str.equals(FILE)) {
|
|
jobAttributes.setDestination(DestinationType.FILE);
|
|
}
|
|
}
|
|
str = props.getProperty(PRINTER_PROP);
|
|
if (str != null) {
|
|
jobAttributes.setPrinter(str);
|
|
}
|
|
str = props.getProperty(FILENAME_PROP);
|
|
if (str != null) {
|
|
jobAttributes.setFileName(str);
|
|
}
|
|
str = props.getProperty(NUMCOPIES_PROP);
|
|
if (str != null) {
|
|
jobAttributes.setCopies(Integer.parseInt(str));
|
|
}
|
|
|
|
this.options = props.getProperty(OPTIONS_PROP, "");
|
|
|
|
str = props.getProperty(ORIENT_PROP);
|
|
if (str != null) {
|
|
if (str.equals(PORTRAIT)) {
|
|
pageAttributes.setOrientationRequested(
|
|
OrientationRequestedType.PORTRAIT);
|
|
} else if (str.equals(LANDSCAPE)) {
|
|
pageAttributes.setOrientationRequested(
|
|
OrientationRequestedType.LANDSCAPE);
|
|
}
|
|
}
|
|
str = props.getProperty(PAPERSIZE_PROP);
|
|
if (str != null) {
|
|
if (str.equals(LETTER)) {
|
|
pageAttributes.setMedia(SIZES[MediaType.LETTER.hashCode()]);
|
|
} else if (str.equals(LEGAL)) {
|
|
pageAttributes.setMedia(SIZES[MediaType.LEGAL.hashCode()]);
|
|
} else if (str.equals(EXECUTIVE)) {
|
|
pageAttributes.setMedia(SIZES[MediaType.EXECUTIVE.hashCode()]);
|
|
} else if (str.equals(A4)) {
|
|
pageAttributes.setMedia(SIZES[MediaType.A4.hashCode()]);
|
|
}
|
|
}
|
|
}
|
|
|
|
private void translateOutputProps() {
|
|
if (props == null) {
|
|
return;
|
|
}
|
|
|
|
String str;
|
|
|
|
props.setProperty(DEST_PROP,
|
|
(jobAttributes.getDestination() == DestinationType.PRINTER) ?
|
|
PRINTER : FILE);
|
|
str = jobAttributes.getPrinter();
|
|
if (str != null && !str.equals("")) {
|
|
props.setProperty(PRINTER_PROP, str);
|
|
}
|
|
str = jobAttributes.getFileName();
|
|
if (str != null && !str.equals("")) {
|
|
props.setProperty(FILENAME_PROP, str);
|
|
}
|
|
int copies = jobAttributes.getCopies();
|
|
if (copies > 0) {
|
|
props.setProperty(NUMCOPIES_PROP, "" + copies);
|
|
}
|
|
str = this.options;
|
|
if (str != null && !str.equals("")) {
|
|
props.setProperty(OPTIONS_PROP, str);
|
|
}
|
|
props.setProperty(ORIENT_PROP,
|
|
(pageAttributes.getOrientationRequested() ==
|
|
OrientationRequestedType.PORTRAIT)
|
|
? PORTRAIT : LANDSCAPE);
|
|
MediaType media = SIZES[pageAttributes.getMedia().hashCode()];
|
|
if (media == MediaType.LETTER) {
|
|
str = LETTER;
|
|
} else if (media == MediaType.LEGAL) {
|
|
str = LEGAL;
|
|
} else if (media == MediaType.EXECUTIVE) {
|
|
str = EXECUTIVE;
|
|
} else if (media == MediaType.A4) {
|
|
str = A4;
|
|
} else {
|
|
str = media.toString();
|
|
}
|
|
props.setProperty(PAPERSIZE_PROP, str);
|
|
}
|
|
|
|
private void throwPrintToFile() {
|
|
SecurityManager security = System.getSecurityManager();
|
|
FilePermission printToFilePermission = null;
|
|
if (security != null) {
|
|
if (printToFilePermission == null) {
|
|
printToFilePermission =
|
|
new FilePermission("<<ALL FILES>>", "read,write");
|
|
}
|
|
security.checkPermission(printToFilePermission);
|
|
}
|
|
}
|
|
|
|
}
|