2013-05-18 2 views
9

Ich arbeite an Itext 5 mit Java. Ich habe Seiten mit mehreren Tabellen mit dynamischen Zeilen. In einigen Fällen wird die letzte Zeile der Tabelle in die nächste Seite mit dem folgenden Header aufgeteilt. Ich verwende setHeaderRows() und setSkipFirstHeader(), um die Fortsetzung der nächsten Seite zu verwalten. Die letzte Zeile hat genug Platz, um auf eine frühere Seite zu passen. Ich möchte diese letzte Zeile auf der gleichen Seite statt auf der nächsten Seite einfügen.iText - vermeiden Sie die letzte Zeile, um Tabellen auf Seite nicht zu trennen, die zur nächsten Seite geteilt wird

Zum Beispiel wird auf Seite 1 die letzte Zeile in die erste Zeile der nächsten Seite aufgeteilt. Stattdessen möchte ich diese Zeile in Seite 1 anpassen, also eine zusätzliche Seite mit allen Leerzeichen speichern.

Ich versuchte mit setExtendLastRow(), aber es funktioniert nicht. Kann jemand dieses Problem beheben? Ich füge einen funktionierenden Beispielcode an.

public class ProposalItextSplitLastRow { 
public static void main(String[] args) { 
    try { 
     Document document = new Document(); 
     document.setPageSize(PageSize.LETTER); 
     document.setMargins(16, 14, 14, 14); 
     PdfWriter writer = PdfWriter.getInstance(document, new FileOutputStream("C:/SplitLastRow.pdf")); 
     document.open(); 
     document.setPageSize(PageSize.LETTER); 
     document.setMargins(16, 14, 42, 38); 

     for (int m = 1; m < 20; m++) { 

      int row = 0; 
      PdfPTable table = new PdfPTable(1); 
      table.setSpacingAfter(0); 
      table.setSpacingBefore(0); 
      table.setWidthPercentage(100); 

      table.setHeaderRows(1); 
      table.setSkipFirstHeader(true); 
      add(table, "Header Row continued " + m, BaseColor.LIGHT_GRAY, row++); 
      add(table, "Header Row normal " + m, BaseColor.LIGHT_GRAY, row++); 

      add(table, "Text Row 1 ", BaseColor.WHITE, row++); 
      add(table, "Text Row 2 ", BaseColor.WHITE, row++); 
      add(table, "Text Row 3 ", BaseColor.WHITE, row++); 

      addPadding(table); 

      document.add(table); 
     } 

     document.close(); 
    } catch (Exception de) { 
     de.printStackTrace(); 
    } 
} 

private static void add(PdfPTable table, String text, BaseColor color, int row) { 
    PdfPCell pdfCellHeader = new PdfPCell(); 
    pdfCellHeader.setBackgroundColor(color); 
    pdfCellHeader.addElement(new Paragraph(new Phrase(text))); 
    table.addCell(pdfCellHeader); 
} 

private static void addPadding(PdfPTable table) { 
    PdfPCell cell = new PdfPCell(); 
    cell.setFixedHeight(2f); 
    cell.setBorder(Rectangle.NO_BORDER); 
    cell.setColspan(table.getNumberOfColumns()); 
    table.addCell(cell); 
} 
} 

Antwort

6

Ich musste das Beispiel ausführen, um Ihre Frage zu verstehen. Sie haben mich verwirrt, indem Sie über einen Header gesprochen haben, der kein Header ist (die Zeilen mit "Header Row normal" sind keine Headerzeilen!) Und Ihr Verweis auf setExtendLastRow() hat auch nicht geholfen (zu erwähnen, dass diese Methode keinen Sinn ergibt) ich, es ist sehr verwirrend).

Dies gesagt, die Lösung für Ihr Problem ist ein Kinderspiel. Ich habe die Hauptklasse neu geschrieben:

