/* ---------- repo page ---------- */

.repo-header h1 { font-weight: 400; font-size: 1.5rem; }
.repo-header h1 a { color: var(--fg); }
.repo-header h1 a:hover { color: var(--accent); }
.repo-header h1 strong { font-weight: 700; }

/* Repo tab bar: Code | Branches | Discussions | Prompts | Settings.
   Underline tabs, verdigris active — GitHub's grammar in amadan's
   ink. Five tabs no longer fit a phone, so the bar scrolls sideways
   instead of clipping (scrollbar hidden — the cut-off next label is
   the affordance, same as GitHub's own mobile tab strip). */
.tabs {
  display: flex;
  gap: 0.25rem;
  border-bottom: 1px solid var(--border);
  margin: 1rem 0 0;
}
/* Each tab is a Lucide icon + label pair (same recipe as .subtabs a);
   inline-flex keeps the two on one centered line. */
.tabs a {
  display: inline-flex;
  align-items: center;
  gap: 0.45rem;
  padding: 0.5rem 0.9rem;
  color: var(--fg-muted);
  font-size: 0.95rem;
  border-bottom: 2px solid transparent;
  margin-bottom: -1px;
}
.tabs a:hover { color: var(--fg); text-decoration: none; }
.tabs a.active { color: var(--fg); font-weight: 600; border-bottom-color: var(--accent); }

/* Code toolbar: branch picker, Files|Commits sub-tabs, then a
   right-aligned group (Go to file, Clone). Every control in the row
   shares the .btn box (same font-size and vertical padding), so the
   row reads as one height. */
.code-toolbar { display: flex; flex-wrap: wrap; align-items: center; gap: 0.75rem; margin: 1rem 0; }
/* Toolbar controls carry a Lucide icon before their label. */
.code-toolbar .btn { display: inline-flex; align-items: center; gap: 0.45rem; }
.toolbar-slot { display: flex; align-items: center; gap: 0.75rem; }
.toolbar-right { display: flex; align-items: center; gap: 0.75rem; margin-left: auto; }
.subtabs { display: inline-flex; border: 1px solid var(--border); border-radius: var(--radius-ctl); overflow: hidden; }
.subtabs a { display: inline-flex; align-items: center; gap: 0.45rem; padding: 0.35rem 0.8rem; font-size: 0.9rem; color: var(--fg-muted); }
.subtabs a + a { border-left: 1px solid var(--border); }
.subtabs a:hover { color: var(--fg); background: var(--bg-inset); text-decoration: none; }
.subtabs a.active { background: var(--accent-wash); color: var(--accent-emph); font-weight: 600; }

/* The visible "Go to file" affordance for the `t` switcher, with a
   quiet keycap hint. Templates render it hidden; switcher.js unhides
   it once a file source is attached. */
.goto-file { display: inline-flex; align-items: center; gap: 0.45rem; color: var(--fg-muted); }
.goto-file kbd {
  font-family: var(--mono);
  font-size: 0.7rem;
  line-height: 1;
  padding: 0.15rem 0.3rem;
  border: 1px solid var(--border);
  border-radius: 4px;
  background: var(--bg);
  color: var(--fg-muted);
}

/* Clone and Download popovers: a <details> so the content is one click
   away with no JS; the panel is flat like the menus. */
details.clone-pop, details.download-pop { position: relative; }
details.clone-pop > summary, details.download-pop > summary { list-style: none; cursor: pointer; }
details.clone-pop > summary::-webkit-details-marker, details.download-pop > summary::-webkit-details-marker { display: none; }
.pop-panel {
  position: absolute;
  right: 0;
  top: calc(100% + 0.4rem);
  width: min(34rem, 88vw);
  background: var(--bg);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  padding: 0.75rem 1rem;
  z-index: 20;
}
.pop-panel pre { margin: 0 0 0.25rem; background: var(--bg-inset); border-radius: var(--radius-ctl); padding: 0.6rem 0.75rem; overflow-x: auto; }
.pop-panel code { font-size: 0.85rem; white-space: nowrap; }
.pop-panel .tier-note { margin-bottom: 0; }
.download-list { list-style: none; margin: 0; padding: 0; width: max-content; }
.download-list a { display: block; padding: 0.3rem 0; }

/* Branch picker (branchpicker.js): a .btn trigger — so it sits at the
   same height as everything else in the toolbar row — opening an
   anchored typeahead menu, filter input on top, fuzzy-matched list
   below (the switcher's grammar, anchored instead of modal). The
   plaintext page server-renders this markup so it paints in final
   geometry; the <noscript> fallback form keeps the plain select +
   Go button. */
