مقال تقني

تحويل XFA إلى AcroForm وتسطيحه في Delphi باستخدام HotPDF

"يرجى الانتظار... إذا لم تُستبدل هذه الرسالة في النهاية بالمحتويات الصحيحة للمستند، فقد لا يستطيع عارض PDF لديك عرض هذا النوع من المستندات". إذا كان خط أنابيب المستندات لديك قد ابتلع يومًا نماذج حكومية أو تأمينية، فقد رأيت هذه الصفحة. ليست تلفًا؛ إنها الصفحة البديلة التي يعرضها نموذج XFA ديناميكي لأي عارض يفتقر إلى معالج XFA، وهذا يعني اليوم تقريبًا كل عارض باستثناء Acrobat المكتبي. ترى الأرشيفات، وعارضات الويب، والاستخراج الآلي صفحة واحدة عديمة الفائدة. يعالج HotPDF، مكتبة losLab لـ PDF في Delphi وC++Builder، ذلك بمسار تحويل يحول نماذج XFA إلى مستندات AcroForm أصلية يستطيع أي قارئ مطابق عرضها

نموذجان للنماذج يبدوان متشابهين فقط

يخزن AcroForm، كما يعرفه ISO 32000-1 §12.7، كل حقل ككائن PDF له widget annotation وتدفق مظهر؛ الصفحة التي تراها محتوى PDF حقيقي، وبيانات النموذج تركب فوقه. يأخذ XFA الاتجاه المعاكس: النموذج مستند XML، حزمة XDP محمولة في خانة /XFA من قاموس AcroForm، والصفحات المرئية تُولّد عند الفتح بواسطة محرك تخطيط XFA. في نموذج XFA ديناميكي، لا تكون صفحات PDF داخل الملف إلا الصفحة البديلة "يرجى الانتظار"، لأن المحتوى الحقيقي لم يوجد قط كـ PDF

النموذجان متنافيان عمليًا: يعالج المستند إما كـ XFA أو كـ AcroForm، والأدوات التي تتجاهل خانة /XFA لا ترى إلا الغلاف البديل. حسم ISO 32000-2 الجدل بإهمال XFA من PDF 2.0 تمامًا، وهذا سبب تحول "حوّله إلى AcroForm ما دمنا نستطيع" إلى مطلب ingestion قياسي لا حالة غريبة

لا يعرض كل نموذج XFA الصفحة البديلة، وهذا سبب وجوب تصنيف خطوط ingestion قبل التحويل. تحمل نماذج XFA الثابتة صفحات PDF مسبقة التصيير إلى جانب XML، لذلك تعرض في كل مكان ولا تتصرف إلا على نحو غير متسق عند تعبئتها؛ أما النماذج الديناميكية فتحمل الصفحة البديلة فقط ويجب تحويلها كي تكون قابلة للاستخدام أصلًا. المميز الموثوق هو المستند نفسه لا امتداد الملف ولا المرسل: النموذج الذي يعرض محتوى حقيقيًا في عارض غير Adobe لكنه لا يزال يحمل خانة /XFA هو ثابت أو هجين، والنموذج الذي يعرض صفحة التحذير ديناميكي. صنّف كل ملف intake ضمن إحدى هاتين السلتين وسجل التصنيف، لأن النوعين يفشلان بطرق مختلفة لاحقًا، وتذكرة دعم عن نموذج مؤرشف فارغ تُجاب في ثوان عندما يقول سجل الإدخال "dynamic XFA, converted, 47 fields mapped, 2 warnings"

تسطيح مستند XFA محمل إلى حقول أصلية

تعمل نقطة دخول التحويل في HotPDF على مستند محمل. يحلل FlattenLoadedXFA حزم قالب XFA وبياناته، ويرتب النموذج، ويعيد بناءه كحقول AcroForm حقيقية على صفحات PDF حقيقية:

var
  Pdf: THotPDF;
  MappedCount, I: Integer;
  Warnings: TStrings;
