Java使用itext生成复杂数据的pdf的示例代码
作者:Java小王子呀
首先,什么是Itext
Apache iText 是一个开源 Java 库,支持 PDF 文档的开发和转换。
在本教程中,我们将学习如何使用 iText 开发可以创建、转换和操作 PDF 文档的 Java 程序。
Itext目前遵从AGPL开源协议,AGPL 可以说是最严格的 GPL 了,强传染性,即使是 RPC 调用也会被感染,不发行软件而是作为 web 服务对外提供也必须开放源代码
目前Itext有很多product开始收费,但你所需的功能基本上open source都能满足
特点:
以下是 iText 库的显着特点 −
- Interactive − iText 为你提供类(API)来生成交互式 PDF 文档。使用这些,你可以创建地图和书籍。
- Adding bookmarks, page numbers, etc − 使用 iText,你可以添加书签、页码和水印。
- Split & Merge − 使用 iText,你可以将现有的 PDF 拆分为多个 PDF,还可以向其中添加/连接其他页面。
- Fill Forms − 使用 iText,你可以在 PDF 文档中填写交互式表单。
- Save as Image − 使用 iText,你可以将 PDF 保存为图像文件,例如 PNG 或 JPEG。
- Canvas − iText 库为您提供了一个 Canvas 类,你可以使用它在 PDF 文档上绘制各种几何形状,如圆形、线条等。
- Create PDFs − 使用 iText,你可以从 Java 程序创建新的 PDF 文件。你也可以包含图像和字体。
下载地址:Examples
一 上依赖
<!-- ITEXTPDF 依赖 -->
<dependency>
<groupId>com.itextpdf</groupId>
<artifactId>itextpdf</artifactId>
<version>${com.itextpdf.version}</version>
</dependency>
<com.itextpdf.version>5.5.13.2</com.itextpdf.version>二 ctroller层
HttpServletResponse:用于将生成的 PDF 文件直接写入 HTTP 响应流中,以便客户端可以下载或查看 PDF 文件。
目前,方法声明抛出了 Exception,这会导致所有未捕获的异常都被抛出到客户端。为了提高代码的健壮性,建议捕获特定的异常,并根据不同的异常类型返回适当的 HTTP 状态码和错误信息。
例如,你可以使用 @ExceptionHandler 来捕获常见的异常,如 IOException、DocumentException 等,并返回 500 Internal Server Error 或其他适当的响应。
@PostMapping(value = "print/sorting", produces = MediaType.APPLICATION_PDF_VALUE)
@ApiOperation(value = "打印分拣清单(新)", produces = MediaType.APPLICATION_PDF_VALUE)
public void printSortingNew(@Valid @RequestBody SortingPrintRequest request, HttpServletResponse response){
crossdockSortingService.printSortingNew(request,response);
}三 Service层
按照业务逻辑从数据库获取数据并处理数据,放到合适的对象里
(这里主要是和业务相关,不必深究里面内容,最后能得出需要的数据传出即可)
@Override
public void printSorting(SortingPrintRequest request, HttpServletResponse response) throws IOException {
Crossdock crossdock1 = crossdockService.getByFieldValue(request.getOrderNo(), Crossdock::getOrderNo);
Set<String> idSet = Sets.newHashSet();idSet.add(crossdock1.getId());
// 集装箱编号/柜号、柜型
List<Crossdock> crossdockList = crossdockService.listByFieldValueSet(idSet, Crossdock::getId);
if (ObjectUtils.isEmpty(crossdockList)) {
throw new ApiException(ResultCode.PARAMES_INVALID);
}
// 统计快递、卡派、自提、存仓数量
List<CrossdockPlan> crossdockPlanByOrderList = crossdockPlanService.listByFieldValueSet(idSet, CrossdockPlan::getOrderId);
Map<String, List<CrossdockPlan>> crossdockPlanOrderIdMap = crossdockPlanByOrderList.stream().collect(Collectors.groupingBy(CrossdockPlan::getOrderId));
// 客户id、公司
// 客户(发件人)信息 customerVo
Set<String> customerIdSet = crossdockList.stream().map(Crossdock::getCustomerId).collect(Collectors.toSet());
Map<String, Customer> customerMap = customerService.mapByFieldValueSet(customerIdSet, Customer::getId);
// 箱数统计,分拣表
List<CrossdockSorting> crossdockSortingList = listByFieldValueSet(idSet, CrossdockSorting::getOrderId);
Map<String, List<CrossdockSorting>> crossdockSortingMap = crossdockSortingList.stream().collect(Collectors.groupingBy(CrossdockSorting::getOrderId));
Set<String> sortingIdSet = crossdockSortingList.stream().map(CrossdockSorting::getId).collect(Collectors.toSet());
List<CrossdockSortingItem> crossdockSortingItemList = crossdockSortingItemService.listByFieldValueSet(sortingIdSet, CrossdockSortingItem::getSortingId);
Map<String, List<CrossdockSortingItem>> crossdockSortingItemMap = crossdockSortingItemList.stream().collect(Collectors.groupingBy(CrossdockSortingItem::getSortingId));
// 公司信息
Set<String> companySet = crossdockList.stream().map(Crossdock::getCompanyId).collect(Collectors.toSet());
Map<String, Company> companyMap = companyService.mapByFieldValueSet(companySet, Company::getId);
// 拼接参数
List<ExportSortingVo> exportSortingVoList = new ArrayList<>();
Map<String, List<ExportSortingDetailVo>> exportSortingDetailVoMap = new HashMap<>(16);
for (Crossdock crossdock : crossdockList) {
ExportSortingVo exportSortingVo = new ExportSortingVo();
exportSortingVo.setKey(crossdock.getOrderNo());
exportSortingVo.setCabinetType(crossdock.getContainerType());
exportSortingVo.setCtnr(crossdock.getContainerNo());
exportSortingVo.setCompany(companyMap.containsKey(crossdock.getCompanyId()) ? companyMap.get(crossdock.getCompanyId()).getName() : null);
if (customerMap.containsKey(crossdock.getCustomerId())) {
exportSortingVo.setCustomerCode(customerMap.get(crossdock.getCustomerId()).getCode());
}
// 设置统计数量
if (crossdockPlanOrderIdMap.containsKey(crossdock.getId())) {
List<CrossdockPlan> crossdockPlanList = crossdockPlanOrderIdMap.get(crossdock.getId());
// 快递
Map<String, List<CrossdockPlan>> shippingTypeMap = crossdockPlanList.stream().collect(Collectors.groupingBy(CrossdockPlan::getShippingType));
if (shippingTypeMap.containsKey(CrossdockEnums.ShippingType.EXPRESS.name())) {
List<CrossdockPlan> expressCrossdockPlanList = shippingTypeMap.get(CrossdockEnums.ShippingType.EXPRESS.name());
BigDecimal expressAmount = expressCrossdockPlanList.stream().filter(crossdockPlan -> !ObjectUtils.isEmpty(crossdockPlan.getTotalAmount()))
.map(CrossdockPlan::getTotalAmount).reduce(BigDecimal.ZERO, BigDecimal::add);
exportSortingVo.setUps(expressAmount);
}
// 卡车
if (shippingTypeMap.containsKey(CrossdockEnums.ShippingType.TRUCK.name())) {
List<CrossdockPlan> truckCrossdockPlanList = shippingTypeMap.get(CrossdockEnums.ShippingType.TRUCK.name());
BigDecimal truckAmount = truckCrossdockPlanList.stream().filter(crossdockPlan -> !ObjectUtils.isEmpty(crossdockPlan.getTotalAmount()))
.map(CrossdockPlan::getTotalAmount).reduce(BigDecimal.ZERO, BigDecimal::add);
exportSortingVo.setTruck(truckAmount);
}
// 自提
if (shippingTypeMap.containsKey(CrossdockEnums.ShippingType.SELF.name())) {
List<CrossdockPlan> selfCrossdockPlanList = shippingTypeMap.get(CrossdockEnums.ShippingType.SELF.name());
BigDecimal selfAmount = selfCrossdockPlanList.stream().filter(crossdockPlan -> !ObjectUtils.isEmpty(crossdockPlan.getTotalAmount()))
.map(CrossdockPlan::getTotalAmount).reduce(BigDecimal.ZERO, BigDecimal::add);
exportSortingVo.setSelf(selfAmount);
}
// 总数
BigDecimal totalAmount = crossdockPlanList.stream().filter(crossdockPlan -> !ObjectUtils.isEmpty(crossdockPlan.getTotalAmount()))
.map(CrossdockPlan::getTotalAmount).reduce(BigDecimal.ZERO, BigDecimal::add);
exportSortingVo.setTotal(crossdock.getTotalAmount()); //这里设置的总箱数应该是转运单里面的总箱数
// 留仓/hold
BigDecimal warehouseAmount = crossdock.getTotalAmount().subtract(totalAmount);
exportSortingVo.setWarehouse(warehouseAmount);
}
exportSortingVoList.add(exportSortingVo);
// 设置分拣详细信息
List<ExportSortingDetailVo> exportSortingDetailVoList = new ArrayList<>();
if (crossdockSortingMap.containsKey(crossdock.getId())) {
List<CrossdockSorting> crossdockSortingByOrderIdList = crossdockSortingMap.get(crossdock.getId());
for (CrossdockSorting crossdockSorting : crossdockSortingByOrderIdList) {
if (crossdockSortingItemMap.containsKey(crossdockSorting.getId())) {
CrossdockPlan plan = crossdockPlanService.getByFieldValue(crossdockSorting.getSortingPlanRid(), CrossdockPlan::getSortingPlanRid);
List<CrossdockPlanGoods> planGoodsList = null;
if (plan != null) {
planGoodsList = crossdockPlanGoodsService.list(new QueryWrapper<CrossdockPlanGoods>().lambda()
.eq(CrossdockPlanGoods::getPlanId, plan.getId()));
}
// 箱子信息
List<CrossdockSortingItem> crossdockSortingItems = crossdockSortingItemMap.get(crossdockSorting.getId());
for (CrossdockSortingItem crossdockSortingItem : crossdockSortingItems) {
ExportSortingDetailVo exportSortingDetailVo = new ExportSortingDetailVo();
exportSortingDetailVo.setInstructions(crossdockSortingItem.getNote());
exportSortingDetailVo.setOrderNo(crossdockSortingItem.getPlNo());
exportSortingDetailVo.setBoxesNo(crossdockSortingItem.getPackageNum());
exportSortingDetailVo.setCbm(BigDecimal.ZERO);
if (CollectionUtils.isNotEmpty(planGoodsList)){
List<CrossdockPlanGoods> filterPlanGoodsList = planGoodsList.stream()
.filter(Objects::nonNull)
.filter(x -> Objects.equals(x.getFbaNumber(), crossdockSortingItem.getPlNo()))
.collect(Collectors.toList());
exportSortingDetailVo.setCbm(CollectionUtils.isNotEmpty(filterPlanGoodsList) ? filterPlanGoodsList.get(0).getCbm() : BigDecimal.ZERO);
}
exportSortingDetailVo.setPalletsNo(crossdockSorting.getInboundPallet());
exportSortingDetailVo.setStorageLocation(null);
exportSortingDetailVo.setSubtotalQuantity(crossdockSorting.getPackageNum());
if (plan != null && plan.getIsHold()) {
exportSortingDetailVo.setWarehouseCode(crossdockSorting.getSortingNote() + "-HOLD");
} else {
exportSortingDetailVo.setWarehouseCode(crossdockSorting.getSortingNote());
}
exportSortingDetailVoList.add(exportSortingDetailVo);
}
exportSortingDetailVoMap.put(crossdock.getOrderNo(), exportSortingDetailVoList);
}
}
}
}
complexFill(exportSortingVoList, exportSortingDetailVoMap, response);
}上面数据处理好放进去然后继续调用
public void complexFill(List<ExportSortingVo> baseInfoList, Map<String, List<ExportSortingDetailVo>> detailInfoMap, HttpServletResponse response) throws IOException {
byte[] pdfBytes = convertExcelToPdf(baseInfoList,detailInfoMap);
// 设置响应头
response.setContentType("application/pdf");
response.setHeader("Content-Disposition", "attachment; filename="+detailInfoMap.keySet().iterator().next()+".pdf");
// 获取响应输出流
OutputStream outputStream = response.getOutputStream();
outputStream.write(pdfBytes);
outputStream.flush();
outputStream.close();
//打印日志
PrintLogCreateRequest request = new PrintLogCreateRequest();
request.setPrintNo(detailInfoMap.keySet().iterator().next());
request.setPrintType(PrintEnums.type.SORTING.name());
printLogService.createPrintLog(request);
}捕获特定异常:目前,方法声明抛出了
IOException,但没有处理其他可能的异常(如NullPointerException或IllegalArgumentException)。建议捕获特定的异常,并根据不同的异常类型返回适当的错误信息。
private byte[] convertExcelToPdf(List<ExportSortingVo> baseInfoList,Map<String, List<ExportSortingDetailVo>> detailInfoMap) throws IOException{
Document document = new Document();
ByteArrayOutputStream pdfOutputStream = new ByteArrayOutputStream();
try {
PdfWriter writer = PdfWriter.getInstance(document, pdfOutputStream);
BaseFont bf = BaseFont.createFont(TEMPLATE_FONT, BaseFont.IDENTITY_H, BaseFont.NOT_EMBEDDED);
// 设置页边距
document.setMargins(1, 1, 10, 10);
document.open();
ExportSortingVo sorting = baseInfoList.get(0);
PdfPTable table = new PdfPTable(8); // 有8列
// 第一行
PdfPCell cell1 = new PdfPCell(new Paragraph("客户编号:"+sorting.getCustomerCode(),new Font(bf,12,Font.NORMAL)));
cell1.setColspan(1);
cell1.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell1);
PdfPCell cell2 = new PdfPCell(new Paragraph("总数",new Font(bf,12,Font.NORMAL)));
cell2.setColspan(1);
cell2.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell2);
PdfPCell cell3 = new PdfPCell(new Paragraph(" ",new Font(bf,12,Font.NORMAL)));
cell3.setColspan(1);
cell3.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell3);
PdfPCell cell4 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(sorting.getTotal()) ? StringUtils.EMPTY : sorting.getTotal().stripTrailingZeros().toPlainString(),new Font(bf,12,Font.NORMAL)));
cell4.setColspan(3);
cell4.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell4);
PdfPCell cell5 = new PdfPCell(new Paragraph("拆柜公司",new Font(bf,12,Font.NORMAL)));
cell5.setColspan(1);
cell5.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell5);
PdfPCell cell6 = new PdfPCell(new Paragraph(" ",new Font(bf,12,Font.NORMAL)));
cell6.setColspan(1);
cell6.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell6);
// 第二行
PdfPCell cell7 = new PdfPCell(new Paragraph("公司:"+sorting.getCompany(),new Font(bf,12,Font.NORMAL)));
cell7.setColspan(1);
cell7.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell7);
PdfPCell cell8 = new PdfPCell(new Paragraph("UPS/Fedex",new Font(bf,12,Font.NORMAL)));
cell8.setColspan(1);
cell8.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell8);
PdfPCell cell9 = new PdfPCell(new Paragraph(" ", new Font(bf, 12, Font.NORMAL)));
cell9.setColspan(1);
cell9.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell9);
PdfPCell cell10 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(sorting.getUps()) ? StringUtils.EMPTY : sorting.getUps().stripTrailingZeros().toPlainString(), new Font(bf, 12, Font.NORMAL)));
cell10.setColspan(3);
cell10.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell10);
PdfPCell cell11 = new PdfPCell(new Paragraph("拆柜码头", new Font(bf, 12, Font.NORMAL)));
cell11.setColspan(1);
cell11.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell11);
PdfPCell cell12 = new PdfPCell(new Paragraph(" ", new Font(bf, 12, Font.NORMAL)));
cell12.setColspan(1);
cell12.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell12);
// 第三行
PdfPCell cell13 = new PdfPCell(new Paragraph("柜号:"+sorting.getCtnr(),new Font(bf,12,Font.NORMAL)));
cell13.setColspan(1);
cell13.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell13);
PdfPCell cell14 = new PdfPCell(new Paragraph("留仓/Hold",new Font(bf,12,Font.NORMAL)));
cell14.setColspan(1);
cell14.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell14);
PdfPCell cell15 = new PdfPCell(new Paragraph(" ", new Font(bf, 12, Font.NORMAL)));
cell15.setColspan(1);
cell15.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell15);
PdfPCell cell16 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(sorting.getWarehouse()) ? StringUtils.EMPTY : sorting.getWarehouse().stripTrailingZeros().toPlainString(), new Font(bf, 12, Font.NORMAL)));
cell16.setColspan(3);
cell16.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell16);
PdfPCell cell17 = new PdfPCell(new Paragraph("拆柜开始时间", new Font(bf, 12, Font.NORMAL)));
cell17.setColspan(1);
cell17.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell17);
PdfPCell cell18 = new PdfPCell(new Paragraph(" ", new Font(bf, 12, Font.NORMAL)));
cell18.setColspan(1);
cell18.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell18);
// 第四行
PdfPCell cell19 = new PdfPCell(new Paragraph("柜式:"+sorting.getCabinetType(),new Font(bf,12,Font.NORMAL)));
cell19.setColspan(1);
cell19.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell19);
PdfPCell cell20 = new PdfPCell(new Paragraph("卡派",new Font(bf,12,Font.NORMAL)));
cell20.setColspan(1);
cell20.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell20);
PdfPCell cell21 = new PdfPCell(new Paragraph(" ", new Font(bf, 12, Font.NORMAL)));
cell21.setColspan(1);
cell21.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell21);
PdfPCell cell22 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(sorting.getTruck()) ? StringUtils.EMPTY : sorting.getTruck().stripTrailingZeros().toPlainString(), new Font(bf, 12, Font.NORMAL)));
cell22.setColspan(3);
cell22.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell22);
PdfPCell cell23 = new PdfPCell(new Paragraph("拆柜结束时间", new Font(bf, 12, Font.NORMAL)));
cell23.setColspan(1);
cell23.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell23);
PdfPCell cell24 = new PdfPCell(new Paragraph(" ", new Font(bf, 12, Font.NORMAL)));
cell24.setColspan(1);
cell24.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell24);
// 第五行
PdfPCell cell25 = new PdfPCell(new Paragraph(" ",new Font(bf,12,Font.NORMAL)));
cell25.setColspan(1);
cell25.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell25);
PdfPCell cell26 = new PdfPCell(new Paragraph("自提",new Font(bf,12,Font.NORMAL)));
cell26.setColspan(1);
cell26.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell26);
PdfPCell cell27 = new PdfPCell(new Paragraph(" ", new Font(bf, 12, Font.NORMAL)));
cell27.setColspan(1);
cell27.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell27);
PdfPCell cell28 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(sorting.getSelf()) ? StringUtils.EMPTY : sorting.getSelf().stripTrailingZeros().toPlainString(), new Font(bf, 12, Font.NORMAL)));
cell28.setColspan(1);
cell28.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell28);
PdfPCell cell29 = createBarcodeImage(writer, sorting.getKey());
cell29.setColspan(4);
cell29.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell29);
//第六行
PdfPCell cell31 = new PdfPCell(new Paragraph("订单号", new Font(bf, 12, Font.NORMAL)));
cell31.setColspan(1);
cell31.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell31);
PdfPCell cell32 = new PdfPCell(new Paragraph("箱子数量", new Font(bf, 12, Font.NORMAL)));
cell32.setColspan(1);
cell32.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell32);
PdfPCell cell33 = new PdfPCell(new Paragraph("体积", new Font(bf, 12, Font.NORMAL)));
cell33.setColspan(1);
cell33.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell33);
PdfPCell cell34 = new PdfPCell(new Paragraph("仓库代码", new Font(bf, 12, Font.NORMAL)));
cell34.setColspan(1);
cell34.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell34);
PdfPCell cell35 = new PdfPCell(new Paragraph("数量小计", new Font(bf, 12, Font.NORMAL)));
cell35.setColspan(1);
cell35.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell35);
PdfPCell cell36 = new PdfPCell(new Paragraph("存储位置", new Font(bf, 12, Font.NORMAL)));
cell36.setColspan(1);
cell36.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell36);
PdfPCell cell37 = new PdfPCell(new Paragraph("托盘数量", new Font(bf, 12, Font.NORMAL)));
cell37.setColspan(1);
cell37.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell37);
PdfPCell cell38 = new PdfPCell(new Paragraph("外箱标记或说明", new Font(bf, 12, Font.NORMAL)));
cell38.setColspan(1);
cell38.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell38);
//第七行
List<ExportSortingDetailVo> detailList = detailInfoMap.get(sorting.getKey());
//按照仓库代码的A-Z顺序来排序
detailList.sort(Comparator.comparing(ExportSortingDetailVo::getWarehouseCode, Comparator.nullsLast(Comparator.naturalOrder())));
Map<String, Long> warehouseCodeCountMap = detailList.stream().filter(Objects::nonNull).map(ExportSortingDetailVo::getWarehouseCode).filter(Objects::nonNull)
.collect(Collectors.groupingBy(Function.identity(),Collectors.counting()));
Map<String, Integer> firstOccurrenceMap = new HashMap<>();
for (int i = 0; i < detailList.size(); i++) {
ExportSortingDetailVo detail = detailList.get(i);
String warehouseCode = detail.getWarehouseCode();
if (warehouseCode != null && !firstOccurrenceMap.containsKey(warehouseCode)) {
firstOccurrenceMap.put(warehouseCode, i);
}
}
for (int i = 0; i < detailList.size(); i++) {
ExportSortingDetailVo detail = detailList.get(i);
PdfPCell cell39 = new PdfPCell(new Paragraph(detail.getOrderNo(), new Font(bf, 12, Font.NORMAL)));
cell39.setColspan(1);
cell39.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell39);
PdfPCell cell40 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(detail.getBoxesNo()) ? StringUtils.EMPTY : detail.getBoxesNo().stripTrailingZeros().toPlainString(), new Font(bf, 12, Font.NORMAL)));
cell40.setColspan(1);
cell40.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell40);
PdfPCell cell41 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(detail.getCbm()) ? StringUtils.EMPTY : detail.getCbm().stripTrailingZeros().toPlainString(), new Font(bf, 12, Font.NORMAL)));
cell41.setColspan(1);
cell41.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell41);
Integer i1 = firstOccurrenceMap.get(detail.getWarehouseCode());
Long l = warehouseCodeCountMap.get(detail.getWarehouseCode());
if (i1 == i) {
PdfPCell cell42 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(detail.getWarehouseCode()) ? StringUtils.EMPTY : detail.getWarehouseCode(), new Font(bf, 12, Font.NORMAL)));
cell42.setColspan(1);
cell42.setRowspan(Math.toIntExact(l));
cell42.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
cell42.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
table.addCell(cell42);
PdfPCell cell43 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(detail.getSubtotalQuantity()) ? StringUtils.EMPTY : detail.getSubtotalQuantity().stripTrailingZeros().toPlainString(), new Font(bf, 12, Font.NORMAL)));
cell43.setColspan(1);
cell43.setRowspan(Math.toIntExact(l));
cell43.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
cell43.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
table.addCell(cell43);
PdfPCell cell44 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(detail.getStorageLocation()) ? StringUtils.EMPTY : detail.getStorageLocation(), new Font(bf, 12, Font.NORMAL)));
cell44.setColspan(1);
cell44.setRowspan(Math.toIntExact(l));
cell44.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
cell44.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
table.addCell(cell44);
PdfPCell cell45 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(detail.getPalletsNo()) ? StringUtils.EMPTY : detail.getPalletsNo().stripTrailingZeros().toPlainString(), new Font(bf, 12, Font.NORMAL)));
cell45.setColspan(1);
cell45.setRowspan(Math.toIntExact(l));
cell45.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
cell45.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE);
table.addCell(cell45);
}
PdfPCell cell46 = new PdfPCell(new Paragraph(ObjectUtils.isEmpty(detail.getInstructions()) ? StringUtils.EMPTY : detail.getInstructions(), new Font(bf, 12, Font.NORMAL)));
cell46.setColspan(1);
cell46.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
table.addCell(cell46);
}
document.add(table);
} catch (DocumentException e) {
log.error("error!", e);
throw new ApiException(ResultCode.FAULT);
}
document.close();
return pdfOutputStream.toByteArray();
}上面代码就是一行行的把值塞进去,
值得一提的是行合并,也就是几行明细对应一行的内容
代码
按照仓库代码的A-Z顺序来排序 处
detailList中的ExportSortingDetailVo对象将按照warehouseCode的字母表顺序进行排序,null值排在最后。
warehouseCodeCountMap是一个Map<String, Long>,其中键是仓库代码,值是该仓库代码在detailList中出现的次数。firstOccurrenceMap是一个Map<String, Integer>,其中键是仓库代码,值是该仓库代码在detailList中第一次出现的索引位置。
看这里可能有点不明白,看到效果图相信你会恍然大悟的

四 条形码工具类
private PdfPCell createBarcodeImage(PdfWriter writer, String code) {
Barcode128 barcode = new Barcode128();
barcode.setCode(code);
barcode.setCodeType(Barcode128.CODE128);
barcode.setSize(12); // 设置条形码的字体大小
barcode.setBaseline(10); // 设置基线位置
barcode.setX(1.5f); // 设置条形码的宽度
barcode.setBarHeight(50f); // 设置条形码的高度
// 将条形码转换为 Image 对象
Image barcodeImage = barcode.createImageWithBarcode(writer.getDirectContent(), null, null);
PdfPCell cell = new PdfPCell(barcodeImage);
cell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER);
return cell;
}五 效果图

大概是上面这个样子
具体图表根据实际业务进行构建代码
以上就是Java使用itext生成复杂数据的pdf的示例代码的详细内容,更多关于Java itext生成pdf的资料请关注脚本之家其它相关文章!
