rastrillo / fiesta Public

Clone
git clone https://amadan.net/rastrillo/fiesta

Plain git — no account needed to clone.

Download

Download this file

1/*! Fiesta 1.0.0 | MPL-2.0 | https://fiesta.rastrillo.org */
2(function () {
3 "use strict";
4
5 var ROOT = "[rst-shell-sidebar],[rst-shell-console],.rst-shell-sidebar,.rst-shell-console";
6 var INDEX = '[rst-shell-sidebar~="index"],[rst-shell-console~="index"],.rst-shell-sidebar--index,.rst-shell-console--index';
7 var PAGE = '[rst-shell-sidebar~="page"],[rst-shell-console~="page"],.rst-shell-sidebar--page,.rst-shell-console--page';
8 var BACK = "[rst-shell-back] > a[href],.rst-shell__back > a[href]";
9 var NAV = "[rst-shell-nav] a[href],.rst-shell__nav a[href]";
10 var NARROW = "(max-width: 799.98px)";
11 var RETURN = "rst-shell-return", WENT_BACK = "rst-shell-back";
12
13 function store(fn) {
14 try { return fn(window.sessionStorage); } catch (e) { return null; }
15 }
16 function take(key) {
17 return store(function (s) { var v = s.getItem(key); s.removeItem(key); return v; });
18 }
19 function place(href) {
20 var u = new URL(href, location.href);
21 return u.origin === location.origin ? u.pathname + u.search : null;
22 }
23 function view(sel) {
24 var r = document.querySelector(ROOT);
25 return !!r && r.matches(sel);
26 }
27
28 function returnFocus() {
29 if (document.prerendering || !view(INDEX)) return;
30 var rec = take(RETURN), links, hit = null, i, id;
31 if (!matchMedia(NARROW).matches) return;
32 links = document.querySelectorAll(NAV);
33 for (i = 0; rec && !hit && i < links.length; i++) {
34 if (place(links[i].href) === rec) hit = links[i];
35 }
36 if (!hit && location.hash) {
37 try { id = decodeURIComponent(location.hash.slice(1)); } catch (e) { id = location.hash.slice(1); }
38 hit = document.getElementById(id);
39 if (hit && !hit.matches(NAV)) hit = null;
40 }
41 if (hit) hit.focus();
42 }
43
44 function reveal(e) {
45 var back = take(WENT_BACK) === location.pathname + location.search, a = window.navigation && navigation.activation;
46 if (!back && a && a.navigationType === "traverse" && a.from && a.entry) back = a.entry.index < a.from.index;
47 returnFocus();
48 if (e.viewTransition && e.viewTransition.types) e.viewTransition.types.add(back ? "back" : "forward");
49 }
50 if ("onpagereveal" in window) window.addEventListener("pagereveal", reveal);
51 else window.addEventListener("pageshow", returnFocus);
52
53 function leave() {
54 if (view(PAGE)) store(function (s) { s.setItem(RETURN, location.pathname + location.search); });
55 }
56 window.addEventListener("onpageswap" in window ? "pageswap" : "pagehide", leave);
57
58 document.addEventListener("click", function (e) {
59 var a = e.target.closest && e.target.closest(BACK), nav = window.navigation, cur, prev, want;
60 if (!a || e.defaultPrevented || e.button !== 0 || e.ctrlKey || e.metaKey || e.shiftKey || e.altKey) return;
61 want = place(a.href);
62 if (want !== null) store(function (s) { s.setItem(WENT_BACK, want); });
63 cur = nav && nav.currentEntry;
64 if (!cur || cur.index < 1) return;
65 prev = nav.entries()[cur.index - 1];
66 if (want !== null && prev && !prev.sameDocument && prev.url && place(prev.url) === want) {
67 e.preventDefault();
68 history.back();
69 }
70 });
71})();
72