/* ---------------------------------------------------------------------------
   Site theme for jwildfire.github.io
   All-light: paper #fafaf8 · graphite ink #1f2328 · plum links #6c3270
   A seven-hue muted spectrum (oklch 0.68 / 0.12) marks the months of the
   writing list, and a thin honeycomb strip carries it through dividers.
   Instrument Serif (headings) · Instrument Sans (body) · IBM Plex Mono (meta)
   Loaded after minima's main.css; overrides by cascade order.
   The R/Pharma keynote page (/keynote/) shares the base but keeps its orange.
--------------------------------------------------------------------------- */

:root {
  --kn-bg: #fafaf8;
  --kn-rail-bg: #f3f4f1;
  --kn-ink: #1f2328;
  --kn-soft: #5b6470;
  --kn-faint: #98a0aa;
  --kn-softer: #7a838e;        /* between soft and faint: release blurbs */
  --kn-accent: #6c3270;        /* plum: links, dates, active states */
  --kn-accent-deep: #522456;
  --kn-accent-soft: rgba(108, 50, 112, 0.12);
  --kn-card: #ffffff;
  --kn-rule: #e4e6e3;
  --kn-code-bg: #f3f4f1;
  --kn-event: #f97316;         /* orange, reserved for the R/Pharma keynote */
  --kn-event-deep: #c2410c;

  /* Spectrum: equal lightness and chroma, hue steps of ~50 degrees. */
  --spec-0: #d87972;
  --spec-1: #c78a3b;
  --spec-2: #77a95b;
  --spec-3: #00afa9;
  --spec-4: #519fdd;
  --spec-5: #988bdd;
  --spec-6: #c67bb6;
  --spec-gradient: linear-gradient(90deg, var(--spec-0), var(--spec-1), var(--spec-2), var(--spec-3), var(--spec-4), var(--spec-5), var(--spec-6));
  --spec-gradient-diag: linear-gradient(135deg, var(--spec-0), var(--spec-1), var(--spec-2), var(--spec-3), var(--spec-4), var(--spec-5), var(--spec-6));

  /* Release marker: a small tag outline, used as a mask so it takes any colour. */
  --tag-mask: url("data:image/svg+xml;utf8,%3Csvg xmlns%3D'http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg' viewBox%3D'0 0 24 24' fill%3D'none' stroke%3D'%23000' stroke-width%3D'2.6' stroke-linecap%3D'round' stroke-linejoin%3D'round'%3E%3Cpath d%3D'M20.59 13.41l-7.17 7.17a2 2 0 0 1-2.83 0L2 12V2h10l8.59 8.59a2 2 0 0 1 0 2.82z'%2F%3E%3Ccircle cx%3D'7.5' cy%3D'7.5' r%3D'1.2' fill%3D'%23000'%2F%3E%3C%2Fsvg%3E");

  /* Honeycomb outline tile, used as a mask so a colour shows through the strokes. */
  --hex-mask: url("data:image/svg+xml;utf8,%3Csvg xmlns%3D'http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg' width%3D'5.543' height%3D'9.600' viewBox%3D'0 0 5.543 9.600'%3E%3Cg fill%3D'none' stroke%3D'%23000' stroke-width%3D'0.9'%3E%3Cpolygon points%3D'2.77%2C0.00 5.54%2C1.60 5.54%2C4.80 2.77%2C6.40 -0.00%2C4.80 0.00%2C1.60'%2F%3E%3Cpolygon points%3D'0.00%2C4.80 2.77%2C6.40 2.77%2C9.60 0.00%2C11.20 -2.77%2C9.60 -2.77%2C6.40'%2F%3E%3Cpolygon points%3D'5.54%2C4.80 8.31%2C6.40 8.31%2C9.60 5.54%2C11.20 2.77%2C9.60 2.77%2C6.40'%2F%3E%3Cpolygon points%3D'2.77%2C9.60 5.54%2C11.20 5.54%2C14.40 2.77%2C16.00 -0.00%2C14.40 0.00%2C11.20'%2F%3E%3Cpolygon points%3D'0.00%2C-4.80 2.77%2C-3.20 2.77%2C-0.00 0.00%2C1.60 -2.77%2C-0.00 -2.77%2C-3.20'%2F%3E%3Cpolygon points%3D'5.54%2C-4.80 8.31%2C-3.20 8.31%2C-0.00 5.54%2C1.60 2.77%2C-0.00 2.77%2C-3.20'%2F%3E%3C%2Fg%3E%3C%2Fsvg%3E");

  --kn-sans: "Instrument Sans", system-ui, sans-serif;
  --kn-serif: "Instrument Serif", Georgia, serif;
  --kn-mono: "IBM Plex Mono", ui-monospace, "SF Mono", Menlo, monospace;
}

