diff --git a/internal/web/handlers_public.go b/internal/web/handlers_public.go deleted file mode 100644 index b0ca5d3..0000000 --- a/internal/web/handlers_public.go +++ /dev/null @@ -1,14 +0,0 @@ -package web - -import "net/http" - -type HomeData struct { - Title string -} - -func (s *Server) handleHome() http.HandlerFunc { - return func(w http.ResponseWriter, r *http.Request) { - data := HomeData{Title: "NFeeder"} - view(w, r, "home", data) - } -} diff --git a/internal/web/handlers_user.go b/internal/web/handlers_user.go deleted file mode 100644 index efb3895..0000000 --- a/internal/web/handlers_user.go +++ /dev/null @@ -1 +0,0 @@ -package web diff --git a/static/css/app.css b/static/css/app.css deleted file mode 100644 index e69de29..0000000 diff --git a/static/css/index.css b/static/css/index.css deleted file mode 100644 index 8f4f0ce..0000000 --- a/static/css/index.css +++ /dev/null @@ -1,467 +0,0 @@ -/** - * By Oskar Wickström - * Licensed under the MIT License (https://github.com/owickstrom/the-monospace-web/blob/main/LICENSE.md) - **/ -@import url('https://fonts.cdnfonts.com/css/jetbrains-mono-2'); - -:root { - --font-family: "JetBrains Mono", monospace; - --line-height: 1.20rem; - --border-thickness: 2px; - --text-color: #000; - --text-color-alt: #666; - --background-color: #fff; - --background-color-alt: #eee; - - --font-weight-normal: 500; - --font-weight-medium: 600; - --font-weight-bold: 800; - - font-family: var(--font-family); - font-optical-sizing: auto; - font-weight: var(--font-weight-normal); - font-style: normal; - font-variant-numeric: tabular-nums lining-nums; - font-size: 18px; -} - -@media (prefers-color-scheme: dark) { - :root { - --text-color: #fff; - --text-color-alt: #aaa; - --background-color: #000; - --background-color-alt: #111; - } -} - -* { - box-sizing: border-box; -} - - -* + * { - margin-top: var(--line-height); -} - -html { - display: flex; - width: 100%; - margin: 0; - padding: 0; - flex-direction: column; - align-items: center; - background: var(--background-color); - color: var(--text-color); -} - -body { - position: relative; - width: 100%; - margin: 0; - padding: var(--line-height) 2ch; - max-width: calc(min(80ch, round(down, 100%, 1ch))); - line-height: var(--line-height); - overflow-x: hidden; -} - -@media screen and (max-width: 480px) { - :root { - font-size: 14px; - } - body { - padding: var(--line-height) 1ch; - } -} - -h1, h2, h3, h4, h5, h6 { - font-weight: var(--font-weight-bold); - margin: calc(var(--line-height) * 2) 0 var(--line-height); - line-height: var(--line-height); -} - -h1 { - font-size: 2rem; - line-height: calc(2 * var(--line-height)); - margin-bottom: calc(var(--line-height) * 2); - text-transform: uppercase; -} -h2 { - font-size: 1rem; - text-transform: uppercase; -} - -hr { - position: relative; - display: block; - height: var(--line-height); - margin: calc(var(--line-height) * 1.5) 0; - border: none; - color: var(--text-color); -} -hr:after { - display: block; - content: ""; - position: absolute; - top: calc(var(--line-height) / 2 - var(--border-thickness)); - left: 0; - width: 100%; - border-top: calc(var(--border-thickness) * 3) double var(--text-color); - height: 0; -} - -a { - text-decoration-thickness: var(--border-thickness); -} - -a:link, a:visited { - color: var(--text-color); -} - -p { - margin-bottom: var(--line-height); -} - -strong { - font-weight: var(--font-weight-bold); -} -em { - font-style: italic; -} - -sub { - position: relative; - display: inline-block; - margin: 0; - vertical-align: sub; - line-height: 0; - width: calc(1ch / 0.75); - font-size: .75rem; -} - -table { - position: relative; - top: calc(var(--line-height) / 2); - width: calc(round(down, 100%, 1ch)); - border-collapse: collapse; - margin: 0 0 calc(var(--line-height) * 2); -} - -th, td { - border: var(--border-thickness) solid var(--text-color); - padding: - calc((var(--line-height) / 2)) - calc(1ch - var(--border-thickness) / 2) - calc((var(--line-height) / 2) - (var(--border-thickness))) - ; - line-height: var(--line-height); - vertical-align: top; - text-align: left; -} -table tbody tr:first-child > * { - padding-top: calc((var(--line-height) / 2) - var(--border-thickness)); -} - - -th { - font-weight: 700; -} -.width-min { - width: 0%; -} -.width-auto { - width: 100%; -} - -.header { - margin-bottom: calc(var(--line-height) * 2); -} -.header h1 { - margin: 0; -} -.header tr td:last-child { - text-align: right; -} - -p { - word-break: break-word; - word-wrap: break-word; - hyphens: auto; -} - -img, video { - display: block; - width: 100%; - object-fit: contain; - overflow: hidden; -} -img { - font-style: italic; - color: var(--text-color-alt); -} - -details { - border: var(--border-thickness) solid var(--text-color); - padding: calc(var(--line-height) - var(--border-thickness)) 1ch; - margin-bottom: var(--line-height); -} - -summary { - font-weight: var(--font-weight-medium); - cursor: pointer; -} -details[open] summary { - margin-bottom: var(--line-height); -} - -details ::marker { - display: inline-block; - content: '▶'; - margin: 0; -} -details[open] ::marker { - content: '▼'; -} - -details :last-child { - margin-bottom: 0; -} - -pre { - white-space: pre; - overflow-x: auto; - margin: var(--line-height) 0; - overflow-y: hidden; -} -figure pre { - margin: 0; -} - -pre, code { - font-family: var(--font-family); -} - -code { - font-weight: var(--font-weight-medium); -} - -figure { - margin: calc(var(--line-height) * 2) 3ch; - overflow-x: auto; - overflow-y: hidden; -} - -figcaption { - display: block; - font-style: italic; - margin-top: var(--line-height); -} - -ul, ol { - padding: 0; - margin: 0 0 var(--line-height); -} - -ul { - list-style-type: square; - padding: 0 0 0 2ch; -} -ol { - list-style-type: none; - counter-reset: item; - padding: 0; -} -ol ul, -ol ol, -ul ol, -ul ul { - padding: 0 0 0 3ch; - margin: 0; -} -ol li:before { - content: counters(item, ".") ". "; - counter-increment: item; - font-weight: var(--font-weight-medium); -} - -li { - margin: 0; - padding: 0; -} - -li::marker { - line-height: 0; -} - -::-webkit-scrollbar { - height: var(--line-height); -} - -input, button, textarea { - border: var(--border-thickness) solid var(--text-color); - padding: - calc(var(--line-height) / 2 - var(--border-thickness)) - calc(1ch - var(--border-thickness)); - margin: 0; - font: inherit; - font-weight: inherit; - height: calc(var(--line-height) * 2); - width: auto; - overflow: visible; - background: var(--background-color); - color: var(--text-color); - line-height: normal; - -webkit-font-smoothing: inherit; - -moz-osx-font-smoothing: inherit; - -webkit-appearance: none; -} - -input[type=checkbox], -input[type=radio] { - display: inline-grid; - place-content: center; - vertical-align: top; - width: 2ch; - height: var(--line-height); - cursor: pointer; -} -input[type=checkbox]:checked:before, -input[type=radio]:checked:before { - content: ""; - width: 1ch; - height: calc(var(--line-height) / 2); - background: var(--text-color); -} -input[type=radio], -input[type=radio]:before { - border-radius: 100%; -} - -button:focus, input:focus { - --border-thickness: 3px; - outline: none; -} - -input { - width: calc(round(down, 100%, 1ch)); -} -::placeholder { - color: var(--text-color-alt); - opacity: 1; -} -::-ms-input-placeholder { - color: var(--text-color-alt); -} -button::-moz-focus-inner { - padding: 0; - border: 0 -} - -button { - text-transform: uppercase; - font-weight: var(--font-weight-medium); - cursor: pointer; -} - -button:hover { - background: var(--background-color-alt); -} -button:active { - transform: translate(2px, 2px); -} - -label { - display: block; - width: calc(round(down, 100%, 1ch)); - height: auto; - line-height: var(--line-height); - font-weight: var(--font-weight-medium); - margin: 0; -} - -label input { - width: 100%; -} - -.tree, .tree ul { - position: relative; - padding-left: 0; - list-style-type: none; - line-height: var(--line-height); -} -.tree ul { - margin: 0; -} -.tree ul li { - position: relative; - padding-left: 1.5ch; - margin-left: 1.5ch; - border-left: var(--border-thickness) solid var(--text-color); -} -.tree ul li:before { - position: absolute; - display: block; - top: calc(var(--line-height) / 2); - left: 0; - content: ""; - width: 1ch; - border-bottom: var(--border-thickness) solid var(--text-color); -} -.tree ul li:last-child { - border-left: none; -} -.tree ul li:last-child:after { - position: absolute; - display: block; - top: 0; - left: 0; - content: ""; - height: calc(var(--line-height) / 2); - border-left: var(--border-thickness) solid var(--text-color); -} - -.grid { - --grid-cells: 0; - display: flex; - gap: 1ch; - width: calc(round(down, 100%, (1ch * var(--grid-cells)) - (1ch * var(--grid-cells) - 1))); - margin-bottom: var(--line-height); -} - -.grid > *, -.grid > input { - flex: 0 0 calc(round(down, (100% - (1ch * (var(--grid-cells) - 1))) / var(--grid-cells), 1ch)); -} -.grid:has(> :last-child:nth-child(1)) { --grid-cells: 1; } -.grid:has(> :last-child:nth-child(2)) { --grid-cells: 2; } -.grid:has(> :last-child:nth-child(3)) { --grid-cells: 3; } -.grid:has(> :last-child:nth-child(4)) { --grid-cells: 4; } -.grid:has(> :last-child:nth-child(5)) { --grid-cells: 5; } -.grid:has(> :last-child:nth-child(6)) { --grid-cells: 6; } -.grid:has(> :last-child:nth-child(7)) { --grid-cells: 7; } -.grid:has(> :last-child:nth-child(8)) { --grid-cells: 8; } -.grid:has(> :last-child:nth-child(9)) { --grid-cells: 9; } - -/* DEBUG UTILITIES */ - -.debug .debug-grid { - --color: color-mix(in srgb, var(--text-color) 10%, var(--background-color) 90%); - position: absolute; - top: 0; - left: 0; - right: 0; - bottom: 0; - z-index: -1; - background-image: - repeating-linear-gradient(var(--color) 0 1px, transparent 1px 100%), - repeating-linear-gradient(90deg, var(--color) 0 1px, transparent 1px 100%); - background-size: 1ch var(--line-height); - margin: 0; -} - -.debug .off-grid { - background: rgba(255, 0, 0, 0.1); -} - -.debug-toggle-label { - text-align: right; -} diff --git a/static/css/reset.css b/static/css/reset.css deleted file mode 100644 index aabd759..0000000 --- a/static/css/reset.css +++ /dev/null @@ -1,48 +0,0 @@ -/* http://meyerweb.com/eric/tools/css/reset/ - v2.0 | 20110126 - License: none (public domain) -*/ - -html, body, div, span, applet, object, iframe, -h1, h2, h3, h4, h5, h6, p, blockquote, pre, -a, abbr, acronym, address, big, cite, code, -del, dfn, em, img, ins, kbd, q, s, samp, -small, strike, strong, sub, sup, tt, var, -b, u, i, center, -dl, dt, dd, ol, ul, li, -fieldset, form, label, legend, -table, caption, tbody, tfoot, thead, tr, th, td, -article, aside, canvas, details, embed, -figure, figcaption, footer, header, hgroup, -menu, nav, output, ruby, section, summary, -time, mark, audio, video { - /*margin: 0;*/ - padding: 0; - border: 0; - font-size: 100%; - font: inherit; - vertical-align: baseline; -} -/* HTML5 display-role reset for older browsers */ -article, aside, details, figcaption, figure, -footer, header, hgroup, menu, nav, section { - display: block; -} -body { - line-height: 1; -} -ol, ul { - list-style: none; -} -blockquote, q { - quotes: none; -} -blockquote:before, blockquote:after, -q:before, q:after { - content: ''; - content: none; -} -table { - border-collapse: collapse; - border-spacing: 0; -} diff --git a/static/js/index.js b/static/js/index.js deleted file mode 100644 index 4379fc2..0000000 --- a/static/js/index.js +++ /dev/null @@ -1,120 +0,0 @@ -function gridCellDimensions() { - const element = document.createElement("div"); - element.style.position = "fixed"; - element.style.height = "var(--line-height)"; - element.style.width = "1ch"; - document.body.appendChild(element); - const rect = element.getBoundingClientRect(); - document.body.removeChild(element); - return { width: rect.width, height: rect.height }; -} - -// Add padding to each media to maintain grid. -function adjustMediaPadding() { - const cell = gridCellDimensions(); - - function setHeightFromRatio(media, ratio) { - const rect = media.getBoundingClientRect(); - const realHeight = rect.width / ratio; - const diff = cell.height - (realHeight % cell.height); - media.style.setProperty("padding-bottom", `${diff}px`); - } - - function setFallbackHeight(media) { - const rect = media.getBoundingClientRect(); - const height = Math.round((rect.width / 2) / cell.height) * cell.height; - media.style.setProperty("height", `${height}px`); - } - - function onMediaLoaded(media) { - var width, height; - switch (media.tagName) { - case "IMG": - width = media.naturalWidth; - height = media.naturalHeight; - break; - case "VIDEO": - width = media.videoWidth; - height = media.videoHeight; - break; - } - if (width > 0 && height > 0) { - setHeightFromRatio(media, width / height); - } else { - setFallbackHeight(media); - } - } - - const medias = document.querySelectorAll("img, video"); - for (media of medias) { - switch (media.tagName) { - case "IMG": - if (media.complete) { - onMediaLoaded(media); - } else { - media.addEventListener("load", () => onMediaLoaded(media)); - media.addEventListener("error", function() { - setFallbackHeight(media); - }); - } - break; - case "VIDEO": - switch (media.readyState) { - case HTMLMediaElement.HAVE_CURRENT_DATA: - case HTMLMediaElement.HAVE_FUTURE_DATA: - case HTMLMediaElement.HAVE_ENOUGH_DATA: - onMediaLoaded(media); - break; - default: - media.addEventListener("loadeddata", () => onMediaLoaded(media)); - media.addEventListener("error", function() { - setFallbackHeight(media); - }); - break; - } - break; - } - } -} - -adjustMediaPadding(); -window.addEventListener("load", adjustMediaPadding); -window.addEventListener("resize", adjustMediaPadding); - -function checkOffsets() { - const ignoredTagNames = new Set([ - "THEAD", - "TBODY", - "TFOOT", - "TR", - "TD", - "TH", - ]); - const cell = gridCellDimensions(); - const elements = document.querySelectorAll("body :not(.debug-grid, .debug-toggle)"); - for (const element of elements) { - if (ignoredTagNames.has(element.tagName)) { - continue; - } - const rect = element.getBoundingClientRect(); - if (rect.width === 0 && rect.height === 0) { - continue; - } - const top = rect.top + window.scrollY; - const left = rect.left + window.scrollX; - const offset = top % (cell.height / 2); - if(offset > 0) { - element.classList.add("off-grid"); - console.error("Incorrect vertical offset for", element, "with remainder", top % cell.height, "when expecting divisible by", cell.height / 2); - } else { - element.classList.remove("off-grid"); - } - } -} - -const debugToggle = document.querySelector(".debug-toggle"); -function onDebugToggle() { - document.body.classList.toggle("debug", debugToggle.checked); -} -debugToggle.addEventListener("change", onDebugToggle); -onDebugToggle();