Skip to content

Commit 533264d

Browse files
committed
docs(nav[spa]): wrap DOM swap in View Transitions API for smooth crossfade
why: SPA navigation instantly replaces DOM content, causing a jarring visual jump between pages instead of a smooth transition. what: - Wrap swap+reinit in document.startViewTransition() when available - Add 150ms crossfade animation via ::view-transition pseudo-elements - Progressive enhancement: unsupported browsers get instant swap
1 parent 19d375c commit 533264d

2 files changed

Lines changed: 30 additions & 12 deletions

File tree

docs/_static/css/custom.css

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -198,6 +198,16 @@ article {
198198
* content-visibility and badge-specific height to prevent CLS.
199199
* ────────────────────────────────────────────────────────── */
200200

201+
202+
/* ── View Transitions (SPA navigation) ────────────────────
203+
* Crossfade between pages during SPA navigation.
204+
* Browsers without View Transitions API get instant swap.
205+
* ────────────────────────────────────────────────────────── */
206+
::view-transition-old(root),
207+
::view-transition-new(root) {
208+
animation-duration: 150ms;
209+
}
210+
201211
img {
202212
content-visibility: auto;
203213
}

docs/_static/js/spa-nav.js

Lines changed: 20 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -160,21 +160,29 @@
160160
if (!doc.querySelector(".article-container"))
161161
throw new Error("no article");
162162

163-
swap(doc);
163+
var applySwap = function () {
164+
swap(doc);
165+
166+
if (!isPop) history.pushState({ spa: true }, "", url);
167+
168+
if (!isPop) {
169+
var hash = new URL(url, location.href).hash;
170+
if (hash) {
171+
var el = document.querySelector(hash);
172+
if (el) el.scrollIntoView();
173+
} else {
174+
window.scrollTo(0, 0);
175+
}
176+
}
164177

165-
if (!isPop) history.pushState({ spa: true }, "", url);
178+
reinit();
179+
};
166180

167-
if (!isPop) {
168-
var hash = new URL(url, location.href).hash;
169-
if (hash) {
170-
var el = document.querySelector(hash);
171-
if (el) el.scrollIntoView();
172-
} else {
173-
window.scrollTo(0, 0);
174-
}
181+
if (document.startViewTransition) {
182+
document.startViewTransition(applySwap);
183+
} else {
184+
applySwap();
175185
}
176-
177-
reinit();
178186
} catch (err) {
179187
if (err.name === "AbortError") return;
180188
window.location.href = url;

0 commit comments

Comments
 (0)