/* Base ----------------------------------------------------------------------*/

body {
  background: var(--kn-bg);
  color: var(--kn-ink);
  font-family: var(--kn-sans);
  font-size: 1.04rem;
  line-height: 1.62;
  -webkit-font-smoothing: antialiased;
}

h1, h2, h3, h4, h5, h6 { font-family: var(--kn-serif); font-weight: 400; letter-spacing: -0.01em; }

a, a:visited { color: var(--kn-accent); }
a:hover { color: var(--kn-accent-deep); text-decoration: underline; text-underline-offset: 0.2em; }
:focus-visible { outline: 2px solid var(--kn-accent); outline-offset: 3px; border-radius: 2px; }

/* Honeycomb strip: the spectrum, seen through a band of tiny hex outlines.
   Applied as a pseudo-element on dividers so the text above is unaffected. */
hr, .site-header::before, .site-footer::before, .wf-rail::before, .wf-sechead::after, .wf-foot::before {
  background: var(--spec-gradient);
  -webkit-mask-image: var(--hex-mask);
  mask-image: var(--hex-mask);
  -webkit-mask-repeat: repeat;
  mask-repeat: repeat;
  -webkit-mask-size: auto 9.6px;
  mask-size: auto 9.6px;
  -webkit-mask-position: left top;
  mask-position: left top;
}

hr {
  border: 0;
  height: 9px;
  margin: 2.4rem 0;
  opacity: 0.9;
}

/* Header (posts and interior pages) ------------------------------------------*/

.site-header {
  position: relative;
  background: var(--kn-bg);
  border-top: none;
  border-bottom: 1px solid var(--kn-rule);
}
.site-header::before {
  content: "";
  position: absolute;
  left: 0; right: 0; top: 0;
  height: 9px;
}
.site-title, .site-title:visited, .site-title:hover {
  color: var(--kn-ink);
  font-family: var(--kn-serif);
  font-size: 1.5rem;
  letter-spacing: 0;
}
.site-nav { background: transparent; border: none; }
.site-nav .page-link {
  color: var(--kn-soft);
  font-family: var(--kn-mono);
  font-size: 0.84rem;
}
.site-nav .page-link:hover { color: var(--kn-accent); text-decoration: none; }
.site-nav .github-link { display: inline-flex; align-items: center; }
.site-nav .github-icon { vertical-align: middle; display: block; }
@media screen and (max-width: 600px) {
  .site-nav { background: var(--kn-card); border: 1px solid var(--kn-rule); }
  .site-nav .menu-icon > svg { fill: var(--kn-ink); }
  .site-nav .menu-icon > svg path { fill: var(--kn-ink); }
}

/* Post list (archive) ---------------------------------------------------------*/

.post-meta {
  color: var(--kn-accent);
  font-family: var(--kn-mono);
  font-size: 0.76rem;
  letter-spacing: 0.06em;
  text-transform: uppercase;
}
.post-list > li { margin-bottom: 2.2rem; }
.post-link {
  font-family: var(--kn-serif);
  font-size: 1.7rem;
  line-height: 1.15;
  color: var(--kn-ink);
}
.post-link:visited { color: var(--kn-ink); }
.post-link:hover { color: var(--kn-accent); text-decoration: none; }
.post-list-heading { font-family: var(--kn-serif); }

/* Posts ------------------------------------------------------------------------*/

.post-title { font-family: var(--kn-serif); font-weight: 400; letter-spacing: -0.01em; }
.post-content { color: var(--kn-ink); }
.post-content h2, .post-content h3 { margin-top: 2rem; }

