ContainerPrintable

Aus Byte-Welt Wiki
Zur Navigation springenZur Suche springen

<code=java> /*

* ContainerPrintable.java
* We can pass the container to be printed in the constructor.
* The printing is done in segments of height 10.
* We can adapt the segment height using method setSegmentHeight(..)
*/

import java.awt.*; import java.awt.print.*; import java.awt.geom.*; import java.util.logging.*; import javax.print.attribute.*; import javax.print.attribute.standard.*;

public class ContainerPrintable implements Printable {

   private Container container;//The container to print
   private int segmentHeight = 10;//The container's segment height
   private int totalWidth;//To save total width.
   private int last = -1;//The most recent page index asked to print
   private int segment = 0;//The next segment to print
   private final Rectangle clip = new Rectangle(0, 0, 0, 0);//To store an area to be printed
   private final Rectangle tempRect = new Rectangle(0, 0, 0, 0);
   static private PrintRequestAttributeSet attr;
   public ContainerPrintable(final Container container) {
       this.container = container;
       container.setBackground(Color.WHITE);
       totalWidth = container.getWidth();
   }
   public int print(final Graphics graphics, final PageFormat pageFormat, final int pageIndex)
           throws PrinterException {
       final int imgWidth = (int) pageFormat.getImageableWidth();
       final int imgHeight = (int) pageFormat.getImageableHeight();
       if (imgWidth <= 0) {
           throw new PrinterException("Width of printable area is too small.");
       }
       // the amount of vertical space available for printing the container
       int availableSpace = imgHeight;
       if (availableSpace <= 0) {
           throw new PrinterException("Height of printable area is too small.");
       }
       // we need a scale factor to fit the container's entire width on the page
       double scaleFactor = 1.0D;
       if (totalWidth > imgWidth) {
           scaleFactor = (double) imgWidth / (double) totalWidth;
       }
       while (last < pageIndex) {
           if (segment >= getSegmentCount()) {// if we are finished with all segments
               return NO_SUCH_PAGE;
           }
           int scaledHeight = (int) (availableSpace / scaleFactor);
           // calculate the area of the container to be printed for this page
           nextClip(scaledHeight);
           last++;
       }
       // translate into the coordinate system of the pageFormat
       Graphics2D g2d = (Graphics2D) graphics;
       g2d.translate(pageFormat.getImageableX(), pageFormat.getImageableY());
       // constrain the container output to the available space
       tempRect.x = 0;
       tempRect.y = 0;
       tempRect.width = imgWidth;
       tempRect.height = availableSpace;
       g2d.clip(tempRect);
       // if we have a scale factor, scale the graphics object to fit the entire width
       if (scaleFactor != 1.0D) {
           g2d.scale(scaleFactor, scaleFactor);
           // otherwise, ensure that the current portion of the container is centered horizontally
       } else {
           int diff = (imgWidth - clip.width) / 2;
           g2d.translate(diff, 0);
       }
       // store the old transform and clip for later restoration
       AffineTransform oldTrans = g2d.getTransform();
       Shape oldClip = g2d.getClip();
       // print the current section of the container
       g2d.translate(-clip.x, -clip.y);
       g2d.clip(clip);
       container.print(g2d);
       // restore the original transform and clip
       g2d.setTransform(oldTrans);
       g2d.setClip(oldClip);
       return PAGE_EXISTS;
   }
   private int getSegmentCount() {
       int height = container.getHeight();
       int count = height / segmentHeight;
       if (count * segmentHeight < height) {
           count++;
       }
       return count;
   }
   public void setSegmentHeight(final int segmentHeight) {
       this.segmentHeight = segmentHeight;
   }
   public int getSegmentHeight() {
       return segmentHeight;
   }
   private void nextClip(final int pageHeight) {
       clip.x = 0;
       clip.y += clip.height;// adjust clip to the top of the next set of segments
       clip.height = 0;// adjust clip height to be zero
       // fit as many segments as possible, and at least one
       int segmentCount = getSegmentCount();
       do {
           clip.height += segmentHeight;
           if (++segment >= segmentCount) {
               break;
           }
       } while (clip.height + segmentHeight <= pageHeight);
       clip.width = totalWidth;
   }
   static public void print(final Printable printable) {
       print(printable, true);
   }
   static public void print(final Printable printable, final boolean portrait) {
       print(printable, portrait, new Insets(10, 10, 10, 10));
   }
   static public void print(final Printable printable, final boolean portrait, final Insets insets) {
       PrinterJob pjob = PrinterJob.getPrinterJob();
       pjob.setPrintable(printable);
       // create an attribute set to store attributes from the print dialog
       if (attr == null) {
           attr = new HashPrintRequestAttributeSet();
           float leftMargin = insets.left;
           float rightMargin = insets.right;
           float topMargin = insets.top;
           float bottomMargin = insets.bottom;
           if (portrait) {
               attr.add(OrientationRequested.PORTRAIT);
           } else {
               attr.add(OrientationRequested.LANDSCAPE);
               leftMargin = insets.top;
               rightMargin = insets.bottom;
               topMargin = insets.right;
               bottomMargin = insets.left;
           }
           attr.add(MediaSizeName.ISO_A4);
           MediaSize mediaSize = MediaSize.ISO.A4;
           float mediaWidth = mediaSize.getX(Size2DSyntax.MM);
           float mediaHeight = mediaSize.getY(Size2DSyntax.MM);
           attr.add(new MediaPrintableArea(
                   leftMargin, topMargin,
                   (mediaWidth - leftMargin - rightMargin),
                   (mediaHeight - topMargin - bottomMargin), Size2DSyntax.MM));
       }
       if (pjob.printDialog(attr)) {
           try {
               pjob.print(attr);
           } catch (PrinterException ex) {
               Logger.getLogger(ContainerPrintable.class.getName()).log(Level.SEVERE, null, ex);
           }
       }
   }

} </code=java> <code=java> /*

* ContainerPrintableDemo.java
*
*/

import java.awt.*; import java.awt.event.*; import javax.swing.*;

public class ContainerPrintableDemo extends JFrame {

   private JButton btPrint;
   private JColorChooser colorChooser;
   public ContainerPrintableDemo() {
       super("ContainerPrintableDemo");
       setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
       btPrint = new JButton("Print...");
       colorChooser = new JColorChooser();
       btPrint.addActionListener(new ActionListener() {
           public void actionPerformed(ActionEvent evt) {
               ContainerPrintable.print(new ContainerPrintable(colorChooser));
           }
       });
       getContentPane().add(btPrint, BorderLayout.PAGE_START);
       getContentPane().add(colorChooser, BorderLayout.CENTER);
       pack();
       setLocationRelativeTo(null);
   }
   public static void main(final String[] args) {
       Runnable gui = new Runnable() {
           public void run() {
               new ContainerPrintableDemo().setVisible(true);
           }
       };
       //GUI must start on EventDispatchThread:
       SwingUtilities.invokeLater(gui);
   }

} </code=java>