/* ══════════════════════════════════════════════════════════════════════
   listing.css — PAGE LAYOUT for the forum HOME page (functions/index.js)
   and the CATEGORY listing (functions/c/[slug].js). Nothing else links it.

   WHAT THIS FILE IS NOT. It does not define the list, tab, pill, avatar,
   pager or badge PRIMITIVES — .bf-list, .bf-list-row, .bf-list-row__main /
   __title / __meta / __stat / __latest, .bf-list-head, .bf-tabs / .bf-tab,
   .bf-pill*, .bf-badge, .bf-pin, .bf-avatar*, .bf-pager*, .bf-crumbs,
   .bf-empty and .bf-num all live in /forum.css, which every page already
   loads through shell(). Defining any of them a second time here is how two
   design systems quietly diverge; this sheet only positions them.

   WHAT IT IS. Two things a shared primitive cannot know:
     1. the COLUMN TEMPLATE of a row on THIS page (a category row has four
        columns, a thread row has three — same primitive, different grid), and
     2. the bands around the lists (page head, block heads, the rules panel).
   Both are scoped under .bfl-cats / .bfl-threads / .bfl-* so they can never
   reach a .bf-list-row on the thread page or in the chrome.

   COLOUR. Every value below is a token from /forum.css's :root — there is no
   raw hex in this file. The one hsl() is the deterministic avatar/marker hue,
   whose --av-h channel is set per element by the server (see index.js's
   avatarHue()) exactly as the shared contract specifies.

   LIGHT THEME ONLY, deliberately: the forum matches the store, which has one
   theme. No prefers-color-scheme block belongs here.
═══════════════════════════════════════════════════════════════════════ */

/* ── PAGE HEAD ─────────────────────────────────────────────────────────
   Compact by design. What stood here before was a marketing hero plus a
   gradient promo card, which pushed every thread title below the fold —
   the one thing a forum front page exists to show. One h1, one line, one
   quiet stat row, then straight into the rooms. */
.bfl-head{
  display:flex;
  flex-direction:column;
  gap:6px;
}
.bfl-title{
  font-family:var(--f-display);
  font-weight:500;
  font-size:var(--t-h2);
  letter-spacing:-.015em;
  line-height:1.1;
  color:var(--ink);
  margin:0;
}
.bfl-lede{
  font-family:var(--f-text);
  font-size:16px;
  line-height:1.6;
  color:var(--body);
  max-width:66ch;
  margin:0;
}
/* The old stat CLUSTER was two big numbers in their own dl, competing with
   the headline. A forum's totals are orientation, not a headline — mono,
   small, one line, the same idiom as every other label in the system. */
/* The orientation line. Still mono, still small — but it was 11px at
   2.36:1 on the canvas, which is a decorative smudge where the forum states
   how big it is. Lifted to the meta tier and given its figures real ink:
   "1,566 threads" is the single most reassuring thing on the page for a
   stranger deciding whether anyone is here. */
.bfl-stats{
  font-family:var(--f-mono);
  font-size:11.5px;
  letter-spacing:.07em;
  text-transform:uppercase;
  color:var(--body);
  margin:4px 0 0;
  display:flex;
  flex-wrap:wrap;
  align-items:baseline;
  gap:6px;
}
.bfl-stats .bf-num{ color:var(--ink); font-weight:600; }
.bfl-sep{ color:var(--text-mute); }

/* Category page head — the same band with the New-thread action pinned right. */
.bfl-cat-head{
  flex-direction:row;
  flex-wrap:wrap;
  align-items:flex-end;
  justify-content:space-between;
  gap:16px;
}
.bfl-cat-head-text{
  display:flex;
  flex-direction:column;
  gap:6px;
  flex:1;
  min-width:min(100%, 300px);
}

/* ── BLOCKS (a heading + its list) ─────────────────────────────────────
   .bf-main is already a flex column with a --s3 gap, so a block only owns
   the space between its own head and its list. */
.bfl-block{
  display:flex;
  flex-direction:column;
  gap:10px;
}
.bfl-block-head{
  display:flex;
  flex-wrap:wrap;
  align-items:center;
  justify-content:space-between;
  gap:12px;
  padding-bottom:2px;
}
.bfl-block-title{
  font-family:var(--f-display);
  font-weight:500;
  font-size:var(--t-h3);
  letter-spacing:-.01em;
  line-height:1.2;
  color:var(--ink);
  margin:0;
}
.bfl-block-blurb{
  font-family:var(--f-text);
  font-size:14px;
  line-height:1.5;
  color:var(--body);
  margin:-4px 0 0;
}

/* ── COLUMN TEMPLATES ──────────────────────────────────────────────────
   The only thing this sheet asserts about .bf-list-row: how many columns it
   has HERE and how wide they are. Everything else about the row — the
   hairline, the hover wash, the whole-row click target — is the primitive's.

   CATEGORY ROW: marker | name + description | threads | posts | latest.
   The two numeric columns are fixed and narrow so the eye can compare down
   the column; "latest" gets a hard ceiling so a long thread title cannot
   push the numbers around. */