blockquote {
  color: var(--kn-soft);
  border-left: 4px solid var(--kn-accent);
  font-style: normal;
  letter-spacing: 0;
}

pre, code {
  border: 1px solid var(--kn-rule);
  background-color: var(--kn-code-bg);
  border-radius: 6px;
}
code { font-family: var(--kn-mono); font-size: 0.86em; }
.hljs, pre code { background: var(--kn-code-bg) !important; }

/* Collapsible sections (e.g. abstract details) ------------------------------------*/

.post-content details {
  background: var(--kn-card);
  border: 1px solid var(--kn-rule);
  border-radius: 14px;
  padding: 1rem 1.3rem;
  margin: 0 0 1.4rem;
}
.post-content details[open] { border-color: var(--kn-accent); }
.post-content summary {
  font-family: var(--kn-mono);
  font-size: 0.84rem;
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  cursor: pointer;
}
.post-content summary:hover { color: var(--kn-accent); }

/* Footnotes --------------------------------------------------------------------*/

.footnotes {
  margin-top: 3rem;
  border-top: 1px solid var(--kn-rule);
  padding-top: 1.2rem;
  font-size: 0.92rem;
  color: var(--kn-soft);
}

/* Footnote markers + hover/focus tooltip (see /js/footnotes.js) */
a.footnote {
  text-decoration: none;
  font-weight: 500;
  padding: 0 0.1em;
}
a.footnote:hover { color: var(--kn-accent-deep); }

.fn-tooltip {
  position: absolute;
  z-index: 60;
  max-width: min(360px, calc(100vw - 24px));
  background: var(--kn-card);
  color: var(--kn-ink);
  border: 1px solid var(--kn-rule);
  border-radius: 10px;
  box-shadow: 0 10px 30px rgba(31, 35, 40, 0.14);
  padding: 0.7rem 0.9rem;
  font-family: var(--kn-sans);
  font-size: 0.86rem;
  line-height: 1.5;
}
.fn-tooltip[hidden] { display: none; }
.fn-tooltip p { margin: 0; }
.fn-tooltip p + p { margin-top: 0.5rem; }
.fn-tooltip a, .fn-tooltip a:visited { color: var(--kn-accent); }
.fn-tooltip a:hover { color: var(--kn-accent-deep); }

/* Comments (giscus) ------------------------------------------------------------*/

.post-comments {
  margin-top: 3rem;
  border-top: 1px solid var(--kn-rule);
  padding-top: 1.4rem;
}
.post-comments .comments-heading {
  font-family: var(--kn-serif);
  font-weight: 400;
  font-size: 1.5rem;
  margin: 0 0 0.4rem;
}
.post-comments .comments-note {
  color: var(--kn-soft);
  font-size: 0.88rem;
  margin: 0 0 1.2rem;
}

/* Footer ------------------------------------------------------------------------*/

.site-footer {
  position: relative;
  background: var(--kn-rail-bg);
  color: var(--kn-soft);
  border-top: 1px solid var(--kn-rule);
}
.site-footer::before {
  content: "";
  position: absolute;
  left: 0; right: 0; top: -1px;
  height: 9px;
}
.site-footer a, .site-footer a:visited { color: var(--kn-ink); }
.site-footer a:hover { color: var(--kn-accent); }
.footer-heading { font-family: var(--kn-serif); color: var(--kn-ink); }
.site-footer .username, .contact-list, .social-media-list { color: var(--kn-soft); }
.social-media-list .icon path, .site-footer svg path { fill: var(--kn-soft); }

/* Keynote banner: the one place the blog uses orange, as an event colour -----------*/

