einfaches Drucken von Text (und ggf Bildern,gemischt)

kleinfritzchen

Aktives Mitglied
Hallo,
ich hab jetzt ein Inventur-Programm fast fertig . Was mir noch fehlt ist jetzt die Möglichkeit die Ergebnisse auszudrucken.
Kann mir mal jemand einen Tip geben wo ich hierzu deutsche Hilfe bekomme? oder mal einen Tip geben wie ich da rangehen kann?
Das Programm soll nachher die Daen aus einer Tabelle lesen und sie in Datensätzen zeilenweise ausdrucken. Vielleicht auch mit einer Kopfzeile die dann auch eine Grafik enthält.
Im Moment weis ich nicht wie ich vorgehen soll und in welcher Reihenfolge ich was abarbeiten muss.
Ziel ist es mindestens eine (evtl. mehrseitigen) Ausdruck der Tabelle zu bekommen.

schon mal im vorraus DANKE!

MfG Fritz
 
Hallo,

was ich mit meinem Halbwissenschon mitbekommen habe ist, dass Drucken in Java nicht gerade eine einfache Geschichte ist.
Da du sagst, du hast Tabellen würde sich meiner Meinung nach anbieten JTable zu verwenden. JTable hat schon eine Druckfunktion die sich einfach über table.print() (glaube ich) aufrufen lässt und dann ach akzeptable Ergebnisse liefert.

Gruß
 
Hallo,
so einfach scheint es nicht zu sein. Hier muss man anscheinend mit einer "Fabrikmethode" arbeiten und das zu druckende Objekt (also die Seite ) erst zusammenbauen.
so ganz verstanden hab ich das noch nicht aber ich krieg schon mal eine Textzeile auf das Blatt.
Im netz hab ich auch keine einfache erklährung gefunden. die Printmethode ist recht abstrakt gehalten und man muss noch eine menge definieren.
da muss ich wohl noch ein wenig suchen.... bis ich es verstanden hab.

