Internal PDF state container.
Summary
Functions
Add a radio button group: one field, one widget per choice.
Open an artifact: content that is decoration rather than meaning.
Open a structure element, bracketing whatever is drawn until it is closed.
Close the innermost open artifact.
Close the innermost open structure element.
Set the document's natural language, as a BCP 47 tag such as "en-GB".
Declare a PDF/A conformance level, adding what archival validity requires.
Record the intent to sign a signature field.
Whether this document carries logical structure.
Types
@type annotation() :: %{ type: :link, rect: {number(), number(), number(), number()}, target: link_target(), border: annotation_border() }
@type begin_artifact_op() :: {:begin_artifact}
@type begin_marked_content_op() :: {:begin_marked_content, String.t(), non_neg_integer()}
@type bookmark() :: %{title: String.t(), page_number: pos_integer()}
What a push button does when clicked.
A push button holds no value, so an action is the only reason to have one.
@type clip_even_odd_op() :: :clip_even_odd
@type clip_op() :: :clip
@type embedded_font() :: %{ :format => :ttf | :otf, :name => String.t(), :data => binary(), :subset => embedded_font_subset_mode(), optional(:ttf_metrics) => ttf_metrics() }
@type embedded_font_option() :: {:subset, embedded_font_subset_mode()} | {:enforce_embedding_permissions, boolean()}
@type embedded_font_subset_mode() :: :none | :ascii_basic | :used_text
@type end_marked_content_op() :: {:end_marked_content}
@type fill_even_odd_op() :: :fill_even_odd
@type fill_op() :: :fill
@type form_field() :: %{ :type => form_field_type(), :name => String.t(), :page_number => pos_integer(), :rect => {number(), number(), number(), number()}, :value => String.t() | boolean(), :flags => non_neg_integer(), :font => String.t(), :size => number(), :border => annotation_border(), optional(:max_length) => pos_integer(), optional(:tooltip) => String.t(), optional(:options) => [String.t()], optional(:widgets) => [radio_widget()], optional(:action) => button_action(), optional(:label) => String.t() }
@type form_field_type() ::
:text | :checkbox | :choice | :radio | :push_button | :signature
@type graphics_state_op() :: :save_state | :restore_state
@type image() :: %{ :format => :jpeg | :png, :data => binary(), :width => pos_integer(), :height => pos_integer(), :bits_per_component => pos_integer(), :color_space => image_color_space(), optional(:decode_parms) => map(), optional(:alpha_data) => binary(), optional(:alpha_decode_parms) => map() }
@type image_color_space() :: :device_gray | :device_rgb | :device_cmyk
@type image_op() :: {:image, number(), number(), number(), number(), pos_integer()}
@type link_target() :: {:url, String.t()} | {:page, pos_integer()}
@type op() :: text_op() | text_rotated_op() | draw_op() | rect_op() | circle_op() | move_to_op() | line_to_op() | bezier_op() | stroke_op() | fill_op() | fill_even_odd_op() | clip_op() | clip_even_odd_op() | line_style_op() | graphics_state_op() | color_op() | image_op() | begin_marked_content_op() | begin_artifact_op() | end_marked_content_op()
@type paint() :: :stroke | :fill | :fill_even_odd | :fill_and_stroke | :none
@type radio_widget() :: %{ export_value: String.t(), page_number: pos_integer(), rect: {number(), number(), number(), number()} }
One button within a radio group.
A radio group is a single field with several on-page widgets, one per choice.
export_value is the value the field takes when that button is the selected
one, and is what appears in the filled document.
@type stroke_op() :: :stroke
@type t() :: %Tincture.PDF{ annotations: %{required(pos_integer()) => [annotation()]}, bookmarks: [bookmark()], current_font: font(), current_page: pos_integer(), embedded_fonts: %{optional(String.t()) => embedded_font()}, encryption: map() | nil, form_fields: [form_field()], images: %{required(pos_integer()) => image()}, language: String.t() | nil, mcid_counters: %{optional(pos_integer()) => non_neg_integer()}, metadata: %{optional(atom()) => String.t()}, next_image_id: pos_integer(), operations: [op()], page_size: page_size(), pages: %{required(pos_integer()) => [op()]}, pdf_a: {2 | 3, :b | :u | :a} | nil, signature: map() | nil, structure_stack: [Tincture.PDF.Structure.t()], structure_tree: [Tincture.PDF.Structure.t()] }
@type ttf_metrics() :: map()
Functions
@spec add_bookmark(t(), String.t(), pos_integer()) :: t()
Add a radio button group: one field, one widget per choice.
Unlike every other field type this is not one dictionary. The specification models a radio group as a parent field holding the value, with a kid widget for each button, and the button's export value is the name of its "on" appearance state. Choosing a button sets the parent's value to that name.
buttons is a list of keyword lists, each needing :value, :x, :y and
:size, and optionally :page.
Open an artifact: content that is decoration rather than meaning.
Rules, borders, background shading and repeating page furniture carry no information a reader needs. In a tagged document every operator must be either tagged or marked as an artifact — content that is neither is a conformance failure, and is read out as stray noise.
An artifact has no structure element and no marked-content id; it exists only to say "skip this".
@spec begin_structure(t(), Tincture.PDF.Structure.tag(), keyword()) :: t()
Open a structure element, bracketing whatever is drawn until it is closed.
Content elements also open a marked-content sequence in the page's content stream, which is what ties the drawn operators to this element.
Close the innermost open artifact.
Close the innermost open structure element.
@spec page_annotations(t(), pos_integer()) :: [annotation()]
@spec page_numbers(t()) :: [pos_integer()]
@spec page_operations(t(), pos_integer()) :: [op()]
@spec register_image(t(), image()) :: {t(), pos_integer()}
@spec register_otf_font(t(), String.t(), Path.t(), [embedded_font_option()]) :: t()
@spec register_ttf_font(t(), String.t(), Path.t(), [embedded_font_option()]) :: t()
Set the document's natural language, as a BCP 47 tag such as "en-GB".
Required for a document to be accessible: without it a screen reader has to guess which language to pronounce the text as.
@spec set_page(t(), pos_integer()) :: t()
Declare a PDF/A conformance level, adding what archival validity requires.
Sets an sRGB output intent, a /Metadata stream carrying the PDF/A
identification, and a file identifier.
Record the intent to sign a signature field.
The signature itself cannot be computed here: it covers the finished file,
so it is applied during Tincture.export/2.
Whether this document carries logical structure.