.keynote-banner {
  display: block;
  background: var(--kn-card);
  border: 1px solid var(--kn-rule);
  border-radius: 16px;
  border-left: 5px solid var(--kn-event);
  padding: 1.4rem 1.6rem;
  margin: 0.5rem 0 2.4rem;
  text-decoration: none;
  transition: box-shadow 140ms ease, transform 140ms ease;
}
.keynote-banner:hover {
  text-decoration: none;
  transform: translateY(-2px);
  box-shadow: 0 12px 30px rgba(31, 35, 40, 0.12);
}
.keynote-banner-kicker {
  display: block;
  font-family: var(--kn-mono);
  font-size: 0.72rem;
  font-weight: 600;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--kn-event-deep);
  margin-bottom: 0.45rem;
}
.keynote-banner-headline {
  display: block;
  font-family: var(--kn-serif);
  font-size: 1.45rem;
  line-height: 1.2;
  color: var(--kn-ink);
  margin-bottom: 0.55rem;
}
.keynote-banner-headline em { color: var(--kn-event-deep); font-style: italic; }
.keynote-banner-cta {
  display: block;
  font-family: var(--kn-mono);
  font-size: 0.8rem;
  color: var(--kn-soft);
}
.keynote-banner:hover .keynote-banner-cta { color: var(--kn-event-deep); }

/* Post navigation (override.css companions) ----------------------------------------*/

.post_navi-label { font-family: var(--kn-mono); font-size: 0.72rem; text-transform: uppercase; letter-spacing: 0.08em; opacity: 1; color: var(--kn-faint); }
.post_navi .post_navi-arrow { color: var(--kn-accent); opacity: 0.55; }
.share-links { font-family: var(--kn-mono); font-size: 0.8rem; }

/* ==================================================================================
   Homepage: split-rail layout (_layouts/home.html)
   Light sticky rail (identity + nav + CV) beside a scrolling column of writing,
   then projects. The rail carries the honeycomb strip along its top edge.
   ================================================================================== */

.wf-skip { position: absolute; left: -200vw; top: 0; background: var(--kn-ink); color: var(--kn-bg); padding: 0.6rem 1rem; z-index: 10; }
.wf-skip:focus { left: 1rem; top: 1rem; }

.wf-home, .wf-home *, .wf-home *::before, .wf-home *::after { box-sizing: border-box; }

.wf-home {
  display: grid;
  grid-template-columns: minmax(300px, 380px) 1fr;
  min-height: 100vh;
}

/* Rail ------------------------------------------------------------------------------*/

.wf-rail {
  position: sticky;
  top: 0;
  height: 100vh;
  overflow-y: auto;
  background: var(--kn-rail-bg);
  color: var(--kn-ink);
  border-right: 1px solid var(--kn-rule);
  padding: clamp(1.6rem, 3vw, 2.8rem);
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  gap: 1.5rem;
}
.wf-rail::before {
  content: "";
  position: absolute;
  left: 0; right: 0; top: 0;
  height: 9px;
}
.wf-wordmark, .wf-wordmark:visited {
  display: block;
  font-family: var(--kn-serif);
  font-size: clamp(2.2rem, 3.4vw, 2.7rem);
  line-height: 1;
  color: var(--kn-ink);
  text-decoration: none;
  margin-bottom: 0.5rem;
}
.wf-wordmark:hover { color: var(--kn-accent); text-decoration: none; }
.wf-name {
  font-family: var(--kn-mono);
  font-size: 0.74rem;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--kn-accent);
  margin: 0 0 0.9rem;
}
.wf-pitch { color: var(--kn-soft); font-size: 1rem; margin: 0 0 1.4rem; }

.wf-nav { display: flex; flex-direction: column; gap: 0.15rem; font-family: var(--kn-mono); font-size: 0.84rem; }
.wf-nav a, .wf-nav a:visited {
  color: var(--kn-ink);
  text-decoration: none;
  padding: 0.5rem 0.7rem;
  border-radius: 8px;
  display: flex;
  justify-content: space-between;
}
.wf-nav a:hover { background: var(--kn-accent-soft); color: var(--kn-ink); text-decoration: none; }
.wf-nav .wf-arr { color: var(--kn-accent); }