.bfl-cats .bf-list-row,
.bfl-cats .bf-list-head{
  display:grid;
  grid-template-columns:10px minmax(0,1fr) 68px 68px minmax(0, 300px);
  align-items:center;
  gap:14px;
}
/* THREAD ROW: avatar | title + meta | replies | activity. */
.bfl-threads .bf-list-row,
.bfl-threads .bf-list-head{
  display:grid;
  grid-template-columns:26px minmax(0,1fr) 68px 84px;
  align-items:center;
  gap:14px;
}
/* Column labels sit over the numeric columns, so they align the same way the
   values do. */
.bfl-cats-head > :nth-child(3),
.bfl-cats-head > :nth-child(4),
.bfl-threads-head > :nth-child(3),
.bfl-threads-head > :nth-child(4){ text-align:right; }

/* The row's main cell is a stack; the primitive supplies its type, this only
   makes it a column that can shrink. */
.bfl-cats .bf-list-row__main,
.bfl-threads .bf-list-row__main{
  display:flex;
  flex-direction:column;
  gap:2px;
  min-width:0;
}
/* Two lines of description maximum. A category blurb is orientation, not
   copy — a third line starts pushing rows apart and the list stops being a
   list. */
.bfl-cat-desc{
  display:-webkit-box;
  -webkit-line-clamp:2;
  line-clamp:2;
  -webkit-box-orient:vertical;
  overflow:hidden;
}

/* Title + its markers on one line, markers never wrapping mid-word. */
.bfl-title-line{
  display:flex;
  align-items:center;
  flex-wrap:wrap;
  gap:8px;
  min-width:0;
}
.bfl-title-line .bf-list-row__title{ min-width:0; overflow-wrap:anywhere; }

/* The unit under each number ("threads", "replies"). Mono micro-caps, so the
   figure stays the loud part — a bare number in a listing is exactly the
   insider shorthand a stranger has to decode.

   The INTENT above was always right and the RENDER was the exact opposite:
   forum.css's `.bf-list-row__stat > span:first-child` (0,2,1) out-specified
   this rule (0,1,0) and handed the label the number's 14px/600/.80 ink while
   the figure itself sat at 12.5px/400. forum.css now restates that selector
   the right way round at the bottom of its own file; this rule agrees with
   it instead of losing to it. */
.bfl-stat-label{
  display:block;
  font-family:var(--f-mono);
  font-size:9.5px;
  font-weight:500;
  letter-spacing:.1em;
  text-transform:uppercase;
  color:var(--text-ghost);
  line-height:1.3;
}

/* Last-activity column. Mono + tabular so the times form a readable column
   rather than a ragged edge. "8h ago" is half of what a forum listing is
   FOR — it is the proof that the place is alive — so it reads at the meta
   tier, not below it. */
.bfl-when{
  font-family:var(--f-mono);
  font-size:11.5px;
  letter-spacing:.03em;
  color:var(--body);
  text-align:right;
  font-variant-numeric:tabular-nums;
  white-space:nowrap;
}

/* ── CATEGORY MARKER ───────────────────────────────────────────────────
   A 10px stripe in the category's own deterministic hue: the cheapest thing
   that makes six rows distinguishable at a glance without six icons, six
   illustrations, or the six loud cards this list replaced. --av-h is set on
   the element by the server. */
/* Taller and a shade more saturated. This stripe is the only colour in the
   category list and it was doing the work of six illustrations at 26px of
   4px-wide, half-desaturated hue — easy to miss entirely. */
.bfl-marker{
  width:4px;
  height:34px;
  border-radius:var(--radius-pill);
  background:hsl(var(--av-h, 190) 48% 40%);
  justify-self:center;
  flex:none;
}

/* ── LATEST-ACTIVITY COLUMN ────────────────────────────────────────────
   Avatar + thread link + who/when, stacked tight on the right of a category
   row. z-index/position keep this link clickable above the primitive's
   whole-row target — the row routes into the category, this one link routes
   into the thread. */
.bfl-cats .bf-list-row__latest{
  display:flex;
  align-items:center;
  gap:9px;
  min-width:0;
}
.bfl-latest-text{
  display:flex;
  flex-direction:column;
  gap:1px;
  min-width:0;
}
.bfl-latest-link{
  position:relative;
  z-index:1;
  font-family:var(--f-text);
  font-size:13.5px;
  font-weight:600;
  line-height:1.35;
  color:var(--ink-soft);
  text-decoration:none;
  overflow:hidden;
  text-overflow:ellipsis;
  white-space:nowrap;
  transition:color var(--dur-base) var(--ease-out);
}
.bfl-latest-link:hover{ color:var(--teal); text-decoration:underline; text-underline-offset:3px; }

/* ── THE EMPTY ROOM ────────────────────────────────────────────────────
   Five rooms all saying "No threads yet" in disabled grey read as a forum
   that failed, not one that is new. Same words, same link, given the warm
   ground and the live invitation they should always have had: the sentence
   is clay-ink (the store's own clay, walked down to 6.29:1 on white so it
   can legally carry text) and the link is a real teal call to action.
   The row behind it picks up --warm-tint in forum.css. */
