我一直在寻找答案,但是找不到很好的教程。我正在使用Java itext生成pdf。我有一张桌子,上面打印了50多行,约占2页。在继续打印列表之前,我需要将上一页的最后5行打印到下一页。Example:row 31row 32row 33row 34row 35row 36--end of page 1--row 32row 33row 34row 35row 36row 37
关于如何执行此操作的任何想法?Currently it prints like this:row 35row 36--end of page 1--row 37row 38
代码:(专注于启动循环,不要介意那些标题)
PdfPTable table = new PdfPTable(4);
table.setWidthPercentage(97);
table.setWidths(new float[] {10, 45, 25, 25});
PdfPCell c1 = new PdfPCell(new Phrase("Logo", FontFactory.getFont(FontFactory.TIMES_ROMAN, 14)));
c1.setPadding(5);
c1.setHorizontalAlignment(Element.ALIGN_LEFT);
c1.setVerticalAlignment(Element.ALIGN_CENTER);
c1.setBorder(0);
c1.setColspan(4);
table.addCell(c1);
c1 = new PdfPCell(new Phrase("09/01/2013 - 09/15/2013", FontFactory.getFont(FontFactory.TIMES_ROMAN, 12)));
c1.setPadding(5);
c1.setHorizontalAlignment(Element.ALIGN_LEFT);
c1.setVerticalAlignment(Element.ALIGN_CENTER);
c1.setBorder(0);
c1.setColspan(4);
c1.setPaddingBottom(20);
table.addCell(c1);
//start header
c1 = new PdfPCell(new Phrase(" ", FontFactory.getFont(FontFactory.TIMES_ROMAN, 12)));
c1.setPaddingBottom(5);
c1.setHorizontalAlignment(Element.ALIGN_LEFT);
c1.setBackgroundColor(WebColors.getRGBColor("#99CCFF"));
c1.setBorder(1);
table.addCell(c1);
c1 = new PdfPCell(new Phrase("Name", FontFactory.getFont(FontFactory.TIMES_ROMAN, 12)));
c1.setPaddingBottom(5);
c1.setHorizontalAlignment(Element.ALIGN_LEFT);
c1.setBackgroundColor(WebColors.getRGBColor("#99CCFF"));
c1.setBorder(1);
table.addCell(c1);
c1 = new PdfPCell(new Phrase("Number", FontFactory.getFont(FontFactory.TIMES_ROMAN, 12)));
c1.setPaddingBottom(5);
c1.setHorizontalAlignment(Element.ALIGN_LEFT);
c1.setBackgroundColor(WebColors.getRGBColor("#99CCFF"));
c1.setBorder(1);
table.addCell(c1);
c1 = new PdfPCell(new Phrase("Amount", FontFactory.getFont(FontFactory.TIMES_ROMAN, 12)));
c1.setPaddingBottom(5);
c1.setHorizontalAlignment(Element.ALIGN_RIGHT);
c1.setBackgroundColor(WebColors.getRGBColor("#99CCFF"));
c1.setBorder(1);
table.addCell(c1);
//end header
//start for loop
for(int a=0; a<50; a++)
{
int border=0;
if(a%5==0)
{border=1;}
c1 = new PdfPCell(new Phrase((a+1)+"", FontFactory.getFont(FontFactory.TIMES_ROMAN, 12)));
c1.setHorizontalAlignment(Element.ALIGN_LEFT);
c1.setBorder(border);
c1.setPaddingBottom(5);
table.addCell(c1);
c1 = new PdfPCell(new Phrase("Last Name, First Name", FontFactory.getFont(FontFactory.TIMES_ROMAN, 12)));
c1.setHorizontalAlignment(Element.ALIGN_LEFT);
c1.setBorder(border);
c1.setPaddingBottom(5);
table.addCell(c1);
c1 = new PdfPCell(new Phrase("1", FontFactory.getFont(FontFactory.TIMES_ROMAN, 12)));
c1.setHorizontalAlignment(Element.ALIGN_CENTER);
c1.setBorder(border);
c1.setPaddingBottom(5);
table.addCell(c1);
c1 = new PdfPCell(new Phrase("1", FontFactory.getFont(FontFactory.TIMES_ROMAN, 12)));
c1.setHorizontalAlignment(Element.ALIGN_RIGHT);
c1.setBorder(border);
c1.setPaddingBottom(5);
table.addCell(c1);
}
//end for loop
subCatPart.add(table);
最佳答案
您不能使用document.add()
来实现。相反,您需要使用writeSelectedRows()
方法编写特定的行。例如,参见RepeatLastRows方法。
在此示例中,我有一个包含99行的表。如果我使用document.add()
将此表添加到文档中,它将需要3页,而第三页将仅显示3行。您希望此页面显示5行,比上一页重复2行。
假设我们有一个A4页面的页边距为36pt,这就是完成的过程。这意味着可用表面的尺寸为523乘770磅:
// we create a table that spans the width of the page and that has 99 rows
PdfPTable table = new PdfPTable(1);
table.setTotalWidth(523);
for (int i = 1; i < 100; i++)
table.addCell("row " + i);
请注意,我设置了总宽度。如果使用
writeSelectedRows()
而不指定宽度,则会出现异常。我们初始化一些参数:
PdfContentByte canvas = writer.getDirectContent();
int currentRowStart = 0;
int currentRow = 0;
int totalRows = table.getRows().size();
我们将创建一个循环,只要
currentRow
低于totalRows
,该循环就会继续:while (true) {
// available height of the page
float available_height = 770;
// how many rows fit the height?
while (available_height > 0 && currentRow < totalRows) {
available_height -= table.getRowHeight(currentRow++);
}
// we stop as soon as all the rows are counted
if (currentRow == totalRows)
break;
// we draw part the rows that fit the page and start a new page
table.writeSelectedRows(currentRowStart, --currentRow, 36, 806, canvas);
document.newPage();
currentRowStart = currentRow;
}
在此循环中,我们已经填充了两页:一页显示1至48行,另一页显示49至96行。当我们跳出循环时,currentRow为99,currentRowStart为96(这是该行的索引)第97行)。这意味着将仅显示第97、98和99行。我们想显示5行,因此我们相应地更改
currentRow
的值。if (currentRow - currentRowStart < 5)
currentRowStart = currentRow - 5;
table.writeSelectedRows(currentRowStart, currentRow, 36, 806, canvas);
请查看生成的PDF,您将看到第三页从第95行开始(该行已在第2页上显示)。
更新:我误以为我认为只有在最后一页上只有少数几行时才需要重复行。实际要求是每次拆分表时始终重复5行。
我已经稍微更新了我的原始示例。请参见RepeatLastRows2。您更改了
currentRowStart
的值,以便开始返回5行,但是您忘记了更新currentRow
的值。结果,您没有从可用高度中减去足够的空间。另外,如果只有5行(或更少)容纳单个页面,请一次又一次地重复相同的5行,以确保不会引入无限循环(或
ArrayIndexOutOfBoundsExceptions
)。