diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 0000000..5ca234d --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,3 @@ +{ + "liveServer.settings.file": "index.html" +} \ No newline at end of file diff --git a/assets/app.js b/assets/app.js index c6c3ff9..646f20d 100644 --- a/assets/app.js +++ b/assets/app.js @@ -455,7 +455,12 @@ function resolveRoute(pathname) { } } } - return { tab: SITE_TREE[0], group: SITE_TREE[0].groups[0], item: SITE_TREE[0].groups[0].items[0] }; + return { + is404: true, + tab: SITE_TREE[0], + group: { title: "Error" }, + item: { title: "404 Not Found", path: path } + }; } function renderNavTabs(currentTab) { @@ -837,6 +842,47 @@ function loadPage() { document.title = route.item.title + " — Vyla"; var contentEl = document.getElementById("main-content"); + + document.body.classList.remove("is-404"); + + var route = resolveRoute(window.location.pathname); + renderNavTabs(route.tab); + renderSidebar(route.tab, route.item); + + document.title = route.item.title + " — Vyla"; + + var contentEl = document.getElementById("main-content"); + + if (route.is404) { + document.body.classList.add("is-404"); + document.title = "404 - Page Not Found — Vyla"; + + if (contentEl) { + contentEl.classList.remove("content-animate"); + contentEl.innerHTML = + '
' + + '
404
' + + '
PAGE NOT FOUND
' + + '

But if you don\'t change your direction, and if you keep looking, you may end up where you are heading.

' + + ' Take me home' + + '
'; + + var tocList = document.getElementById("toc-list"); + if (tocList) tocList.innerHTML = ""; + var prevBtn = document.getElementById("footer-prev"); + var nextBtn = document.getElementById("footer-next"); + if (prevBtn) prevBtn.classList.add("hidden"); + if (nextBtn) nextBtn.classList.add("hidden"); + window.scrollTo(0, 0); + } + var sidebar = document.getElementById("sidebar"); + if (sidebar && sidebar.classList.contains("open")) { + sidebar.classList.remove("open"); + document.body.classList.remove("nav-open"); + } + return; + } + if (contentEl) { contentEl.classList.remove("content-animate"); contentEl.innerHTML = @@ -854,7 +900,8 @@ function loadPage() { fetch(route.item.file) .then(function (res) { - if (!res.ok) throw new Error("Not found"); + var ctype = res.headers.get("content-type") || ""; + if (!res.ok || ctype.indexOf("text/html") !== -1) throw new Error("Not found"); return res.text(); }) .then(function (md) { diff --git a/assets/styling/404.css b/assets/styling/404.css new file mode 100644 index 0000000..c938933 --- /dev/null +++ b/assets/styling/404.css @@ -0,0 +1,81 @@ +body.is-404 #sidebar, +body.is-404 #toc, +body.is-404 #mobile-bar, +body.is-404 .footer-nav { + display: none !important; +} + +body.is-404 #content-wrapper { + padding: 0 !important; + margin: 0 auto !important; + max-width: 100% !important; + width: 100% !important; +} + +body.is-404 #content-col, +body.is-404 #main-wrap, +body.is-404 #main-content { + max-width: 100% !important; + width: 100% !important; + margin: 0 !important; +} + +body.is-404 .error-container { + display: flex; + flex-direction: column; + align-items: center; + justify-content: center; + min-height: calc(80vh - 120px); + padding: 40px 20px; + box-sizing: border-box; + text-align: center; +} + +body.is-404 .error-code { + margin: 0 0 16px; + color: var(--color-text-primary); + font-size: clamp(74px, 14vw, 112px); + font-weight: 700; + line-height: 1; + letter-spacing: -2px; +} + +body.is-404 .error-title { + margin: 0 0 24px; + color: var(--color-text-primary); + font-size: 18px; + font-weight: 800; + letter-spacing: 0.12em; + text-transform: uppercase; +} + +body.is-404 .error-desc { + max-width: 440px; + margin: 0 0 32px; + color: var(--muted-light); + font-size: 15.5px; + line-height: 1.6; +} + +html.dark body.is-404 .error-desc { + color: var(--muted-dark); +} + +body.is-404 .btn-home { + display: inline-flex; + align-items: center; + justify-content: center; + padding: 10px 28px; + border-radius: 9999px; + background: var(--bg-dark); + color: var(--bg-light) !important; + font-size: 14.5px; + font-weight: 500; + text-decoration: none !important; + transition: background 0.2s ease, border-color 0.2s ease, color 0.2s ease; +} + +html.dark body.is-404 .btn-home { + background: var(--bg-light); + color: var(--bg-dark) !important; +} \ No newline at end of file diff --git a/assets/styling/layout.css b/assets/styling/layout.css index d8b8af8..8c335bf 100644 --- a/assets/styling/layout.css +++ b/assets/styling/layout.css @@ -204,6 +204,7 @@ html.dark #sidebar li a:hover { gap: 92px; max-width: 100%; box-sizing: border-box; + width: 80vw; } #main-wrap { diff --git a/assets/styling/prose.css b/assets/styling/prose.css index 3316ca2..7e83520 100644 --- a/assets/styling/prose.css +++ b/assets/styling/prose.css @@ -138,6 +138,7 @@ main.prose pre { background: rgba(250, 250, 250); --fade-l: 0px; --fade-r: 0px; + scrollbar-width: none; -webkit-mask-image: linear-gradient(to right, transparent 0, #000 var(--fade-l), #000 calc(100% - var(--fade-r)), transparent 100%); mask-image: linear-gradient(to right, transparent 0, #000 var(--fade-l), #000 calc(100% - var(--fade-r)), transparent 100%); } diff --git a/home.txt b/home.txt index d3dc3e6..c09aef2 100644 --- a/home.txt +++ b/home.txt @@ -257,15 +257,15 @@
+ src="https://www.pexels.com/download/video/14517238/">
-
+ src="https://www.pexels.com/download/video/14517238/">
diff --git a/index.html b/index.html index f6526cf..5ffa528 100644 --- a/index.html +++ b/index.html @@ -78,6 +78,7 @@ +