.bfl-latest-empty{
  position:relative;
  z-index:1;
  font-size:13.5px;
  line-height:1.4;
  color:var(--clay-ink);
  white-space:normal;
}
/* nowrap on the LINK only: the sentence may wrap after the dash, but
   "start the first one" breaking across two lines mid-phrase turns the one
   call to action in an empty room into visual debris. */
.bfl-latest-empty .bfl-latest-link{
  display:inline;
  overflow:visible;
  white-space:nowrap;
  color:var(--teal);
  font-weight:700;
  text-decoration:underline;
  text-underline-offset:3px;
  text-decoration-thickness:1.5px;
}
.bfl-latest-empty .bfl-latest-link:hover{ color:var(--accent-press); }

/* A member's own held/removed thread, marked for that member only. Clay, not
   red: it is a queue state, not an error. */
.bfl-badge-state{ color:var(--clay); border-color:var(--clay); }

/* ── THE RULES PANEL ───────────────────────────────────────────────────
   Kept, demoted. It used to sit half-width beside a cramped thread list,
   taking the same visual weight as the forum's actual content. It is now a
   quiet full-width band at the foot of the page, where posting rules belong:
   findable when you go looking, not competing with the threads. */
/* Warm ground rather than a bare rule: this band is the first thing a
   first-time poster reads before they type, and a set of house rules on the
   naked canvas reads as fine print. On the store's own paper it reads as a
   welcome note. */
.bfl-rules{
  border:1px solid var(--warm-rule);
  border-radius:var(--radius-sm);
  background:var(--warm-band);
  padding:16px 18px;
  display:flex;
  flex-direction:column;
  gap:8px;
  align-items:flex-start;
}
.bfl-rules-title{
  font-family:var(--f-mono);
  font-size:11px;
  font-weight:600;
  letter-spacing:.15em;
  text-transform:uppercase;
  color:var(--teal);
  margin:0;
}
.bfl-rules-list{
  display:grid;
  grid-template-columns:repeat(auto-fit, minmax(240px, 1fr));
  gap:4px 24px;
  margin:0;
  padding:0;
  list-style:none;
}
.bfl-rules-list li{
  font-family:var(--f-text);
  font-size:14px;
  line-height:1.55;
  color:var(--body);
  padding-left:15px;
  position:relative;
}
.bfl-rules-list li::before{
  content:'';
  position:absolute;
  left:0;
  top:.62em;
  width:4px;
  height:4px;
  border-radius:50%;
  background:var(--teal);
}

/* ── RESPONSIVE ────────────────────────────────────────────────────────
   Below 900px the "latest activity" column is the first to go: on a phone a
   truncated thread title in a 120px gutter is noise, and the row still says
   name, description and both counts. */
@media (max-width:900px){
  .bfl-cats .bf-list-row,
  .bfl-cats .bf-list-head{
    grid-template-columns:10px minmax(0,1fr) 62px 62px;
  }
  .bfl-cats .bf-list-row__latest,
  .bfl-cats-head > :nth-child(5){ display:none; }
}

/* Below 620px both lists drop to three columns. The category row sheds its
   "posts" total (threads is the number that routes a reader, and it keeps its
   label so the survivor is never a bare figure). The thread row keeps its
   last-activity time — that is half of what a forum listing is FOR — by
   wrapping it onto a second grid row under the title instead of hiding it.

   Child indexes, not :last-of-type: every cell in these rows is a <span>, so
   a type selector would match whichever span happens to come last rather than
   the column meant. */
@media (max-width:620px){
  .bfl-cats .bf-list-row,
  .bfl-cats .bf-list-head{
    grid-template-columns:10px minmax(0,1fr) 58px;
    gap:10px;
  }
  .bfl-cats .bf-list-row > :nth-child(4),
  .bfl-cats-head > :nth-child(4){ display:none; }

  .bfl-threads .bf-list-row,
  .bfl-threads .bf-list-head{
    grid-template-columns:26px minmax(0,1fr) 58px;
    /* grid-auto-flow:row is LOAD-BEARING here, not tidying. The base
       .bf-list-row rule (forum.css) sets grid-auto-flow:column with
       grid-auto-columns:max-content. Under column flow, the .bfl-when rule
       below — grid-column:2/3, meant to drop the date onto a second ROW
       under the title — instead displaced .bf-list-row__main out of column 2
       and spawned a 4th implicit column for the reply count. Measured at
       390px: tracks resolved to 26px/164px/58px/48px against a 3-track
       template, the title was crushed into 58px and wrapped to four lines,
       the category pill overlapped the reply count, and the date sat where
       the title should be. Row flow makes the explicit placement land on
       row 2 as intended and stops implicit columns being created at all. */
    grid-auto-flow:row;
    gap:2px 10px;
  }
  .bfl-threads .bf-list-row > .bfl-when{
    grid-column:2 / 3;
    text-align:left;
  }
  .bfl-threads-head > :nth-child(4){ display:none; }

  .bfl-cat-head{ flex-direction:column; align-items:flex-start; }
  .bfl-block-head{ align-items:flex-start; flex-direction:column; gap:8px; }
}
