Я хочу создать таблицу с повторяющимися заголовками, как изображение, которое я прикрепил к своему сообщению.
Я хочу заполнить первые три столбца слева до конца таблицы, а затем заполнить вторые три столбца справа от таблицы.
Я использовал одну таблицу с 6 столбцами, как показано на странице. Я получил данные из базы данных в соответствии с порядком дат, и я хочу разместить свои данные в таблице, как на картинке.
Я могу создать таблицу с помощью iText в java, но я не знаю, как создать таблицу с этим стилем с помощью iText. пожалуйста, помогите мне, если это возможно.




Это относительно просто.
Сначала я создал класс, представляющий одну запись данных.
static class Record{
public String firstname;
public String lastname;
public Record(String firstname, String lastname){
this.firstname = firstname;
this.lastname = lastname;
}
public String getFirstname(){return firstname;}
public String getLastname(){return lastname;}
public boolean equals(Object o){
if (o instanceof Record){
Record r = (Record) o;
return r.firstname.equals(firstname) && r.lastname.equals(lastname);
}
return false;
}
}
Я также создал метод, который случайным образом генерирует подобные объекты, используя персонажей Симпсонов.
private static Random RANDOM = new Random(System.currentTimeMillis());
public Record randomRecord(){
String[] fn = {"Marge", "Homer", "Bart", "Lisa", "Nelson", "Apu", "Doris", "Seymour"};
String[] ln = {"Bouvier", "Simpson", "Muntz", "Nahasapeemapetilan", "Skinner"};
return new Record(fn[RANDOM.nextInt(fn.length)], ln[RANDOM.nextInt(ln.length)]);
}
Код для создания таблицы выглядит так:
List<Record> recordList = new ArrayList<>();
for(int i=0;i<17;i++)
recordList.add(randomRecord());
File outputFile = getOutputFile();
PdfDocument pdfDocument = new PdfDocument(new PdfWriter(outputFile));
Document layoutDocument = new Document(pdfDocument);
int numberOfItemsInFirstHalf = (int) Math.ceil(recordList.size() / 2.0);
Table table = new Table(new float[]{0.16f, 0.16f, 0.16f, 0.16f, 0.16f, 0.16f});
// header
for(int i=0;i<2;i++) {
table.addCell(new Cell().add(new Paragraph("Number")).setBackgroundColor(new DeviceRgb(74,189,172)));
table.addCell(new Cell().add(new Paragraph("Firstname")).setBackgroundColor(new DeviceRgb(74,189,172)));
table.addCell(new Cell().add(new Paragraph("Lastname")).setBackgroundColor(new DeviceRgb(74,189,172)));
}
// table
for(int i=0;i<numberOfItemsInFirstHalf;i++){
Record r0 = recordList.get(i);
Record r1 = (i+numberOfItemsInFirstHalf) < recordList.size() ? recordList.get(i + numberOfItemsInFirstHalf) : null;
table.addCell(new Cell().add(new Paragraph((i + 1)+"")));
table.addCell(new Cell().add(new Paragraph(r0.getFirstname())));
table.addCell(new Cell().add(new Paragraph(r0.getLastname())));
if (r1 == null){
table.addCell(new Cell().add(new Paragraph("")));
table.addCell(new Cell().add(new Paragraph("")));
table.addCell(new Cell().add(new Paragraph("")));
}else{
table.addCell(new Cell().add(new Paragraph((i + numberOfItemsInFirstHalf + 1)+"")));
table.addCell(new Cell().add(new Paragraph(r1.getFirstname())));
table.addCell(new Cell().add(new Paragraph(r1.getLastname())));
}
}
layoutDocument.add(table);
pdfDocument.close();
который создает следующий PDF-документ:
Да, этот код явно не учитывает разбиение на страницы. Если вы этого хотите, вам нужно будет отслеживать, где разбита таблица. Но основной принцип останется прежним.
Спасибо. Есть ли способ узнать, где разбита таблица?
При добавлении элемента IE в документ вы можете запросить у средства визуализации его дочерние элементы. Если таблица разделена, вы ожидаете увидеть SplitRenderer.
Я поискал в сети, но не смог найти ни одного примера, который используется SplitRenderer. Я новичок, и до сих пор я использовал простую структуру iText, поэтому я ничего не знаю о SplitRenderer, но я стараюсь изо всех сил. Большое спасибо.
Я не совсем понял, как вы хотите, чтобы ваша таблица обрабатывалась при разделении, и предположил, что вы ищете макет из двух столбцов. В этом случае для вас есть предопределенный класс ColumnDocumentRenderer. Если установлено в экземпляре документа, это позволяет размещать содержимое документа в столбцы.
Итак, я определил столбцы:
Rectangle pageSize = pdfDocument.getDefaultPageSize();
Rectangle[] areas = new Rectangle[2];
areas[0] = new Rectangle(36, 36, ((float) pageSize.getWidth() / 2) - 35.75f, pageSize.getHeight() - 72);
areas[1] = new Rectangle((float) pageSize.getWidth() / 2 - 0.25f, 36, ((float) pageSize.getWidth() / 2) - 35.75f , pageSize.getHeight() - 72);
Затем я применил средство визуализации к экземпляру документа:
layoutDocument.setRenderer(new ColumnDocumentRenderer(layoutDocument, areas));
Результат на разделении выглядит так:

