/* =========================================================================
   LazyBlog — reusable components
   Tag chips, callouts (highlight-box, story-card), freq-tag,
   view-source-link, section-tag, tables, video embeds, TOC base,
   pagination.
   ========================================================================= */

/* ---------- Tag chip ---------- */
.tag-chip {
    display: inline-block;
    padding: 3px 12px;
    border: 1px solid var(--accent-dim);
    color: var(--accent);
    font-family: 'Share Tech Mono', monospace;
    font-size: 11px;
    text-decoration: none;
    border-radius: 2px;
    letter-spacing: 1px;
}
.tag-chip:hover { background: var(--primary-glow); border-color: var(--accent); }

/* ---------- View source / edit links ---------- */
.view-source-link {
    display: inline-block;
    font-family: 'Share Tech Mono', monospace;
    font-size: 11px;
    color: var(--accent);
    letter-spacing: 2px;
    text-decoration: none;
    border: 1px solid var(--accent-dim);
    padding: 7px 14px;
}
.view-source-link:hover { background: var(--primary-glow); border-color: var(--accent); }
/* EDIT button only shown to admin; subtle filled tint marks it as the primary
   in-page action without breaking the bracketed-link family. */
.view-source-link-edit { background: var(--primary-glow); }
.view-source-link-edit:hover { background: var(--accent); color: var(--bg); }

/* ---------- highlight-box (from markdown ::: highlight) ---------- */
.highlight-box {
    background: var(--panel);
    border: 1px solid var(--primary-dim);
    border-left: 3px solid var(--primary);
    padding: 16px 18px;
    margin: 20px 0;
    font-family: 'Share Tech Mono', monospace;
    font-size: 14px;
    color: var(--primary);
    line-height: 1.75;
}
.highlight-box p { margin: 6px 0; color: var(--primary); }
.highlight-box strong { color: var(--primary); }

/* ---------- story-card (from markdown ::: story) ---------- */
.story-card {
    background: var(--panel);
    border: 1px solid var(--border);
    border-radius: 3px;
    padding: 20px;
    margin: 24px 0;
    position: relative;
}
.story-card::before {
    content: attr(data-icon);
    position: absolute;
    top: 14px; right: 18px;
    font-size: 26px;
    opacity: 0.55;
}
.story-card .story-title {
    font-family: 'VT323', monospace;
    font-size: clamp(22px, 4vw, 26px);
    color: var(--accent);
    text-shadow: 0 0 8px var(--accent-dim);
    margin-bottom: 10px;
    padding-right: 42px;
    letter-spacing: 1px;
}
.story-card p { margin: 8px 0; color: var(--text); }

/* ---------- freq-tag (from markdown unit-pattern <code> upgrade) ---------- */
.freq-tag {
    display: inline-block;
    background: var(--primary-glow);
    border: 1px solid var(--primary-dim);
    padding: 2px 8px;
    border-radius: 2px;
    font-family: 'Share Tech Mono', monospace;
    font-size: 13px;
    color: var(--primary);
    margin: 0 2px;
    white-space: nowrap;
}

/* ---------- mark (extended-markdown ==highlight==) ----------
   Phosphor highlighter — same look as the active TOC link so highlighted
   prose visually rhymes with the active section indicator. */
.post-body mark {
    background: var(--primary);
    color: var(--bg);
    padding: 0 4px;
    border-radius: 1px;
    text-shadow: none;
}

/* ---------- del (extended-markdown ~~strikethrough~~) ---------- */
.post-body del {
    color: var(--text-dim);
    text-decoration: line-through;
    text-decoration-thickness: 1px;
}

/* ---------- Task lists (extended-markdown `- [ ]` / `- [x]`) ----------
   CommonMark TaskListExtension emits a plain `<li>` whose first child is
   `<input type="checkbox" disabled>`. We drop the bullet on those `<li>`s
   and restyle the checkbox as a CRT-tile box. `:has()` is supported in
   every browser this site already targets (CSS Grid + clamp() era). */
.post-body li:has(> input[type="checkbox"]) {
    list-style: none;
    margin-left: -1.1em;
}
.post-body input[type="checkbox"][disabled] {
    appearance: none;
    -webkit-appearance: none;
    width: 13px;
    height: 13px;
    margin-right: 8px;
    vertical-align: -2px;
    border: 1px solid var(--primary-dim);
    background: var(--panel);
    border-radius: 2px;
    cursor: default;
}
.post-body input[type="checkbox"][disabled]:checked {
    background: var(--primary);
    border-color: var(--primary);
    box-shadow: 0 0 6px var(--primary-glow);
    position: relative;
}
.post-body input[type="checkbox"][disabled]:checked::after {
    content: '✓';
    position: absolute;
    top: -3px;
    left: 1px;
    font-family: 'Share Tech Mono', monospace;
    font-size: 12px;
    color: var(--bg);
    line-height: 1;
}