.branch-picker { position: relative; display: inline-block; font-size: 0.9rem; }
.branch-picker select { font: inherit; font-size: 0.9rem; margin: 0 0.4rem; padding: 0.25rem 0.3rem; }
/* JS off: the server-rendered trigger has no behavior to wire — hide
   it and let the <noscript> form own the slot. (Pre-2023 browsers
   without the `scripting` media feature show both; the form still
   works.) */
@media (scripting: none) {
  .branch-picker > .branch-trigger { display: none; }
}
.branch-trigger { display: inline-flex; align-items: center; gap: 0.4rem; max-width: min(20rem, 60vw); }
.branch-trigger .branch-word { color: var(--fg-muted); font-weight: 400; }
.branch-trigger .branch-name { font-weight: 600; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.branch-trigger .caret { color: var(--fg-muted); font-size: 0.65em; }
.branch-menu {
  position: absolute;
  left: 0;
  top: calc(100% + 0.4rem);
  width: min(22rem, 88vw);
  background: var(--bg);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  box-shadow: 0 8px 24px rgba(0, 0, 0, 0.15);
  overflow: hidden;
  z-index: 30;
}
.branch-filter {
  width: 100%;
  border: 0;
  border-bottom: 1px solid var(--border);
  background: var(--bg);
  color: var(--fg);
  font: inherit;
  font-size: 0.9rem;
  padding: 0.5rem 0.75rem;
  outline: none;
}
.branch-options {
  list-style: none;
  margin: 0;
  padding: 0.25rem 0;
  max-height: 40vh;
  overflow-y: auto;
  font-family: var(--mono);
  font-size: 0.85rem;
}
.branch-option {
  padding: 0.35rem 0.75rem;
  cursor: pointer;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.branch-option.active { background: var(--bg-inset); box-shadow: inset 2px 0 0 var(--accent); }
.branch-option.current { font-weight: 700; }
.branch-option b { color: var(--accent); }
.branch-default { margin-left: 0.5rem; padding: 0 0.35rem; border: 1px solid var(--border); border-radius: 999px; font-size: 0.75em; font-weight: 400; color: var(--fg-muted); }
.browse-missing { padding: 1.5rem 0; }
.browse-missing h2 { margin-top: 0; }
.browse-missing-branches { list-style: none; padding: 0; display: flex; flex-wrap: wrap; gap: 0.5rem; }
.branch-empty { padding: 0.5rem 0.75rem; color: var(--fg-muted); }

/* Phones: the toolbar holds one unwrapped row — the "branch" word and
   the button labels drop away (aria-labels keep the names for
   assistive tech), leaving the Lucide icons; the branch name truncates
   instead of wrapping the row (Paul, 2026-08-09). */
@media (max-width: 720px) {
  .code-toolbar { flex-wrap: nowrap; gap: 0.5rem; }
  .toolbar-slot, .toolbar-right { gap: 0.5rem; }
  .code-toolbar .branch-picker { min-width: 0; }
  .code-toolbar .branch-picker select { max-width: 35vw; }
  .branch-trigger .branch-word { display: none; }
  /* iOS Safari zooms the page when a focused text control is under
     16px; the picker focuses its filter input on open, so both it and
     the <noscript> select must hold the 16px line on phones. */
  .branch-filter, .branch-picker select { font-size: 1rem; }
  .subtab-label, .code-toolbar .btn-label, .goto-file kbd { display: none; }
  .subtabs a { padding: 0.35rem 0.6rem; }
  .goto-file, details.clone-pop > summary.btn, details.download-pop > summary.btn { padding: 0.35rem 0.55rem; }
  /* With labels gone these boxes would collapse to the 1em icon;
     hold them at a text control's height (1.5 line box + 0.35rem
     vertical padding + 1px borders) so the row stays one height. */
  .subtabs a, .goto-file, details.clone-pop > summary.btn, details.download-pop > summary.btn { min-height: calc(1.5em + 0.7rem + 2px); }
  /* Five tabs no longer fit a phone: the bar scrolls sideways instead
     of clipping (scrollbar hidden — the cut-off next label is the
     affordance, GitHub's own mobile tab grammar). Scoped to phones so
     desktop keeps the active tab's underline overlapping the bar's
     hairline cleanly (an always-on clip container would shave it). */
  /* overflow-y must be pinned: `auto` on one axis forces the other
     from `visible` to `auto`, and any y-overflow then makes the bar
     itself vertically scrollable (a joggling tab strip on touch). */
  .tabs { overflow-x: auto; overflow-y: hidden; scrollbar-width: none; }
  .tabs::-webkit-scrollbar { display: none; }
  /* The -1px underline overlap is exactly that y-overflow — and the
     clip container shaves the overlapped pixel anyway, so it buys
     nothing on phones. Dropped: the bar has zero scrollable height. */
  .tabs a { white-space: nowrap; margin-bottom: 0; }
  /* The two segmented controls compress identically (subtabs above). */
  .discussion-filter a, .discussion-filter button { padding: 0.35rem 0.6rem; }
}

.repo-main {
  display: grid;
  grid-template-columns: 280px minmax(0, 1fr);
  gap: 1.5rem;
  align-items: start;
}
/* No file selected: collapse the empty content column instead of
   leaving a field of dead paper beside the tree. */
.repo-main.no-file { grid-template-columns: minmax(0, 280px); }
@media (max-width: 800px) {
  .repo-main { grid-template-columns: 1fr; }
}

.tree-col {
  border: 1px solid var(--border);
  border-radius: var(--radius);
  padding: 0.5rem 0.75rem;
  background: var(--bg-inset);
  font-size: 0.9rem;
}
ul.tree, ul.tree ul { list-style: none; margin: 0; padding-left: 1rem; }
ul.tree { padding-left: 0; }
ul.tree li { padding: 0.1rem 0; }
ul.tree .icon { margin-right: 0.35rem; color: var(--fg-muted); }

/* Disclosed agent badge (agent-accounts, 2026-08-13): short name +
   bot icon, operator in the title attribute. */
.actor-agent { white-space: nowrap; }
.actor-agent .icon-bot { margin-left: 0.25rem; color: var(--fg-muted); }
ul.tree .tree-dir > details > summary > .icon { color: var(--accent); }
.tree-file a { color: var(--fg); }
.tree-file a:hover { color: var(--accent); text-decoration: none; }
.tree-dir > a { font-weight: 600; color: var(--fg); }
.tree-dir > a:hover { color: var(--accent); text-decoration: none; }
.tree-dir summary { cursor: pointer; font-weight: 600; }

.content-col { min-width: 0; }

.readme-below { margin-top: 1.5rem; }
/* A code page is a code page: once a file is open (E2EE client drops
   .no-file), the README below it goes away. The plaintext page makes
   the same call server-side (browse_render.go). */
.repo-main:not(.no-file) + .readme-below { display: none; }

.readme, .file-viewer {
  border: 1px solid var(--border);
  border-radius: var(--radius);
  padding: 1rem 1.25rem;
  margin-bottom: 1.5rem;
  overflow-x: auto;
}
.file-viewer h3 { font-family: var(--mono); font-size: 0.9rem; margin-top: 0; }

.amadan-markdown { max-width: 72ch; }
/* The README is the page, not a comment in a thread: it fills its card
   the way GitHub's does, instead of wrapping at 72ch and leaving half
   the box empty (Paul, 2026-08-09). Discussion posts and branch
   descriptions keep the measure. */
.readme .amadan-markdown { max-width: none; }
/* Preview/Code tabs on a markdown file view — the .subtabs recipe,
   covering both shapes: the plaintext page's server-side links and the
   E2EE viewer's client-side buttons (site/js/views.js). */
.file-view-tabs { display: inline-flex; border: 1px solid var(--border); border-radius: var(--radius-ctl); overflow: hidden; margin-bottom: 0.75rem; }
.file-view-tabs a, .file-view-tabs button { display: inline-flex; align-items: center; padding: 0.35rem 0.8rem; font: inherit; font-size: 0.9rem; color: var(--fg-muted); background: none; border: 0; cursor: pointer; }
.file-view-tabs a + a, .file-view-tabs button + button { border-left: 1px solid var(--border); }
.file-view-tabs a:hover, .file-view-tabs button:hover { color: var(--fg); background: var(--bg-inset); text-decoration: none; }
.file-view-tabs a.active, .file-view-tabs button.active { background: var(--accent-wash); color: var(--accent-emph); font-weight: 600; }
/* The rendered document is the page, same as the README's card. */
.file-preview .amadan-markdown { max-width: none; }
.amadan-markdown pre { background: var(--code-bg); padding: 0.75rem; border-radius: var(--radius-ctl); overflow-x: auto; }
.amadan-markdown code { background: var(--code-bg); padding: 0.1rem 0.3rem; border-radius: 4px; font-size: 0.85em; }
.amadan-markdown pre code { background: none; padding: 0; }

table.file-lines {
  border-collapse: collapse;
  width: 100%;
  font-family: var(--mono);
  font-size: 0.8125rem;
  line-height: 1.45;
  tab-size: 4;
}
table.file-lines td.ln {
  color: var(--fg-muted);
  text-align: right;
  padding-right: 0.75rem;
  user-select: none;
  width: 1%;
  white-space: nowrap;
  vertical-align: top;
  font-variant-numeric: tabular-nums;
}
table.file-lines td.code { white-space: pre; }
table.file-lines tr:hover td { background: var(--bg-inset); }
/* Phones: code still scrolls sideways rather than wrapping, but a
   notch smaller so a useful stretch of each line fits in view
   (Paul, 2026-08-09: 13px reads too big to parse on mobile). */
@media (max-width: 720px) {
  table.file-lines { font-size: 0.75rem; }
  table.file-lines td.ln { padding-right: 0.5rem; }
}

/* Syntax highlighting (site/js/syntax.js token kinds) — tinted to the
   Ink & Verdigris palette: strings take the verdigris accent family,
   keywords the red-lead danger family, comments/numbers stay muted
   ink so color marks meaning, not noise. */
:root {
  --hl-com: #5c6660;
  --hl-str: #0b6e63;
  --hl-kw: #b03a25;
  --hl-num: #9a6700;
}
@media (prefers-color-scheme: dark) {
  :root {
    --hl-com: #93a09a;
    --hl-str: #4cc4b5;
    --hl-kw: #f0704f;
    --hl-num: #d4a72c;
  }
}
/* CI log coloring (cilogview.js). Two families share one block: the
   inferred kinds (a go-test verdict, a shard header, amadan's own
   voice) and the ANSI colors, for the rarer log that colored itself.
   Both reuse the palette already on the page — the green is the one
   .ci-success wears — so a log agrees with the dot above it. */
:root {
  --log-pass: #1a7f37;
  --log-fail: #b03a25;
  --log-muted: #5c6660;
  --log-yellow: #9a6700;
  --log-blue: #1f4f9c;
  --log-magenta: #8250df;
  --log-cyan: #0b6e63;
}
@media (prefers-color-scheme: dark) {
  :root {
    --log-pass: #4ac26b;
    --log-fail: #f0704f;
    --log-muted: #93a09a;
    --log-yellow: #d4a72c;
    --log-blue: #6ea8fe;
    --log-magenta: #c39cf5;
    --log-cyan: #4cc4b5;
  }
}
.log-pass { color: var(--log-pass); }
.log-fail { color: var(--log-fail); }
.log-skip,
.log-run,
.log-time { color: var(--log-muted); }
/* A shard banner and amadan's own notice are the log's structure
   rather than its content — muted, but weighted so they still read as
   the boundaries they are when scrolling a long log. */
.log-head { color: var(--log-muted); font-weight: 600; }
.log-notice { color: var(--log-muted); font-style: italic; }
/* ANSI: the tool colored itself, so we render its choice. Bright black
   (90) arrives as .log-muted, which is what it means in practice. */
.log-black { color: var(--fg); }
.log-red { color: var(--log-fail); }
.log-green { color: var(--log-pass); }
.log-yellow { color: var(--log-yellow); }
.log-blue { color: var(--log-blue); }
.log-magenta { color: var(--log-magenta); }
.log-cyan { color: var(--log-cyan); }
.log-white { color: var(--fg); }
.log-muted { color: var(--log-muted); }
.log-b { font-weight: 700; }

.hl-com { color: var(--hl-com); font-style: italic; }
.hl-str { color: var(--hl-str); }
.hl-kw { color: var(--hl-kw); }
.hl-num { color: var(--hl-num); }
.too-large { color: var(--fg-muted); font-style: italic; }

/* A file page's own "Download this file" link (raw-and-render follow-up:
   the whole-repo Download button doesn't help when what you want is one
   binary asset out of a zip). Matches .btn's icon-plus-text shape without
   pulling in the button chrome — this is a link, not an action trigger. */
.file-actions { margin: 0 0 0.75rem; }
.raw-link { display: inline-flex; align-items: center; gap: 0.3rem; }

/* Full-width file list (plaintext server-rendered browse) — the
   GitHub-shaped name / last-commit-message / last-changed table. The
   E2EE page keeps the .repo-main two-column grid above. */
.repo-files { margin-top: 0.5rem; }


/* A file page showing an image (raw-and-render, 2026-08-26). Bounded by
   the reading column rather than shown at natural size: a 4000px
   screenshot committed to a repo should not decide the page's width. */
.file-image { margin: 0; padding: 1rem; text-align: center; }
.file-image img {
  max-width: 100%;
  height: auto;
  /* The checkerboard is what makes a transparent PNG legible in both
     themes without picking a background colour that lies about it. */
  background-color: var(--bg-subtle, #f6f6f4);
  background-image:
    linear-gradient(45deg, var(--border) 25%, transparent 25%),
    linear-gradient(-45deg, var(--border) 25%, transparent 25%),
    linear-gradient(45deg, transparent 75%, var(--border) 75%),
    linear-gradient(-45deg, transparent 75%, var(--border) 75%);
  background-size: 16px 16px;
  background-position: 0 0, 0 8px, 8px -8px, -8px 0;
  border: 1px solid var(--border);
  border-radius: var(--radius-ctl);
}
