تقنية

pointer-events: لماذا يبقى العنصر قابلًا للوصول بلوحة المفاتيح؟

العداد يبقى صفرًا بالنقر، ويصبح واحدًا بعد Tab ثم Enter على الزر.
رسم مؤلف لنتيجة الزر في التجربة؛ لا يحمل disabled. [1] [3]

تضيف pointer-events: none إلى زر، فيتوقف عن الاستجابة لنقرة الفأرة. لكن الوصول إليه بمفتاح Tab قد يظل ممكنًا. [1]

تستبعد none العنصر من استهداف المؤشر؛ لا تُخرجه وحدها من التنقل المتسلسل بلوحة المفاتيح. [1]

الخلاصة السريعة

  • قارن النقر مع الوصول بمفتاح Tab على الزر نفسه. [1]
  • اختبر التنشيط أيضًا: وصول التركيز ليس ضغط الزر. [3]
  • ضع none على طبقة زخرفية ليمر استهداف النقر إلى ما تحتها. [2]
  • قد تستقبل معالجات الأب أحداثًا تستهدف ابنًا أعاد auto. [2]

جهّز مقارنة صغيرة

قارن النقر مع الوصول بمفتاح Tab على الزر نفسه. [1]

احفظ المثال في HTML: ضع CSS داخل style، وJavaScript بعد الأزرار داخل script. لا تضف disabled أو tabindex. انقر جرّب؛ يبقى العداد صفرًا في هذه التجربة. [1]

مرّر الشيفرة أفقيًا عند الحاجة.

<button id="before" type="button">ابدأ</button>
<button id="demo" type="button">جرّب</button>
<button id="after" type="button">التالي</button>
<p>العداد: <output id="count">0</output></p>

مرّر الشيفرة أفقيًا عند الحاجة.

#demo { pointer-events: none; }

مرّر الشيفرة أفقيًا عند الحاجة.

const demo = document.getElementById("demo");
const count = document.getElementById("count");
let hits = 0;
demo.addEventListener("click", () => {
  count.textContent = String(++hits);
});

انتقل ثم شغّل

اختبر التنشيط أيضًا: وصول التركيز ليس ضغط الزر. [3]

انقر ابدأ، ثم اضغط Tab للوصول إلى جرّب، وبعده Enter. في اختبارنا على Edge صار العداد واحدًا؛ وTab التالي نقل التركيز إلى التالي. أعد تحميل الصفحة قبل إعادة المقارنة. [1] [3]

يوضح معيار HTML أن تنشيط العنصر بوسيلة أخرى يولّد click أيضًا. لذلك لا تفترض أن كل click بدأ بفأرة. [3]

دع النقر يعبر طبقة الزينة

ضع none على طبقة زخرفية ليمر استهداف النقر إلى ما تحتها. [2]

أضف المثال التالي وشيفرته بالطريقة نفسها. تغطي الطبقة الشفافة الزر؛ مع none تظهر under في وحدة التحكم عند نقره. غيّر قيمة الطبقة وحدها إلى auto وأعد التحميل؛ تستقبل الطبقة النقرة بدل الزر. اللون هنا لتحديد موضعها. [2]

مرّر الشيفرة أفقيًا عند الحاجة.

<div class="stack">
  <button id="under" type="button">تحت الطبقة</button>
  <span class="veil" aria-hidden="true"></span>
</div>

مرّر الشيفرة أفقيًا عند الحاجة.

.stack { position: relative; display: inline-block; }
.veil {
  position: absolute;
  inset: 0;
  background: #15a8a833;
  pointer-events: none;
}

مرّر الشيفرة أفقيًا عند الحاجة.

document.getElementById("under").addEventListener("click", () => {
  console.log("under");
});

انتبه لحدود الاستبعاد

قد تستقبل معالجات الأب أحداثًا تستهدف ابنًا أعاد auto. [2]

تُورث الخاصية، لكن يمكن للابن ضبط auto. عند استهدافه قد يمر الحدث بأبيه خلال الانتشار؛ عبارة «أوقفت كل المستمعات» غير صحيحة. المثال يقتصر على HTML وقيمتي auto وnone؛ لم نفحص اللمس أو إتاحة صفحة كاملة. [2]

المصادر ومتابعة القراءة

  1. MDN: pointer-events (يفتح في نافذة جديدة)developer.mozilla.org
  2. W3C: استبعاد استهداف المؤشر (يفتح في نافذة جديدة)drafts.csswg.org
  3. WHATWG: تنشيط العناصر (يفتح في نافذة جديدة)html.spec.whatwg.org

أُعدّ هذا المقال بصياغة عربية أصلية بالاستناد إلى المصادر أعلاه، وهو مدخل تمهيدي إلى الموضوع. اقرأ منهجية المحتوى وحدوده.