/* ---------- Footnotes (extended-markdown `[^N]`) ----------
   Inline `<sup>` reference + bottom `<div class="footnotes">` section.
   Treats the section as a phosphor sub-panel below the main content. */
.post-body sup .footnote-ref {
    color: var(--accent);
    text-decoration: none;
    font-family: 'Share Tech Mono', monospace;
    font-size: 11px;
    padding: 0 2px;
}
.post-body sup .footnote-ref:hover {
    color: var(--primary);
    text-shadow: 0 0 4px var(--primary-glow-strong);
}
.post-body sup .footnote-ref::before { content: '['; color: var(--primary-dim); }
.post-body sup .footnote-ref::after  { content: ']'; color: var(--primary-dim); }

.post-body .footnotes {
    margin-top: 48px;
    padding-top: 18px;
    border-top: 1px dashed var(--border);
    font-family: 'Share Tech Mono', monospace;
    font-size: 13px;
    color: var(--text-dim);
}
.post-body .footnotes hr { display: none; }
.post-body .footnotes ol { padding-left: 24px; margin: 8px 0; }
.post-body .footnotes li { margin: 6px 0; }
.post-body .footnotes li::marker { color: var(--accent); }
.post-body .footnotes p { margin: 4px 0; color: var(--text-dim); }
.post-body .footnote-backref {
    color: var(--accent);
    text-decoration: none;
    margin-left: 4px;
}
.post-body .footnote-backref:hover {
    color: var(--primary);
    text-shadow: 0 0 4px var(--primary-glow-strong);
}

/* ---------- Sidenotes (wide-screen footnote rendering) ----------
   MarkdownRenderer::injectSidenotes() duplicates each footnote body into an
   inline `<span class="sidenote">` after its `[^N]` reference. Default
   (narrow/mobile): sidenotes hidden, the bottom `.footnotes` list shows.
   Wide (>=1400px): each note is lifted out of flow and parked in the blank
   right margin OUTSIDE the reading column — the post body keeps its full
   width, the note sits beside its reference (Tufte-style margin note), and
   the bottom list is hidden.

   Breakpoint 1440px, not 1200px: `main` caps at 1020px, so the space right of
   the body content box is main's 48px padding + (viewport-1020)/2 of outer
   margin. That only clears the note width (200px + 28px gap) with room to
   spare once the viewport is ~1440px wide. Body has `overflow-x: clip`, so a
   note wider than that space would be silently cut — hence the hard gate +
   bottom-list fallback below. */
/* Unscoped hide so the sidenote copy never shows outside a `.post-body`
   container — e.g. the editor's inline live-preview panel renders the same
   server HTML but isn't `.post-body`, and would otherwise duplicate the note
   text (inline copy + bottom list). Only the >=1440px rule below re-shows it. */
.sidenote { display: none; }

@media (min-width: 1440px) {
    /* Positioned ancestor so each note anchors to the body's right edge. */
    .post-body { position: relative; }
    .post-body .footnotes { display: none; }

    .post-body .sidenote {
        display: block;
        position: absolute;
        /* left:100% = right edge of the body content box; the note then lives
           entirely in the margin to the right, never inside the text column.
           `top` stays auto so it sits at its in-flow position — level with the
           reference line. */
        left: 100%;
        margin-left: 28px;
        width: 200px;
        font-family: 'Share Tech Mono', monospace;
        font-size: 12px;
        line-height: 1.6;
        letter-spacing: 0.3px;
        color: var(--text-dim);
        text-align: left;
    }
    .post-body .sidenote-num { color: var(--accent); margin-right: 5px; }
    .post-body .sidenote a { color: var(--accent); text-decoration: none; }
    .post-body .sidenote a:hover {
        color: var(--primary);
        text-shadow: 0 0 4px var(--primary-glow-strong);
    }
    /* The number acts as a "jump back" handle — post.js blinks the matching
       `[N]` reference when it's clicked. */
    .post-body .sidenote-num { cursor: pointer; }
}

