You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用C#读取PDF中手动添加的文本?iTextSharp读取失败解决方案

解决iTextSharp无法读取PDF手动添加文本的问题

你遇到的核心问题是:通过FoxIt Reader、Nuance PDF等工具手动添加的文本,大多以**PDF表单域(Form Field)或注释(Annotation)**的形式存储,而默认的LocationTextExtractionStrategy只会提取页面内容流中的原生文本,不会处理这些附加元素。以下是具体解决思路:

1. 提取表单域中的文本

很多PDF编辑器添加的文本会被保存为表单域,可通过AcroFields对象遍历读取:

string parsedText = string.Empty;
using (PdfReader reader = new PdfReader(pdfPath))
{
    // 提取页面原生文本
    ITextExtractionStrategy its = new LocationTextExtractionStrategy();
    parsedText = PdfTextExtractor.GetTextFromPage(reader, 1, its);

    // 提取表单域文本
    AcroFields fields = reader.AcroFields;
    foreach (string fieldName in fields.Fields.Keys)
    {
        string fieldValue = fields.GetField(fieldName);
        if (!string.IsNullOrEmpty(fieldValue))
        {
            // 将表单域文本追加到结果中,或单独处理目标发票编号
            parsedText += "\n" + fieldValue;
            // 可根据字段名或值特征筛选发票编号,比如字段名包含"InvoiceNo"等
        }
    }
}

2. 提取注释中的文本

如果文本是以自由文本注释(FreeText)或普通文本注释(Text)形式添加的,需要遍历页面的注释集合:

using (PdfReader reader = new PdfReader(pdfPath))
{
    for (int pageNum = 1; pageNum <= reader.NumberOfPages; pageNum++)
    {
        PdfDictionary pageDict = reader.GetPageN(pageNum);
        PdfArray annots = pageDict.GetAsArray(PdfName.ANNOTS);
        if (annots == null) continue;

        foreach (PdfObject annotObj in annots.ArrayList)
        {
            PdfDictionary annotDict = (PdfDictionary)PdfReader.GetPdfObject(annotObj);
            PdfName subtype = annotDict.GetAsName(PdfName.SUBTYPE);

            // 处理自由文本注释(常见的手动添加文本类型)
            if (PdfName.FREETEXT.Equals(subtype))
            {
                PdfString content = annotDict.GetAsString(PdfName.CONTENTS);
                if (content != null)
                {
                    string annotText = content.ToUnicodeString();
                    // 处理注释文本,比如匹配发票编号格式
                }
            }
            // 处理普通文本注释(便签类)
            else if (PdfName.TEXT.Equals(subtype))
            {
                PdfString content = annotDict.GetAsString(PdfName.CONTENTS);
                if (content != null)
                {
                    string annotText = content.ToUnicodeString();
                    // 处理注释文本
                }
            }
        }
    }
}

3. 优化编码处理

你原代码中的编码转换是冗余的,iTextSharp的GetTextFromPage和ToUnicodeString已经处理了Unicode编码,直接使用即可避免乱码问题。

注意事项

  • 不同PDF编辑器的文本存储逻辑可能不同,建议先通过PDF分析工具(如iText RUPS)查看目标文本的存储类型(表单域/注释),再针对性处理。
  • 可通过正则表达式匹配发票编号的格式(比如固定长度数字、前缀+数字等),快速定位目标内容。

内容的提问来源于stack exchange,提问作者Helyx

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.19 09:10:35