iText5提取裁剪PDF时获取Acrobat不可见文本,如何让其忽略该隐藏文本?
问题:iText5提取裁剪PDF时会获取已舍弃的隐藏文本,如何忽略这些文本?
我有一份从大PDF裁剪出来的小型PDF文档,发现用自定义位置策略的iText5还是会提取到裁剪后被舍弃的所有文本,但这些文本在Acrobat Reader里完全看不到。请问怎么让iText5检测并忽略这类隐藏文本?
编辑1 - 之前链接的文档有误
编辑2 - 附上代码片段
public class MyLocationTextExtractionStrategy : LocationTextExtractionStrategy { public void RenderText(TextRenderInfo renderInfo) { string text = renderInfo.GetText(); } }
解决方案
这个问题其实很好理解:裁剪PDF大多只是给页面设置了裁剪框(Crop Box),相当于给文档加了个“可视窗口”,但原始文档里的文本并没有被真正删除——那些“隐藏”的文本只是在裁剪框之外,iText5默认的提取策略不会主动检查文本是否在可见区域内,所以会一股脑全提出来。
要解决这个问题,你只需要在自定义的提取策略里加个判断逻辑:只保留落在裁剪框范围内的文本就行。具体可以这么做:
步骤1:获取页面的裁剪框
在处理目标页面时,先从PdfReader里拿到该页面的裁剪框信息,如果没有设置裁剪框,就用媒体框(Media Box)替代,代码大概是这样:
PdfReader reader = new PdfReader("你的PDF文件路径"); int targetPage = 1; // 你要处理的页码 Rectangle cropBox = reader.GetCropBox(targetPage) ?? reader.GetMediaBox(targetPage);
步骤2:修改自定义提取策略,添加位置判断
调整你的MyLocationTextExtractionStrategy,在RenderText方法里先判断当前文本片段的位置是否和裁剪框有交集,只有符合条件的文本才交给父类处理。修改后的代码示例:
public class CroppedTextExtractionStrategy : LocationTextExtractionStrategy { private readonly Rectangle _visibleArea; public CroppedTextExtractionStrategy(Rectangle visibleArea) { _visibleArea = visibleArea; } public override void RenderText(TextRenderInfo renderInfo) { // 获取当前文本片段的完整边界矩形 Rectangle textBounds = renderInfo.GetDescentLine().GetBoundingRectangle(); textBounds.Merge(renderInfo.GetAscentLine().GetBoundingRectangle()); // 判断文本是否在可视区域内(有重叠或完全包含) if (_visibleArea.Intersects(textBounds)) { // 只有可视区域内的文本才进行提取 base.RenderText(renderInfo); } } }
步骤3:用新策略提取文本
在提取页面文本时,把拿到的裁剪框传入自定义策略即可:
using (PdfReader reader = new PdfReader("你的PDF文件路径")) { int targetPage = 1; Rectangle cropBox = reader.GetCropBox(targetPage) ?? reader.GetMediaBox(targetPage); ITextExtractionStrategy strategy = new CroppedTextExtractionStrategy(cropBox); string extractedText = PdfTextExtractor.GetTextFromPage(reader, targetPage, strategy); }
额外注意事项
- 如果你的PDF页面有旋转角度,记得要同步旋转裁剪框和文本的坐标,iText的
Rectangle类提供了Rotate()方法可以处理这个情况。 - 如果遇到文本片段部分在可视区域内的情况,上面的代码会提取整个片段;如果需要更精确地截断部分可见的文本,可能需要额外处理字符的位置,但大部分场景下,判断文本片段是否和裁剪框相交就足够满足需求了。
这样修改后,iText5就只会提取裁剪框内的可见文本,再也不会把那些被裁剪掉的隐藏内容带出来啦。
内容的提问来源于stack exchange,提问作者Sau001
相关产品推荐
相关产品推荐

