/*
Copyright (c) 2003-2008 ITerative Consulting Pty Ltd. All Rights Reserved.
Redistribution and use in source and binary forms, with or without modification, are permitted
provided that the following conditions are met:
o Redistributions of source code must retain the above copyright notice, this list of conditions and
the following disclaimer.
o Redistributions in binary form must reproduce the above copyright notice, this list of conditions
and the following disclaimer in the documentation and/or other materials provided with the distribution.
o This jcTOOL Helper Class software, whether in binary or source form may not be used within,
or to derive, any other product without the specific prior written permission of the copyright holder
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package DisplayProject.printing;
import java.awt.Component;
import java.awt.Container;
import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.print.PageFormat;
import java.awt.print.Paper;
import java.awt.print.PrinterException;
import java.awt.print.PrinterJob;
import javax.print.PrintService;
import javax.print.PrintServiceLookup;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JScrollPane;
import javax.swing.ScrollPaneConstants;
import javax.swing.table.TableCellRenderer;
import DisplayProject.Constants;
import DisplayProject.UIutils;
import DisplayProject.controls.ArrayField;
import DisplayProject.controls.MultiLineTextField;
import DisplayProject.table.ArrayFieldCellRenderer;
import DisplayProject.table.TextFieldCellRenderer;
import Framework.Array_Of_TextData;
import Framework.ErrorMgr;
import Framework.TextData;
/**
* A simple utility class that provides
* a number of helper methods to simulate Forte printing.
* @author Peter
* @author Craig Mitchell
*/
public class PrintUtilities {
private static PrinterJob currentJob;
private static PrintDocument printDoc;
private static PrintOptionsDesc defaultPrintOptions = null;
public static double defaultPrintMargin = 7.2; // expressed in points
/**
* The PrintDialog method displays your window system�s standard print dialogs. You have the choice between displaying the standard page setup dialog or the standard print job dialog.
* @param options
* @param showSetupDialog not implemented
* @param showJobDialog not implemented
* @return javax.swing.JOptionPane.OK_OPTION to open the file or javax.swing.JOptionPane.CANCEL_OPTION to cancel the dialog.
*/
public static int printDialog(PrintOptionsDesc options, boolean showSetupDialog, boolean showJobDialog){
if (currentJob == null){
currentJob = PrinterJob.getPrinterJob();
}
if (currentJob.printDialog()){
return javax.swing.JOptionPane.OK_OPTION;
} else {
return javax.swing.JOptionPane.CANCEL_OPTION;
}
}
public static PrinterJob getPrinterJob(){
if (currentJob == null){
currentJob = PrinterJob.getPrinterJob();
}
return currentJob;
}
/**
* The OpenPrintDocument method creates a new print document.
* When you want to begin printing, you must create a PrintDocument object by invoking the OpenPrintDocument method on your WindowSystem object.
* Once you have created a print document, you can print any number of pages as part of that document.
* @param printOptions
* @param docName
* @param hasCancelDialog not implemented
*/
public static PrintDocument openPrintDocument(PrintOptionsDesc printOptions, String docName, boolean hasCancelDialog){
printDoc = new PrintDocument();
printDoc.setPrintOptions(printOptions);
printDoc.setDocumentName(docName);
return printDoc;
}
public static PrintDocument openPrintDocument(PrintOptionsDesc printOptions, TextData docName, boolean hasCancelDialog){
return openPrintDocument(printOptions, docName.toString(), hasCancelDialog);
}
/**
* Converts the printing measurement "Point" to mils
*
* @param points
*/
public static int pointsToMils(double points) {
int mils = (int) points / 72 * 1000;
return mils;
}
/**
* Converts mils to points
* @param mils
*/
public static double milsToPoints(int mils) {
double points = mils / 1000 * 72;
return points;
}
/**
* Cancels the printing of a specified document
* @param document
*/
public static void cancelPrintDocument(PrintDocument document){
PrintUtilities.getPrinterJob().cancel();
printDoc = null;
}
/**
* This method expands the field for printing.
*/
public static void expandFieldForPrint(JComponent comp, boolean isRecursive, boolean removeScrollBars) {
UIutils.processGUIActions();
// --------------------------------------------------------------------
// Expand array fields
// --------------------------------------------------------------------
if (comp instanceof ArrayField) {
ArrayField af = (ArrayField)comp;
af.setVisibleRows(af.getRowCount());
if (removeScrollBars) {
((JScrollPane)af.getParent().getParent()).setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);
((JScrollPane)af.getParent().getParent()).setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_NEVER);
}
// Expand any text fields that are in the array field
for (int i=0; i<af.getColumnCount(); i++) {
TableCellRenderer cellRenderer = af.getCellRenderer(0, i);
if (cellRenderer instanceof ArrayFieldCellRenderer &&
((ArrayFieldCellRenderer)cellRenderer).getRenderer() instanceof TextFieldCellRenderer) {
((TextFieldCellRenderer)((ArrayFieldCellRenderer)cellRenderer).getRenderer()).setPrinting(removeScrollBars);
}
}
Container parent = af.getParent();
while (parent != null) {
if (parent instanceof JFrame) {
((JFrame)parent).validate();
((JFrame)parent).pack();
}
parent = parent.getParent();
}
}
// --------------------------------------------------------------------
// Expand text fields
// --------------------------------------------------------------------
else if (comp instanceof MultiLineTextField) {
MultiLineTextField tf = (MultiLineTextField)comp;
if (tf.getParent() != null && tf.getParent().getParent() instanceof JScrollPane) {
JScrollPane sp = (JScrollPane)tf.getParent().getParent();
sp.setSize(tf.getPreferredSize());
sp.setMinimumSize(tf.getPreferredSize());
sp.setPreferredSize(tf.getPreferredSize());
if (removeScrollBars) {
sp.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);
sp.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_NEVER);
}
}
Container parent = tf.getParent();
while (parent != null) {
if (parent instanceof JFrame) {
((JFrame)parent).validate();
((JFrame)parent).pack();
}
parent = parent.getParent();
}
}
// --------------------------------------------------------------------
// Remove the border on JScrollPanes
// --------------------------------------------------------------------
else if (comp instanceof JScrollPane) {
((JScrollPane)comp).setBorder(null);
}
// --------------------------------------------------------------------
// Recuse into the children
// --------------------------------------------------------------------
if (isRecursive) {
for (Component tmpComp : comp.getComponents()) {
if (tmpComp instanceof JComponent) {
PrintUtilities.expandFieldForPrint((JComponent)tmpComp, isRecursive, removeScrollBars);
}
}
}
UIutils.processGUIActions();
}
/**
* this method expands the JFrame for printing.
*/
public static void expandFieldForPrint(JFrame comp, boolean isRecursive, boolean removeScrollBars){
expandFieldForPrint(UIutils.getForm(comp), isRecursive, removeScrollBars);
}
/**
* Prints the document and closes it.
*/
public static void closePrintDocument(PrintDocument doc){
defaultPrintOptions = null;
PrinterJob printJob = getPrinterJob();
printJob.setPageable(doc);
try {
printJob.print();
printDoc = null;
} catch(PrinterException pe) {
RuntimeException errorVar = new RuntimeException(pe.getMessage(), pe);
ErrorMgr.addError(errorVar);
throw errorVar;
}
}
/**
* calculates the average character width based on the default font
* @param font
* @return size in mils
*/
public static int averageCharInMils(Font font){
int screenPixels = UIutils.averageCharacter(font);
int mils = screenPixels * 1000 / 96;
return mils;
}
/**
* calculates the default line height based on a font
* @param font
* @return size in mils
*/
public static int defaultLineHeight(Font font){
JLabel label = new JLabel();
FontMetrics fm = label.getFontMetrics(font);
int screenLineSize = fm.getHeight();
int mils = screenLineSize * 1000 / 96;
return mils;
}
/**
* returns the current print document. Returns null if there is no current document.
*/
public static PrintDocument currentPrintDocument(){
return printDoc;
}
/**
* Returns the default print options
*/
public static PrintOptionsDesc getDefaultPrintOptions() {
if (defaultPrintOptions == null) {
defaultPrintOptions = new PrintOptionsDesc();
}
PrinterJob pjob = PrinterJob.getPrinterJob();
PageFormat defaultPage = pjob.defaultPage();
Paper paper = new Paper();
double imagableWidth = defaultPage.getPaper().getWidth() - (defaultPrintMargin * 2);
double imagableHeight = defaultPage.getPaper().getHeight() - (defaultPrintMargin * 2);
// Swap the width and height if in landscape mode
if (defaultPrintOptions.getForteOrientation() == Constants.PO_LANDSCAPE) {
double tmpWidth = imagableWidth;
imagableWidth = imagableHeight;
imagableHeight = tmpWidth;
}
paper.setSize(defaultPage.getPaper().getWidth(), defaultPage.getPaper().getHeight());
paper.setImageableArea(defaultPrintMargin, defaultPrintMargin, imagableWidth, imagableHeight);
defaultPrintOptions.setPaper(paper);
return defaultPrintOptions;
}
/**
* The getPrinterList method retrieves the names of the printers currently defined on the system.
* @return Array of printer names
*/
public static Array_Of_TextData<TextData> getPrinterList(){
PrintService[] services = PrintServiceLookup.lookupPrintServices(null, null) ;
Array_Of_TextData<TextData> names = new Array_Of_TextData<TextData>();
for (PrintService service : services){
names.add(new TextData(service.getName()));
}
return names;
}
}