UNPKG

@syncfusion/ej2-pdf

Version:

Feature-rich JavaScript PDF library with built-in support for loading and manipulating PDF document.

2,235 lines 94.7 kB
import { _PdfDictionary, _PdfName, _PdfReference } from './../pdf-primitives';
import { PdfField, PdfTextBoxField, PdfButtonField, PdfCheckBoxField, PdfRadioButtonListField, PdfComboBoxField, PdfListBoxField, PdfSignatureField } from './field';
import { _getInheritableProperty, _getPageIndex, _isNullOrUndefined } from './../utils';
import { PdfFormFieldsTabOrder, PdfRotationAngle, _FieldFlag, _SignatureFlag } from './../enumerator';
import { PdfPage } from './../pdf-page';
import { PdfAnnotationCollection } from './../annotations/annotation-collection';
import { PdfWidgetAnnotation } from './../annotations/annotation';
import { initializeTelemetryFeature } from '@syncfusion/ej2-base';
/**
 * Represents a PDF form.
 * ```typescript
 * // Load an existing PDF document
 * let document: PdfDocument = new PdfDocument(data, password);
 * // Access the form of the PDF document
 * let form: PdfForm = document.form;
 * // Save the document
 * document.save('output.pdf');
 * // Destroy the document
 * document.destroy();
 * ```
 */