.wf-cv, .wf-cv:visited {
  margin-top: 1.4rem;
  display: block;
  text-align: center;
  font-family: var(--kn-mono);
  font-size: 0.84rem;
  font-weight: 500;
  text-decoration: none;
  background: var(--kn-ink);
  color: #fff;
  padding: 0.8rem 1.1rem;
  border-radius: 10px;
  transition: background 120ms ease;
}
.wf-cv:hover { background: var(--kn-accent); color: #fff; text-decoration: none; }

.wf-contact { list-style: none; margin: 0; padding: 0; font-family: var(--kn-mono); font-size: 0.74rem; display: flex; flex-direction: column; gap: 0.4rem; }
.wf-contact a, .wf-contact a:visited { color: var(--kn-soft); text-decoration: none; }
.wf-contact a:hover { color: var(--kn-accent); }

/* Main column -----------------------------------------------------------------------*/

.wf-main { padding: clamp(2rem, 4vw, 3.2rem); max-width: 60rem; }
.wf-sec + .wf-sec { margin-top: 3rem; }
.wf-sechead {
  position: relative;
  display: flex;
  align-items: baseline;
  gap: 0.9rem;
  border-bottom: 1px solid var(--kn-rule);
  padding-bottom: 0.7rem;
  margin-bottom: 1.4rem;
}
.wf-sechead::after {
  content: "";
  position: absolute;
  left: 0; right: 0; bottom: -1px;
  height: 9px;
  opacity: 0.9;
}
.wf-sechead h2 { font-family: var(--kn-serif); font-weight: 400; font-size: clamp(1.25rem, 2vw, 1.45rem); margin: 0; }
.wf-count { font-family: var(--kn-mono); font-size: 0.74rem; color: var(--kn-faint); margin-left: auto; }
.wf-count a, .wf-count a:visited { color: var(--kn-faint); }
.wf-count a:hover { color: var(--kn-accent); }

/* Writing / Releases toggles in the News section head (js/news-filter.js). Both are
   pressed by default; pressing the only active one swaps to the other, so the list
   is never empty. */
.wf-toggle { display: inline-flex; gap: 0.3rem; margin-left: 0.4rem; align-self: center; }
.wf-tog {
  appearance: none;
  display: inline-flex;
  align-items: center;
  font: 500 0.72rem/1 var(--kn-mono);
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--kn-faint);
  background: transparent;
  border: 1px solid var(--kn-rule);
  border-radius: 999px;
  padding: 0.38rem 0.75rem 0.38rem 0.6rem;
  cursor: pointer;
  transition: background 120ms ease, color 120ms ease, border-color 120ms ease;
}
.wf-tog .wf-ico { margin-right: 0.45em; opacity: 0.35; filter: grayscale(1); transition: opacity 120ms ease, filter 120ms ease; }
.wf-tog:hover { color: var(--kn-accent); border-color: var(--kn-accent); }
.wf-tog[aria-pressed="true"] { background: var(--kn-card); border-color: var(--kn-soft); color: var(--kn-ink); }
.wf-tog[aria-pressed="true"] .wf-ico { opacity: 1; filter: none; }
.wf-tog[aria-pressed="true"]:hover { border-color: var(--kn-accent); color: var(--kn-accent); }

/* Item markers: a spectrum-filled hex for a post, a monochrome tag for a release. */
.wf-ico {
  display: inline-block;
  flex: none;
  width: 0.8em;
  height: 0.8em;
  vertical-align: -0.08em;
  margin-right: 0.5em;
}
.wf-ico-post {
  height: 0.9em;
  background: var(--spec-gradient-diag);
  clip-path: polygon(50% 0, 100% 25%, 100% 75%, 50% 100%, 0 75%, 0 25%);
}
.wf-ico-rel {
  width: 0.85em;
  height: 0.85em;
  background: var(--kn-faint);
  -webkit-mask: var(--tag-mask) center / contain no-repeat;
  mask: var(--tag-mask) center / contain no-repeat;
}

.wf-projlist { list-style: none; margin: 0; padding: 0; }
.wf-projlist li {
  display: grid;
  grid-template-columns: 11rem minmax(0, 1fr);
  gap: 0.25rem 1.4rem;
  padding: 0.9rem 0;
  border-bottom: 1px solid var(--kn-rule);
  align-items: baseline;
}
.wf-proj-name, .wf-proj-name:visited {
  font-family: var(--kn-serif);
  font-size: 1.25rem;
  line-height: 1.15;
  color: var(--kn-ink);
  text-decoration: none;
}
.wf-proj-name:hover { color: var(--kn-accent); text-decoration: none; }
.wf-proj-body { display: flex; flex-wrap: wrap; align-items: baseline; gap: 0.3rem 1.2rem; }
.wf-proj-stub { color: var(--kn-soft); font-size: 0.94rem; flex: 1 1 22rem; }
.wf-proj-links { font-family: var(--kn-mono); font-size: 0.74rem; display: flex; gap: 0.9rem; }
.wf-proj-links a { text-decoration: none; }
.wf-proj-links a:hover { text-decoration: underline; }

