Chrome 105 wprowadza 2 nowe metody w interfejsie NavigateEvent
interfejsu API nawigacji (wprowadzonego w wersji 102), aby ulepszyć metody, które w praktyce okazały się problematyczne. intercept()
, który pozwala deweloperom kontrolować stan po nawigacji, zastępuje transitionWhile()
, który okazał się trudny w użyciu. Metoda scroll()
, która przewija do zakotwiczenia określonego w adresie URL, zastępuje metodę restoreScroll()
, która nie działa w przypadku niektórych typów nawigacji.
W tym artykule opisuję problemy związane z tymi metodami i sposoby ich rozwiązania.
NavigateEvent.transitionWhile()
Metoda NavigateEvent.trasitionWhile()
, wprowadzona w ramach interfejsu Navigation API w wersji Chrome 102, przechwytuje nawigację w przypadku przejść po stronie klienta w aplikacjach jednostronicowych. Pierwszym argumentem jest obietnica, która sygnalizuje przeglądarce i innym częściom aplikacji internetowej, że jest gotowa.
W praktyce nie działało to dobrze. Przyjrzyjmy się temu wspólnemu formatowi kodowania:
event.transitionWhile((async () => {
doSyncStuff();
await doAsyncStuff();
})());
Pod względem funkcjonalności jest to równoważne z podanym niżej kodem. Powoduje to, że część nawigacji jest wykonywana, zanim interfejs API dowie się, że deweloper chce ją przechwycić.
doSyncStuff();
event.transitionWhile((async () => {
await doAsyncStuff();
})());
Przykładem, w którym może to spowodować problemy z aplikacją, jest logika przywracania przewijania, która rejestruje pozycje przewijania po zmianie DOM, a nie przed nią.
Co się zmieniło
Aby zastąpić transitionWhile()
, obecna specyfikacja wprowadza NavigateEvent.intercept()
. Nowa metoda przyjmuje obiekt obsługi oprócz właściwości focusReset
i scrollRestoration
obsługiwanych przez transitionWhile()
. Nowy handler zawsze działa po zatwierdzeniu nawigacji, a takie rzeczy jak pozycje przewijania zostały już przechwycone, co pozwala uniknąć problemów z transitionWhile()
.
Metoda transitionWhile()
jest nadal dostępna, ale została wycofana i zostanie usunięta w Chrome 108.
Korzystanie z funkcji intercept()
Zdarzenie NavigateEvent.intercept()
podlega tym samym ograniczeniom co zdarzenie transitionWhile()
, ponieważ nie może być wywoływane w przypadku wszystkich zdarzeń nawigacyjnych. Nie można przechwycić nawigacji między domenami ani przechodzenia między dokumentami. Spowoduje to wygenerowanie obiektu DOMException
typu "SecurityError"
.
Aby użyć intercept()
, po prostu prześlij niestandardowy moduł obsługi podczas wywoływania.
navigation.addEventListener("navigate", event => {
event.intercept({
async handler() {
doSyncStuff();
await doAsyncStuff();
}
});
});
NavigateEvent.scroll()
Nawigacja, np. z góry strony do kotwicy (czyli przejście z /a
do /a#id
), jest obsługiwana całkowicie przez przeglądarkę, nawet w przypadku aplikacji jednostronicowych. Natomiast przejście do kotwicy na innej „stronie” (z /a
do /b#id
), które jest proste w przypadku aplikacji wielostronicowych, jest bardziej skomplikowane w przypadku aplikacji jednostronicowych. Aplikacja musi przechwycić nawigację do /b#id
za pomocą NavigateEvent.transitionWhile()
, a potem wywołać NavigateEvent.restoreScroll()
, aby wyświetlić kotwicę. Jak już wspomnieliśmy, jest to obecnie trudne do zrobienia.
Co się zmieniło
W aplikacjach jednostronicowych możesz teraz określić, czy przewijanie do kotwicy ma obsługiwać przeglądarka, czy kod.
Używanie scroll()
Domyślnie przeglądarka będzie automatycznie obsługiwać przewijanie, gdy tylko zostanie spełniony warunek przechwytywania. Jeśli chcesz samodzielnie obsługiwać przewijanie, ustaw scroll
na "manual"
, a następnie wywołaj NavigateEvent.scroll()
, gdy przeglądarka ma spróbować ustawić pozycję przewijania.
navigation.addEventListener("manual", event => {
scroll: "manual",
event.intercept({
async handler() {
doSyncStuff();
// Handle scrolling earlier than by default:
event.scroll();
await doAsyncStuff();
}
});
});
Metoda restoreScroll()
jest nadal dostępna, ale została wycofana i zostanie usunięta w Chrome 108.
Podsumowanie
Mamy nadzieję, że wkrótce zaktualizujemy nasz artykuł o interfejsie Navigation API. Tymczasem specyfikacja tego interfejsu API zawiera wiele informacji przeznaczonych specjalnie dla programistów internetowych.