;(
 
hallo,
hier mal 2 Teile die mir das drucken von Text ermöglichen:

teil 1 (Action Listener)
Java:
if (arg0.getSource() ==btnDrucken){
				datModel.speichern();
				pjob = PrinterJob.getPrinterJob();
			    if ( pjob.printDialog() == false )
			      return;
			    pjob.setPrintable( new TextPrintable() );
			    try {
					pjob.print();
				} catch (PrinterException e) {
					System.out.println("Fehler beim drucken");
					e.printStackTrace();
				}

und hier der "drucker..."
Java:
 class TextPrintable implements Printable
	  {
	    Font font = new Font( "Times", Font.PLAIN, 20 );
	    public int print( Graphics g, PageFormat pageFormat, int pageIndex )
	    {
	      if ( pageIndex >= 2 )
	        return Printable.NO_SUCH_PAGE;
	      g.setFont( font );
	      g.drawString( "Hallo auf Seite " + pageIndex, 200, 50 );
	      return Printable.PAGE_EXISTS;
	    }
	  }

Soweit sogut, aber wie kann ich jetzt ein Bild hinzufügen und welches Bildformat geht?
ich hab hier ein Logo im gif Format das ich einfügen möchte.
weis jemand iwe sowas geht???

MfG Fritz
 
Habe sowas mal mit diesem DocumentRenderer (findest du bei sun oder auch hier in der Suche) und einer JEditorPane gemacht. Steck da jetzt nicht mehr voll drin, der DocumentRenderer ist ein wenig verändert meine ich.

Hier mal ein funktionierenders Bsp.: Hab das jetzt extra zusammenbebastelt, wäre nett wenn du denn noch mal feedback geben könntest bzw. falls du dir was für die Kopf und Fußzeile überlegst dies auch hier veröffentlichen könntest.
Das Problem ist immer der Seitenumbruch, allerdings wenn die Tabellenzeilen immer die selbe höhe haben lässt sich da was basteln, dass man immer nach bestimmter Zeilenanzahl Kopf und Fußzeile einsetzt.
Schaus dir einfach mal an!
Du brauchst ein Bild namens Bild.gif welches in einen Ordner images liegt. Bei exportierter jar-Datei im selben Ordner wie die jar oder bei eclipse in selben Ordner wie der src Ordner.

Ach so, wenn man Druckt werden die Tabellenrahmen leider nicht angezeigt.


Java:
package printJEP;

public class Start {
	public static void main(String[] args) {
		new JPaneWindow();
	}
}



Java:
package printJEP;

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.print.PageFormat;
import java.awt.print.Paper;
import javax.swing.JEditorPane;
import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JScrollPane;
import javax.swing.WindowConstants;

	public class JPaneWindow{

			private static final long serialVersionUID = 1L;
			
			JEditorPane jEPane;
			HTMLText htmlText;

		JPaneWindow(){
			
			// Frame erstellen
			JFrame frame = new JFrame();
			frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
    		frame.setTitle("Titel");
    		
    		// Menübar mit Druckfunktion
    		JMenuBar menubar = new JMenuBar();
			JMenu menu1 = new JMenu("Datei");
			menubar.add(menu1);
		    JMenuItem menu1_0 = new JMenuItem("Drucken");
		    menu1_0.addActionListener(new MenuLauscher());
		    menu1.add(menu1_0);
			frame.setJMenuBar(menubar);

		    
			
		    jEPane = new JEditorPane();
			jEPane.setContentType("text/html");
//			textarea.setEditable();
			htmlText = new HTMLText();		
			jEPane.setText(htmlText.getText());
			JScrollPane scrol = new JScrollPane(jEPane);
    		frame.add(scrol);
    		frame.setExtendedState(JFrame.MAXIMIZED_BOTH);
    		jEPane.setCaretPosition(0);// Cursor in die erste Zeile setzen
    		frame.setVisible(true);
    	}	
		
		
		
 		class MenuLauscher implements ActionListener{

 			@Override
 			public void actionPerformed(ActionEvent arg0) {
 				
 				PageFormat pageFormat = new PageFormat();
 	            Paper a4paper = new Paper();
 	            double paperWidth = 8.26;
 	            double paperHeight = 11.69;
 	            a4paper.setSize(paperWidth * 72.0, paperHeight * 72.0);
 	            double leftMargin = 0.78; /* should be about 2cm */
 	            double rightMargin = 0.78;
 	            double topMargin = 0.78;
 	            double bottomMargin = 0.78;	 
 	            a4paper.setImageableArea(leftMargin * 72.0, topMargin * 72.0,
 	                    (paperWidth - leftMargin - rightMargin) * 72.0,
 	                    (paperHeight- topMargin - bottomMargin) * 72.0);
 	            pageFormat.setPaper(a4paper);
// 	            pageFormat.setOrientation(PageFormat.LANDSCAPE); 
 	            DocumentRenderer documentRenderer = new DocumentRenderer(pageFormat,htmlText.getPDF_Titel());
 	            documentRenderer.print(jEPane);
 			}		
 		}
	}


Java:
package printJEP;

import java.io.File;
	
	public class HTMLText{
		
		String getPDF_Titel(){
			return 	"" +
						"pdf-Titel" +
					"";	
		}
		
		String getText(){
			
			String text = "<table><table border=\"3\">"+
							"<tr>" +
							" <th>Über 1</th>"+
							"<th><font color=red>Über 2</font></th>"+
							"<th>Bild</th>"+
							"</tr>";
			
			for(int i=0; i<100; i++){
				text+=

					"<tr>"+
							"<td>Zelle1</td>"+
							"<td><font size =5><b> Zelle 2</b></font></td> " +
							"<td><img src=\"file:///"+ new File("").getAbsolutePath()+"\\images\\Bild.gif"+"\"><br></td>" +
					"</tr>";
			}
			
			text+="</table>";
			return 	text;
		}
	
	}


Java:
package printJEP;

import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.Shape;
import java.awt.print.PageFormat;
import java.awt.print.Printable;
import java.awt.print.PrinterException;
import java.awt.print.PrinterJob;
import javax.swing.JEditorPane;
import javax.swing.text.Document;
import javax.swing.text.PlainDocument;
import javax.swing.text.View;
import javax.swing.text.html.HTMLDocument;
 
public class DocumentRenderer implements Printable {
 
    protected int currentPage = -1; // Used to keep track of when
 
    // the page to print changes.
 
    protected JEditorPane jeditorPane; // Container to hold the
 
    // Document. This object will
    // be used to lay out the
    // Document for printing.
 
    protected double pageEndY = 0; // Location of the current page
 
    // end.
 
    protected double pageStartY = 0; // Location of the current page
 
    // start.
 
    protected boolean scaleWidthToFit = true; // boolean to allow control over
 
    // whether pages too wide to fit
    // on a page will be scaled.
 
    /*
     * The DocumentRenderer class uses pFormat and pJob in its methods. Note
     * that pFormat is not the variable name used by the print method of the
     * DocumentRenderer. Although it would always be expected to reference the
     * pFormat object, the print method gets its PageFormat as an argument.
     */
    protected PageFormat pFormat;
 
    protected PrinterJob pJob;
 
    /*
     * The constructor initializes the pFormat and PJob variables.
     */
    public DocumentRenderer(PageFormat pForm, String jobName) {
        pFormat = pForm;
        pJob = PrinterJob.getPrinterJob();
        pJob.setJobName(jobName);
    }
 
    /*
     * Method to get the current Document
     */
    public Document getDocument() {
        if (jeditorPane != null)
            return jeditorPane.getDocument();
        else
            return null;
    }
 
    /*
     * Method to get the current choice the width scaling option.
     */
    public boolean getScaleWidthToFit() {
        return scaleWidthToFit;
    }
 
    /*
     * pageDialog() displays a page setup dialog.
     */
    public void pageDialog() {
        pFormat = pJob.pageDialog(pFormat);
    }
 
    /*
     * The print method implements the Printable interface. Although Printables
     * may be called to render a page more than once, each page is painted in
     * order. We may, therefore, keep track of changes in the page being
     * rendered by setting the currentPage variable to equal the pageIndex, and
     * then comparing these variables on subsequent calls to this method. When
     * the two variables match, it means that the page is being rendered for the
     * second or third time. When the currentPage differs from the pageIndex, a
     * new page is being requested.
     * 
     * The highlights of the process used print a page are as follows:
     * 
     * I. The Graphics object is cast to a Graphics2D object to allow for
     * scaling. II. The JEditorPane is laid out using the width of a printable
     * page. This will handle line breaks. If the JEditorPane cannot be sized at
     * the width of the graphics clip, scaling will be allowed. III. The root
     * view of the JEditorPane is obtained. By examining this root view and all
     * of its children, printView will be able to determine the location of each
     * printable element of the document. IV. If the scaleWidthToFit option is
     * chosen, a scaling ratio is determined, and the graphics2D object is
     * scaled. V. The Graphics2D object is clipped to the size of the printable
     * page. VI. currentPage is checked to see if this is a new page to render.
     * If so, pageStartY and pageEndY are reset. VII. To match the coordinates
     * of the printable clip of graphics2D and the allocation rectangle which
     * will be used to lay out the views, graphics2D is translated to begin at
     * the printable X and Y coordinates of the graphics clip. VIII. An
     * allocation Rectangle is created to represent the layout of the Views.
     * 
     * The Printable Interface always prints the area indexed by reference to
     * the Graphics object. For instance, with a standard 8.5 x 11 inch page
     * with 1 inch margins the rectangle X = 72, Y = 72, Width = 468, and Height =
     * 648, the area 72, 72, 468, 648 will be painted regardless of which page
     * is actually being printed.
     * 
     * To align the allocation Rectangle with the graphics2D object two things
     * are done. The first step is to translate the X and Y coordinates of the
     * graphics2D object to begin at the X and Y coordinates of the printable
     * clip, see step VII. Next, when printing other than the first page, the
     * allocation rectangle must start laying out in coordinates represented by
     * negative numbers. After page one, the beginning of the allocation is
     * started at minus the page end of the prior page. This moves the part
     * which has already been rendered to before the printable clip of the
     * graphics2D object.
     * 
     * X. The printView method is called to paint the page. Its return value
     * will indicate if a page has been rendered.
     * 
     * Although public, print should not ordinarily be called by programs other
     * than PrinterJob.
     */
    public int print(Graphics graphics, PageFormat pageFormat, int pageIndex) {
        double scale = 1.0;
        Graphics2D graphics2D;
        View rootView;
        // I
        graphics2D = (Graphics2D) graphics;
        // II
        jeditorPane.setSize((int) pageFormat.getImageableWidth(),
                Integer.MAX_VALUE);
        jeditorPane.validate();
        // III
        rootView = jeditorPane.getUI().getRootView(jeditorPane);
        // IV
        if ((scaleWidthToFit)
                && (jeditorPane.getMinimumSize().getWidth() > pageFormat
                        .getImageableWidth())) {
            scale = pageFormat.getImageableWidth()
                    / jeditorPane.getMinimumSize().getWidth();
            graphics2D.scale(scale, scale);
        }
        // V
        graphics2D.setClip((int) (pageFormat.getImageableX() / scale),
                (int) (pageFormat.getImageableY() / scale), (int) (pageFormat
                        .getImageableWidth() / scale), (int) (pageFormat
                        .getImageableHeight() / scale));
        // VI
        if (pageIndex > currentPage) {
            currentPage = pageIndex;
            pageStartY += pageEndY;
            pageEndY = graphics2D.getClipBounds().getHeight();
        }
        // VII
        graphics2D.translate(graphics2D.getClipBounds().getX(), graphics2D
                .getClipBounds().getY());
        // VIII
        Rectangle allocation = new Rectangle(0, (int) -pageStartY,
                (int) (jeditorPane.getMinimumSize().getWidth()),
                (int) (jeditorPane.getPreferredSize().getHeight()));
        // X
        if (printView(graphics2D, allocation, rootView)) {
            return Printable.PAGE_EXISTS;
        } else {
            pageStartY = 0;
            pageEndY = 0;
            currentPage = -1;
            return Printable.NO_SUCH_PAGE;
        }
    }
 
    /*
     * print(HTMLDocument) is called to set an HTMLDocument for printing.
     */
    public void print(HTMLDocument htmlDocument) {
        setDocument(htmlDocument);
        printDialog();
    }
 
    /*
     * print(JEditorPane) prints a Document contained within a JEDitorPane.
     */
    public void print(JEditorPane jedPane) {
        setDocument(jedPane);
        printDialog();
    }
 
    /*
     * print(PlainDocument) is called to set a PlainDocument for printing.
     */
    public void print(PlainDocument plainDocument) {
        setDocument(plainDocument);
        printDialog();
    }
 
    /*
     * A protected method, printDialog(), displays the print dialog and
     * initiates printing in response to user input.
     */
    protected void printDialog() {
        if (pJob.printDialog()) {
            pJob.setPrintable(this, pFormat);
            try {
                pJob.print();
            } catch (PrinterException printerException) {
                pageStartY = 0;
                pageEndY = 0;
                currentPage = -1;
                System.out.println("Error Printing Document");
            }
        }
    }
 
    /*
     * printView is a recursive method which iterates through the tree structure
     * of the view sent to it. If the view sent to printView is a branch view,
     * that is one with children, the method calls itself on each of these
     * children. If the view is a leaf view, that is a view without children
     * which represents an actual piece of text to be painted, printView
     * attempts to render the view to the Graphics2D object.
     * 
     * I. When any view starts after the beginning of the current printable
     * page, this means that there are pages to print and the method sets
     * pageExists to true. II. When a leaf view is taller than the printable
     * area of a page, it cannot, of course, be broken down to fit a single
     * page. Such a View will be printed whenever it intersects with the
     * Graphics2D clip. III. If a leaf view intersects the printable area of the
     * graphics clip and fits vertically within the printable area, it will be
     * rendered. IV. If a leaf view does not exceed the printable area of a page
     * but does not fit vertically within the Graphics2D clip of the current
     * page, the method records that this page should end at the start of the
     * view. This information is stored in pageEndY.
     */
    protected boolean printView(Graphics2D graphics2D, Shape allocation,
            View view) {
        boolean pageExists = false;
        Rectangle clipRectangle = graphics2D.getClipBounds();
        Shape childAllocation;
        View childView;
 
        if (view.getViewCount() > 0) {
            for (int i = 0; i < view.getViewCount(); i++) {
                childAllocation = view.getChildAllocation(i, allocation);
                if (childAllocation != null) {
                    childView = view.getView(i);
                    if (printView(graphics2D, childAllocation, childView)) {
                        pageExists = true;
                    }
                }
            }
        } else {
            // I
            if (allocation.getBounds().getMaxY() >= clipRectangle.getY()) {
                pageExists = true;
                // II
                if ((allocation.getBounds().getHeight() > clipRectangle
                        .getHeight())
                        && (allocation.intersects(clipRectangle))) {
                    view.paint(graphics2D, allocation);
                } else {
                    // III
                    if (allocation.getBounds().getY() >= clipRectangle.getY()) {
                        if (allocation.getBounds().getMaxY() <= clipRectangle
                                .getMaxY()) {
                            view.paint(graphics2D, allocation);
                        } else {
                            // IV
                            if (allocation.getBounds().getY() < pageEndY) {
                                pageEndY = allocation.getBounds().getY();
                            }
                        }
                    }
                }
            }
        }
        return pageExists;
    }
 
    /*
     * Method to set the content type the JEditorPane.
     */
    protected void setContentType(String type) {
        jeditorPane.setContentType(type);
    }
 
    /*
     * Method to set an HTMLDocument as the Document to print.
     */
    public void setDocument(HTMLDocument htmlDocument) {
        jeditorPane = new JEditorPane();
        setDocument("text/html", htmlDocument);
    }
 
    /*
     * Method to set the Document to print as the one contained in a
     * JEditorPane. This method is useful when Java does not provide direct
     * access to a particular Document type, such as a Rich Text Format
     * document. With this method such a document can be sent to the
     * DocumentRenderer class enclosed in a JEditorPane.
     */
    public void setDocument(JEditorPane jedPane) {
        jeditorPane = new JEditorPane();
        setDocument(jedPane.getContentType(), jedPane.getDocument());
    }
 
    /*
     * Method to set a PlainDocument as the Document to print.
     */
    public void setDocument(PlainDocument plainDocument) {
        jeditorPane = new JEditorPane();
        setDocument("text/plain", plainDocument);
    }
 
    /*
     * Method to set the content type and document of the JEditorPane.
     */
    protected void setDocument(String type, Document document) {
        setContentType(type);
        jeditorPane.setDocument(document);
    }
 
    /*
     * Method to set the current choice of the width scaling option.
     */
    public void setScaleWidthToFit(boolean scaleWidth) {
        scaleWidthToFit = scaleWidth;
    }
}
 
Zuletzt bearbeitet:
Hallo
an dich Kalle Mett, werd dein Beispiel mal ausprobieren!
hab auch selber schon was gebastelt, da gehe ich über die Seitenhöhe in Pixel die ich ja über pageFormat bekomme. mit der Texthöhe. Aus diesen Daten kann ich mir dann die Anzahl Zeilen ausrechnen.
Was ich aer jetzt noch nicht hinkriege ist der Seitenumbruck damit ich dann auf der zweiten Seite auch die Kopfzeile und Fußzeile hab.
Hier in dem Prog. hab ich noch keine Fußzeile aber die kopfzele hab ich hingekriegt.
was ich übrigens festgestellt hab ist das man anscheinend keine NullPointerException auslösen kann und es deshalb besser ist keine While - Schleife zu verwenden!
der Ansatz den ich hier verwendet hab ist anscheinend nicht der passende genau wegen dem Problem mit dem SeitenUmbruch.
Hier mal was einfaches was mir auch schon ein Stück weiter geholfen hat:Drucken mit Java @ tutorials.de: Tutorials, Forum & Hilfe
Und für Text hier:Java ist auch eine Insel – 14.13 Drucken
(in der 9. Ausgabe ist leider nichts mehr über drucken)

Java:
class TextPrintable implements Printable
	  {
	    Font fText = new Font( "Times", Font.PLAIN, 12 );
	    Font ueberschrift=new Font("Arial",Font.BOLD,14);
	    int i=0;
	    int sBreite, sHoehe, lSRand,anzZ,zAbstand ;
	    FontMetrics o= getFontMetrics(fText);
	    
	    public int print( Graphics g, PageFormat pageFormat, int pageIndex )
	    {
	    lSRand=Integer.parseInt(getOption("LinkerRand"));
	    	sBreite=(int)pageFormat.getWidth()-lSRand;
	    	sHoehe=(int) pageFormat.getHeight();
	      anzZ=(sHoehe-80)/o.getHeight()/2;
	      zAbstand=o.getHeight();
	      int yPos=80;
	      //Ueberschrift
	      File d=new File(getOption("InventurPfad"));
	      String dName=d.getName();
	      String ueberText=dName.subSequence(0, dName.length()-4).toString();
	      System.out.println("Überschrift :"+ueberText);
	      
	      System.out.println(o.stringWidth(ueberText)+" breite");
	      g.setFont(ueberschrift);
	      g.drawString(ueberText, ((sBreite-lSRand)/2-(o.stringWidth(ueberText))/2), 40);
	    	if ( pageIndex >= 1 )
	        return Printable.NO_SUCH_PAGE;
	      g.setFont( fText );
	      double hoehe=50;
	      g.drawImage(scLogo, 20, 30, scLogo.getWidth(null),scLogo.getHeight(null),null);
	      g.drawLine(18, 60, 550, 60);//Waagerecht unter Logo
	      g.drawLine(100, 20, 100, 60);//Linie neben Logo senkrecht
	      g.drawLine(490,20,490,60);//senkrechte linie rechts
	      g.drawString("Seite "+pageIndex, 500, 52);
System.out.println(yPos+"  "+sHoehe+"  i: "+i+" getElementCount :"+(datModel.a.aListe.getElementCount()));
	      //	      g.drawString(pageFormat.getWidth()+"breit   "+
//	    		  pageFormat.getHeight()+" Höhe", 20, 400);
	      for (int i=0;i< (datModel.a.aListe.getElementCount());i++)
	      
	      {
	    	  
	    	  System.out.println(i);
	    	 // System.out.println(datModel.a.aListe.get(i).artNr);
	    	  g.setFont(fText);
	    	  g.drawString(datModel.a.aListe.get(i).artNr,
	    			  20,
	    			  yPos);
	    	  g.drawString(datModel.a.aListe.get(i).f3+"", 120,yPos);
	    	  g.drawString(datModel.a.aListe.get(i).einheit, 200, yPos);
	    		
	    		yPos=yPos+zAbstand;
	    		if (yPos>=sHoehe){
	    			
	    		}
	      }
	      System.out.println(pageFormat.getImageableHeight());
	      //g.drawString( "Hallo auf Seite " + pageIndex, 20, 50 );
	      return Printable.PAGE_EXISTS;
	    }
	  }
}
 
Hallo,
hab mal das Beispiel von Kalle Mett ausprobiert, sieht gut aus! da kann man was draus machen. Ich versteh zwar noch nicht alles aber das wesetliche hab ich verstanden.
Mit der Kopfzeile als eine Grafik muss ich noch ein bschen rumprobieren....

MfG Fritz
 
Ja do könnte man was machen, müsste man den Rand von oben verringern und die "Zeichenfläche" vergrößern.

Habe mir gestern mal diese PaperClips-Geschichte von Huecheln angesehen und die Beispiele durchlaufen lassen. Ist vll sogar noch einfacher da man ja dort immerhin schon mal Kopf und Fußzeile hat, wobei die Anordnung aber auch noch nicht so ganz optimal ist.
 
Hallo, bin am asteln und hab grad das problem das ich nicht weis wo ch die kopfzeile als Bild und die Fußzeile integrieren muss damit es funktionier das die jeweils auf jeder seite mitgedruckt werden.
kann mir da mal jemand helfen?
MfG Fritz:rtfm:
 

Zurück
Oben