var PdfForm = /** @class */ (function () {
    /**
     * Represents a loaded from the PDF document.
     *
     * @private
     * @param {_PdfDictionary} dictionary Form dictionary.
     * @param {_PdfCrossReference} crossReference Cross reference object.
     */
    function PdfForm(dictionary, crossReference) {
        /**
         * Indicates use of a default appearance for widgets.
         *
         * @private
         */
        this._isDefaultAppearance = false;
        /**
         * Indicates whether the form contains fields with kids.
         *
         * @private
         */
        this._hasKids = false;
        /**
         * Indicates whether to generate appearance streams for fields.
         *
         * @private
         */
        this._setAppearance = false;
        /**
         * Exports fields even if they are empty.
         *
         * @private
         */
        this._exportEmptyFields = false;
        /**
         * Collection of parsed field instances.
         *
         * @private
         */
        this._fieldCollection = [];
        /**
         * Signature flag indicating required usage or certification.
         *
         * @private
         */
        this._signFlag = _SignatureFlag.none;
        /**
         * Cached indicator for NeedAppearances usage.
         *
         * @private
         */
        this._isNeedAppearances = false;
        /**
         * List of form names in document order.
         *
         * @private
         */
        this._formNames = [];
        /**
         * Enables automatic naming for newly added fields.
         *
         * @private
         */
        this._fieldAutoNaming = false;
        /**
         * Generated or user-specified field names.
         *
         * @private
         */
        this._fieldName = [];
        /**
         * Cache of fonts used across fields keyed by font name.
         *
         * @private
         */
        this._fontCache = new Map();
        /**
         * Indicates whether additional post-processing is required.
         *
         * @private
         */
        this._requiresPostProcessing = false;
        /**
         * Indicates whether the kids are valid or not.
         *
         * @private
         */
        this._isValidKids = false;
        this._dictionary = dictionary;
        this._crossReference = crossReference;
        this._parsedFields = new Map();
        this._fields = [];
        this._addedFieldNames = new Set();
        this._createFields();
    }
    Object.defineProperty(PdfForm.prototype, "count", {
        /**
         * Gets the fields count (Read only).
         *
         * @returns {number} Fields count.
         *
         * ```typescript
         * // Load an existing PDF document
         * let document: PdfDocument = new PdfDocument(data, password);
         * // Access loaded form
         * let form: PdfForm = document.form;
         * // Gets the fields count
         * let count: number = form.count;
         * // Destroy the document
         * document.destroy();
         * ```
         */
        get: function () {
            return this._fields.length;
        },
        enumerable: true,
        configurable: true
    });
    Object.defineProperty(PdfForm.prototype, "needAppearances", {
        /**
         * Gets a value indicating whether need appearances (Read only).
         *
         * @returns {boolean} Need appearances.
         *
         * ```typescript
         * // Load an existing PDF document
         * let document: PdfDocument = new PdfDocument(data, password);
         * // Access loaded form
         * let form: PdfForm = document.form;
         * // Gets the boolean flag indicating need appearances
         * let needAppearances: number = form.needAppearances;
         * // Destroy the document
         * document.destroy();
         * ```
         */
        get: function () {
            if (this._dictionary.has('NeedAppearances')) {
                this._needAppearances = this._dictionary.get('NeedAppearances');
            }
            return this._needAppearances;
        },
        enumerable: true,
        configurable: true
    });
    Object.defineProperty(PdfForm.prototype, "exportEmptyFields", {
        /**
         * Gets a value indicating whether allow to export empty fields or not.
         *
         * @returns {boolean} Export empty fields.
         * ```typescript
         * // Load an existing PDF document
         * let document: PdfDocument = new PdfDocument(data, password);
         * // Access loaded form
         * let form: PdfForm = document.form;
         * // Gets a value indicating whether allow to export empty fields or not.
         * let exportEmptyFields: boolean = form.exportEmptyFields;
         * // Save the document
         * document.save('output.pdf');
         * // Destroy the document
         * document.destroy();
         * ```
         */
        get: function () {
            return this._exportEmptyFields;
        },
        /**
         * Sets a value indicating whether allow to export empty fields or not.
         *
         * @param {boolean} value Export empty fields.
         * ```typescript
         * // Load an existing PDF document
         * let document: PdfDocument = new PdfDocument(data, password);
         * // Access loaded form
         * let form: PdfForm = document.form;
         * // Sets a value indicating whether allow to export empty fields or not.
         * form.exportEmptyFields = false;
         * // Save the document
         * document.save('output.pdf');
         * // Destroy the document
         * document.destroy();
         * ```
         */
        set: function (value) {
            this._exportEmptyFields = value;
        },
        enumerable: true,
        configurable: true
    });
    Object.defineProperty(PdfForm.prototype, "_signatureFlag", {
        /**
         * Gets the current signature flags of the form (`SigFlags`).
         *
         * @private
         * @returns {_SignatureFlag} The active signature flags bitmask.
         */
        get: function () {
            return this._signFlag;
        },
        /**
         * Sets the form's signature flags and updates the `SigFlags` entry in the AcroForm dictionary.
         *
         * @private
         * @param {_SignatureFlag} value The signature flags bitmask to set.
         * @returns {void}
         */
        set: function (value) {
            if (value !== this._signFlag) {
                this._signFlag = value;
                this._dictionary.update('SigFlags', value);
            }
        },
        enumerable: true,
        configurable: true
    });
    Object.defineProperty(PdfForm.prototype, "fieldAutoNaming", {
        /**
         * Gets a value indicating whether the automatic field naming is enabled for form fields.
         *
         * @returns {boolean} Indicates if field auto naming is enabled.
         *
         * ```typescript
         * // Create new document.
         * let document: PdfDocument = new PdfDocument();
         * // Access loaded form
         * let form: PdfForm = document.form;
         * // Gets the value indicating if automatic field naming is enabled
         * let fieldAutoNaming: boolean = form.fieldAutoNaming;
         * // Destroy the document
         * document.destroy();
         * ```
         */
        get: function () {
            return this._fieldAutoNaming;
        },
        /**
         * Sets a value indicating whether field auto-naming is enabled for form fields.
         *
         * @param {boolean} value Enable or disable field auto naming. The default value is false.
         * ```typescript
         * // Create a new document
         * let document: PdfDocument = new PdfDocument();
         * // Access loaded form
         * let form: PdfForm = document.form;
         * // Enable automatic field naming for new form fields.
         * form.fieldAutoNaming = true;
         * // Save the document
         * document.save('output.pdf');
         * // Destroy the document
         * document.destroy();
         * ```
         */
        set: function (value) {
            this._fieldAutoNaming = value;
        },
        enumerable: true,
        configurable: true
    });
    /**
     * Gets the `PdfField` at the specified index.
     *
     * ```typescript
     * // Load an existing PDF document
     * let document: PdfDocument = new PdfDocument(data, password);
     * // Access the loaded form field
     * let field: PdfField = document.form.fieldAt(0);
     * // Save the document
     * document.save('output.pdf');
     * // Destroy the document
     * document.destroy();
     * ```
     *
     * @param {number} index Field index.
     * @returns {PdfField} Loaded PDF form field at the specified index.
     */
    PdfForm.prototype.fieldAt = function (index) {
        if (index < 0 || index >= this._fields.length) {
            throw Error('Index out of range.');
        }
        var field;
        if (this._parsedFields.has(index)) {
            field = this._parsedFields.get(index);
            this._isNeedAppearances = true;
        }
        else {
            var dictionary = void 0;
            var ref = this._fields[index]; // eslint-disable-line
            if (ref && ref instanceof _PdfReference) {
                dictionary = this._crossReference._fetch(ref);
            }
            if (dictionary) {
                field = this._parseFields(dictionary, ref);
                this._parsedFields.set(index, field);
                if (field && field instanceof PdfField) {
                    field._annotationIndex = index;
                }
            }
        }
        return field;
    };
    /**
     * Builds a map of widget annotation references from all pages in the document.
     * This collection is used to associate terminal fields with their corresponding
     * page-level widget annotations, enabling proper field-to-page linkage.
     *
     * @private
     * @returns {void}
     */
    PdfForm.prototype._getPageWidgetCollection = function () {
        this._pageWidgetReference = new Map();
        var document = this._crossReference._document;
        if (!document) {
            return;
        }
        for (var i = 0; i < document.pageCount; i++) {
            var page = document.getPage(i);
            if (!page || !page._pageDictionary) {
                continue;
            }
            var widgetAnnots = [];
            if (page._pageDictionary.has('Annots')) {
                widgetAnnots = page._pageDictionary.getRaw('Annots');
                if (widgetAnnots instanceof _PdfReference) {
                    widgetAnnots = this._crossReference._fetch(widgetAnnots);
                }
            }
            if (widgetAnnots && Array.isArray(widgetAnnots)) {
                for (var j = 0; j < widgetAnnots.length; j++) {
                    var ref = widgetAnnots[j];
                    if (ref && ref instanceof _PdfReference) {
                        var annotDictionary = this._crossReference._fetch(ref);
                        if (annotDictionary && annotDictionary.has('Subtype') && annotDictionary.get('Subtype') &&
                            annotDictionary.get('Subtype').name === 'Widget') {
                            this._pageWidgetReference.set(ref, annotDictionary);
                        }
                    }
                }
            }
        }
    };
    /**
     * Retrieves a form field by its index within the terminal fields collection.
     * Resolves the field dictionary with its associated page widget reference when available.
     *
     * @private
     * @param {number} index The index of the field in the terminal fields array.
     * @returns {PdfField} The parsed PDF form field, or `null` if not found or out of range.
     */
    PdfForm.prototype._getField = function (index) {
        var _this = this;
        if (!this._terminalFields || index < 0 || index >= this._terminalFields.length) {
            return null;
        }
        if (!this._pageWidgetReference) {
            this._getPageWidgetCollection();
        }
        var dictionary = this._terminalFields[index];
        var ref = dictionary._reference;
        var acroFields = this._dictionary ? this._dictionary.get('Fields') : null; // eslint-disable-line
        if (acroFields && this._pageWidgetReference && this._pageWidgetReference.size > 0) {
            var _found_1 = false;
            this._pageWidgetReference.forEach(function (wdict, wref) {
                if (_found_1) {
                    return;
                }
                if (dictionary && _this._compareWidgets(wdict, dictionary)) {
                    if (!dictionary.has('P')) {
                        dictionary = wdict;
                        if (_this._fieldsMap && _this._fieldsMap.has(wdict)) {
                            ref = _this._fieldsMap.get(wdict);
                        }
                    }
                    _found_1 = true;
                }
            });
        }
        var field = this._parseFields(dictionary, ref);
        if (field) {
            field._form = this;
        }
        return field;
    };
    /**
     * Parses a form field from a given field dictionary, resolving page widget associations
     * and constructing the appropriate PDF field type via `_parseFields`.
     *
     * @private
     * @param {_PdfDictionary} fieldDictionary The field dictionary to parse.
     * @returns {PdfField} The constructed PDF form field, or `null` if parsing fails.
     */
    PdfForm.prototype._getFieldFromDictionary = function (fieldDictionary) {
        var _this = this;
        if (!this._pageWidgetReference) {
            this._getPageWidgetCollection();
        }
        var dictionary = fieldDictionary;
        var ref = dictionary._reference;
        var acroFields = this._dictionary ? this._dictionary.get('Fields') : null; // eslint-disable-line
        if (acroFields && this._pageWidgetReference && this._pageWidgetReference.size > 0) {
            var found_1 = false;
            this._pageWidgetReference.forEach(function (wdict, wref) {
                if (found_1) {
                    return;
                }
                if (dictionary && _this._compareWidgets(wdict, dictionary)) {
                    if (!dictionary.has('P')) {
                        dictionary = wdict;
                        if (_this._fieldsMap && _this._fieldsMap.has(wdict)) {
                            ref = _this._fieldsMap.get(wdict);
                        }
                    }
                    found_1 = true;
                }
            });
        }
        var field = this._parseFields(dictionary, ref);
        if (field) {
            field._form = this;
        }
        return field;
    };
    /**
     * Parses a terminal form field from its dictionary and reference, instantiating the appropriate
     * field type based on `FT` and `Ff` (e.g., text, button, choice, signature).
     *
     * @private
     * @param {_PdfDictionary} dictionary The field dictionary to parse.
     * @param {_PdfReference} reference The indirect reference of the field.
     * @returns {PdfField} The constructed field instance.
     */
    PdfForm.prototype._parseFields = function (dictionary, reference) {
        var field;
        if (dictionary) {
            var key = _getInheritableProperty(dictionary, 'FT', false, true, 'Parent');
            var fieldFlags = 0;
            var flag = _getInheritableProperty(dictionary, 'Ff', false, true, 'Parent');
            if (typeof flag !== 'undefined') {
                fieldFlags = flag;
            }
            if (key) {
                switch (key.name.toLowerCase()) {
                    case 'tx':
                        field = PdfTextBoxField._load(this, dictionary, this._crossReference, reference);
                        break;
                    case 'btn':
                        if ((fieldFlags & _FieldFlag.pushButton) !== 0) {
                            field = PdfButtonField._load(this, dictionary, this._crossReference, reference);
                        }
                        else if ((fieldFlags & _FieldFlag.radio) !== 0) {
                            field = PdfRadioButtonListField._load(this, dictionary, this._crossReference, reference);
                        }
                        else {
                            field = PdfCheckBoxField._load(this, dictionary, this._crossReference, reference);
                        }
                        break;
                    case 'ch':
                        if ((fieldFlags & _FieldFlag.combo) !== 0) {
                            field = PdfComboBoxField._load(this, dictionary, this._crossReference, reference);
                        }
                        else {
                            field = PdfListBoxField._load(this, dictionary, this._crossReference, reference);
                        }
                        break;
                    case 'sig':
                        field = PdfSignatureField._load(this, dictionary, this._crossReference, reference);
                        break;
                }
            }
        }
        return field;
    };
    /**
     * Add a new `PdfField`.
     *
     * ```typescript
     * // Load an existing PDF document
     * let document: PdfDocument = new PdfDocument(data, password);
     * // Add a new form field
     * let index: number = document.form.add(field);
     * // Save the document
     * document.save('output.pdf');
     * // Destroy the document
     * document.destroy();
     * ```
     *
     * @param {PdfField} field Field object to add.
     * @returns {number} Field index.
     */
    PdfForm.prototype.add = function (field) {
        initializeTelemetryFeature('AcroForm', 'PDFLibrary');
        if (this._fields.length > 0) {
            var fieldsCollection = this._getFields();
            var old = fieldsCollection.find(function (oldField) { return oldField.name === field.name; }); // eslint-disable-line
            if (old && this._fieldAutoNaming) {
                var newName = this._getCorrectName(field._name);
                field._name = newName;
                field._dictionary.update('T', newName);
                this._fieldName.push(field._name);
                return this._doAdd(field);
            }
            else if (old && ((old instanceof PdfSignatureField && (old._isLoaded
                || old._crossReference._document._isLoaded)) ||
                !(old instanceof PdfSignatureField)) && this._checkType(old, field)) {
                this._fieldName.push(field._name);
                return this._groupingFormFields(field, old);
            }
        }
        this._requiresPostProcessing = true;
        this._fieldName.push(field._name);
        return this._doAdd(field);
    };
    /**
     * Adds a field to the form, updates the AcroForm `Fields` array, caches the parsed field,
     * and sets appearance/signature flags when applicable.
     *
     * @private
     * @param {PdfField} field The field to add to the form.
     * @returns {number} The index of the added field in the form.
     */
    PdfForm.prototype._doAdd = function (field) {
        if (this._fields.indexOf(field._ref) === -1) {
            this._fields.push(field._ref);
            this._dictionary.update('Fields', this._fields);
            this._parsedFields.set(this._fields.length - 1, field);
            field._form = this;
            this._crossReference._root._updated = true;
            if (field instanceof PdfSignatureField) {
                field._form._signatureFlag = _SignatureFlag.signatureExists | _SignatureFlag.appendOnly;
            }
            this._isNeedAppearances = true;
        }
        return (this._fields.length - 1);
    };
    /**
     * Groups a new field with an existing field having the same name by wiring widget parents,
     * merging kids, syncing flags/appearance, and handling radio options/selection where needed.
     *
     * @private
     * @param {PdfField} field The new field to group.
     * @param {PdfField} oldField The existing field with the same name.
     * @returns {number} The index of the grouped field (existing field’s index).
     */
    PdfForm.prototype._groupingFormFields = function (field, oldField) {
        if (oldField._name === field._name) {
            if (oldField.flatten || field.flatten) {
                field.flatten = true;
                oldField.flatten = true;
            }
        }
        if (!(field instanceof PdfRadioButtonListField && oldField instanceof PdfRadioButtonListField)) {
            var widgetDictionary = field.itemAt(0)._dictionary;
            if (widgetDictionary && widgetDictionary.has('Parent')) {
                delete widgetDictionary._map.Parent;
            }
            field.itemAt(0)._dictionary.set('Parent', oldField._ref);
            var fieldKidRef = field.itemAt(0)._ref;
            var oldFieldKids = oldField._dictionary.get('Kids'); // eslint-disable-line
            if (oldFieldKids && oldFieldKids.length > 0) {
                oldFieldKids.push(fieldKidRef);
                oldField._dictionary.update('Kids', oldFieldKids);
                oldField._dictionary._updated = true;
            }
            else {
                this._updateFieldsKids(oldField, field);
            }
            if (field instanceof PdfCheckBoxField && oldField instanceof PdfCheckBoxField) {
                var newItem = field.itemAt(0);
                var newValue = void 0;
                if (newItem && typeof newItem.exportValue === 'string') {
                    newValue = newItem.exportValue;
                }
                var appendedIndex = oldField.itemsCount - 1;
                oldField._parsedItems.set(appendedIndex, newItem);
                newItem._field = oldField;
                newItem._index = appendedIndex;
                if (!newValue && newValue !== '') {
                    return this._fields.length - 1;
                }
                var matchIndex = this._findFirstByExportValue(oldField, newValue);
                var groupHasSameExportValue = matchIndex >= 0;
                var oldSelectedValue = this._getSelectedExportValue(oldField);
                if (newItem.checked) {
                    if (groupHasSameExportValue) {
                        var matched = oldField.itemAt(matchIndex);
                        if (matched && !matched.checked) {
                            matched._field._isUpdating = false;
                            matched.checked = true;
                        }
                        if (!newItem.checked) {
                            newItem.checked = true;
                        }
                    }
                    else {
                        newItem.checked = true;
                    }
                }
                else {
                    if (oldSelectedValue && oldSelectedValue === newValue) {
                        newItem.checked = true;
                    }
                    else if (groupHasSameExportValue) {
                        var matched = oldField.itemAt(matchIndex);
                        if (matched && matched.checked && !newItem.checked) {
                            newItem.checked = true;
                        }
                    }
                }
                return this._fields.length - 1;
            }
            if ((field instanceof PdfButtonField && oldField instanceof PdfButtonField)) {
                if (!oldField._setAppearance) {
                    oldField._setAppearance = true;
                }
            }
            return this._fields.length - 1;
        }
        else {
            var baseDictionary = oldField._dictionary;
            if (baseDictionary && baseDictionary.has('Opt')) {
                delete baseDictionary._map.Opt;
            }
            var _radioButtonGroupingFields = [];
            _radioButtonGroupingFields.push(oldField);
            _radioButtonGroupingFields.push(field);
            var itemCount_1 = 0;
            var globalSelectedIndex_1 = -1;
            _radioButtonGroupingFields.forEach(function (field) {
                if (field.selectedIndex >= 0) {
                    var selectedItemIndex = itemCount_1 + field.selectedIndex;
                    if (selectedItemIndex > globalSelectedIndex_1) {
                        globalSelectedIndex_1 = selectedItemIndex;
                    }
                }
                itemCount_1 += field._kids.length;
            });
            if (oldField._kids.length !== oldField._parsedItems.size) {
                for (var j = 0; j < oldField._kids.length; j++) {
                    var existingItem = oldField._parsedItems.get(j);
                    if (!existingItem || existingItem.value !== oldField.itemAt(j).value) {
                        oldField._parsedItems.set(j, oldField.itemAt(j));
                    }
                }
            }
            var fieldKids = field._dictionary.get('Kids'); // eslint-disable-line
            if (fieldKids.length > 0) {
                var oldFieldKids = oldField._dictionary.get('Kids'); // eslint-disable-line
                var itemsCount = oldField.itemsCount;
                for (var i = 0; i < field.itemsCount; i++) {
                    var widgetDictionary = field.itemAt(i)._dictionary;
                    if (widgetDictionary && widgetDictionary.has('Parent')) {
                        delete widgetDictionary._map.Parent;
                    }
                    widgetDictionary.set('Parent', oldField._ref);
                    field.itemAt(i)._field = oldField;
                    field.itemAt(i)._index = itemsCount++;
                    itemCount_1++;
                    var fieldKidRef = field.itemAt(i)._ref;
                    oldFieldKids.push(fieldKidRef);
                }
                oldField._dictionary.update('Kids', oldFieldKids);
                oldField._dictionary._updated = true;
            }
            oldField.allowUnisonSelection = field.allowUnisonSelection;
            var count = oldField._parsedItems.size;
            for (var j = 0; j < field.itemsCount; j++) {
                oldField._parsedItems.set(count, field.itemAt(j));
                count++;
            }
            if (!field.allowUnisonSelection) {
                this._addItemsToOptionsArray(oldField);
            }
            if (_radioButtonGroupingFields.length > 0 && globalSelectedIndex_1 >= 0 && globalSelectedIndex_1 < itemCount_1) {
                _radioButtonGroupingFields[0].selectedIndex = globalSelectedIndex_1;
            }
            return this._fields.length - 1;
        }
    };
    /**
     * Finds the first item index within a checkbox field that has an `exportValue`
     * matching the provided `value`.
     *
     * @private
     * @param {PdfCheckBoxField} field The checkbox field to search.
     * @param {string} value The export value to match.
     * @returns {number} The index of the first matching item, or `-1` when not found.
     */
    PdfForm.prototype._findFirstByExportValue = function (field, value) {
        if (!field || field.itemsCount <= 0 || value == null) {
            return -1;
        }
        for (var i = 0; i < field.itemsCount; i++) {
            var item = field.itemAt(i);
            if (item && item.exportValue === value) {
                return i;
            }
        }
        return -1;
    };
    /**
     * Returns the export value of the currently selected item in a checkbox field.
     * If the field dictionary contains a `/V` entry it is returned first; otherwise
     * the checked state of individual `PdfStateItem`s is consulted.
     *
     * @private
     * @param {PdfCheckBoxField} field The checkbox field to query.
     * @returns {string} The selected export value, or `undefined` if none.
     */
    PdfForm.prototype._getSelectedExportValue = function (field) {
        var exportValue;
        if (!field) {
            return undefined;
        }
        if (field._dictionary && field._dictionary.has('V')) {
            var v = field._dictionary.get('V');
            if (v && typeof v.name === 'string') {
                exportValue = v.name;
            }
        }
        for (var i = 0; i < field.itemsCount; i++) {
            var item = field.itemAt(i);
            if (item && item.checked) {
                exportValue = item.exportValue;
            }
        }
        return exportValue;
    };
    /**
     * Converts a standalone field into a parent with `Kids` by creating a new parent dictionary,
     * moving relevant entries, and attaching both the old and new field widgets under it.
     *
     * @private
     * @param {PdfField} oldField The existing field that will become the parent.
     * @param {PdfField} newField The new field whose first widget is added as a kid.
     * @returns {void}
     */
    PdfForm.prototype._updateFieldsKids = function (oldField, newField) {
        var oldFieldDict = oldField._dictionary;
        var newDict = new _PdfDictionary(this._crossReference);
        var newFieldRef = this._crossReference._getNextReference();
        var fieldKeys = ['FT', 'T', 'V', 'Ff', 'Opt', 'I', 'TU'];
        fieldKeys.forEach(function (key) {
            if (oldFieldDict.has(key)) {
                newDict.update(key, oldFieldDict.get(key));
                delete oldFieldDict._map[key]; // eslint-disable-line
            }
        });
        oldField._dictionary._updated = true;
        oldFieldDict.set('Parent', newFieldRef);
        newField.itemAt(0)._dictionary.set('Parent', newFieldRef);
        var kidElements = [];
        kidElements.push(oldField._ref);
        var fieldKidRef = newField.itemAt(0)._ref;
        kidElements.push(fieldKidRef);
        newDict.update('Kids', kidElements);
        newDict._updated = true;
        this._crossReference._cacheMap.set(newFieldRef, newDict);
        var acroForm = this._crossReference._document._catalog._catalogDictionary.get('AcroForm'); // eslint-disable-line
        var fields = acroForm.get('Fields'); // eslint-disable-line
        var index = fields.indexOf(oldField._ref);
        if (index !== -1) {
            fields[index] = newFieldRef;
        }
        oldField._ref = newFieldRef;
        oldField._dictionary = newDict;
        oldField._kids = newDict.get('Kids');
        oldField._dictionary._updated = true;
    };
    /**
     * Populates the `Opt` array for a radio button group when duplicate export values are present,
     * ensuring unique option entries for appearance resolution.
     *
     * @private
     * @param {PdfField} baseField The radio button field used to derive option values.
     * @returns {void}
     */
    PdfForm.prototype._addItemsToOptionsArray = function (baseField) {
        var seenValues = new Set();
        var duplicateValues = new Set();
        var allValues = [];
        var radioField = baseField;
        for (var i = 0; i < radioField.itemsCount; i++) {
            var value = radioField.itemAt(i).value;
            allValues.push(value);
            if (seenValues.has(value)) {
                duplicateValues.add(value);
            }
            else {
                seenValues.add(value);
            }
        }
        if (duplicateValues.size > 0) {
            baseField._dictionary.set('Opt', allValues);
        }
    };
    /**
     * Computes a unique field name by appending a generated identifier when the base name already exists.
     *
     * @private
     * @param {string} name The proposed field name.
     * @returns {string} A unique field name derived from the input.
     */
    PdfForm.prototype._getCorrectName = function (name) {
        var correctName = name;
        var existingIndex = this._fieldName.indexOf(name);
        if (existingIndex !== -1) {
            var uid = this._generateUniqueIdentifier();
            correctName = name + "_" + uid;
        }
        return correctName;
    };
    /**
     * Generates a simple pseudo-random identifier string for field auto-naming.
     *
     * @private
     * @returns {string} The generated identifier.
     */
    PdfForm.prototype._generateUniqueIdentifier = function () {
        return Math.floor(Math.random() * 10000).toString();
    };
    /**
     * Remove the specified PDF form field.
     *
     * ```typescript
     * // Load an existing PDF document
     * let document: PdfDocument = new PdfDocument(data, password);
     * // Access the loaded form field
     * let field: PdfField = document.form.fieldAt(3);
     * // Remove the form field
     * document.form.removeField(field);
     * // Save the document
     * document.save('output.pdf');
     * // Destroy the document
     * document.destroy();
     * ```
     *
     * @param {PdfField} field Field object to remove.
     * @returns {void} Nothing.
     */
    PdfForm.prototype.removeField = function (field) {
        var index = this._fields.indexOf(field._ref);
        if (index >= 0) {
            this.removeFieldAt(index);
        }
    };
    /**
     * Remove the PDF form field from specified index.
     *
     * ```typescript
     * // Load an existing PDF document
     * let document: PdfDocument = new PdfDocument(data, password);
     * // Remove the form field from the specified index
     * document.form.removeFieldAt(3);
     * // Save the document
     * document.save('output.pdf');
     * // Destroy the document
     * document.destroy();
     * ```
     *
     * @param {number} index Field index to remove.
     * @returns {void} Nothing.
     */
    PdfForm.prototype.removeFieldAt = function (index) {
        var field = this.fieldAt(index);
        if (field) {
            if (field._kidsCount > 0) {
                for (var i = field._kidsCount - 1; i >= 0; i--) {
                    var item = field.itemAt(i);
                    var page = void 0;
                    if (item) {
                        page = item._getPage();
                        if (page) {
                            page._removeAnnotation(item._ref);
                        }
                    }
                }
            }
            else if (field._dictionary.has('Subtype') && field._dictionary.get('Subtype').name === 'Widget') {
                var page = field.page;
                if (page) {
                    page._removeAnnotation(field._ref);
                }
            }
            this._parsedFields.delete(index);
            this._reorderParsedAnnotations(index);
        }
        this._fields.splice(index, 1);
        var document = this._crossReference._document;
        var catalog = document._catalog;
        if (this._fields.length === 0 && document && catalog && catalog._catalogDictionary) {
            catalog._catalogDictionary._updated = true;
            this._crossReference._allowCatalog = true;
        }
        this._dictionary.set('Fields', this._fields);
        this._dictionary._updated = true;
    };
    /**
     * Rebuilds the parsed fields cache after a removal, compacting indices above the removed position.
     *
     * @private
     * @param {number} index The removed field index.
     * @returns {void}
     */
    PdfForm.prototype._reorderParsedAnnotations = function (index) {
        var result = new Map();
        this._parsedFields.forEach(function (value, key) {
            if (key > index) {
                result.set(key - 1, value);
            }
            else {
                result.set(key, value);
            }
        });
        this._parsedFields = result;
    };
    /**
     * Sets the flag to indicate the new appearance creation
     * If true, appearance will not be created. Default appearance has been considered.
     * If false, new appearance stream has been created from field values and updated as normal appearance.
     *
     * ```typescript
     * // Load an existing PDF document
     * let document: PdfDocument = new PdfDocument(data, password);
     * // Set boolean flag to create a new appearance stream for form fields.
     * document.form.setDefaultAppearance(false);
     * // Save the document
     * document.save('output.pdf');
     * // Destroy the document
     * document.destroy();
     * ```
     *
     * @param {boolean} value Set default appearance.
     * @returns {void} Nothing.
     */
    PdfForm.prototype.setDefaultAppearance = function (value) {
        this._setAppearance = !value;
        this._needAppearances = value;
        this._isDefaultAppearance = value;
    };
    PdfForm.prototype.orderFormFields = function (tabOrder) {
        var _this = this;
        if (tabOrder === null || typeof tabOrder === 'undefined') {
            this.orderFormFields(new Map());
        }
        else {
            var tab_1;
            var document_1 = this._crossReference._document;
            var value_1;
            if (tabOrder && tabOrder instanceof Map) {
                var setTabOrder_1 = true;
                if (tabOrder.size > 0) {
                    this._tabCollection = tabOrder;
                }
                else {
                    setTabOrder_1 = false;
                    this._tabCollection = tabOrder;
                }
                var fieldCollection_1 = new Map();
                this._fieldCollection = this._getFields();
                if (_isNullOrUndefined(this._fieldCollection) && this._fieldCollection.length > 0) {
                    var page = this._fieldCollection[0].page;
                    if (page && document_1) {
                        this._fieldCollection.forEach(function (field) {
                            if (field.page) {
                                var index = _getPageIndex(document_1, _this._sortItemByPageIndex(field, true)._pageDictionary);
                                if (index >= 0) {
                                    if (fieldCollection_1.has(index)) {
                                        value_1 = fieldCollection_1.get(index);
                                        value_1.push(field);
                                    }
                                    else {
                                        value_1 = [];
                                        value_1.push(field);
                                        fieldCollection_1.set(index, value_1);
                                    }
                                    var page_1 = document_1.getPage(index);
                                    if (!_this._tabCollection.has(index)) {
                                        _this._tabCollection.set(index, page_1.tabOrder);
                                    }
                                    if (setTabOrder_1) {
                                        page_1.tabOrder = _this._tabCollection.get(index);
                                    }
                                }
                            }
                        });
                        var fieldsCount_1 = 0;
                        fieldCollection_1.forEach(function (value, key) {
                            _this._tabOrder = _this._tabCollection.get(key);
                            if (_this._tabOrder !== PdfFormFieldsTabOrder.structure) {
                                var fields = value;
                                fields.sort(function (pdfField1, pdfField2) {
                                    return _this._compareFields(pdfField1, pdfField2);
                                });
                                fields.forEach(function (field, j) {
                                    var fieldIndex = _this._fieldCollection.indexOf(field);
                                    if (fieldIndex !== -1 && fieldIndex !== fieldsCount_1 + j) {
                                        var fieldToMove = _this._fieldCollection[fieldIndex];
                                        _this._fieldCollection.splice(fieldIndex, 1);
                                        _this._fieldCollection.splice(fieldsCount_1 + j, 0, fieldToMove);
                                    }
                                });
                            }
                            fieldsCount_1 += value.length;
                        });
                    }
                }
            }
            else {
                this._tabOrder = tabOrder;
                tab_1 = this._getOrder(this._tabOrder);
                this._fieldCollection = this._getFields();
                this._fieldCollection.sort(function (pdfField1, pdfField2) {
                    return _this._compareFields(pdfField1, pdfField2);
                });
            }
            this._parsedFields.clear();
            this._fieldCollection.forEach(function (field, i) {
                _this._parsedFields.set(i, field);
                _this._fields[i] = field._ref;
                if (tab_1) {
                    field.page._pageDictionary.update('Tabs', tab_1);
                }
            });
            this._dictionary.update('Fields', this._fields);
        }
    };
    /**
     * Traverses the AcroForm field tree, collects terminal fields, repairs missing `Parent` links,
     * and initializes the form's field list and known form names.
     *
     * @private
     * @returns {void}
     */
    PdfForm.prototype._createFields = function () {
        var _this = this;
        var fields; // eslint-disable-line
        var fieldsMap = new Map();
        if (this._dictionary && this._dictionary.has('Fields')) {
            fields = this._dictionary.get('Fields');
        }
        var count = 0;
        var nodes = []; // eslint-disable-line
        var terminalFields = [];
        while (fields && fields.length > 0) {
            var _loop_1 = function () {
                var ref = fields[count]; // eslint-disable-line
                var fieldDictionary = void 0;
                if (ref && ref instanceof _PdfReference) {
                    fieldDictionary = this_1._crossReference._fetch(ref);
                    if (fieldDictionary && fieldDictionary instanceof _PdfDictionary) {
                        fieldsMap.set(fieldDictionary, ref);
                    }
                }
                var fieldKids = void 0;
                if (fieldDictionary && fieldDictionary instanceof _PdfDictionary && fieldDictionary.has('Kids')) {
                    fieldKids = fieldDictionary.get('Kids');
                    if (fieldKids && fieldKids.length > 0) {
                        fieldKids.forEach(function (reference) {
                            if (reference instanceof _PdfReference) {
                                var kidsDict = _this._crossReference._fetch(reference);
                                if (kidsDict) {
                                    fieldsMap.set(kidsDict, reference);
                                    if (!kidsDict.has('Parent')) {
                                        kidsDict.update('Parent', ref);
                                    }
                                }
                            }
                        });
                    }
                }
                if (!fieldKids) {
                    if (fieldDictionary && fieldDictionary instanceof _PdfDictionary) {
                        if (terminalFields.indexOf(fieldDictionary) === -1) {
                            terminalFields.push(fieldDictionary);
                            if (fieldDictionary.has('T')) {
                                var fieldName = fieldDictionary.get('T');
                                if (this_1._formNames.indexOf(fieldName) === -1) {
                                    this_1._formNames.push(fieldName);
                                }
                            }
                        }
                    }
                }
                else {
                    var isNode = (!fieldDictionary.has('FT')) || this_1._isNode(fieldKids);
                    if (isNode) {
                        nodes.push({ fields: fields, count: count });
                        this_1._hasKids = true;
                        count = -1;
                        fields = fieldKids;
                    }
                    else {
                        terminalFields.push(fieldDictionary);
                        if (fieldDictionary.has('T')) {
                            var fieldName = fieldDictionary.get('T');
                            if (this_1._formNames.indexOf(fieldName) === -1) {
                                this_1._formNames.push(fieldName);
                            }
                        }
                    }
                }
            };
            var this_1 = this;
            for (; count < fields.length; count++) {
                _loop_1();
            }
            if (nodes.length === 0) {
                break;
            }
            var entry = nodes.pop(); // eslint-disable-line
            fields = entry.fields;
            count = entry.count + 1;
        }
        this._terminalFields = terminalFields;
        this._fieldsMap = fieldsMap;
        this._createFieldCollection(terminalFields, fieldsMap);
    };
    PdfForm.prototype._createFieldCollection = function (terminalFields, fieldsMap) {
        var pageWidgets = new Map();
        var document = this._crossReference._document;
        var widgetCollection = [];
        this._widgetDictionary = new Map();
        if (document) {
            for (var i = 0; i < document.pageCount; i++) {
                var page = document.getPage(i);
                if (!page || !page._pageDictionary) {
                    continue;
                }
                var pageDictionary = page._pageDictionary;
                var widgetAnnots = [];
                if (pageDictionary && pageDictionary.has('Annots')) {
                    widgetAnnots = pageDictionary.getRaw('Annots');
                    if (widgetAnnots instanceof _PdfReference) {
                        widgetAnnots = this._crossReference._fetch(widgetAnnots);
                    }
                }
                var widgets = [];
                if (widgetAnnots && Array.isArray(widgetAnnots) && widgetAnnots.length > 0) {
                    for (var j = 0; j < widgetAnnots.length; j++) {
                        var ref = widgetAnnots[j];
                        if (ref && ref instanceof _PdfReference) {
                            widgetCollection.push(ref);
                            var annotDictionary = this._crossReference._fetch(ref);
                            if (annotDictionary && annotDictionary.has('Subtype') &&
                                annotDictionary.get('Subtype').name === 'Widget') {
                                annotDictionary._reference = ref;
                                if (annotDictionary.has('T')) {
                                    var tname = annotDictionary.get('T');
                                    if (this._formNames.indexOf(tname) === -1) {
                                        if (tname) {
                                            var arr = this._widgetDictionary.get(tname);
                                            if (!arr) {
                                                arr = [];
                                                this._widgetDictionary.set(tname, arr);
                                            }
                                            arr.push(annotDictionary);
                                        }
                                    }
                                }
                                widgets.push(annotDictionary);
                            }
                        }
                    }
                    pageWidgets.set(i, widgets);
                }
            }
        }
        for (var i = 0; i < terminalFields.length; i++) {
            var fieldDictionary = terminalFields[i];
            var fieldRef = fieldsMap.get(fieldDictionary);
            if (fieldRef && this._removeInvalidFields(fieldDictionary, pageWidgets, fieldRef, widgetCollection)) {
                if (this._fields.indexOf(fieldRef) === -1) {
                    this._fields.push(fieldRef);
                }
            }
        }
        if (terminalFields.length > 0) {
            this._processRemainingWidgets();
        }
        this._createFormFieldsFromWidgets(terminalFields.length);
    };
    PdfForm.prototype._processRemainingWidgets = function () {
        var document = this._crossReference._document;
        for (var i = 0; i < document.pageCount; i++) {
            var page = document.getPage(i);
            if (!page || !page._pageDictionary) {
                continue;
            }
            var pageDictionary = page._pageDictionary;
            var widgetAnnots = [];
            if (pageDictionary.has('Annots')) {
                widgetAnnots = pageDictionary.getRaw('Annots');
                if (widgetAnnots instanceof _PdfReference) {
                    widgetAnnots = this._crossReference._fetch(widgetAnnots);
                }
            }
            for (var j = 0; j < widgetAnnots.length; j++) {
                var ref = widgetAnnots[j];
                if (ref instanceof _PdfReference && this._fields.indexOf(ref) === -1) {
                    var annotDictionary = this._crossReference._fetch(ref);
                    if (annotDictionary &&
                        annotDictionary.has('Subtype') &&
                        annotDictionary.get('Subtype') &&
                        annotDictionary.get('Subtype').name === 'Widget' &&
                        annotDictionary.has('P')) {
                        if (annotDictionary.has('Parent')) {
                            var parentRef = annotDictionary.getRaw('Parent');
                            var annotationParentDictionary = void 0;
                            if (parentRef && parentRef instanceof _PdfReference) {
                                annotationParentDictionary = this._crossReference._fetch(parentRef);
                                if (annotationParentDictionary && annotationParentDictionary.has('T')) {
                                    var parentValue = annotationParentDictionary.get('T');
                                    if (this._formNames.indexOf(parentValue) === -1 && this._fields.indexOf(parentRef) === -1) {
                                        this._fields.push(parentRef);
                                    }
                                }
                            }
                        }
                        else if (annotDictionary.has('FT') && annotDictionary.has('T') && this._formNames.indexOf(annotDictionary.get('T')) === -1) {
                            this._fields.push(ref);
                        }
                    }
                }
            }
        }
    };
    /**
     * Checks whether a field dictionary contains a non-empty `Kids` array.
     *
     * @private
     * @param {_PdfDictionary} dictionary The field dictionary to inspect.
     * @returns {boolean} Returns `true` if `Kids` exists and is non-empty; otherwise, `false`.
     */
    PdfForm.prototype._hasValidKids = function (dictionary) {
        var kidsArray = dictionary.get('Kids'); // eslint-disable-line
        return kidsArray && kidsArray.length > 0;
    };
    /**
     * Validates a field (and its descendants) against the page widget lists, removing any invalid
     * kid references and determining whether the field has at least one valid descendant.
     *
     * @private
     * @param {_PdfDictionary} dictionary The field or node dictionary.
     * @param {Map<number, _PdfDictionary[]>} pageWidgets A mapping of page index to widget dictionaries.
     * @param {_PdfReference} ref The reference of the current field/widget.
     * @param {_PdfReference[]} widgetCollection Flat list of widget references found in pages.
     * @returns {boolean} Returns `true` if the field or any child remains valid; otherwise, `false`.
     */
    PdfForm.prototype._removeInvalidFields = function (dictionary, pageWidgets, ref, widgetCollection) {
        if (!dictionary) {
            return false;
        }
        if (dictionary.has('Kids') && this._hasValidKids(dictionary)) {
            this._isValidKids = true;
            var kidsArray = dictionary.get('Kids'); // eslint-disable-line
            var invalidKids = [];
            var hasValidChild = false;
            for (var i = 0; i < kidsArray.length; i++) {
                var childDictionary = void 0;
                var kidRef = kidsArray[i]; // eslint-disable-line
                if (kidRef instanceof _PdfReference) {
                    childDictionary = this._crossReference._fetch(kidRef);
                }
                else if (kidRef instanceof _PdfDictionary) {
                    childDictionary = kidRef;
                }
                if (childDictionary) {
                    if (childDictionary.has('P')) {
                        var pageRef = childDictionary.get('P'); // eslint-disable-line
                        var pageDictionary = void 0;
                        if (pageRef instanceof _PdfReference) {
                            pageDictionary = this._crossReference._fetch(pageRef);
                        }
                        else if (pageRef instanceof _PdfDictionary) {
                            pageDictionary = pageRef;
                        }
                        if (pageDictionary && pageDictionary.has('Annots')) {
                            var annots = pageDictionary.get('Annots'); // eslint-disable-line
                            if (annots instanceof _PdfReference) {
                                annots = this._crossReference._fetch(annots);
                            }
                            if (annots && Array.isArray(annots)) {
                                var kidExists = annots.indexOf(kidRef) !== -1;
                                if (!kidExists) {
                                    invalidKids.push(i);
                                    continue;
                                }
                            }
                        }
                    }
                    var isChildValid = this._removeInvalidFields(childDictionary, pageWidgets, kidRef, widgetCollection);
                    if (isChildValid) {
                        hasValidChild = true;
                    }
                    else {
                        invalidKids.push(i);
                    }
                }
                else {
                    invalidKids.push(i);
                }
            }
            for (var i = invalidKids.length - 1; i >= 0; i--) {
                kidsArray.splice(invalidKids[i], 1);
            }
            this._isValidKids = false;
            if (kidsArray.length > 0 && hasValidChild) {
                dictionary.update('Kids', kidsArray);
                return true;
            }
            return false;
        }
        else {
            return this._validateField(dictionary, pageWidgets, ref, widgetCollection);
        }
    };
    /**
     * Determines whether a terminal field dictionary represents a valid widget by checking for
     * page and rectangle entries or by matching against known page widgets.
     *
     * @private
     * @param {_PdfDictionary} fieldDictionary The terminal field dictionary to validate.
     * @param {Map<number, _PdfDictionary[]>} pageWidgets A mapping of page index to widget dictionaries.
     * @param {_PdfReference} ref The reference of the field/widget under validation.
     * @param {_PdfReference[]} widgetCollection Flat list of widget references found in pages.
     * @returns {boolean} Returns `true` if the field is valid; otherwise, `false`.
     */
    PdfForm.prototype._validateField = function (fieldDictionary, pageWidgets, ref, widgetCollection) {
        var _this = this;
        if (!fieldDictionary || !pageWidgets) {
            return false;
        }
        if (fieldDictionary.has('P') && fieldDictionary.has('Rect')) {
            return true;
        }
        if (widgetCollection && widgetCollection.indexOf(ref) !== -1) {
            return true;
        }
        var isValid = false;
        pageWidgets.forEach(function (widgets, pageIndex) {
            if (widgets && widgets.length > 0) {
                for (var j = 0; j < widgets.length; j++) {
                    var widget = widgets[j];
                    if (widget && _this._compareWidgets(widget, fieldDictionary)) {
                        if (_this._isValidKids) {
                            isValid = true;
                            if (!fieldDictionary.has('P') && !widget.has('P')) {
                                var page = widget._crossReference._document.getPage(pageIndex);
                                fieldDictionary.update('P', page._ref);
                            }
                            return;
                        }
                        else if (_this._fields.indexOf(widget._reference) === -1) {
                            if (widget.has('FT') && widget.has('Type') && widget.get('Type').name === 'Annot' &&
                                widget.has('Subtype') && widget.get('Subtype').name === 'Widget' && !widget.has('P')) {
                                var page = widget._crossReference._document.getPage(pageIndex);
                                widget.update('P', page._ref);
                            }
                            _this._fields.push(widget._reference);
                            return;
                        }
                    }
                }
            }
        });
        return isValid;
    };
    PdfForm.prototype._compareWidgets = function (widget, annotDictionary) {
        var isSame = false;
        if (widget && annotDictionary) {
            var wCount = widget.size;
            var aCount = annotDictionary.size;
            if (wCount === aCount || wCount + 1 === aCount || wCount === aCount + 1) {
                var widgetType = widget.get('FT');
                var annotType = annotDictionary.get('FT');
                if (widgetType && annotType && widgetType.name === annotType.name) {
                    var widgetName = widget.get('T');
                    var annotName = annotDictionary.get('T');
                    if (widgetName && annotName && widgetName === annotName) {
                        var widgetValue = widget.get('V');
                        var annotValue = annotDictionary.get('V');
                        if (widgetValue && annotValue && widgetValue === annotValue) {
                            isSame = true;
                        }
                        else {
                            if (widget.has('Parent') && annotDictionary.has('Parent')) {
                                var widgetHolder = widget.getRaw('Parent');
                                var annotHolder = annotDictionary.getRaw('Parent');
                                if (widgetHolder && annotHolder &&
                                    widgetHolder === annotHolder) {
                                    isSame = true;
                                }
                            }
                            else if (widget.has('TU') && annotDictionary.has('TU')) {
                                var widgetTU = widget.get('TU');
                                var annotTU = annotDictionary.get('TU');
                                if (widgetTU && annotTU && widgetTU === annotTU) {
                                    isSame = true;
                                }
                            }
                            else {
                                if (widget.has('Rect') && annotDictionary.has('Rect')) {
                                    var widgetArray = widget.get('Rect');
                                    var annotArray = annotDictionary.get('Rect');
                                    if (Array.isArray(widgetArray) && Array.isArray(annotArray) &&
                                        widgetArray.length === annotArray.length) {
                                        var w1 = widgetArray[0];
                                        var a1 = annotArray[0];
                                        var w2 = widgetArray[1];
                                        var a2 = annotArray[1];
                                        if (typeof w1 === 'number' && typeof a1 === 'number' &&
                                            typeof w2 === 'number' && typeof a2 === 'number') {
                                            if (w1 === a1 && w2 === a2) {
                                                isSame = true;
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
                else if (!widgetType && !annotType) {
                    if (widget.has('TU') && annotDictionary.has('TU')) {
                        var widgetTU = widget.get('TU');
                        var annotTU = annotDictionary.get('TU');
                        if (widgetTU && annotTU && widgetTU === annotTU) {
                            isSame = true;
                        }
                        else {
                            isSame = false;
                        }
                    }
                    if (widget.has('Rect') && annotDictionary.has('Rect')) {
                        var widgetArray = widget.get('Rect');
                        var annotArray = annotDictionary.get('Rect');
                        if (Array.isArray(widgetArray) && Array.isArray(annotArray) &&
                            widgetArray.length === annotArray.length) {
                            var w1 = widgetArray[0];
                            var a1 = annotArray[0];
                            var w2 = widgetArray[1];
                            var a2 = annotArray[1];
                            if (typeof w1 === 'number' && typeof a1 === 'number' &&
                                typeof w2 === 'number' && typeof a2 === 'number') {
                                if (w1 === a1 && w2 === a2) {
                                    isSame = true;
                                }
                                else {
                                    isSame = false;
                                }
                            }
                        }
                    }
                }
            }
        }
        return isSame;
    };
    /**
     * Create form fields from previously discovered terminal widgets starting at index.
     * Mirrors the C# CreateFormFieldsFromWidgets logic: add terminal fields not yet added
     * and merge radio-group items when multiple widgets share the same name.
     *
     * @private
     * @param {number} startIndex The starting index into terminal fields.
     * @returns {void}
     */
    PdfForm.prototype._createFormFieldsFromWidgets = function (startIndex) {
        if (!this._terminalFields) {
            return;
        }
        this._processTerminalFields(startIndex);
        this._processWidgetDictionary();
    };
    /**
     * Process terminal fields starting from the specified index.
     * Adds fields to the form, tracking added field names to avoid duplicates.
     *
     * @private
     * @param {number} startIndex The starting index into terminal fields.
     * @returns {void}
     */
    PdfForm.prototype._processTerminalFields = function (startIndex) {
        for (var i = startIndex; i < this._terminalFields.length; i++) {
            var field = this.fieldAt(i);
            if (!field) {
                continue;
            }
            var name_1 = field.name;
            if (name_1 && !this._addedFieldNames.has(name_1)) {
                this._doAdd(field);
                this._addedFieldNames.add(name_1);
            }
            else if (!name_1) {
                this._doAdd(field);
            }
        }
    };
    /**
     * Process widget dictionary to handle radio button groups and single widgets.
     * Merges radio button items when multiple widgets share the same name.
     *
     * @private
     * @returns {void}
     */
    PdfForm.prototype._processWidgetDictionary = function () {
        var _this = this;
        if (!this._widgetDictionary) {
            return;
        }
        this._widgetDictionary.forEach(function (list) {
            if (!list || list.length === 0) {
                return;
            }
            if (list.length > 1) {
                _this._processMultipleWidgets(list);
            }
            else {
                _this._processSingleWidget(list[0]);
            }
        });
    };
    /**
     * Process multiple widgets with the same name, merging radio button items.
     *
     * @private
     * @param {_PdfDictionary[]} list The list of widget dictionaries with the same name.
     * @returns {void}
     */
    PdfForm.prototype._processMultipleWidgets = function (list) {
        var firstDict = list[0];
        var baseField = this._getFieldFromDictionary(firstDict);
        if (baseField) {
            this._terminalFields.push(baseField._dictionary);
            this._doAdd(baseField);
        }
        var radioField = baseField instanceof PdfRadioButtonListField ? baseField : undefined;
        for (var k = 1; k < list.length; k++) {
            var dict = list[k];
            var field = this._getFieldFromDictionary(dict);
            if (!field) {
                continue;
            }
            if (radioField && field instanceof PdfRadioButtonListField) {
                this._mergeRadioButtonItems(radioField, field);
            }
            if (field.name) {
                this._handleFieldNaming(field);
            }
            this._terminalFields.push(field._dictionary);
            this._doAdd(field);
        }
    };
    /**
     * Merge radio button items from one field into another.
     *
     * @private
     * @param {PdfRadioButtonListField} targetField The target radio button field to merge into.
     * @param {PdfRadioButtonListField} sourceField The source radio button field to merge from.
     * @returns {void}
     */
    PdfForm.prototype._mergeRadioButtonItems = function (targetField, sourceField) {
        for (var j = 0; j < sourceField.itemsCount; j++) {
            var item = sourceField.itemAt(j);
            if (item) {
                var insertIndex = targetField._parsedItems.size;
                targetField._parsedItems.set(insertIndex, item);
            }
        }
    };
    /**
     * Handle field naming by either correcting duplicate names or adding to the field name list.
     *
     * @private
     * @param {PdfField} field The field to process for naming.
     * @returns {void}
     */
    PdfForm.prototype._handleFieldNaming = function (field) {
        if (!this._validFieldName(field)) {
            field._dictionary.update('T', this._getCorrectName(field.name));
        }
        else {
            this._fieldName.push(field.name);
        }
    };
    /**
     * Process a single widget dictionary entry.
     *
     * @private
     * @param {_PdfDictionary} dict The widget dictionary to process.
     * @returns {void}
     */
    PdfForm.prototype._processSingleWidget = function (dict) {
        if (!dict) {
            return;
        }
        if (this._terminalFields.indexOf(dict) === -1) {
            this._terminalFields.push(dict);
        }
        var idx = this._terminalFields.length - 1;
        var field = idx >= 0 ? this._getField(idx) : undefined;
        if (field) {
            this._doAdd(field);
        }
    };
    /**
     * Validates whether a field name is unique within the form.
     *
     * @private
     * @param {PdfField} field The field to validate.
     * @returns {boolean} Returns `true` if the field name is valid (unique); otherwise, `false`.
     */
    PdfForm.prototype._validFieldName = function (field) {
        return this._fieldName.indexOf(field.name) === -1;
    };
    /**
     * Determines whether the provided `Kids` collection represents a non widget node
     * (i.e., its first child is not a `Widget` subtype).
     *
     * @private
     * @param {any[]} kids The array of kid dictionaries or references.
     * @returns {boolean} Returns `true` if the entry is a non terminal node; otherwise, `false`.
     */
    PdfForm.prototype._isNode = function (kids) {
        var isNode = false;
        if (_isNullOrUndefined(kids) && kids.length > 0) {
            var entry = kids[0]; // eslint-disable-line
            var dictionary = void 0;
            if (_isNullOrUndefined(entry)) {
                if (entry instanceof _PdfDictionary) {
                    dictionary = entry;
                }
                else if (entry instanceof _PdfReference) {
                    dictionary = this._crossReference._fetch(entry);
                }
            }
            if (dictionary && dictionary.has('Subtype')) {
                var subtype = dictionary.get('Subtype');
                if (subtype && subtype.name !== 'Widget') {
                    isNode = true;
                }
            }
        }
        return isNode;
    };
    /**
     * Enumerates and collects all widget annotation references for the form's fields,
     * traversing each field’s `Kids` or the field itself when no children are present.
     *
     * @private
     * @returns {Array<_PdfReference>} The array of widget references.
     */
    PdfForm.prototype._parseWidgetReferences = function () {
        var _this = this;
        if (typeof this._widgetReferences === 'undefined' && this.count > 0) {
            this._widgetReferences = [];
            this._fields.forEach(function (fieldReference) {
                var dictionary = _this._crossReference._fetch(fieldReference);
                if (dictionary) {
                    if (dictionary.has('Kids')) {
                        var fieldKids = dictionary.get('Kids');
                        if (fieldKids && fieldKids.length > 0) {
                            fieldKids.forEach(function (kidReference) {
                                var kidDictionary;
                                if (kidReference && kidReference instanceof _PdfDictionary) {
                                    kidDictionary = kidReference;
                                }
                                else if (kidReference && kidReference instanceof _PdfReference) {
                                    kidDictionary = _this._crossReference._fetch(kidReference);
                                }
                                if (kidDictionary && kidDictionary.has('Subtype')) {
                                    var subtype = kidDictionary.get('Subtype');
                                    if (subtype && subtype.name === 'Widget') {
                                        _this._widgetReferences.push(kidReference);
                                    }
                                }
                            });
                        }
                    }
                    else {
                        _this._widgetReferences.push(fieldReference);
                    }
                }
            });
        }
        return this._widgetReferences;
    };
    /**
     * Performs post-processing for all fields: applies tab order re arrangement (when manual),
     * generates appearances or flattens as required, and removes fields flattened for the specified page.
     *
     * @private
     * @param {boolean} isFlatten When `true`, flatten field appearances into the page content.
     * @param {PdfPage} [pageToImport] Optional page context to restrict processing/removal.
     * @returns {void}
     */
    PdfForm.prototype._doPostProcess = function (isFlatten, pageToImport) {
        for (var i = this.count - 1; i >= 0; i--) {
            var field = this.fieldAt(i);
            if (field && !field._isLoaded && typeof field._tabIndex !== 'undefined' && field._tabIndex >= 0) {
                var page = field._page;
                if (page &&
                    page._pageDictionary.has('Annots') &&
                    (page.tabOrder === PdfFormFieldsTabOrder.manual || this._tabOrder === PdfFormFieldsTabOrder.manual)) {
                    var annots = page._pageDictionary.get('Annots');
                    var annotationCollection = new PdfAnnotationCollection(annots, this._crossReference, page);
                    page._annotations = annotationCollection;
                    for (var i_1 = 0; i_1 < field.itemsCount; i_1++) {
                        var item = field.itemAt(i_1);
                        if (item && item instanceof PdfWidgetAnnotation) {
                            var index = annots.indexOf(item._ref);
                            if (index < 0) {
                                index = field._annotationIndex;
                            }
                            if (index >= 0) {
                                var annotations = page.annotations._reArrange(field._ref, field._tabIndex, index);
                                page._pageDictionary.update('Annots', annotations);
                                page._pageDictionary._updated = true;
                            }
                        }
                    }
                }
            }
            if (field && ((pageToImport && field.page === pageToImport) || !pageToImport)) {
                if (pageToImport) {
                    field._isImport = true;
                }
                field._doPostProcess(isFlatten || field.flatten);
                if (!isFlatten && field.flatten || (isFlatten && pageToImport && field.page === pageToImport)) {
                    this.removeFieldAt(i);
                }
            }
        }
    };
    /**
     * Resolves a field's index by matching against stored names, indexed names, actual names,
     * and indexed actual names.
     *
     * @private
     * @param {string} name The field name to locate.
     * @returns {number} The matching field index, or `-1` if not found.
     */
    PdfForm.prototype._getFieldIndex = function (name) {
        var index = -1;
        if (this.count > 0) {
            if (!this._fieldNames) {
                this._fieldNames = [];
            }
            if (!this._indexedFieldNames) {
                this._indexedFieldNames = [];
            }
            if (!this._actualFieldNames) {
                this._actualFieldNames = [];
            }
            if (!this._indexedActualFieldNames) {
                this._indexedActualFieldNames = [];
            }
            for (var i = 0; i < this.count; i++) {
                var field = this.fieldAt(i);
                if (field) {
                    var fieldName = field.name;
                    if (fieldName) {
                        this._fieldNames.push(fieldName);
                        this._indexedFieldNames.push(fieldName.split('[')[0]);
                    }
                    var actualName = field.actualName;
                    if (actualName) {
                        this._actualFieldNames.push(actualName);
                        this._indexedActualFieldNames.push(actualName.split('[')[0]);
                    }
                }
            }
            var nameIndex = this._fieldNames.indexOf(name);
            if (nameIndex !== -1) {
                index = nameIndex;
            }
            else {
                nameIndex = this._indexedFieldNames.indexOf(name);
                if (nameIndex !== -1) {
                    index = nameIndex;
                }
                else {
                    nameIndex = this._actualFieldNames.indexOf(name);
                    if (nameIndex !== -1) {
                        index = nameIndex;
                    }
                    else {
                        nameIndex = this._indexedActualFieldNames.indexOf(name);
                        if (nameIndex !== -1) {
                            index = nameIndex;
                        }
                    }
                }
            }
        }
        return index;
    };
    /**
     * Materializes and returns all parsed `PdfField` instances for the current form.
     *
     * @private
     * @returns {PdfField[]} The array of loaded fields.
     */
    PdfForm.prototype._getFields = function () {
        var fields = [];
        for (var i = 0; i < this._fields.length; i++) {
            var field = this.fieldAt(i);
            if (field && field instanceof PdfField) {
                fields.push(field);
            }
        }
        return fields;
    };
    /**
     * Maps a tab order enumeration to its corresponding name object (`'R'`, `'C'`, `'S'`), or `null` for `none`.
     *
     * @private
     * @param {PdfFormFieldsTabOrder} tabOrder The tab order mode.
     * @returns {_PdfName} The corresponding name entry, or `null` if none.
     */
    PdfForm.prototype._getOrder = function (tabOrder) {
        if (tabOrder !== PdfFormFieldsTabOrder.none) {
            var tabs = '';
            if (tabOrder === PdfFormFieldsTabOrder.row) {
                tabs = 'R';
            }
            else if (tabOrder === PdfFormFieldsTabOrder.column) {
                tabs = 'C';
            }
            else if (tabOrder === PdfFormFieldsTabOrder.structure) {
                tabs = 'S';
            }
            return _PdfName.get(tabs);
        }
        return null;
    };
    /**
     * Compares two fields for ordering based on page index and the current tab order mode
     * (`row`, `column`, `manual`, `none`, `structure`, `widget`).
     *
     * @private
     * @param {any} field1 The first field to compare.
     * @param {any} field2 The second field to compare.
     * @returns {number} A negative value if `field1` precedes `field2`, positive if after, or `0` if equal.
     */
    PdfForm.prototype._compareFields = function (field1, field2) {
        var result = 0;
        var xdiff;
        var index;
        var page1 = field1.page;
        var page2 = field2.page;
        var rotation = page1.rotation;
        if (page1 && !page1._isNew && page1 instanceof PdfPage && page2 && !page2._isNew && page2 instanceof PdfPage) {
            var page1Index = this._sortItemByPageIndex(field1, false)._pageIndex;
            var page2Index = this._sortItemByPageIndex(field2, false)._pageIndex;
            var rectangle1 = void 0;
            if (field1._dictionary.has('Kids')) {
                rectangle1 = this._getItemRectangle(field1);
            }
            else {
                rectangle1 = this._getRectangle(field1._dictionary);
            }
            var rectangle2 = void 0;
            if (field2._dictionary.has('Kids')) {
                rectangle2 = this._getItemRectangle(field2);
            }
            else {
                rectangle2 = this._getRectangle(field2._dictionary);
            }
            var firstHeight = rectangle1[3] - rectangle1[1];
            var secondHeight = rectangle2[3] - rectangle2[1];
            if (rectangle1 && rectangle1.length >= 2 && rectangle2 && rectangle2.length >= 2) {
                var x1 = rectangle1[0];
                var y1 = rectangle1[1];
                var x2 = rectangle2[0];
                var y2 = rectangle2[1];
                if (typeof x1 === 'number' && typeof x2 === 'number' &&
                    typeof y1 === 'number' && typeof y2 === 'number') {
                    index = page1Index - page2Index;
                    var columnTolerance = 2;
                    if (this._tabOrder === PdfFormFieldsTabOrder.row) {
                        if (rotation === PdfRotationAngle.angle0) {
                            xdiff = this._compare(y2, y1);
                            if (xdiff !== 0) {
                                var isValid = xdiff === -1 && y1 > y2 && (y1 - firstHeight / 2) < y2;
                                isValid = isValid || (xdiff === 1 && y2 > y1 && (y2 - secondHeight / 2) < y1);
                                if (isValid) {
                                    xdiff = 0;
                                }
                            }
                            if (index !== 0) {
                                result = index;
                            }
                            else if (xdiff !== 0) {
                                result = xdiff;
                            }
                            else {
                                result = this._compare(x1, x2);
                            }
                        }
                        else if (rotation === PdfRotationAngle.angle270) {
                            var xDistance = Math.abs(x1 - x2);
                            if (index !== 0) {
                                result = index;
                            }
                            else if (xDistance <= columnTolerance) {
                                result = this._compare(y2, y1);
                            }
                            else {
                                result = this._compare(x2, x1);
                            }
                        }
                    }
                    else if (this._tabOrder === PdfFormFieldsTabOrder.column) {
                        xdiff = this._compare(x1, x2);
                        if (index !== 0) {
                            result = index;
                        }
                        else if (xdiff !== 0) {
                            result = xdiff;
                        }
                        else {
                            result = this._compare(y2, y1);
                        }
                    }
                    else if (this._tabOrder === PdfFormFieldsTabOrder.manual ||
                        this._tabOrder === PdfFormFieldsTabOrder.none ||
                        this._tabOrder === PdfFormFieldsTabOrder.structure ||
                        this._tabOrder === PdfFormFieldsTabOrder.widget) {
                        if (field1 instanceof PdfField && field2 instanceof PdfField) {
                            var field1Index = field1.tabIndex;
                            var field2Index = field2.tabIndex;
                            xdiff = this._compare(field1Index, field2Index);
                            if (index !== 0) {
                                result = index;
                            }
                            else {
                                result = xdiff;
                            }
                        }
                    }
                }
            }
        }
        return result;
    };
    /**
     * Retrieves the `Rect` array from the specified dictionary.
     *
     * @private
     * @param {_PdfDictionary} dictionary The dictionary containing a `Rect` entry.
     * @returns {number[]} The rectangle `[x1, y1, x2, y2]`, or `undefined` if absent.
     */
    PdfForm.prototype._getRectangle = function (dictionary) {
        var rect;
        if (dictionary && dictionary.has('Rect')) {
            rect = dictionary.getArray('Rect');
        }
        return rect;
    };
    /**
     * Gets a representative widget rectangle for a field with kids, preferring the parent field's
     * rectangle first.
     *
     * @private
     * @param {PdfField} field The field whose widget rectangle is requested.
     * @returns {number[]} The widget rectangle `[x1, y1, x2, y2]`, or `undefined` if unavailable.
     */
    PdfForm.prototype._getItemRectangle = function (field) {
        var result;
        var dictionary = field._dictionary;
        if (!dictionary.has('Kids')) {
            result = this._getRectangle(dictionary);
        }
        if (dictionary.has('Kids')) {
            var kids = dictionary.getArray('Kids');
            if (!kids || kids.length === 0) {
                result = this._getRectangle(dictionary);
            }
            if (_isNullOrUndefined(kids) && kids.length >= 1) {
                if (kids.length === 1) {
                    result = this._getRectangle(kids[0]);
                }
                else {
                    if (field && field.itemsCount > 1) {
                        result = this._getRectangle(field.itemAt(0)._dictionary);
                    }
                    else {
                        var kids_1 = dictionary.getArray('Kids');
                        var minX = Number.MAX_VALUE;
                        var maxY = Number.MIN_VALUE;
                        var maxX = Number.MIN_VALUE;
                        var minY = Number.MAX_VALUE;
                        var hasRect = false;
                        for (var i = 0; i < kids_1.length; i++) {
                            var kidRect = void 0;
                            if (field && field.itemsCount > i && field.itemAt(i)) {
                                kidRect = this._getRectangle(field.itemAt(i)._dictionary);
                            }
                            else {
                                kidRect = this._getRectangle(kids_1[i]);
                            }
                            if (kidRect && kidRect.length === 4) {
                                hasRect = true;
                                minX = Math.min(minX, kidRect[0]);
                                minY = Math.min(minY, kidRect[1]);
                                maxX = Math.max(maxX, kidRect[2]);
                                maxY = Math.max(maxY, kidRect[3]);
                            }
                        }
                        return hasRect ? [minX, minY, maxX, maxY] : this._getRectangle(dictionary);
                    }
                }
            }
        }
        return result;
    };
    /**
     * Compares two numeric values.
     *
     * @private
     * @param {number} x The first number.
     * @param {number} y The second number.
     * @returns {number} Returns `1` if `x > y`, `-1` if `x < y`, otherwise `0`.
     */
    PdfForm.prototype._compare = function (x, y) {
        if (x > y) {
            return 1;
        }
        else if (x < y) {
            return -1;
        }
        else {
            return 0;
        }
    };
    /**
     * Compares two widget references by their rectangles according to the current tab order.
     *
     * @private
     * @param {_PdfReference} x The first widget reference.
     * @param {_PdfReference} y The second widget reference.
     * @returns {number} A negative, positive, or zero value indicating relative order.
     */
    PdfForm.prototype._compareKidsElement = function (x, y) {
        var xDictionary = this._crossReference._fetch(x);
        var yDictionary = this._crossReference._fetch(y);
        var xRect = this._getRectangle(xDictionary);
        var yRect = this._getRectangle(yDictionary);
        var result;
        if (xRect && xRect.length >= 2 && yRect && yRect.length >= 2) {
            var x1 = xRect[0];
            var y1 = xRect[1];
            var x2 = yRect[0];
            var y2 = yRect[1];
            if (typeof x1 === 'number' && typeof x2 === 'number' &&
                typeof y1 === 'number' && typeof y2 === 'number') {
                var xdiff = void 0;
                if (this._tabOrder === PdfFormFieldsTabOrder.row) {
                    xdiff = this._compare(y2, y1);
                    if (xdiff !== 0) {
                        result = xdiff;
                    }
                    else {
                        result = this._compare(x1, x2);
                    }
                }
                else if (this._tabOrder === PdfFormFieldsTabOrder.column) {
                    xdiff = this._compare(x1, x2);
                    if (xdiff !== 0) {
                        result = xdiff;
                    }
                    else {
                        result = this._compare(y2, y1);
                    }
                }
                else {
                    result = 0;
                }
                return result;
            }
        }
        return result;
    };
    /**
     * Sorts a field's items by page/tab order and returns the effective page used for ordering.
     *
     * @private
     * @param {PdfField} field The field whose items should be sorted.
     * @param {boolean} hasPageTabOrder When `true`, uses the page's tab order for sorting.
     * @returns {PdfPage} The page used to determine ordering.
     */
    PdfForm.prototype._sortItemByPageIndex = function (field, hasPageTabOrder) {
        var page = field.page;
        var tabOrder = this._tabOrder;
        this._tabOrder = hasPageTabOrder ? field.page.tabOrder : tabOrder;
        this._sortFieldItems(field);
        if (field._isLoaded && field._kidsCount > 1) {
            page = field.itemAt(0).page;
        }
        this._tabOrder = tabOrder;
        if (typeof page === 'undefined') {
            page = field.page;
        }
        return page;
    };
    /**
     * Sorts the parsed items of supported fields (text, list box, checkbox, radio) using
     * the current tab order comparator.
     *
     * @private
     * @param {PdfField} field The field whose items are to be sorted.
     * @returns {void}
     */
    PdfForm.prototype._sortFieldItems = function (field) {
        var _this = this;
        if (field._isLoaded && (field instanceof PdfTextBoxField ||
            field instanceof PdfListBoxField ||
            field instanceof PdfCheckBoxField ||
            field instanceof PdfRadioButtonListField)) {
            var collection = field._parseItems(); // eslint-disable-line
            collection.sort(function (item1, item2) {
                return _this._compareFieldItem(item1, item2);
            });
            field._parsedItems.clear();
            collection.forEach(function (item, i) {
                field._parsedItems.set(i, item);
            });
        }
    };
    /**
     * Compares two field items by page index and rectangle, honoring the current tab order
     * `row` or `column`.
     *
     * @private
     * @param {any} item1 The first item to compare.
     * @param {any} item2 The second item to compare.
     * @returns {number} A negative, positive, or zero value indicating relative order.
     */
    PdfForm.prototype._compareFieldItem = function (item1, item2) {
        var result = 0;
        if (typeof item1 !== 'undefined' && typeof item2 !== 'undefined') {
            var page1 = item1.page;
            var page2 = item2.page;
            var array1 = this._getRectangle(item1._dictionary);
            var array2 = this._getRectangle(item2._dictionary);
            if (array1 && array2) {
                var x1 = array1[0];
                var y1 = array1[1];
                var x2 = array2[0];
                var y2 = array2[1];
                var xdiff = void 0;
                if (this._tabOrder === PdfFormFieldsTabOrder.row) {
                    xdiff = this._compare(page1._pageIndex, page2._pageIndex);
                    if (xdiff !== 0) {
                        result = xdiff;
                    }
                    else {
                        xdiff = this._compare(y2, y1);
                        if (xdiff !== 0) {
                            result = xdiff;
                        }
                        else {
                            result = this._compare(x1, x2);
                        }
                    }
                }
                else if (this._tabOrder === PdfFormFieldsTabOrder.column) {
                    xdiff = this._compare(page1._pageIndex, page2._pageIndex);
                    if (xdiff !== 0) {
                        result = xdiff;
                    }
                    else {
                        xdiff = this._compare(x1, x2);
                        if (xdiff !== 0) {
                            result = xdiff;
                        }
                        else {
                            result = this._compare(y2, y1);
                        }
                    }
                }
            }
        }
        return result;
    };
    /**
     * Clears the form’s field reference list and the parsed field cache.
     *
     * @private
     * @returns {void}
     */
    PdfForm.prototype._clear = function () {
        this._fields = [];
        this._parsedFields = new Map();
    };
    /**
     * Checks whether two fields are of the same field class (e.g., both text, both radio).
     *
     * @private
     * @param {PdfField} field1 The first field.
     * @param {PdfField} field2 The second field.
     * @returns {boolean} Returns `true` if the field types are compatible; otherwise, `false`.
     */
    PdfForm.prototype._checkType = function (field1, field2) {
        return (field1 instanceof PdfTextBoxField && field2 instanceof PdfTextBoxField) ||
            (field1 instanceof PdfButtonField && field2 instanceof PdfButtonField) ||
            (field1 instanceof PdfCheckBoxField && field2 instanceof PdfCheckBoxField) ||
            (field1 instanceof PdfComboBoxField && field2 instanceof PdfComboBoxField) ||
            (field1 instanceof PdfListBoxField && field2 instanceof PdfListBoxField) ||
            (field1 instanceof PdfRadioButtonListField && field2 instanceof PdfRadioButtonListField) ||
            (field1 instanceof PdfSignatureField && field2 instanceof PdfSignatureField);
    };
    return PdfForm;
}());
export { PdfForm };