.wf-keynote {
  display: block;
  background: var(--kn-card);
  border: 1px solid var(--kn-rule);
  border-radius: 14px;
  border-left: 5px solid var(--kn-event);
  padding: 1.3rem 1.5rem;
  margin: 0 0 2rem;
  text-decoration: none;
  transition: box-shadow 140ms ease, transform 140ms ease;
}
.wf-keynote:hover { text-decoration: none; transform: translateY(-2px); box-shadow: 0 12px 30px rgba(31, 35, 40, 0.12); }
.wf-keynote-kicker {
  display: block;
  font-family: var(--kn-mono);
  font-size: 0.72rem;
  font-weight: 600;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--kn-event-deep);
  margin-bottom: 0.45rem;
}
.wf-keynote-headline { display: block; font-family: var(--kn-serif); font-size: 1.45rem; line-height: 1.2; color: var(--kn-ink); margin-bottom: 0.55rem; }
.wf-keynote-headline em { color: var(--kn-event-deep); font-style: italic; }
.wf-keynote-cta { display: block; font-family: var(--kn-mono); font-size: 0.8rem; color: var(--kn-soft); }
.wf-keynote:hover .wf-keynote-cta { color: var(--kn-event-deep); }

/* News list -------------------------------------------------------------------------*/
/* Every post and release, grouped by month, with a sticky "By month" rail on the right
   that jumps to the matching month heading. Posts are small panels marked with a
   spectrum hex; releases are plain compact lines marked with a monochrome tag. Each month carries one solid hex; the hue advances
   through the spectrum month by month (wf-hue-0 … wf-hue-6, set in home.html), so
   the month rail reads as a vertical rainbow. On narrow screens the rail becomes a
   chip row above the list. */

.wf-hue-0 { --hue: var(--spec-0); }
.wf-hue-1 { --hue: var(--spec-1); }
.wf-hue-2 { --hue: var(--spec-2); }
.wf-hue-3 { --hue: var(--spec-3); }
.wf-hue-4 { --hue: var(--spec-4); }
.wf-hue-5 { --hue: var(--spec-5); }
.wf-hue-6 { --hue: var(--spec-6); }

.wf-hex {
  display: inline-block;
  flex: none;
  width: 0.8em;
  height: 0.9em;
  background: var(--hue, var(--kn-faint));
  clip-path: polygon(50% 0, 100% 25%, 100% 75%, 50% 100%, 0 75%, 0 25%);
}

.wf-writing {
  display: grid;
  grid-template-columns: minmax(0, 1fr) 10rem;
  gap: 0 2.5rem;
  align-items: start;
}

.wf-month { scroll-margin-top: 1.5rem; }
.wf-month + .wf-month { margin-top: 2.4rem; }
.wf-month-head {
  display: flex;
  align-items: center;
  gap: 0.6rem;
  font-family: var(--kn-mono);
  font-weight: 500;
  font-size: 0.74rem;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--kn-ink);
  margin: 0;
  padding-bottom: 0.45rem;
  border-bottom: 1px solid var(--kn-rule);
}
.wf-month-head .wf-hex { width: 0.95em; height: 1.05em; }
.wf-month-n { font-weight: 400; letter-spacing: 0.04em; text-transform: none; color: var(--kn-faint); margin-left: 0.2rem; }