public static void main(String[] args) { 
    try { 
     Document document = new Document(); 
     document.setPageSize(PageSize.LETTER); 
     document.setMargins(16, 14, 14, 14); 
     PdfWriter writer = PdfWriter.getInstance(document, 
       new FileOutputStream("SplitLastRow.pdf")); 
     document.open(); 
     document.setPageSize(PageSize.LETTER); 
     document.setMargins(16, 14, 42, 38); 

     for (int m = 1; m < 20; m++) { 

      int row = 0; 
      PdfPTable table = new PdfPTable(1); 
      table.setSpacingAfter(0); 
      table.setSpacingBefore(0); 
      table.setTotalWidth(document.right() - document.left()); 
      table.setLockedWidth(true); 

      table.setHeaderRows(1); 
      table.setSkipFirstHeader(true); 
      add(table, "Header Row continued " + m, BaseColor.LIGHT_GRAY, row++); 
      add(table, "Header Row normal " + m, BaseColor.LIGHT_GRAY, row++); 

      add(table, "Text Row 1 ", BaseColor.WHITE, row++); 
      add(table, "Text Row 2 ", BaseColor.WHITE, row++); 
      add(table, "Text Row 3 ", BaseColor.WHITE, row++); 

      addPadding(table); 
      if (writer.getVerticalPosition(true) - table.getRowHeight(0) - table.getRowHeight(1) < document.bottom()) { 
       document.newPage(); 
      } 
      document.add(table); 
     } 

     document.close(); 
    } catch (Exception de) { 
     de.printStackTrace(); 
    } 
} 

Vergewissern Sie sich eine Gesamtbreite anstelle eine Breite Prozentsatz und Schloss die Breite definieren. Wie dokumentiert (und wie common sense sagt Ihnen), ein PdfPTable Objekt nicht seine tatsächliche Breite, wenn Sie eine Breite Prozentsatz definieren. Es versteht sich von selbst, dass Sie die Höhe einer Tabelle nicht berechnen können, die ihre tatsächliche Breite nicht kennt.

Verwenden Sie dann getVerticalPosition() Methode, um die aktuelle Position des Cursors abzurufen, und überprüfen Sie, ob die ersten beiden Zeilen auf der Seite passen. Wenn sie vor dem Hinzufügen der Tabelle nicht auf eine neue Seite gehen. Wenn Sie überprüfen möchten, ob die vollständige Tabelle passt, verwenden Sie die Methode getTotalHeight() anstelle der Methode getRowHeight().

+1

Es hat perfekt funktioniert :) Vielen Dank. Ihre Hilfe wird gerne in Anspruch genommen. Entschuldigung für die Verwirrung mit meiner Frage. Ich habe es in den letzten Wochen gekämpft. Dies hat mein Problem mit der Vermeidung der ersten Zeile zum Schneiden von Tabellen auf Seitenaufteilung behoben, die unter http://stackoverflow.com/questions/16548001/itext-avoid-first-row-to-cut-tables-on-page-split veröffentlicht wurde. Nur Kuriositäten zu wissen, warum Ihre Lösung nicht mit table.setWidthPercentage() funktioniert. –

+1

Sie haben vielleicht eine Idee, wie Sie mein anderes Problem lösen können, die letzte Zeile nicht in die nächste Seite zu splitten (nicht in die letzte Zeile der Witwenwaisen). Das passiert mit meinem Code. Kopfzeile normalen 16 Textzeile 1 Textzeile 2 ----- Seitenumbruch ---- Kopfzeile fortgesetzt 16 Text Zeile 3 ich nach einer Lösung suchen nicht einen Seitenumbruch zu haben (split) und Druck Zeile 3 in der ersten Seite, wie Kopfzeile normalen 16 Textzeile 1 Textzeile 2 Text Zeile 3 –

+0

Warum sollte ich beantworten Sie eine Follow-up-Frage, die eine Antwort geschrieben wird, die nicht akzeptiert wird ? Außerdem: zusätzliche Fragen erfordern eine neue Frage. –

-1

Sie können

table.setSplitRows(false); 

tun, aber ich glaube, dass, wenn eine Zeile gibt, die es gewohnt wird nicht angezeigt passen einfach. Es ist einen Versuch wert, aber

+0

Diese Sache wird nicht funktionieren, um alle Tabellen auf einer Seite zusammen zu halten. –

8

Sie können table.setKeepRowsTogather(true);

table.setHeaderRows(1) auch alongwith es

setKeepRowsTogather() überprüft, ob es alle Zeilen Seite halten können, aber teilt die Zeilen, falls die Tabelle über mehrere Seiten erstreckt. In diesem Fall setzt setHeaderRows(1) die Kopfzeilen auf der nächsten Seite wieder.

+2

setKeepRowsTogather arbeitete für mich – wutzebaer

+0

Danke für Ihre Hilfe! Es funktionierte für mich table.setKeepRowsTogather (true) ;, aber in meiner iText-Version (5.5.5) existiert diese Funktion nicht: eigentlich ist es das Gegenstück, es ist table.setKeepTogether (true); – russellhoff

Verwandte Themen