عرض HTML في لوحة رسم ثنائية الأبعاد

تتيح لك واجهة HTML-in-Canvas API عرض أشجار DOM الفرعية التفاعلية التي تسهّل الوصول إليها مباشرةً في سياق لوحة ثنائية الأبعاد. يمكنك الاطّلاع على نظرة عامة على HTML-in-Canvas لمزيد من المعلومات حول واجهة برمجة التطبيقات ومزاياها.

يوضّح هذا الدليل كيفية عرض HTML في لوحة ثنائية الأبعاد. يتطلّب عرض HTML في لوحة ثنائية الأبعاد اتّباع الخطوات التالية:

  1. جهِّز لوحتك. يمكنك ضبط السمات المناسبة بشكل تعريفي لإعلام المتصفّح بأنّه يجب عرض HTML في لوحة رسم. هذا الإعداد متطابق في سياقات 2D وWebGL وWebGPU. تعرَّف على كيفية إعداد لوحة الرسم وكيفية تحديد عناصر HTML ليتم رسمها بشكل مستقل.
  2. ارسم صورة العنصر في لوحة العرض.
  3. [اختياري] مزامنة نموذج العناصر في المستند (DOM) ووحدات البكسل

رسم عناصر HTML في لوحة ثنائية الأبعاد

بعد أن تصبح لوحة الرسم جاهزة ويتم وضع علامة على العناصر على أنّها drawable، يمكنك عرضها في سياق ثنائي الأبعاد باستخدام طريقة drawElementImage().

const canvas = document.getElementById("canvas");
const ctx = canvas.getContext("2d");
const childElement1 = document.getElementById("childElement1");
const childElement2 = document.getElementById("childElement2");

canvas.onpaint = () => {
  ctx.reset();
  // 1. Draw the primary element at coordinate (20, 20)
  ctx.drawElementImage(childElement1, 20, 20);
  // 2. Draw the secondary nested button at a custom offset
  ctx.drawElementImage(childElement2, 40, 90);
}

تتيح الدالة drawElementImage() استخدام الصيغ التي تتضمّن 3 وسيطات و5 وسيطات و7 وسيطات و9 وسيطات، وتقبل مَعلمة options اختيارية:

// 1. Basic position: (element, dx, dy, options?)
ctx.drawElementImage(targetElement, 100, 150);

// 2. Scaled / resized: (element, dx, dy, dWidth, dHeight, options?)
ctx.drawElementImage(targetElement, 100, 150, 180, 60);

// 3. Cropped, default size: (element, sx, sy, swidth, sheight, dx, dy, options?)
ctx.drawElementImage(targetElement, 0, 0, 90, 30, 100, 150);

// 4. Cropped and resized: (element, sx, sy, sWidth, sHeight, dx, dy, dWidth, dHeight, options?)
ctx.drawElementImage(targetElement, 0, 0, 90, 30, 100, 150, 180, 60);
نموذج التحميل الزائد المعلمات تأثير التنسيق
الحجم التلقائي (element, dx, dy) العنصر بأكمله بحجمه التلقائي، مع الزاوية العلوية اليمنى عند (dx, dy).
مربّع الوجهة المخصّصة (element, dx, dy, dwidth, dheight) تغيّر هذه العقدة حجم صورة العنصر الكاملة إلى إطار عرض dw × dh على لوحة الرسم.
مقتصّة، بالحجم التلقائي (element, sx, sy, swidth, sheight, dx, dy) منطقة swidth × sheight فقط التي تبدأ عند (sx, sy)، ويتم رسمها بالحجم التلقائي لتلك المنطقة (المقياس نفسه لنموذج الحجم التلقائي).
شريحة المصدر إلى الوجهة (element, sx, sy, swidth, sheight, dx, dy, dwidth, dheight) يتم اقتصاص العنصر المصدر بدءًا من (sx، sy) بالأبعاد swidth × sheight، ثم يتم ربطه بالوجهة (dx، dy، dwidth، dheight).

مزامنة نموذج DOM ووحدات البكسل

بما أنّ عرض <canvas> أمر ضروري في حين أنّ تنسيق DOM وتصميم CSS تفاعليان، يحتاج المتصفّح إلى آلية للحفاظ على مزامنة وحدات بكسل لوحة العرض ومناطق اختبار مؤشر الماوس التفاعلية وأشجار تسهيل الاستخدام. قبل التعرّف على كيفية مزامنة نموذج DOM ووحدات البكسل، تأكَّد من فهم الحدث paint الذي يتم تشغيله عند تعديل عناصر DOM والحاجة إلى إعادة رسمها.

في سياقات لوحة الرسم ثنائية الأبعاد، يزامن المتصفّح تلقائيًا إحداثيات تنسيق العنصر وحدود تسهيل الاستخدام واختبار مؤشر الماوس مع إحداثيات لوحة الرسم المرسومة.

تعديل شكل العنصر يدويًا

في السيناريوهات المتقدّمة، يمكنك إيقاف المزامنة التلقائية للأشكال الهندسية والتحكّم في التحويلات المكانية يدويًا. مرِّر { preserveElementGeometry: true } إلى drawElementImage() لمنع المتصفّح من إلغاء إحداثيات اختبار مؤشر الماوس الحالية للعنصر تلقائيًا:

// 1. Draw the element without altering its existing hit-test bounds
ctx.drawElementImage(targetElement, elementX, 200, { preserveElementGeometry: true });

// 2. Construct a custom transform matrix as needed,
// assuming scaleX/scaleY = canvas grid pixels per CSS pixel,
// from your resize observer (see "Units and sizing").
const currentTransform = new DOMMatrix();
currentTransform.a = 1.5;          // scale X
currentTransform.e = x / scaleX;   // translate X: grid px → CSS px
currentTransform.f = y / scaleY;   // translate Y: grid px → CSS px

// 3. Explicitly apply the custom transform
canvas.updateElementGeometry(targetElement, { canvasTransform: currentTransform });
في الوضع الثنائي الأبعاد، يتم تعديل هذا الشكل الهندسي تلقائيًا من خلال drawElementImage(). يوضّح هذا العرض التوضيحي كيف تصبح الهندسة غير متزامنة عند ضبط السمة { preserveElementGeometry: true }.

الخطوات التالية