/* ---------- Footnote <-> reference cross-highlight ----------
   Applied by post.js (auto-removed on animationend). The same `fn-lit`
   highlight runs both ways: clicking a `[N]` reference lights its note, and
   clicking a note's number lights the `[N]` reference. */
.post-body .fn-lit {
    animation: fn-lit 1.4s ease-out;
    border-radius: 3px;
}
/* Bold highlight: a solid phosphor wash (inverted text for contrast) that
   fades back to the element's resting style. */
@keyframes fn-lit {
    0%, 15% {
        background-color: var(--primary);
        color: var(--bg);
        text-shadow: none;
    }
    100% {
        background-color: transparent;
        color: var(--primary);
        text-shadow: 0 0 8px var(--primary-glow-strong);
    }
}
@media (prefers-reduced-motion: reduce) {
    .post-body .fn-lit { animation-duration: 0.01ms; }
}

/* ---------- Section tag (used by views) ---------- */
.section-tag, [class*="section"] > .callsign {
    font-family: 'Share Tech Mono', monospace;
    color: var(--primary-dim);
    letter-spacing: 3px;
    text-transform: uppercase;
    font-size: 11px;
    margin-bottom: 8px;
}
/* Mobile: tighten letter-spacing and shrink font so the post meta line
   (`§ [ UNLOCKED ] TRANSMISSION — YYYY-MM-DD — CALLSIGN — N VIEW`) fits
   one line on narrow viewports instead of wrapping mid-segment. The
   earlier 10px + 1.5px letter-spacing was tuned before view-counter +
   UNLOCKED badge stretched the line; now the row reliably broke onto
   "VIEW" alone. nowrap is the contract — keep the line atomic; overflow-x
   auto is the safety net for the smallest viewports so the user can
   scroll the meta horizontally if it still overruns. */
@media (max-width: 600px) {
    .section-tag, [class*="section"] > .callsign {
        letter-spacing: 1px;
        font-size: 10px;
        white-space: nowrap;
        overflow-x: auto;
        -webkit-overflow-scrolling: touch;
        /* Hide the horizontal scrollbar visually — Chrome/Safari paint
           a thin bar when overflow-x:auto kicks in, which reads as a
           UI artifact on the meta line. Touch-scroll still works on
           iOS, and the operator can swipe to see the truncated tail. */
        scrollbar-width: none;
    }
    .section-tag::-webkit-scrollbar,
    [class*="section"] > .callsign::-webkit-scrollbar {
        display: none;
    }
}

/* ---------- Tables (GFM) ----------
   CRT terminal grid: mono font, accent borders, alternating row tint.
   Horizontally scrolls when wider than the column on narrow screens. */
.post-body table {
    width: 100%;
    border-collapse: collapse;
    margin: 20px 0;
    font-family: 'Share Tech Mono', monospace;
    font-size: 13px;
    table-layout: auto;
}
.post-body thead {
    background: var(--panel);
    border-bottom: 1px solid var(--accent-dim);
}
.post-body th {
    color: var(--accent);
    font-weight: normal;
    text-align: left;
    padding: 10px 14px;
    letter-spacing: 1px;
    text-transform: uppercase;
    font-size: 11px;
    white-space: nowrap;
}
.post-body td {
    color: var(--text);
    padding: 8px 14px;
    border-bottom: 1px dashed var(--border);
}
.post-body tbody tr:nth-child(even) td {
    background: rgba(255, 183, 0, 0.025);
}
.post-body tbody tr:hover td {
    background: var(--primary-glow);
}
.post-body table code {
    font-size: 12px;
    padding: 1px 5px;
}

/* ---------- Video embeds (YouTube auto-embed from URL) ----------
   Stays within the article column (unlike post-figure which breaks out
   to full viewport). 16:9 aspect ratio via aspect-ratio. */
.video-embed {
    width: 100%;
    margin: 28px 0;
    position: relative;
    aspect-ratio: 16 / 9;
    background: #000;
    border: 1px solid var(--primary-dim);
}
.video-embed iframe {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    border: 0;
}

