C#/.NET 使用 Spire.PDF 创建符合 ISO 标准的 PDF/UA 文档

落日邮差
落日邮差
发布时间:2026-10-15 | 3人浏览过
原创

PDF/UA(ISO 14289-1)是为提升文档可访问性而制定的国际标准,其核心在于使用带有明确语义的 PDF 标签(Tagged PDF)正确标记内容。对于开发人员而言,在 .NET 环境下利用 Spire.PDF 等成熟 API 库,能够高效地构建符合该规范的结构化文档。本文将详细解析创建流程并提供 C# 与 VB.NET 的实现代码。

PDF/UA 标准概述

PDF/UA,即 Universally Accessible PDF,于 2012 年 8 月作为 ISO 14289-1 标准正式发布。它专为“带标签的 PDF 文档”设定了严格规范,确保残障人士也能通过辅助技术无障碍地阅读文档。

该标准要求:

  • 语义化标签:所有对象必须有适当的标签。
  • 逻辑顺序:标签必须按照阅读的逻辑顺序排列。
  • 验证机制:需符合特定的兼容性规则(如语言设定、替代文本等)。

C#/.NET 创建实现方案

要实现合规的 PDF/UA 文档,通常需要使用第三方 PDF 操作库。以 Spire.PDF for .NET 为例,可以通过编程方式构建 PDF 的结构树(Structure Tree),并添加元数据以通过验证。

准备工作

  1. 环境配置:在 Visual Studio 项目中安装 Spire.PDF NuGet 包,或下载包含 Spire.Pdf.dll 的安装包并手动引用本地路径。
  2. 核心空间:主要涉及 Spire.Pdf.Interchange.TaggedPdf 命名空间,用于处理文档结构和标签。

第 1 步:初始化文档并开启 Tagged 模式

首先创建文档对象,并实例化 PdfTaggedContent。这一步至关重要,因为它是后续所有标签操作的入口。

  • 关键动作:调用 SetLanguage 设置默认语言(如 "en-US"),调用 SetTitle 添加标题,并使用 SetPdfUA1Identification 激活 PDF/UA1 验证标志。
  • 参数说明:PdfStructureElement 是构成结构树的节点,常用的类型包括 Document(文档)、Paragraph(段落)、Span(行内文本)、Figure(图形)等。

第 2 步:构建逻辑结构与添加内容

接下来需要向结构树中添加元素,并在每个元素开始和结束标记时,将实际绘制的文字或图像关联到对应的标签上。

  • 文本处理:使用 BeginMarkedContent 开启标记,执行绘图操作(如 DrawString),最后用 EndMarkedContent 闭合标记。
  • 图片处理:对于 Figure 类型的标签,建议设置 A 属性(Alternative Text,替代文本),以便屏幕阅读器在没有渲染图片时能提供描述信息。

完整代码示例

C# 实现版本

using Spire.Pdf;
using Spire.Pdf.Graphics;
using Spire.Pdf.Interchange.TaggedPdf;
using System.Drawing;

namespace CreatePDFUAfile
{
    class Program
    {
        static void Main(string[] args)
        {
            // 1. 初始化文档
            PdfDocument doc = new PdfDocument();
            doc.Pages.Add();
            // 设置页面为结构化 Tab Order
            doc.Pages[0].SetTabOrder(TabOrder.Structure);

            // 2. 配置 PDF/UA 相关属性
            PdfTaggedContent taggedContent = new PdfTaggedContent(doc);
            taggedContent.SetLanguage("en-US");
            taggedContent.SetTitle("test");
            taggedContent.SetPdfUA1Identification();

            // 3. 字体与画刷准备
            PdfTrueTypeFont font = new PdfTrueTypeFont(new Font("Times New Roman", 10), true);
            PdfSolidBrush brush = new PdfSolidBrush(Color.Black);

            // 4. 构建结构树:Document -> Article -> Paragraph -> Span
            PdfStructureElement article = taggedContent.StructureTreeRoot.AppendChildElement(PdfStandardStructTypes.Document);
            
            // --- 第一段文本 ---
            PdfStructureElement paragraph1 = article.AppendChildElement(PdfStandardStructTypes.Paragraph);
            PdfStructureElement span1 = paragraph1.AppendChildElement(PdfStandardStructTypes.Span);
            span1.BeginMarkedContent(doc.Pages[0]);
            
            PdfStringFormat format = new PdfStringFormat(PdfTextAlignment.Justify);
            doc.Pages[0].Canvas.DrawString(
                "PDF/UA was published as ISO Standard 14289-1 in August 2012 and is by far the first complete definition of a set of requirements for universally accessible PDF documents.",
                font, brush, new Rectangle(40, 80, 450, 80), format);
            span1.EndMarkedContent(doc.Pages[0]);

            // --- 第二段文本 ---
            PdfStructureElement paragraph2 = article.AppendChildElement(PdfStandardStructTypes.Paragraph);
            paragraph2.BeginMarkedContent(doc.Pages[0]);
            doc.Pages[0].Canvas.DrawString(
                "The PDF/UA has some definite requirements at its base that act as the essence of this standard.",
                font, brush, new Rectangle(40, 120, 450, 60), format);
            paragraph2.EndMarkedContent(doc.Pages[0]);

            // --- 第一张图片 (Figure) ---
            PdfStructureElement figure1 = article.AppendChildElement(PdfStandardStructTypes.Figure);
            figure1.Alt = "replacement text1"; // 设置替代文本,增强无障碍性
            figure1.BeginMarkedContent(doc.Pages[0], null);
            PdfImage image = PdfImage.FromFile(@"logo.jpg");
            doc.Pages[0].Canvas.DrawImage(image, new PointF(40, 200), new SizeF(100, 100));
            figure1.EndMarkedContent(doc.Pages[0]);

            // --- 第二张图片 (矩形代表抽象图) ---
            PdfStructureElement figure2 = article.AppendChildElement(PdfStandardStructTypes.Figure);
            figure2.Alt = "replacement text2";
            figure2.BeginMarkedContent(doc.Pages[0], null);
            doc.Pages[0].Canvas.DrawRectangle(PdfPens.Black, new Rectangle(300, 200, 100, 100));
            figure2.EndMarkedContent(doc.Pages[0]);

            // 5. 保存文档
            doc.SaveToFile("CreatePDFUAFile_result.pdf");
            System.Diagnostics.Process.Start("CreatePDFUAFile_result.pdf");
        }
    }
}