Полный код:
@Test
public void tableTest02() throws Exception {
String outFileName = destinationFolder + "tableTest02.pdf";
String cmpFileName = sourceFolder + "cmp_tableTest02.pdf";
PdfDocument pdfDocument = new PdfDocument(new PdfWriter(outFileName));
Document layoutDocument = new Document(pdfDocument);
Table table = new Table(3);
table.setWidth(UnitValue.createPercentValue(100));
Rectangle pageSize = pdfDocument.getDefaultPageSize();
Rectangle[] areas = new Rectangle[2];
areas[0] = new Rectangle(36, 36, ((float) pageSize.getWidth() / 2) - 35.75f, pageSize.getHeight() - 72);
areas[1] = new Rectangle((float) pageSize.getWidth() / 2 - 0.25f, 36, ((float) pageSize.getWidth() / 2) - 35.75f , pageSize.getHeight() - 72);
layoutDocument.setRenderer(new ColumnDocumentRenderer(layoutDocument, areas));
// header
for(int i=0;i<1;i++) {
table.addHeaderCell(new Cell().add(new Paragraph("Number")).setBackgroundColor(new DeviceRgb(74,189,172)));
table.addHeaderCell(new Cell().add(new Paragraph("Firstname")).setBackgroundColor(new DeviceRgb(74,189,172)));
table.addHeaderCell(new Cell().add(new Paragraph("Lastname")).setBackgroundColor(new DeviceRgb(74,189,172)));
}
// table
for(int i=0;i<500;i++){
table.addCell(new Cell().add(new Paragraph((i + 1)+"")));
table.addCell(new Cell().add(new Paragraph("Hello")));
table.addCell(new Cell().add(new Paragraph("World")));
}
layoutDocument.add(table);
pdfDocument.close();
Assert.assertNull(new CompareTool().compareByContent(outFileName, cmpFileName, destinationFolder, "diff"));
}
Сложным моментом было свернуть границы таблицы, но, увеличив ширину на 0,25f и переместив правый столбец на 0,25f влево, я добился того, чтобы границы были размещены одна на другой.
Я прикрепил изображение к своему первому посту, которое показывает стиль таблицы, который мне нужен. Я снова загрузил стиль, который мне нужен, по следующему адресу: ufile.io/uppi0. Я хочу, чтобы этот стиль был на каждой странице, например, вторая страница начинается с номера 42 до 82 и так далее.
1) То есть под заголовком повторяющийся вы имеете в виду, что заголовок должен повторяться только на первой странице? 2) Предположим, что на странице можно разместить 20 строк. Какого результата вы ожидаете: а) или б)? а) 1 11 \ n 2 12 \ n ...... \ n 10 20 \ n ПЕРЕРЫВ 21 31 \ n 22 32 \ n ........ \ n 30 40 \ nb) 1 21 \ n 2 22 \ n ...... \ n 10 30 \ n ПЕРЕРЫВ 11 31 \ n 12 32 \ n ........ \ n 20 40 \ n
Я имею в виду, что на каждой странице у меня есть таблица с этими столбцами: номер, имя, семья, номер, имя, семья. Затем я хочу заполнить их точно так же, как рисунок, который я прикрепляю, и точную нумерацию, которая показана на рисунке, и заполнить таблицу этим шаблоном (как показано на рисунке), пока данные не будут завершены. Другими словами, я хочу иметь 41 запись на первой странице в стиле, показанном на рисунке, и 41 запись на второй странице и так далее.
Хорошо, тогда код, который я предоставил в ответе, вам поможет.
Нет, это не так, потому что он создал одну таблицу с 3 столбцами, а не с 6 столбцами, как я сказал, и пронумеровав каждую строку. Это совсем не соответствовало моему стилю.
Большое спасибо за ответ. Я проверил ваш код, но результат не соответствует моему запросу. например, если у меня есть 250 записей, записи разделены на две страницы, и номера расположены друг под другом, а не рядом друг с другом. На первой странице последнее число - 53, а первое число второй страницы - 54, и это неверно. Я хочу, чтобы на первой странице была 54-я запись, сразу после 53 во вторых трех столбцах справа.