/* ---------- Table of Contents (base styles; floating variant in post.css) ---------- */
.toc {
    background: var(--panel);
    border: 1px solid var(--border);
    border-left: 3px solid var(--accent);
    padding: 16px 20px;
    margin: 24px 0 36px;
}
.toc-label {
    font-family: 'Share Tech Mono', monospace;
    color: var(--accent);
    letter-spacing: 3px;
    text-transform: uppercase;
    font-size: 11px;
    margin-bottom: 10px;
}
.toc-list { list-style: none; margin: 0; padding: 0; }
.toc-list li {
    margin: 4px 0;
    font-family: 'Share Tech Mono', monospace;
    font-size: 13px;
    line-height: 1.55;
}
.toc-list li::before {
    content: '› ';
    color: var(--primary-dim);
}
/* In-body `# Heading` becomes <h1>; mark it with the same `§` glyph the
   site uses for section/transmission tags so it reads as the strongest
   entry in the TOC, sitting flush at the left edge. */
.toc-list li.level-1::before { content: '§ '; color: var(--accent); }
.toc-list li.level-3 { padding-left: 18px; }
.toc-list li.level-3::before { content: '— '; }
.toc-list a {
    color: var(--text);
    text-decoration: none;
    border-bottom: 1px dashed transparent;
}
.toc-list a:hover {
    color: var(--primary);
    border-bottom-color: var(--primary-dim);
    text-shadow: 0 0 6px var(--primary-glow-strong);
}
/* Matching TOC link lights up when its h2 enters the viewport (set by JS).
   Uses a highlighter-style background block (same look as ::selection). */
.toc-list a.is-active {
    background: var(--primary);
    color: var(--bg);
    padding: 0 4px;
    text-shadow: none;
    border-bottom-color: transparent;
}

/* ---------- Pagination ---------- */
.pagination {
    margin-top: 36px;
    padding-top: 22px;
    border-top: 1px solid var(--border);
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 12px;
    flex-wrap: wrap;
}
.page-btn {
    display: inline-block;
    font-family: 'Share Tech Mono', monospace;
    font-size: 11px;
    color: var(--accent);
    border: 1px solid var(--accent-dim);
    padding: 7px 14px;
    text-decoration: none;
    letter-spacing: 2px;
    border-radius: 2px;
    transition: background 0.18s ease, border-color 0.18s ease;
}
.page-btn:hover {
    background: var(--primary-glow);
    border-color: var(--accent);
}
.page-btn-disabled {
    color: var(--text-dim);
    border-color: var(--border);
    cursor: not-allowed;
}
.page-btn-disabled:hover { background: transparent; border-color: var(--border); }
.page-indicator {
    font-family: 'Share Tech Mono', monospace;
    font-size: 11px;
    color: var(--text-dim);
    letter-spacing: 2px;
    text-align: center;
    flex: 1;
}
@media (max-width: 480px) {
    .pagination { justify-content: center; }
    .page-indicator { flex-basis: 100%; order: -1; }
}

/* Password-protected post badge — used in title lines on home/tag/archive/
   search listings to flag posts that gate body content behind a password
   form. Outlined chip (transparent background, theme-color text, dim
   border) so it pairs cleanly with the rest of the chip/tag language on
   the page instead of shouting as a solid knockout pill. Same shape for
   locked and unlocked — the word inside ("LOCKED" vs "UNLOCKED") carries
   the state difference, no extra visual stratification needed. */
.post-lock {
    display: inline-flex;
    align-items: center;
    gap: 4px;
    font-family: 'Share Tech Mono', monospace;
    font-size: 10px;
    line-height: 1;
    letter-spacing: 1.5px;
    color: var(--primary);
    background: transparent;
    border: 1px solid var(--primary-dim);
    padding: 2px 6px;
    margin-left: 6px;
    vertical-align: 1px;
    text-transform: uppercase;
    border-radius: 1px;
    opacity: 0.85;
}
/* Bump the FA glyph one notch above the bracket text so the lock body
   reads as the primary mark rather than punctuation between brackets.
   `inherit` color keeps the icon tinted by --primary like the chip
   text — no per-theme override needed. */
.post-lock .fa {
    font-size: 11px;
    line-height: 1;
    color: inherit;
}
/* When the pill lives inside `.post-tags-row` next to a series chip,
   reset the inline margin-left so flex `gap` controls the spacing. The
   6px margin-left was meant for the case where the pill sits next to
   running text (post title); in a flex row it would double-up the gap. */
.post-tags-row .post-lock {
    margin-left: 0;
}
/* Lock row below the date/summary on the series detail listing. The
   pill no longer sits next to a title, so drop the default margin-left
   and add a small gap above so it doesn't crowd the summary line. */
.series-item-lock {
    margin-top: 6px;
}
.series-item-lock .post-lock {
    margin-left: 0;
}