.wf-months {
  position: sticky;
  top: 1.5rem;
  max-height: calc(100vh - 3rem);
  overflow-y: auto;
  font-family: var(--kn-mono);
}
.wf-months-head {
  font-size: 0.7rem;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--kn-faint);
  margin: 0 0 0.5rem;
}
.wf-months ul { list-style: none; margin: 0; padding: 0; }
.wf-months-year {
  font-size: 0.7rem;
  letter-spacing: 0.06em;
  color: var(--kn-faint);
  margin: 0.7rem 0 0.15rem;
  padding-left: 0.65rem;
}
.wf-months-year:first-child { margin-top: 0; }
.wf-months a, .wf-months a:visited {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  font-size: 0.8rem;
  color: var(--kn-soft);
  text-decoration: none;
  padding: 0.22rem 0.5rem 0.22rem 0.65rem;
  border-left: 2px solid var(--kn-rule);
}
.wf-months a .wf-hex { width: 0.65em; height: 0.75em; }
.wf-months a:hover { color: var(--kn-accent); border-left-color: var(--hue, var(--kn-accent)); text-decoration: none; }
.wf-months-m { flex: 1; }
.wf-months-yr { display: none; }
.wf-months-n { color: var(--kn-faint); }
.wf-months a:hover .wf-months-n { color: var(--kn-accent); }

.wf-posts { list-style: none; margin: 0; padding: 0; }
.wf-posts li {
  display: grid;
  grid-template-columns: 5rem minmax(0, 1fr);
  gap: 0.2rem 1.2rem;
  align-items: baseline;
}
/* A post is a small panel; the panel, not a rule, is what separates it from its neighbours. */
.wf-posts li.wf-item-post {
  background: var(--kn-card);
  border: 1px solid var(--kn-rule);
  border-radius: 10px;
  padding: 1rem 1.15rem;
  margin: 0.7rem 0;
}
.wf-post-date {
  display: flex;
  align-items: center;
  font-family: var(--kn-mono);
  font-size: 0.72rem;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--kn-accent);
  white-space: nowrap;
}
.wf-post-body { display: block; }
.wf-post-title, .wf-post-title:visited {
  display: block;
  font-family: var(--kn-serif);
  font-size: 1.45rem;
  line-height: 1.15;
  color: var(--kn-ink);
  text-decoration: none;
}
.wf-post-title:hover { color: var(--kn-accent); text-decoration: none; }
.wf-post-excerpt { display: block; color: var(--kn-soft); font-size: 0.92rem; margin-top: 0.3rem; }
.wf-more { font-family: var(--kn-mono); font-size: 0.78rem; margin-top: 1.2rem; }

/* Release rows: one compact line per package release, in the same date grid as
   posts but tighter and set in the meta face. Package + version act as the title;
   the blurb wraps if it must, and the links stay together at the end. */
.wf-posts li.wf-item-rel { padding: 0.35rem 1.15rem; gap: 0.1rem 1.2rem; }
.wf-posts li.wf-item-rel + li.wf-item-rel { border-top: 1px dotted var(--kn-rule); }
.wf-posts li.wf-item-rel .wf-post-date { color: var(--kn-soft); }
.wf-rel-body {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 0.15rem 0.7rem;
  font-size: 0.8rem;
  line-height: 1.45;
}
.wf-rel-pkg { font-family: var(--kn-mono); font-weight: 500; font-size: 0.74rem; color: var(--kn-ink); white-space: nowrap; }
.wf-rel-ver { color: var(--kn-accent); font-weight: 400; }
.wf-rel-blurb { color: var(--kn-softer); flex: 1 1 18rem; min-width: 0; }
/* Links flow inline after the blurb text, so a short blurb and its links share one line. */
.wf-rel-links { font-family: var(--kn-mono); font-size: 0.68rem; white-space: nowrap; margin-left: 0.35rem; }
.wf-rel-links a { text-decoration: none; margin-left: 0.55rem; }
.wf-rel-links a:hover { text-decoration: underline; }
.wf-month-n .wf-n-sep { color: var(--kn-rule); }

/* Filter states, set by js/news-filter.js. Empty months are hidden by the script. */
.wf-writing[data-show="posts"] .wf-item-rel,
.wf-writing[data-show="posts"] .wf-n-releases,
.wf-writing[data-show="posts"] .wf-n-sep,
.wf-writing[data-show="releases"] .wf-item-post,
.wf-writing[data-show="releases"] .wf-n-posts,
.wf-writing[data-show="releases"] .wf-n-sep { display: none; }

/* Homepage footer -------------------------------------------------------------------*/