VB.NET 实现版本

Imports Spire.Pdf
Imports Spire.Pdf.Graphics
Imports Spire.Pdf.Interchange.TaggedPdf
Imports System.Drawing

Namespace CreatePDFUAfile
    Class Program
        Private Shared Sub Main(args As String())
            ' 初始化文档
            Dim doc As New PdfDocument()
            doc.Pages.Add()
            doc.Pages(0).SetTabOrder(TabOrder.[Structure])

            ' 配置 PDF/UA 属性
            Dim taggedContent As New PdfTaggedContent(doc)
            taggedContent.SetLanguage("en-US")
            taggedContent.SetTitle("test")
            taggedContent.SetPdfUA1Identification()

            ' 创建字体、画刷
            Dim font As New PdfTrueTypeFont(New Font("Times New Roman", 10), True)
            Dim brush As New PdfSolidBrush(Color.Black)

            ' 构建结构树
            Dim article As PdfStructureElement = taggedContent.StructureTreeRoot.AppendChildElement(PdfStandardStructTypes.Document)

            ' 段落 1
            Dim paragraph1 As PdfStructureElement = article.AppendChildElement(PdfStandardStructTypes.Paragraph)
            Dim span1 As PdfStructureElement = paragraph1.AppendChildElement(PdfStandardStructTypes.Span)
            span1.BeginMarkedContent(doc.Pages(0))
            Dim format As New PdfStringFormat(PdfTextAlignment.Justify)
            doc.Pages(0).Canvas.DrawString(
                "PDF/UA was published as ISO Standard 14289-1 in August 2012",
                font, brush, New Rectangle(40, 80, 450, 80), format)
            span1.EndMarkedContent(doc.Pages(0))

            ' 段落 2
            Dim paragraph2 As PdfStructureElement = article.AppendChildElement(PdfStandardStructTypes.Paragraph)
            paragraph2.BeginMarkedContent(doc.Pages(0))
            doc.Pages(0).Canvas.DrawString(
                "The PDF/UA has some definite requirements at its base",
                font, brush, New Rectangle(40, 120, 450, 60), format)
            paragraph2.EndMarkedContent(doc.Pages(0))

            ' 图片 1
            Dim figure1 As PdfStructureElement = article.AppendChildElement(PdfStandardStructTypes.Figure)
            figure1.Alt = "replacement text1"
            figure1.BeginMarkedContent(doc.Pages(0), Nothing)
            Dim image As PdfImage = PdfImage.FromFile("logo.jpg")
            doc.Pages(0).Canvas.DrawImage(image, New PointF(40, 200), New SizeF(100, 100))
            figure1.EndMarkedContent(doc.Pages(0))

            ' 图片 2
            Dim figure2 As PdfStructureElement = article.AppendChildElement(PdfStandardStructTypes.Figure)
            figure2.Alt = "replacement text2"
            figure2.BeginMarkedContent(doc.Pages(0), Nothing)
            doc.Pages(0).Canvas.DrawRectangle(PdfPens.Black, New Rectangle(300, 200, 100, 100))
            figure2.EndMarkedContent(doc.Pages(0))

            ' 保存文档
            doc.SaveToFile("CreatePDFUAFile_result.pdf")
            System.Diagnostics.Process.Start("CreatePDFUAFile_result.pdf")
        End Sub
    End Class
End Namespace

结果与总结

通过上述代码生成的 CreatePDFUAFile_result.pdf,其内部结构已完全遵循 PDF/UA 规范。在使用 Adobe Acrobat Pro 等专业工具检查时,该文档将被识别为具有无障碍属性的 PDF。

  • 标签完整性:每个可见元素(文字、图形)都被包裹在对应的 Structure Element 中。
  • 语义关联:使用了正确的类型(Paragraph, Figure)并设置了替代文本(Alt)。
  • 验证标志:开启了 PDF/UA1 标识。

以上就是 C#/.NET 结合 Spire.PDF 创建符合 ISO 标准的 PDF/UA 文件的详细内容,更多关于 C# 创建 PDF/UA 文件的技术资料请关注本站其它相关文章!

相关标签:

本站声明

本文内容仅供参考,不代表本站观点。转载或引用请注明出处。如发现内容问题,请通过联系我们页面反馈。

Python 相关产品和应用

全部下载

专题列表