begin
  Pdf := THotPDF.Create(nil);
  try
    Pdf.LoadFromFile('dynamic_xfa.pdf');
    MappedCount := Pdf.FlattenLoadedXFA(True);   // True = fields stay editable
    Warnings := Pdf.XFAFlattenWarnings;
    for I := 0 to Warnings.Count - 1 do
      Log('XFA flatten warning: ' + Warnings[I]); // unmapped elements
    Pdf.SaveLoadedDocument('native_acroform.pdf');
    Log(Format('Mapped %d fields', [MappedCount]));
  finally
    Pdf.Free;
  end;
end;

تعامل مع قيمة الإرجاع وقائمة التحذيرات كجزء من المخرج لا كضجيج debug. التحويل فاقد بطبيعته: لا يوجد مقابل في AcroForm للبرمجة النصية في XFA، والحقول المحسوبة، وسلوك subform الديناميكي، وتسرد XFAFlattenWarnings بالضبط عناصر القالب التي تعذر ربطها. خط أنابيب يؤرشف الملف المحول من دون أرشفة قائمة التحذيرات سيواجه في النهاية سؤال "لماذا صندوق الإجمالي فارغ في النسخة المؤرشفة" بلا جواب مسجل. يقرر وسيط Editable هل تبقى حقول AcroForm الناتجة قابلة للتعبئة؛ مرر True عندما يواصل المستخدمون اللاحقون العمل على النموذج، وسياسات مكافئة لـ False عندما يكون الهدف سجلًا ثابتًا

التحقق من التحويل يجب أن يكون بصريًا وبنيويًا معًا. افتح النموذج المصدر في Acrobat المكتبي، وهو العارض الوحيد الذي لا يزال يشغّل محرك XFA، إلى جانب الملف المحول في أي عارض عادي، وقارن قيم الحقول والتخطيط لنموذج معبأ تمثيلي واحد على الأقل لكل قالب. تؤكد الفحوص البنيوية أن عدد الحقول يطابق MappedCount؛ ولا تؤكد إلا العين أن تاريخًا نسقه XFA كـ 2026-06-11 لم يصل إلى نسخة AcroForm كقيمة خام غير منسقة

العمل من جهة XDP

أحيانًا لا يكون المدخل PDF مملوءًا بل حزمة XDP نفسها، مصدرة من أداة تصميم نماذج أو مستلمة من نظام شريك. يتجاوز ApplyXFAAsAcroForm خطوة التحميل ويطبق الحزمة على المستند الحالي مباشرة:

XDPBytes := TFile.ReadAllBytes('benefit-claim.xdp');
MappedCount := Pdf.ApplyXFAAsAcroForm(XDPBytes, True);

تغطي عائلة الاستدعاءات نفسها اتجاه التأليف أيضًا، عندما تحتاج إلى إنتاج XFA لا استهلاكه: يرفق AddXFAPacket حزمًا منفردة مسماة مثل 'xdp' أو 'config'، ويثبت SetXFADocument حمولة XFA كاملة كتدفق واحد، ويعيد ClearXFAPackets التسجيل إلى الصفر، ويدمج AddXFASignaturePacket مادة توقيع XAdES لسير العمل الذي يوقع بيانات نموذج XML نفسها. توليد XFA في 2026 مطلب متخصص، غالبًا يدفعه مستهلك قديم واحد، لكن عندما يفرضه عقد تجعل هذه الاستدعاءات الأمر تفصيل تهيئة لا أداة منفصلة

التسطيح الآخر: محتوى AcroForm بصراحة

تحمل كلمة "Flatten" معنى ثانيًا يسبب التباسًا متكررًا: حرق مظاهر حقول AcroForm داخل تدفق محتوى الصفحة بحيث لا تبقى كائنات تفاعلية. لا يوفر HotPDF حاليًا API لهذه العملية، ومن الأفضل التخطيط حول هذه الحقيقة بدل اكتشافها في منتصف المشروع. ما تقدمه المكتبة هو قفل على مستوى الحقل عند الإنشاء، إضافة إلى أذونات المستند:

