Form: campos AcroForm interativos e achatamento
Visão geral
Seção intitulada “Visão geral”O módulo Form cria formulários interativos para documentos Portable Document Format (PDF). Ele constrói campos de texto, checkbox, radio, choice (list/combo), botão e assinatura, organiza esses campos em uma hierarquia parent/child, grava-os como objetos PDF com appearance streams e pode achatar o formulário em conteúdo de página estático.
Instalação
Seção intitulada “Instalação”composer require nextpdf/core:^3Visão conceitual
Seção intitulada “Visão conceitual”Um formulário PDF interativo é o AcroForm: uma hierarquia de campos no nível do documento cujos campos terminais são associados a widget annotations nas páginas. A ISO 32000-2 §12.7 define esse formulário, seus dicionários de campos, a raiz do AcroForm e a hierarquia de campos. Este módulo codifica essas estruturas para o engine.
FormFieldManager é a superfície principal. Ela expõe os builders textField(), checkBox(), radioButton(), button() e signatureField(), rastreia os campos e os serializa com writeFields(). Ela emite um appearance stream de Form XObject para cada widget (/Subtype /Form, /BBox), conforme exige a §8.10. FormField é o objeto de valor do campo. FormFieldDictionaryBuilder converte um campo em seu dicionário PDF e aplica entradas específicas de tipo e bits de flag a campos de texto, checkbox, choice e botão. O manager e FormField são @since 1.0.0. O dictionary builder é @since 1.1.0.
FormFieldHierarchy modela a árvore de campos parent/child com addChild(), getRootFieldNames(), getChildren(), getParent() e o visitor walkDepthFirst(). Um nome de campo totalmente qualificado é o caminho com pontos nessa hierarquia, correspondendo ao modelo de campos aninhados da §12.7.
FormFlattener renderiza o formulário como conteúdo de página estático. flatten() retorna um FlattenResult; assim, você pode congelar um formulário preenchido para arquivamento. FieldMDP e FieldMdpAction modelam a transform de bloqueio de campo. Um documento assinado pode bloquear um conjunto nomeado de campos contra modificações posteriores. FieldMdpAction enumera o escopo do bloqueio, e requiresFieldList() indica quando uma lista explícita de campos é obrigatória. FieldMDP é @since 2.0.0.
Superfície da API
Seção intitulada “Superfície da API”| Classe | Membros principais | Função |
|---|---|---|
FormFieldManager | textField(), checkBox(), radioButton(), button(), signatureField(), addChildField(), getHierarchy(), writeFields() | Builder de campos + serializador (@since 1.0.0) |
FormField | objeto de valor do campo | Um campo do AcroForm (@since 1.0.0) |
FormFieldDictionaryBuilder | buildFieldDictionary(), applyTextFieldOptions(), applyCheckBoxOptions(), applyChoiceFieldOptions(), applyButtonOptions() | Builder de campo para dicionário (@since 1.1.0) |
FormFieldHierarchy | addChild(), getRootFieldNames(), getChildren(), getParent(), walkDepthFirst() | Árvore de campos parent/child (@since 2.0.0) |
FormFlattener | flatten(array $fields, array $pages): FlattenResult | Achata o formulário em conteúdo estático (@since 1.0.0) |
FieldMDP | toTransformParams() | Transform de bloqueio de campo (FieldMDP) (@since 2.0.0) |
FieldMdpAction (enum) | requiresFieldList() | Escopo do bloqueio de campo (@since 2.0.0) |
Execute composer docs:generate-api-php -- --module=Form para gerar a tabela completa de PHPDoc.
Exemplo de código — Início rápido
Seção intitulada “Exemplo de código — Início rápido”Fonte: examples/30-form-fields.php.
<?php
declare(strict_types=1);
require_once __DIR__ . '/../vendor/autoload.php';
use NextPDF\Form\FormFieldManager;
$form = new FormFieldManager();
$form->textField(name: 'applicant_name', x: 50, y: 700, w: 200, h: 18);$form->checkBox(name: 'agree_terms', x: 50, y: 660, size: 12);$form->radioButton(name: 'plan', x: 50, y: 620, size: 12 /* + option set */);
// The Writer invokes $form->writeFields(...) during document serialization.Exemplo de código — Produção
Seção intitulada “Exemplo de código — Produção”Construa um conjunto de campos para um documento assinado e, em seguida, bloqueie os campos assinados com FieldMDP.
<?php
declare(strict_types=1);
require_once __DIR__ . '/../vendor/autoload.php';
use NextPDF\Form\FieldMDP;use NextPDF\Form\FieldMdpAction;use NextPDF\Form\FormFieldManager;
$form = new FormFieldManager();$form->textField(name: 'contract_value', x: 50, y: 700, w: 160, h: 18);$form->signatureField(name: 'approver_sig', x: 50, y: 600, w: 200, h: 60);
// Lock only the named fields after signing.$lock = new FieldMDP( action: FieldMdpAction::Include, fields: ['contract_value'],);
$transformParams = $lock->toTransformParams();// $transformParams is attached to the signature's transform method by the signing layer.Casos extremos e pegadinhas
Seção intitulada “Casos extremos e pegadinhas”- Um nome de campo é um caminho com pontos totalmente qualificado em
FormFieldHierarchy. Em um visualizador, dois campos terminais com o mesmo nome totalmente qualificado representam o mesmo campo lógico. Você é responsável pela unicidade. FieldMdpAction::requiresFieldList()informa quando uma lista de campos é obrigatória. Uma açãoInclude/Excludesem a lista exigida cria um bloqueio malformado; verifique a flag.FormFlattener::flatten()remove deliberadamente a interatividade. O resultado é conteúdo estático. Mantenha a fonte interativa caso precise dela mais tarde.- Appearance streams são emitidos por widget. Um campo sem appearance pode renderizar de forma inconsistente entre visualizadores; deixe o manager gerar o appearance em vez de omiti-lo.
signatureField()cria apenas o placeholder do campo. A camada de Security/assinatura produz a assinatura propriamente dita; este módulo não.
Desempenho
Seção intitulada “Desempenho”A criação e a serialização de campos são O(n) em relação à contagem de campos, mais um appearance stream de Form XObject por widget. O custo do achatamento escala com o conteúdo renderizado, não com a contagem de campos. A carga de trabalho de referência padrão permanece dentro do orçamento de 1500 ms de tempo total / 64 MB de pico. O perfil de reprodutibilidade é structural: os números dos objetos e o /ID do trailer variam entre execuções. Dois documentos com o mesmo formulário são estruturalmente iguais, mas não idênticos byte a byte.
Notas de segurança
Seção intitulada “Notas de segurança”Os valores dos campos de formulário são entrada do usuário. O módulo faz escape dos valores de string para a serialização PDF com PdfStringEscaper, de modo que um valor de campo não consiga escapar da sua string PDF e injetar estrutura. Quando um formulário é criptografado, a criptografia AES-256 do documento abrange o conteúdo dos campos. FieldMDP é um controle de segurança: ele bloqueia campos nomeados contra modificações após a assinatura. Um bloqueio de campo que não corresponde ao conjunto de campos assinados compromete esse controle; defina o escopo do bloqueio de forma deliberada. Trate qualquer valor extraído de um formulário preenchido como entrada não confiável. Consulte o modelo de segurança do engine em /modules/core/security/.
Conformidade
Seção intitulada “Conformidade”As estruturas de formulário emitidas por este módulo seguem o modelo de formulário interativo da ISO 32000-2 §12.7: a raiz do AcroForm, os dicionários de campos e a hierarquia de campos do documento. As appearances por widget são emitidas como Form XObjects conforme a §8.10 e documentadas inline em src/Form/. tests/Unit/Form/ exercita esses fatos de implementação. Eles não constituem uma declaração de conformidade PDF 2.0 de ponta a ponta. A conformidade do documento completo é validada pelas suítes oracle e golden em /modules/core/conformance/.
Veja também
Seção intitulada “Veja também”- Módulo Navigation — widget annotations que se pareiam com campos.
- Módulo Security — assinatura e modelo de confiança do FieldMDP.
- Módulo Accessibility — marcação de campos de formulário para PDF/UA.
- Visão geral de conformidade