为什么不打印 iText 7 表单字段值?

Why don't the iText 7 form field values print?

我有一个 PDF,其中包含使用 iText 7 生成的表单。但是,当我填写表单并尝试打印时,表单值没有显示;只有表格大纲显示。如何生成在打印时显示值的表单域?

示例表单生成器:

import java.io.FileNotFoundException;
import java.io.IOException;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.itextpdf.forms.PdfAcroForm;
import com.itextpdf.forms.fields.PdfFormField;
import com.itextpdf.forms.fields.PdfTextFormField;
import com.itextpdf.kernel.font.PdfFont;
import com.itextpdf.kernel.font.PdfFontFactory;
import com.itextpdf.kernel.geom.PageSize;
import com.itextpdf.kernel.pdf.PdfDocument;
import com.itextpdf.kernel.pdf.PdfWriter;
import com.itextpdf.layout.Document;
import com.itextpdf.layout.border.Border;
import com.itextpdf.layout.element.Cell;
import com.itextpdf.layout.element.Table;
import com.itextpdf.layout.renderer.CellRenderer;
import com.itextpdf.layout.renderer.DrawContext;

/**
 * @author Lucas Vander Wal
 *
 */
public final class TestForm {

    private static final Logger log = LoggerFactory.getLogger(TestForm.class);

    private static final PageSize LETTER_SIZE = new PageSize(612, 792),
            LETTER_SIZE_LANDSCAPE = LETTER_SIZE.rotate();

    private static final PdfFont FONT;
    static {
        try {
            FONT = PdfFontFactory.createFont();
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    private static final float FONT_SIZE_12 = 12;

    /**
     * @param args
     */
    public static void main(String[] args) {
        log.info("Running pdf generation...");
        new TestForm().generate("formTest.pdf");
        log.info("Done with pdf generation.");
    }

    private Document doc;
    private PdfDocument pdfDoc;
    private PdfAcroForm form;

    public TestForm() {
    }

    /**
     * Generates the timesheet pdf and saves it to the given file location
     * 
     * @param outputFile
     */
    public void generate(String outputFile) {
        try {
            pdfDoc = new PdfDocument(new PdfWriter(outputFile));
            doc = new Document(pdfDoc, LETTER_SIZE_LANDSCAPE);
            // set document properties
            doc.setFontSize(10);
            float marginSize = doc.getTopMargin();
            doc.setMargins(marginSize / 2, marginSize, marginSize / 2, marginSize);

            form = PdfAcroForm.getAcroForm(pdfDoc, true);

            // build the form
            buildUserInfo();
            // close the document
            doc.close();

        } catch (FileNotFoundException e) {
            log.warn("Unable to save to file: " + outputFile, e);
        }

    }

    private void buildUserInfo() {
        // build the user info table
        Table userTable = new Table(4).setBorder(Border.NO_BORDER).setWidthPercent(100).setMargin(0).setPadding(0);
        // add 4 text entry fields
        this.addFieldToTable(userTable, "nameEmployee", "Name of Employee:");

        // add the table to the document
        this.doc.add(userTable);

    }

    private void addFieldToTable(Table t, String fieldName, String fieldLabel) {
        t.addCell(new Cell().add(fieldLabel).setPadding(5));
        Cell cell = new Cell().setPadding(5);
        cell.setNextRenderer(new CellRenderer(cell) {

            @Override
            public void draw(DrawContext drawContext) {
                super.draw(drawContext);
                PdfTextFormField field = PdfFormField.createText(
                        drawContext.getDocument(), getOccupiedAreaBBox().decreaseHeight(5), fieldName, "",
                        FONT, FONT_SIZE_12);
                form.addField(field);
            }

        });
        t.addCell(cell);
    }
}

PDF 表单域具有影响打印能力的可见性设置。有关详细信息,请参阅 this Adobe page

需要在 PdfFormField 对象上使用 setVisibility() 方法将表单字段设置为 'VISIBLE'。 This iText 7 documentation 解释了如何将表单设置为 'HIDDEN'、'VISIBLE_BUT_DOES_NOT_PRINT' 和 'HIDDEN_BUT_PRINTABLE',但是它没有提到设置为 visible,事实上,visible 不是其中之一PdfFormField 中的静态选项。

上面列出的三个值分别对应整数1、2、3,我凭直觉把visibility设置为0,打印时显示的表单域!

总而言之,调用 PdfFormField.setVisibility(0) 创建可打印的表单域。