如何从iText 7.0.0的Document对象中检索元素用于PDF测试?
当然可以!在iText 7.0.0里,虽然Document的childElements是受保护字段没法直接访问,但官方提供了专门的API来获取元素的位置、尺寸这类布局信息,完全不用去碰那个受保护的属性。下面给你两种实用的方案:
方案1:通过Document渲染器直接获取元素布局信息
在文档生成过程中(还没写入到PDF文件前),可以通过Document的渲染器来遍历所有子元素的渲染实例,每个渲染器都能提供元素的占用区域数据。
示例代码如下:
// 假设你已经创建并填充了Document对象 Document document = ...; DocumentRenderer docRenderer = (DocumentRenderer) document.getRenderer(); IRootRenderer rootRenderer = docRenderer.getRootRenderer(); // 遍历根渲染器下的所有子元素渲染器 for (IElementRenderer childRenderer : rootRenderer.getChildRenderers()) { // 针对段落元素的例子,你可以根据需要判断其他类型(比如Div、Image等) if (childRenderer instanceof ParagraphRenderer) { ParagraphRenderer paraRenderer = (ParagraphRenderer) childRenderer; LayoutArea occupiedArea = paraRenderer.getOccupiedArea(); // 获取元素的坐标和尺寸(注意iText的Y轴是从页面底部往上计算的) float x = occupiedArea.getBBox().getX(); float y = occupiedArea.getBBox().getY(); float width = occupiedArea.getBBox().getWidth(); float height = occupiedArea.getBBox().getHeight(); System.out.printf("段落位置:(%.2f, %.2f),尺寸:%.2f×%.2f%n", x, y, width, height); } }
如果需要定位特定元素,还可以在添加元素时给它设置唯一ID,后续通过ID匹配:
// 添加元素时设置ID Paragraph targetPara = new Paragraph("我是需要检查的段落"); targetPara.setProperty(Property.ID, "target-para-id"); document.add(targetPara); // 后续查找时匹配ID for (IElementRenderer childRenderer : rootRenderer.getChildRenderers()) { if ("target-para-id".equals(childRenderer.getModelElement().getProperty(Property.ID))) { LayoutArea area = childRenderer.getOccupiedArea(); // 处理该元素的位置检查逻辑 } }
方案2:通过PdfDocument解析已渲染页面的元素信息
如果已经把Document写入到PdfDocument中,可以用PdfCanvasProcessor来解析页面内容,提取文本、图形等元素的位置信息,适合验证最终生成的PDF页面。
示例代码:
PdfDocument pdfDoc = ...; // 你的PdfDocument对象 for (int pageNum = 1; pageNum <= pdfDoc.getNumberOfPages(); pageNum++) { PdfPage page = pdfDoc.getPage(pageNum); // 自定义文本提取策略,获取文本位置 PdfCanvasProcessor processor = new PdfCanvasProcessor(new ITextExtractionStrategy() { @Override public void beginTextBlock() {} @Override public void endTextBlock() {} @Override public void renderText(TextRenderInfo renderInfo) { Rectangle textBBox = renderInfo.getBoundingBox(); String text = renderInfo.getText(); System.out.printf("文本「%s」位置:(%.2f, %.2f)%n", text, textBBox.getX(), textBBox.getY()); } @Override public String getResultantText() { return ""; } }); processor.processPageContent(page); }
需要注意的是,iText的页面坐标系Y轴原点在页面底部,向上为正方向,和日常的屏幕坐标系略有不同,检查时别搞混了~
内容的提问来源于stack exchange,提问作者berimbolo
相关产品推荐
相关产品推荐

