Drucken einer großen Swing-Komponente
Ich habe eine Swing-form mit einem benutzerdefinierten Tabelle in eine JScrollPane (es ist nur ein JPanel, nicht eine JTable Unterklasse), und ich bin versucht, es zu erhalten, zu drucken. Wenn ich senden Sie einfach das ganze Bild an den Drucker, der scroll-Bereich schneidet, und wenn ich die Größe des Rahmens ändern, um die Größe der Inhalte der scroll-Bereich, eine Art innere Barriere hält das JFrame immer mehr, als über 1100 Pixel groß.
Andere alternative wäre die Erstellung der content-Bereich des Dialogfelds, ohne die Anbringung an der Wurzel JFrame, weil die JPanel die Größe ist nicht beschränkt, in diesem Fall. Aber, um die Komponenten zu legen, sich selbst und die Größe, um Ihren richtigen Größen, die ich zu benötigen scheinen, um das Fenster displayable, was bedeutet, dass zumindest hinzufügen, um einen JFrame und aufrufenden JFrame.pack(), aber wieder, die 1100 pixel limit kommt zurück.
Hier ist mein code für das drucken der Komponente:
public static void print(final Component comp) {
final float SCALE = .5f;
PrinterJob job = PrinterJob.getPrinterJob();
job.setPrintable(new Printable() {
public int print(Graphics g, PageFormat pf, int page)
throws PrinterException
{
if (page * pf.getImageableHeight() >= SCALE * comp.getHeight())
return NO_SUCH_PAGE;
((Graphics2D)g).translate(pf.getImageableX(), pf.getImageableY()
- page * pf.getImageableHeight());
((Graphics2D)g).scale(SCALE, SCALE);
comp.printAll(g);
return PAGE_EXISTS;
}
});
if (job.printDialog())
try { job.print(); }
catch (PrinterException ex) {}
}
Wenn ich dies Tue, wird die Komponente hat die Größe null:
JPanel c = createPanel(); //This JPanel has a JScrollPane in it with its
//preferredSize equal to that of its viewport component
//(which is not what I do to show the dialog normally)
print(c);
Wenn ich dies Tue, wird die Komponente hat die richtige Größe, aber druckt als solide Grau, weil die sub-Komponenten wurden nicht gelegt:
JPanel c = createPanel();
c.setSize(c.getPeferredSize());
print(c);
Diese scheinen nicht zu einen Unterschied machen:
JPanel c = createPanel();
c.validate();
c.revalidate();
c.repaint();
print(c);
Dies ist das panel größer, aber es hält etwa eine Seite und eine Hälfte groß (1100px):
JPanel c = createPanel();
JFrame f = new JFrame();
f.setContentPane(c);
f.pack();
print(c);
Ich bin running out of Permutationen hier. Weiß jemand, entweder (a) so ändern Sie die OS maximale frame-Größe, (b) wie layout und Farbe ein off-screen-Komponente, oder (c) drucken einer Swing Komponente, die direkt, ohne es zu malen (?). Hilfe ist willkommen.
- d) warum möchten Sie diese ausdrucken? JScrollPane können Sie sehen, dieses große Ding auf dem Bildschirm durch scrollen. Können Sie definieren andere Ansicht für Ihre benutzerdefinierte Tabelle die Daten, die es macht, Druck-freundlich?
- C auf der rechten Seite sehe ich einige Verwandte post, dort sind links/tutorials zum drucken von 2D-Grafiken und Text JComponents auch, wenn ich das richtig verstanden, dein problem ist berechnen paper DPI versus Pixel (immer) von der sichtbaren Container (JScrollPane mit unbekannten Inhalt)
- Ich habe keine Probleme mit unvollständigen Informationen - ich kann die Größe meiner Komponenten nur in Ordnung. Das problem ist mit der Malerei - ich bekomme keine undisplayable Komponenten zu malen (wenig überraschend).
- die Idee ist, dass ich nur die form selbst, und drucken Sie es, anstatt zu erstellen, eine andere version der Formular-Drucker-freundlich. In jedem Fall, ersetzen die JScrollPane mit deren Inhalt direkt in das panel wird nicht funktionieren, aus den gleichen Gründen. Nach dem Austausch, der Inhaltsbereich wird riesig sein, und es wird gequetscht, bis Größe, wenn es gemacht wird, Kš Onnen in einem JFrame (auch wenn nichts gibt es in der layout).
Du musst angemeldet sein, um einen Kommentar abzugeben.
Mithilfe Ihrer benutzerdefinierten panel
paint()
Methode, Rendern von Inhalt in einemBufferedImage
.Nachtrag: Hier ist ein vollständigeres Beispiel der Ansatz, die einfach skaliert die Komponente um die Hälfte. Sie werden wollen zu erhalten, die das Seitenverhältnis in Ihrer tatsächlichen Anwendung.
Wie gezeigt hier, können Sie die Größe des rendering zu passen, die Ziel -
MediaPrintableArea
, oder verwenden SiegetSubimage()
teilen der Inhalte in die Seiten wie gewünscht.getPreferredSize()
geplant und die Skalierung nachdemsetVisible()
; ich habe erweitert das obige Beispiel.JScrollPane
. Wenn Sie versuchen, jede Komponente ist ein direkter Nachkomme derJFrame
(wie Ihre content-Bereich, wie ich es vorher getan hat), wird es nicht werden dürfen beliebig groß sein.haben Sie auf drucken, um das Bauteil ohne scrollpane. die scrollpane wird immer druckt nur den sichtbaren Inhalt.
wenn Sie nicht Zugang zu den createPanel () - Methode, und die Platte, die von dieser Methode enthält nur die scrollpane, können Sie die Komponente, die der scrollpane-Komponente enthält, in der folgenden Weise:
aber wenn Ihr Daten-format als Tabelle, können Sie auch über die Verwendung der JTable. die JTable hat einen eigenen leistungsstarken print () - Methode.
weitere infos unter http://download.oracle.com/javase/tutorial/uiswing/misc/printtable.html
Da eine Komponente in eine JScrollPane kann beliebige Größe, sogar, nachdem es gemacht wird Darstellbare, Meine Lösung ist, zu versuchen, diese:
so, dass ich überprüfen kann, ob das JPanel, ohne dass es die Größe begrenzt auf die maximale Größe eines JFrame. Es hat auch die "unendliche Auflösung" schauen Sie auf die Schriftarten, und die Dinge, die Sie erhalten, drucken Sie die Komponenten direkt, ohne double-buffering, wie trashgod vorgeschlagen.
getContentPane()
;add()
weitergeleitet vonJFrame
.JFrame
's eigeneadd()
Methode als eine Frage der Konvention, weil es kann verwirrend sein für diejenigen, die nicht erkennen, dass Sie Synonyme sind (das zeigt, dass das tatsächliche Verhalten ein wenig deutlicher).print(Component)
Methode, in der OP.Sie in Ihrer Frage erwähnt, dass Sie vielleicht brauchen, um zu drucken, eine unsichtbare Komponente. Wie dies funktioniert, ist hier gezeigt von Java42, ich neu angeordnet, es ein wenig:
Wenn Sie noch brauchen, um mehrere Seiten zu drucken, können Sie kombinieren diese Lösung mit meinem Antwort auf so drucken Sie ein
Component
, um mehrere Seiten