@@ -46,15 +46,14 @@ const posts = (await getCollection("docs"))
4646 <script is:inline >
4747 // Set theme before paint to avoid a flash. Shares Starlight's key so the
4848 // choice carries over to the docs/blog pages.
49+ // Default is DARK regardless of OS; only an explicit toggle overrides it.
4950 (function () {
5051 try {
51- const stored = localStorage.getItem("starlight-theme");
52- const theme =
53- stored === "light" || stored === "dark"
54- ? stored
55- : window.matchMedia("(prefers-color-scheme: dark)").matches
56- ? "dark"
57- : "light";
52+ let theme = localStorage.getItem("starlight-theme");
53+ if (theme !== "light" && theme !== "dark") {
54+ theme = "dark";
55+ localStorage.setItem("starlight-theme", theme);
56+ }
5857 document.documentElement.dataset.theme = theme;
5958 } catch (e) {}
6059 })();
@@ -66,7 +65,7 @@ const posts = (await getCollection("docs"))
6665 <Image class =" brand-mark" src ={ mark } alt =" " width ={ 28 } height ={ 28 } aria-hidden =" true" />
6766 Data Privacy Stack
6867 </a >
69- <nav class =" links" >
68+ <nav id = " nav-links " class =" links" >
7069 <a href =" #about" >About</a >
7170 <a href =" #projects" >Projects</a >
7271 <a href =" #governance" >Governance</a >
@@ -79,6 +78,10 @@ const posts = (await getCollection("docs"))
7978 <svg class =" icon-sun" width =" 18" height =" 18" viewBox =" 0 0 24 24" fill =" none" stroke =" currentColor" stroke-width =" 2" stroke-linecap =" round" ><circle cx =" 12" cy =" 12" r =" 4" /><path d =" M12 2v2M12 20v2M4.93 4.93l1.41 1.41M17.66 17.66l1.41 1.41M2 12h2M20 12h2M6.34 17.66l-1.41 1.41M19.07 4.93l-1.41 1.41" /></svg >
8079 <svg class =" icon-moon" width =" 18" height =" 18" viewBox =" 0 0 24 24" fill =" currentColor" ><path d =" M21 12.79A9 9 0 1 1 11.21 3 7 7 0 0 0 21 12.79z" /></svg >
8180 </button >
81+ <button id =" menu-toggle" class =" menu-toggle" type =" button" aria-label =" Toggle menu" aria-expanded =" false" aria-controls =" nav-links" >
82+ <svg class =" icon-menu" width =" 22" height =" 22" viewBox =" 0 0 24 24" fill =" none" stroke =" currentColor" stroke-width =" 2" stroke-linecap =" round" ><path d =" M3 6h18M3 12h18M3 18h18" /></svg >
83+ <svg class =" icon-close" width =" 22" height =" 22" viewBox =" 0 0 24 24" fill =" none" stroke =" currentColor" stroke-width =" 2" stroke-linecap =" round" ><path d =" M6 6l12 12M18 6 6 18" /></svg >
84+ </button >
8285 </header >
8386
8487 <main id =" top" >
@@ -244,6 +247,25 @@ const posts = (await getCollection("docs"))
244247 document.documentElement.dataset.theme = next;
245248 try { localStorage.setItem("starlight-theme", next); } catch (e) {}
246249 });
250+
251+ // Mobile hamburger menu
252+ const nav = document.querySelector(".nav");
253+ const mbtn = document.getElementById("menu-toggle");
254+ const setMenu = (open) => {
255+ nav.classList.toggle("open", open);
256+ mbtn?.setAttribute("aria-expanded", open ? "true" : "false");
257+ };
258+ mbtn?.addEventListener("click", () =>
259+ setMenu(!nav.classList.contains("open"))
260+ );
261+ // Close after choosing a destination
262+ document
263+ .querySelectorAll("#nav-links a")
264+ .forEach((a) => a.addEventListener("click", () => setMenu(false)));
265+ // Close on Escape
266+ document.addEventListener("keydown", (e) => {
267+ if (e.key === "Escape") setMenu(false);
268+ });
247269 </script >
248270
249271 <style >
@@ -339,6 +361,46 @@ const posts = (await getCollection("docs"))
339361 :root[data-theme="dark"] .theme-toggle .icon-sun { display: none; }
340362 :root[data-theme="dark"] .theme-toggle .icon-moon { display: block; }
341363
364+ /* Mobile hamburger (hidden on desktop) */
365+ .menu-toggle {
366+ display: none;
367+ place-items: center;
368+ width: 36px; height: 36px;
369+ border-radius: 999px;
370+ border: 1px solid var(--card-border);
371+ background: var(--card-bg);
372+ color: var(--text);
373+ cursor: pointer;
374+ }
375+ .menu-toggle .icon-close { display: none; }
376+ .nav.open .menu-toggle .icon-menu { display: none; }
377+ .nav.open .menu-toggle .icon-close { display: block; }
378+
379+ @media (max-width: 880px) {
380+ .nav { flex-wrap: nowrap; }
381+ .menu-toggle { display: inline-grid; }
382+ .links {
383+ display: none;
384+ position: absolute;
385+ top: 100%;
386+ left: 0;
387+ right: 0;
388+ flex-direction: column;
389+ align-items: stretch;
390+ gap: 0;
391+ padding: 0.4rem 0;
392+ background: var(--nav-bg);
393+ backdrop-filter: saturate(180%) blur(10px);
394+ border-bottom: 1px solid var(--nav-border);
395+ }
396+ .nav.open .links { display: flex; }
397+ .links a {
398+ padding: 0.75rem clamp(1rem, 5vw, 3rem);
399+ font-size: 1rem;
400+ }
401+ .links a:hover { background: rgba(127, 127, 127, 0.1); color: var(--accent-strong); }
402+ }
403+
342404 main { width: min(1040px, 92vw); margin: 0 auto; }
343405
344406 /* Hero */
0 commit comments