.wf-foot { position: relative; margin-top: 3rem; border-top: 1px solid var(--kn-rule); padding-top: 1.6rem; }
.wf-foot::before { content: ""; position: absolute; left: 0; right: 0; top: -1px; height: 9px; opacity: 0.9; }
.wf-foot-strap { font-family: var(--kn-serif); font-size: 1.4rem; color: var(--kn-ink); margin: 0 0 0.6rem; }
.wf-foot-links { font-family: var(--kn-mono); font-size: 0.78rem; display: flex; flex-wrap: wrap; gap: 0.4rem 1.3rem; margin: 0; color: var(--kn-faint); }

@media screen and (max-width: 900px) {
  .wf-home { grid-template-columns: 1fr; }
  .wf-rail { position: static; height: auto; border-right: none; border-bottom: 1px solid var(--kn-rule); }
  .wf-posts li, .wf-projlist li { grid-template-columns: 1fr; }
  .wf-sechead { flex-wrap: wrap; row-gap: 0.5rem; }
  .wf-posts li.wf-item-post { padding: 0.9rem 1rem; }
  .wf-posts li.wf-item-rel { padding: 0.45rem 0.25rem; }
  .wf-toggle { margin-left: 0; order: 3; flex-basis: 100%; }

  /* Month rail becomes a wrapping chip row above the list. */
  .wf-writing { grid-template-columns: 1fr; }
  .wf-months { position: static; max-height: none; order: -1; margin-bottom: 1.6rem; }
  .wf-months ul { display: flex; flex-wrap: wrap; gap: 0.4rem; }
  .wf-months-year { display: none; }
  .wf-months-yr { display: inline; }
  .wf-months a, .wf-months a:visited {
    border: 1px solid var(--kn-rule);
    border-radius: 999px;
    padding: 0.2rem 0.65rem;
    background: var(--kn-card);
  }
  .wf-months a:hover { border-color: var(--hue, var(--kn-accent)); }
  .wf-month { scroll-margin-top: 1rem; }
}

/* Shared footer on posts and interior pages (_includes/footer.html) ------------------*/

.site-footer .footer-strap { font-family: var(--kn-serif); font-size: 1.5rem; color: var(--kn-ink); margin: 0 0 0.8rem; }
.site-footer .footer-links { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: 0.4rem 1.4rem; font-family: var(--kn-mono); font-size: 0.78rem; }
.site-footer .footer-links a, .site-footer .footer-links a:visited { color: var(--kn-soft); text-decoration: none; }
.site-footer .footer-links a:hover { color: var(--kn-accent); }
.site-footer .footer-links .p-name { color: var(--kn-ink); }

/* CV link in the header nav on interior pages ---------------------------------------*/

.site-nav .cv-link, .site-nav .cv-link:visited {
  color: var(--kn-accent);
  border: 1px solid rgba(108, 50, 112, 0.45);
  border-radius: 7px;
  padding: 0.2rem 0.6rem;
}
.site-nav .cv-link:hover { background: var(--kn-accent); color: #fff; text-decoration: none; }

/* Projects page (/projects/) -------------------------------------------------------*/

.projects-intro { color: var(--kn-soft); margin-bottom: 2rem; }
.projects-list { border-top: 2px solid var(--kn-ink); }
.projects-row {
  display: grid;
  grid-template-columns: 15rem minmax(0, 1fr);
  gap: 0.6rem 2rem;
  padding: 1.5rem 0;
  border-bottom: 1px solid var(--kn-rule);
  align-items: start;
}
.projects-row h2 { font-family: var(--kn-serif); font-weight: 400; font-size: 1.6rem; margin: 0; }
.projects-role {
  font-family: var(--kn-mono);
  font-size: 0.7rem;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--kn-faint);
  margin: 0.35rem 0 0;
}
.projects-detail p { margin: 0; }
.projects-links { font-family: var(--kn-mono); font-size: 0.76rem; display: flex; flex-wrap: wrap; gap: 0.4rem 1.4rem; margin-top: 0.8rem !important; }
.projects-links a { text-decoration: none; }
.projects-links a:hover { text-decoration: underline; }
.projects-more { font-size: 0.92rem; color: var(--kn-soft); margin-top: 1.6rem; }

@media screen and (max-width: 700px) {
  .projects-row { grid-template-columns: 1fr; }
}
