Structure
Structure
تغطي هذه الصفحة تنقل المستند والهيكل المنطقي: المخططات (الإشارات المرجعية)، جداول المحتويات، الوجهات المسماة، وشجرة الهيكل الموسومة المستخدمة لإمكانية الوصول وإعادة التدفق.
المخططات (الإشارات المرجعية)
Document.GetOutlines() تُعيد شجرة المخطط الحالية كـ OutlineItem[] ([] عندما لا يوجد /Outlines); Document.SetOutlines() تستبدلها — تمرير [] يزيل المخطط بالكامل. كل OutlineItem يحتوي على Title، وDest (رقم صفحة أو وجهة مسماة)، وChildren اختياري للتعشيق، وتنسيق (Color، Bold، Italic، Open).
const items: OutlineItem[] = sections.map((s) => {
const item: OutlineItem = { Title: s.title, Dest: { name: s.dest } };
if (s.subtype === 'sales') {
item.Open = true;
item.Children = ['Pasta', 'Pizza', 'Antipasti']
.map((cat) => ({ Title: cat, Dest: { name: s.dest } }));
}
return item;
});
doc.SetOutlines(items);جدول المحتويات
Page.AddTOC() تُظهر قائمة من كائنات TOCEntry — كل منها يحتوي على title وpage رقم الهدف — داخل مستطيل على الصفحة، مع عناوين مُلتفة، ونقاط توصيل، وعناوين صفحات مُحاذاة إلى اليمين. تُرجع AddTOCResult تُبلغ عن عدد الإدخالات التي تم رسمها، وعند كون الصندوق صغيرًا جدًا، تُبلغ عن remainder التي لم تتسع.
page.AddTOC(
sections.map((s, i) => ({ title: `${i + 1}. ${s.title}`, page: s.page.Number })),
[72, 160, 400, 400],
{ font: 'Helvetica', fontSize: 13, rowGap: 18 },
);الوجهات المسماة
Document.GetNamedDestinations() تُعيد كل الوجهة المُسماة — بدمج شجرة أسماء /Names /Dests والقاموس القديم /Dests — كأزواج { name, dest }، حيث إن dest هو PageDest ({ page, view }). هذه هي نفس الأهداف المُسماة التي يمكن لـ OutlineItem.Dest أو توضيح ارتباط الإشارة إليه بالاسم بدلاً من رقم صفحة صريح.
const destNames = new Set(doc.GetNamedDestinations().map((d) => d.name));
for (const { name, dest } of doc.GetNamedDestinations()) {
console.log(name, '-> page', dest.page);
}شجرة البنية الموسومة
Document.AutoTag() تستنتج وتؤلف /StructTreeRoot من تخطيط الصفحة — العناوين عن طريق تجميع أحجام الخط، الفقرات عن طريق كتل النص، الجداول عن طريق هندسة الحواشي، وقرارات /Figure مقابل /Artifact لكل صورة — وتُعيد AutoTagReport مع عدد لكل نوع عنصر. Document.GetStructTree() تقرأ StructTreeRoot الناتج، أو null عندما يكون المستند غير موسوم.
const report = doc.AutoTag({ lang: 'en-US', title: 'Quarterly Report', tables: true });
console.log(report.headings, report.paragraphs, report.tables, report.figures);
const tree = doc.GetStructTree();
console.log(tree ? tree.GetText() : '(no structure tree)');المحتوى الذي يُضاف بعد أن AutoTag() قد تم تشغيله — مثل صفحة تُملأ لاحقًا — لا يغطيه ذلك المرور ولن يتم وضع علامة مزدوجة عليه. StructTreeRoot.Append() و StructElement.MarkContent() هما API التحرير اليدوي إلى جانب الطريقة الاستدلالية: Append() يضيف عنصرًا فرعيًا من نوع معين، وMarkContent() يحدد منطقة صفحة كأنها تنتمي إلى ذلك العنصر.
نصائح وأفضل الممارسات
- شغِّل
Document.AutoTag()مرة واحدة، بعد أن يصبح محتوى الصفحة نهائيًا — فهو لا يعيد وضع علامات على المحتوى المضاف لاحقًا، لذا ضع علامة يدوية على أي شيء يُضاف فيما بعد باستخدامStructTreeRoot.Append()/StructElement.MarkContent(). - مرّر
opts.titleإلىAutoTag()— فهو أيضًا يحدد/ViewerPreferences /DisplayDocTitle، وهو ما يتطلبه PDF/UA جنبًا إلى جنب مع عنوان المستند. - يمكن لـ
OutlineItem.Destاستهداف إما صفحة صريحة أو وجهة مُسماة ({ name: '...' }) — استخدم الوجهات المُسماة عندما قد يتغير رقم الصفحة المستهدفة مع تغير المحتوى. - تحقق من
AddTOCResult.remainderعندما يكون الترقيم التلقائي معطلاً — صندوق جدول المحتويات صغير جدًا لجميع الإدخالات يتوقف عن الرسم بصمت بدلاً من تجاوز حد الصندوق.
مشكلات شائعة
| المشكلة | السبب | الإصلاح |
|---|---|---|
Document.GetStructTree() يرجع null | لم يتم وسم المستند | استدعِ Document.AutoTag() أو Document.CreateStructTree() أولاً |
| رابط عنصر المخطط لا يتم حله | إن Dest الخاص به يحدد وجهة غير موجودة في Document.GetNamedDestinations() | تأكد من وجود الوجهة المسماة، أو استخدم صفحة صريحة Dest بدلاً من ذلك |
Page.AddTOC() يتوقف قبل القسم الأخير | الهدف rect صغير جدًا لكل إدخال وautoPaginate معطل | وسّع الـrect، مرّر autoPaginate: true، أو عالج AddTOCResult.remainder |
المحتوى المضاف بعد AutoTag() غير موجود في شجرة الهيكل | AutoTag() يعلّم فقط المحتوى الموجود عندما تم تشغيله | ضع علامة يدوية على المحتوى اللاحق باستخدام StructTreeRoot.Append() / StructElement.MarkContent() |
FAQ
كيف أضيف إشارات مرجعية إلى ملف PDF؟
أنشئ مصفوفة من كائنات OutlineItem (Title, Dest, اختياري Children) ومرّرها إلى Document.SetOutlines().
هل يمكن لجدول المحتويات أن يمتد على صفحات متعددة؟
نعم — مرّر autoPaginate: true في خيارات Page.AddTOC()، أو تحقق من AddTOCResult.remainder واستدعِ AddTOC() مرة أخرى على صفحة جديدة لأي شيء لم يتسع.
كيف أجعل ملف PDF قابلاً للوصول (موسومًا)؟
استدعِ Document.AutoTag()، الذي يستنتج العناوين والفقرات والجداول والرسوم من تخطيط الصفحة. للمحتوى المضاف لاحقًا، أو حيث تحتاج نتيجة الخوارزمية إلى تصحيح، استخدم StructTreeRoot.Append() وStructElement.MarkContent() مباشرةً.
ما الفرق بين وجهة رقم الصفحة ووجهة مسماة؟
وجهة رقم الصفحة (PageDest) تستهدف صفحة صريحة ذات ترقيم يبدأ من 1. وجهة مسماة (NamedDest) تستهدف اسمًا يقوم عارض المستند بحلّه عبر جداول الوجهات المسماة الخاصة بالمستند — وهذا مفيد عندما قد تتحرك الصفحة المستهدفة.
API Reference ملخص
| فئة/طريقة | وصف |
|---|---|
Document.GetOutlines() / Document.SetOutlines() | قراءة أو استبدال شجرة مخطط المستند (الإشارة المرجعية) |
OutlineItem | عقدة مخطط واحدة: Title، Dest، اختياري Children |
Page.AddTOC() | عرض جدول المحتويات داخل مستطيل الصفحة |
TOCEntry / AddTOCResult | بيانات صف TOC، ونتيجة رسمه |
Document.GetNamedDestinations() | قائمة بكل الوجهات المسماة في المستند |
Document.AutoTag() | استنتاج وإنشاء شجرة بنية موسومة من تخطيط الصفحة |
Document.GetStructTree() / Document.CreateStructTree() | اقرأ أو أنشئ StructTreeRoot الخاص بالمستند |
StructTreeRoot.Append() / StructElement.Append() / StructElement.MarkContent() | أنشئ يدويًا أو وسّع شجرة الهيكل |