June 26, 2018 | General, Important features

PDF Accessibility with PDF/UA Generation


PDF Accessibility with PDF/UA Generation

Create tagged PDFs using GdPicture.NET Document Imaging SDK

Hi everyone,

You agree that accessibility is crucial when your business requires to share comprehensible documents among various people, no matter what their ability to access the materials is.
It does not only concern people with disabilities using assistive technologies like screen readers. Nowadays it also covers people using mobile devices.
Accessibility is for everyone.

The solution calls tagged PDF documents.

What are Tags?

The recent release (from June 21st, 2018) of GdPicture.NET now extends its features to allow you to create a tagged PDF/UA document. What does this mean?

It is a well-known fact that a PDF document may include a structure in addition to the common page content.

This structure represents various instructions behind the scenes, which describe the document’s logic.
They can hold supplementary information about images, figures, tables, like their titles or some useful descriptive text.
They also can store information about sections, paragraphs, like their heading, naming, as well as their font size or font style.
They allow distinguishing between the real page content and some graphical items not relevant to the contained information.
Every single part of the document content, like text including individual characters, graphics, other objects like annotations or even form fields can attach to such an instruction in the document’s backstage. These structural elements are called tags.

The Tag Tree

The whole document logic is composed using these structure elements organized in the structure hierarchy, so-called logical structure tree or tag tree.

Tags hold information about each element of the document.

This object is stored separately from the visible document content. This way all tags are treated independently of their associated items identifying visible parts of the document placed on its pages. Such an approach produce the logical order of the document content in opposite to content creation order. This logical order, as an extension of the reading order, helps to understand the relationship between objects on the page.

The structure of a tagged PDF is logical and follows the reading order.

What is PDF/UA?

As explained by the PDF Association, PDF/UA is the common name for ISO 14289, an international standard defining the correct use of PDF tagging for accessibility purposes. PDF/UA identifies the components and properties of PDF technology which are relevant to accessibility, and provides requirements and restrictions on their use.

Since June 21st, GdPicture.NET provides support for generating PDF/Universal Accessibility (PDF/UA).

PDF/UA Validation

It is not so complicated to add tags to your PDF document. However, it is tricky to attach them correctly to create a valid tagged PDF document.
Good news is that many free available PDF/UA validators can assist you to verify the generated tag’s tree. You will find some examples here.

Benefits of Tagged PDFs and PDF/UA

  • Well-tagged PDF documents fit much better when displaying on different screens or mobile devices.
  • They are very well prepared for screen readers to be useful for people with disabilities.
  • Moreover, tags are necessary to achieve 508 compliance for your PDF documents.
  • Last, but not least, with the PDF/UA compliant documents, you are very close to reaching the accessibility requirements for the Web entitled as WCAG 2.0.

More and more companies and organizations are now required to use PDF accessible documents only, especially governmental and state agencies, to provide access for everyone.

Ready to be accessible? Start using tags with GdPicture.NET toolkit right now!

Resources and Methods

If you want to know more about PDF accessibility and PDF/UA, you will find very useful information on the PDF Association website on these pages:
https://www.pdfa.org/publication/pdfua-flyer/
https://www.pdfa.org/publication/pdfua-reference-suite/


Founded in 2006 as the PDF/A Competence Center, the PDF Association exists to promote the adoption and implementation of International Standards for PDF technology.

The GdPicture methods to tagg and generate accessible PDFs:

AttachTagToAnnotation Method (GdPicturePDF)

SetTagAttribute(Int32,String,String) Method

Creating a tagged PDF document from scratch