// Lock the value at field creation: read-only text field
Pdf.CurrentPage.AddTextField('CaseNumber', 'BC-2026-0117',
  Rect(50, 700, 220, 720), 0, [ffReadOnly]);

// Belt and suspenders: restrict form filling document-wide
Pdf.ActivateProtection := True;
Pdf.CryptKeyLength := aes256;
Pdf.OwnerPassword := 'records-owner';
Pdf.ProtectOptions := [prPrint, prInformationCopy, prExtractContent];
// fill permission withheld: prFillAnnotations is absent from the set

افهم ما يحققه هذا وما لا يحققه. الحقل read-only لا يزال موجودًا ككائن نموذج: يظهر في لوحة الحقول لدى العارض، وقيمته قابلة للاستخراج عبر API النماذج، وأداة تعيد كتابة الملف تستطيع مسح العلم. ترفع أعلام الأذونات العتبة أكثر لكنها تعتمد على تعاون العارض، كما يقر ISO 32000-1 نفسه. إذا طلب منظم أن لا يحتوي السجل المؤرشف على أي كائنات نموذج إطلاقًا، فالجواب الهندسي الصادق مع HotPDF اليوم هو إعادة توليد المستند، ورسم قيم الحقول كمحتوى TextOut عادي في مستند جديد باستخدام القيم المحملة، لا الادعاء أن أعلام read-only هي تسطيح. تذكر أن CryptKeyLength يجب أن يُضبط قبل BeginDoc عندما تسلك مسار الأذونات؛ التفاصيل موجودة في مقال تشفير AES-256 والأذونات

عواقب الأرشفة: XFA ومعايير المطابقة

يرفض PDF/A وPDF/X كلاهما XFA صراحة، لذلك يجب أن يحول خط ingestion الذي يغذي أرشيف ISO 19005 قبل أن يتحقق، وترتيب العمليات ثابت: تحميل، FlattenLoadedXFA، حفظ، ثم تشغيل مسار توليد أو تحقق الأرشفة على نتيجة AcroForm. تحقق من المخرج المحول عبر veraPDF بدل افتراض أن التحويل يعني المطابقة؛ التحويل يصلح نموذج النماذج، لا الخطوط ولا اللون ولا metadata. سلوك الحقول على جانب AcroForm، ومحفزات JavaScript، وإجراءات submit، وسكربتات التحقق، لها صندوق أدواتها الخاص، ومغطاة في مقال حقول وإجراءات HotPDF AcroForm

الأسئلة الشائعة

لماذا يعرض نموذج PDF لدي صفحة "يرجى الانتظار" فقط؟

إنه نموذج XFA ديناميكي، والعارض لديك لا يملك معالج XFA. محتوى PDF المرئي مجرد بديل؛ حوّل المستند باستخدام FlattenLoadedXFA للحصول على صفحات وحقول يستطيع كل عارض عرضها

هل يحافظ FlattenLoadedXFA على الحسابات والسكربتات؟

لا. برمجة XFA ومنطق التخطيط الديناميكي غير قابلين للتحويل إلى AcroForm؛ القيم المحسوبة الموجودة في بيانات النموذج تُنقل كقيم ثابتة، وتسرد XFAFlattenWarnings كل عنصر تعذر ربطه. راجع تلك القائمة قبل الوثوق بالمخرج

هل يستطيع HotPDF جعل النموذج غير تفاعلي تمامًا؟

ليس عبر تسطيح باستدعاء واحد: لا توجد API لتسطيح محتوى AcroForm. اجمع حقول ffReadOnly مع قيود الأذونات لمقاومة العبث، أو أعد توليد المستند مع رسم القيم كنص عادي عندما يكون انعدام كائنات النماذج مطلبًا صارمًا

مرجع المنتج

واجهات تسجيل XFA والتحويل والنماذج في هذه المقالة جزء من HotPDF Component لـ Delphi وC++Builder؛ وتوثق وثائقه مجموعة ميزات XFA كما توسعت عبر الإصدارات الأخيرة