يقدّم الإصدار 105 من Chrome طريقتَين جديدتَين في NavigateEvent
لواجهة برمجة التطبيقات Navigation API (التي تم تقديمها في الإصدار 102) لتحسين الطرق التي تبيّن أنّها تسبب مشاكل في الممارسة. يحلّ الإجراء intercept()
محلّ الإجراء transitionWhile()
الذي تبيّن أنّه صعب الاستخدام، ويسمح للمطوّرين بالتحكم في الحالة بعد التنقّل. تستبدل طريقة scroll()
، التي تنتقل إلى إشارة مرجعية محدّدة في عنوان URL، طريقة restoreScroll()
التي لا تعمل مع جميع أنواع التنقّل.
في هذه المقالة، سأوضّح المشاكل المتعلّقة بكلتا الطريقتَين وكيفية حلّها باستخدام الطرق الجديدة.
NavigateEvent.transitionWhile()
تعمل طريقة NavigateEvent.trasitionWhile()
، التي تم تقديمها مع Navigation API في الإصدار 102 من Chrome، على اعتراض عمليات التنقّل في عمليات النقل من جهة العميل في تطبيقات الصفحة الواحدة. الوسيطة الأولى هي وعد يشير إلى المتصفّح وأجزاء أخرى من تطبيق الويب بأنّه قد اكتمل.
لم يحقّق هذا الإجراء نتائج جيدة على أرض الواقع. راجِع نمط الترميز الشائع التالي:
event.transitionWhile((async () => {
doSyncStuff();
await doAsyncStuff();
})());
وهذا مكافئ وظيفيًا للرمز البرمجي أدناه. ويؤدي ذلك إلى تنفيذ جزء من عملية التنقّل قبل أن تدرك واجهة برمجة التطبيقات أنّ المطوّر يريد اعتراض عملية التنقّل.
doSyncStuff();
event.transitionWhile((async () => {
await doAsyncStuff();
})());
على سبيل المثال، يمكن أن يؤدي ذلك إلى حدوث خلل في التطبيق في ما يتعلّق بمنطق استعادة الانتقال إلى أعلى أو أسفل الصفحة، حيث يتم تسجيل مواضع الانتقال إلى أعلى أو أسفل الصفحة بعد تغيير نموذج DOM بدلاً من قبله.
التغييرات التي أُجريت
لاستبدال transitionWhile()
، تُقدّم المواصفة الحالية NavigateEvent.intercept()
. تأخذ الطريقة الجديدة معالِجًا بالإضافة إلى السمتَين focusReset
وscrollRestoration
المتوافقتَين مع transitionWhile()
. يتم تنفيذ المعالج الجديد دائمًا بعد اكتمال التنقّل، ويتم تسجيل عناصر مثل مواضع التمرير، ما يتجنّب المشاكل المتعلّقة بـ transitionWhile()
.
لا تزال طريقة transitionWhile()
متاحة، ولكن تم إيقافها نهائيًا وستتم إزالتها في الإصدار 108 من Chrome.
استخدام دالة intercept()
تسري القيود نفسها على NavigateEvent.intercept()
مثل transitionWhile()
، إذ لا يمكن استدعاؤه في جميع أحداث التنقّل. لا يمكن اعتراض عمليات التنقّل بين مصادر مختلفة، ولا يمكن أيضًا عبور المستندات المختلفة. سيؤدي ذلك إلى طرح DOMException
من النوع "SecurityError"
.
لاستخدام intercept()
، ما عليك سوى تمرير معالِجك المخصّص عند استدعائه.
navigation.addEventListener("navigate", event => {
event.intercept({
async handler() {
doSyncStuff();
await doAsyncStuff();
}
});
});
NavigateEvent.scroll()
يعالج المتصفّح بالكامل عملية التنقّل، مثل الانتقال من أعلى الصفحة إلى عنصر ربط (يُعرَف ذلك بالانتقال من /a
إلى /a#id
)، حتى في التطبيقات المكوّنة من صفحة واحدة. ولكنّ الانتقال إلى عنصر ربط في "صفحة" أخرى (/a
إلى /b#id
)، وهو أمر بسيط في التطبيقات المكوّنة من صفحات متعددة، يكون أكثر تعقيدًا في التطبيقات المكوّنة من صفحة واحدة. على التطبيق اعتراض عملية التنقّل إلى /b#id
باستخدام NavigateEvent.transitionWhile()
، ثمّ استدعاء NavigateEvent.restoreScroll()
لعرض العنصر الثابت. كما ذكرنا أعلاه، من الصعب حاليًا إجراء ذلك.
التغييرات التي أُجريت
في التطبيقات المكوّنة من صفحة واحدة، يمكنك الآن التحكّم في ما إذا كان المتصفّح سيتولى الانتقال إلى عنصر ربط أو سيتولى ذلك الرمز البرمجي.
استخدام scroll()
سيحاول المتصفّح تلقائيًا معالجة الانتقال للأعلى أو للأسفل بعد أن ينتهي معالج الاعتراض من تنفيذ مهامه. إذا كنت تريد معالجة الانتقال للأعلى أو للأسفل بنفسك، اضبط scroll
على "manual"
، ثم استخدِم NavigateEvent.scroll()
عندما يحاول المتصفّح ضبط موضع الانتقال للأعلى أو للأسفل.
navigation.addEventListener("manual", event => {
scroll: "manual",
event.intercept({
async handler() {
doSyncStuff();
// Handle scrolling earlier than by default:
event.scroll();
await doAsyncStuff();
}
});
});
لا تزال طريقة restoreScroll()
متاحة، ولكن تم إيقافها نهائيًا وستتم إزالتها في الإصدار 108 من Chrome.
الخاتمة
نأمل أن نُجري قريبًا تعديلات على مقالتنا حول Navigation API. في الوقت الحالي، تحتوي مواصفات واجهة برمجة التطبيقات هذه على الكثير من المعلومات المخصّصة لمطوّري الويب.