Sample Code (C#)

//We assume that GdPicture has been correctly installed and unlocked.
using (GdPicturePDF oGdPicturePDF = new GdPicturePDF())
{
    //Creating a new PDF document.
    if ((oGdPicturePDF.NewPDF(PdfConformance.PDF_UA_1) == GdPictureStatus.OK) &&
        (oGdPicturePDF.NewPage(PdfPageSizes.PdfPageSizeA4) == GdPictureStatus.OK))
    {
        //This is required to have a valid PDF_UA document.
        oGdPicturePDF.SetTitle("My first PDF/UA document");
        // Add the font for drawing a text.
        string fontResName = oGdPicturePDF.AddTrueTypeFontU("Arial", false, false, true);
        oGdPicturePDF.SetTextSize(18);
        //Adding the first image to the PDF document.
        string logo1 = oGdPicturePDF.AddJpegImageFromFile("brand1.jpg");
        if (oGdPicturePDF.GetStat() == GdPictureStatus.OK)
        {
            //Adding the second image to the PDF document.
            string logo2 = oGdPicturePDF.AddJpegImageFromFile("brand2.jpg");
            if (oGdPicturePDF.GetStat() == GdPictureStatus.OK)
            {
                //Creating a root tag and set the language.
                int tagRootID = oGdPicturePDF.GetTagRootID();
                if ((oGdPicturePDF.GetStat() != GdPictureStatus.OK) ||
                    (oGdPicturePDF.SetLanguage("en-US") != GdPictureStatus.OK))
                    goto error;
                //Creating a section tag for the document content.
                int tagSection = oGdPicturePDF.NewTag(tagRootID, "Sect");
                if (oGdPicturePDF.GetStat() != GdPictureStatus.OK) goto error;
                //Creating a tag for the text of the sentence.
                if ((oGdPicturePDF.BeginMarkedContentSequence(tagSection, "Span") != GdPictureStatus.OK) ||
                    (oGdPicturePDF.DrawText(fontResName, 20, 750, "The product") != GdPictureStatus.OK) ||
                    (oGdPicturePDF.EndMarkedContent() != GdPictureStatus.OK))
                    goto error;
                //Creating a tag and setting its properties for the first image.
                int tagLogo1 = oGdPicturePDF.NewTag(tagSection, "Figure");
                if (oGdPicturePDF.GetStat() != GdPictureStatus.OK) goto error;
                if ((oGdPicturePDF.SetTagAlternateDescription(tagLogo1, "This is a logo of brand1.") != GdPictureStatus.OK) ||
                    (oGdPicturePDF.SetTagAttribute(tagLogo1, "BBox", new double[] { 125, 750, 221.75, 771.75 }) != GdPictureStatus.OK))
                    goto error;
                //Creating a tag for the image itself and drawing the image.
                if ((oGdPicturePDF.BeginMarkedContentSequence(tagLogo1, "Figure") != GdPictureStatus.OK) ||
                    (oGdPicturePDF.DrawImage(logo1, 125, 750, 96.75f, 21.75f) != GdPictureStatus.OK) ||
                    (oGdPicturePDF.EndMarkedContent() != GdPictureStatus.OK))
                    goto error;
                //Creating a tag for the text of the sentence.
                if ((oGdPicturePDF.BeginMarkedContentSequence(tagSection, "Span") != GdPictureStatus.OK) ||
                    (oGdPicturePDF.DrawText(fontResName, 230, 750, "is powered by") != GdPictureStatus.OK) ||
                    (oGdPicturePDF.EndMarkedContent() != GdPictureStatus.OK))
                    goto error;
                //Creating a tag and setting its properties for the second image.
                int tagLogo2 = oGdPicturePDF.NewTag(tagSection, "Figure");
                if (oGdPicturePDF.GetStat() != GdPictureStatus.OK) goto error;
                if ((oGdPicturePDF.SetTagAlternateDescription(tagLogo2, "This is a logo of brand2.") != GdPictureStatus.OK) ||
                    (oGdPicturePDF.SetTagAttribute(tagLogo2, "BBox", new double[] { 350, 750, 446.75, 771.75 }) != GdPictureStatus.OK))
                    goto error;
                //Creating a tag for the image itself and drawing the image.
                if ((oGdPicturePDF.BeginMarkedContentSequence(tagLogo2, "Figure") != GdPictureStatus.OK) ||
                    (oGdPicturePDF.DrawImage(logo2, 350, 750, 96.75f, 21.75f) != GdPictureStatus.OK) ||
                    (oGdPicturePDF.EndMarkedContent() != GdPictureStatus.OK))
                    goto error;
                error:
                if (oGdPicturePDF.GetStat() == GdPictureStatus.OK)
                {
                    //Saving the created document.
                    if (oGdPicturePDF.SaveToFile("tagged_document.pdf") == GdPictureStatus.OK)
                        MessageBox.Show("Your tagged PDF document has been successfully created.", "Creating a Tagged PDF Example", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    else
                        MessageBox.Show("The error occured when saving. Error: " + oGdPicturePDF.GetStat().ToString(), "Creating a Tagged PDF Example", MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
                else
                    MessageBox.Show("The error occured when creating tags. Error: " + oGdPicturePDF.GetStat().ToString(), "Creating a Tagged PDF Example", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            else
                MessageBox.Show("The error occured when adding the second image. Error: " + oGdPicturePDF.GetStat().ToString(), "Creating a Tagged PDF Example", MessageBoxButtons.OK, MessageBoxIcon.Error);
        }
        else
            MessageBox.Show("The error occured when adding the first image. Error: " + oGdPicturePDF.GetStat().ToString(), "Creating a Tagged PDF Example", MessageBoxButtons.OK, MessageBoxIcon.Error);
        oGdPicturePDF.CloseDocument();
    }
    else
        MessageBox.Show("The new document can't be created. Error: " + oGdPicturePDF.GetStat().ToString(), "Creating a Tagged PDF Example", MessageBoxButtons.OK, MessageBoxIcon.Error);
}

See you next time!

Gabriela


Tags: