/* ==========================================================================
   ChartGPT — chartgpt.co
   Design system. Hand-written, no framework, no build step.
   Concept: "the plot area". The page behaves like an instrument panel —
   hairline rules read as axes, tick marks mark sections, and the categorical
   series palette (s1..s5) is the brand's colour, used on data first.
   ========================================================================== */

/* --- 1. Tokens ----------------------------------------------------------- */

:root {
  /* Surfaces */
  --paper: #EDF0F1;
  /* cool graph-paper grey */
  --paper-deep: #E2E7EA;
  --panel: #FFFFFF;
  --ink: #0F1D2B;
  /* deep slate navy — the "brand black" */
  --ink-2: #405669;
  --ink-3: #7C8FA0;
  --rule: #D6DDE2;
  --rule-soft: #E6EBEE;

  /* Categorical series — this is the brand palette */
  --s1: #1B4BE0;
  --s2: #F2A33C;
  --s3: #12A594;
  --s4: #D9426E;
  --s5: #7048D8;

  --s1-wash: #E8EDFD;
  --s3-wash: #E3F5F2;

  --ok: #12A594;
  --warn: #B4690E;

  /* Type */
  --display: "Schibsted Grotesk", "Helvetica Neue", Arial, sans-serif;
  --body: "Inter", -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
  --mono: "IBM Plex Mono", ui-monospace, "SF Mono", Menlo, monospace;

  /* Rhythm */
  --gut: 24px;
  --shell: 1200px;
  --radius: 6px;
  --radius-lg: 12px;

  --lift: 0 1px 2px rgba(15, 29, 43, .06), 0 8px 24px -12px rgba(15, 29, 43, .18);
}

/* --- 2. Reset ------------------------------------------------------------ */

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

html {
  -webkit-text-size-adjust: 100%;
  scroll-behavior: smooth;
}

@media (prefers-reduced-motion: reduce) {
  html {
    scroll-behavior: auto;
  }

  *,
  *::before,
  *::after {
    animation-duration: .001ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: .001ms !important;
  }
}

body {
  margin: 0;
  background: var(--paper);
  color: var(--ink);
  font-family: var(--body);
  font-size: 16.5px;
  line-height: 1.62;
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
}

img,
svg {
  max-width: 100%;
  display: block;
}

button {
  font: inherit;
  color: inherit;
}

a {
  color: var(--ink);
  text-decoration-color: var(--ink-3);
  text-underline-offset: 3px;
}

a:hover {
  text-decoration-color: var(--s1);
}

:focus-visible {
  outline: 2px solid var(--s1);
  outline-offset: 3px;
  border-radius: 2px;
}

::selection {
  background: #C9D6FB;
}

/* --- 3. Type scale ------------------------------------------------------- */

h1,
h2,
h3,
h4,
h5 {
  font-family: var(--display);
  font-weight: 600;
  letter-spacing: -.021em;
  line-height: 1.12;
  margin: 0 0 .5em;
  text-wrap: balance;
}

h1 {
  font-size: clamp(2.3rem, 4.6vw, 3.5rem);
  letter-spacing: -.032em;
}

h2 {
  font-size: clamp(1.7rem, 3.1vw, 2.45rem);
  letter-spacing: -.026em;
}

h3 {
  font-size: clamp(1.16rem, 1.7vw, 1.4rem);
}

h4 {
  font-size: 1.02rem;
  letter-spacing: -.01em;
}

p {
  margin: 0 0 1.1em;
}

p:last-child {
  margin-bottom: 0;
}

.lede {
  font-size: clamp(1.06rem, 1.7vw, 1.22rem);
  line-height: 1.58;
  color: var(--ink-2);
  max-width: 62ch;
}

.muted {
  color: var(--ink-2);
}

.small {
  font-size: .875rem;
  line-height: 1.55;
}

.num {
  font-family: var(--mono);
  font-variant-numeric: tabular-nums;
  letter-spacing: -.02em;
}

/* --- 4. Shell & rhythm --------------------------------------------------- */

.shell {
  width: 100%;
  max-width: var(--shell);
  margin-inline: auto;
  padding-inline: var(--gut);
}

.shell-narrow {
  max-width: 760px;
}

.shell-mid {
  max-width: 960px;
}

.band {
  padding-block: clamp(56px, 8vw, 104px);
}

.band-tight {
  padding-block: clamp(40px, 5vw, 64px);
}

.band-panel {
  background: var(--panel);
  border-block: 1px solid var(--rule);
}

.band-ink {
  background: var(--ink);
  color: #E7EDF2;
}

.band-ink h1,
.band-ink h2,
.band-ink h3 {
  color: #FFF;
}

.band-ink .lede,
.band-ink .muted {
  color: #A9BCCB;
}

/* Links inside a dark band go white — but NOT buttons. `.band-ink a` is
   specificity (0,1,1) and beat `.btn-on-ink` (0,1,0), which made the white
   "Make a chart" button render white-on-white and vanish. Keep the :not(.btn). */
.band-ink a:not(.btn) {
  color: #FFF;
  text-decoration-color: #6E8CA3;
}

/* Section head: a heading sitting on an axis baseline with a tick */
.sec-head {
  border-bottom: 1px solid var(--rule);
  padding-bottom: 18px;
  margin-bottom: 40px;
  display: flex;
  flex-wrap: wrap;
  align-items: flex-end;
  justify-content: space-between;
  gap: 16px;
  position: relative;
}

.sec-head::after {
  content: "";
  position: absolute;
  left: 0;
  bottom: -1px;
  width: 34px;
  height: 3px;
  background: var(--s1);
}

.sec-head h2 {
  margin: 0;
  max-width: 22ch;
}

.sec-head p {
  margin: 0;
  color: var(--ink-2);
  max-width: 46ch;
  font-size: .95rem;
}

.band-ink .sec-head {
  border-color: #2A3D4F;
}

/* --- 5. Buttons ---------------------------------------------------------- */

.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  font-family: var(--display);
  font-weight: 500;
  font-size: .95rem;
  letter-spacing: -.01em;
  padding: 11px 20px;
  border-radius: var(--radius);
  border: 1px solid transparent;
  cursor: pointer;
  text-decoration: none;
  transition: background-color .15s ease, border-color .15s ease, color .15s ease;
  white-space: nowrap;
}

.btn-primary {
  background: var(--ink);
  color: #fff;
}

.btn-primary:hover {
  background: #1A3348;
}

.btn-accent {
  background: var(--s1);
  color: #fff;
}

.btn-accent:hover {
  background: #143BB8;
}

.btn-quiet {
  background: var(--panel);
  border-color: var(--rule);
  color: var(--ink);
}

.btn-quiet:hover {
  border-color: var(--ink-3);
  background: #fff;
}

.btn-ghost {
  background: transparent;
  color: var(--ink);
  padding-inline: 4px;
}

.btn-ghost:hover {
  color: var(--s1);
}

.btn-lg {
  padding: 14px 26px;
  font-size: 1rem;
}

.btn-sm {
  padding: 8px 14px;
  font-size: .875rem;
}

.btn-on-ink {
  background: #fff;
  color: var(--ink);
}

.btn-on-ink:hover {
  background: #DCE6EE;
}

.btn-outline-ink {
  border-color: #3A5062;
  color: #fff;
  background: transparent;
}

.btn-outline-ink:hover {
  border-color: #8FA6B7;
}

.btn[disabled] {
  opacity: .5;
  cursor: not-allowed;
}

.btn-row {
  display: flex;
  flex-wrap: wrap;
  gap: 12px;
  align-items: center;
}

/* --- 6. Header ----------------------------------------------------------- */

.masthead {
  position: sticky;
  top: 0;
  z-index: 60;
  background: rgba(237, 240, 241, .86);
  backdrop-filter: saturate(1.4) blur(10px);
  border-bottom: 1px solid var(--rule);
}

.masthead-in {
  display: flex;
  align-items: center;
  gap: 28px;
  height: 62px;
}

.brand {
  display: inline-flex;
  align-items: center;
  gap: 9px;
  font-family: var(--display);
  font-weight: 600;
  font-size: 1.09rem;
  letter-spacing: -.03em;
  text-decoration: none;
  color: var(--ink);
}

.brand svg {
  flex: none;
}

.brand span i {
  font-style: normal;
  color: var(--ink-3);
  font-weight: 500;
}

.nav {
  display: flex;
  align-items: center;
  gap: 4px;
  margin-left: 8px;
}

.nav a,
.nav-trigger {
  font-family: var(--display);
  font-size: .93rem;
  font-weight: 450;
  color: var(--ink-2);
  text-decoration: none;
  padding: 8px 11px;
  border-radius: var(--radius);
  border: 0;
  background: none;
  cursor: pointer;
  display: inline-flex;
  align-items: center;
  gap: 5px;
}

.nav a:hover,
.nav-trigger:hover {
  color: var(--ink);
  background: rgba(255, 255, 255, .75);
}

.nav a[aria-current="page"] {
  color: var(--ink);
  font-weight: 500;
}

.nav-item {
  position: relative;
}

.nav-panel {
  position: absolute;
  top: calc(100% + 10px);
  left: -12px;
  min-width: 480px;
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  box-shadow: var(--lift);
  padding: 12px;
  display: none;
  grid-template-columns: 1fr 1fr;
  gap: 2px;
}

/* Click-driven only. Hover opening was unreliable: .nav-panel is offset 10px
   below the trigger, and crossing that gap dropped the hover and closed the
   menu. Visibility now follows the button's aria-expanded state, so the
   accessible state and the visual state cannot disagree. */
.nav-trigger[aria-expanded="true"] + .nav-panel {
  display: grid;
}

.nav-trigger[aria-expanded="true"] {
  color: var(--ink);
  background: rgba(255, 255, 255, .75);
}

/* No chevron rotation: a CSS transform on this inline <svg> computes to the
   identity matrix here, and the `rotate` property would not animate reliably
   either. The open state is already signalled by the trigger's background and
   by the panel appearing, so the arrow is left alone. */

.nav-panel a {
  display: block;
  padding: 10px 12px;
  border-radius: var(--radius);
  color: var(--ink);
  font-weight: 500;
  line-height: 1.35;
}

.nav-panel a small {
  display: block;
  color: var(--ink-2);
  font-weight: 400;
  font-size: .82rem;
  font-family: var(--body);
  margin-top: 2px;
}

.nav-panel a:hover {
  background: var(--paper);
}

.masthead-end {
  margin-left: auto;
  display: flex;
  align-items: center;
  gap: 10px;
}

.burger {
  display: none;
  border: 1px solid var(--rule);
  background: var(--panel);
  border-radius: var(--radius);
  padding: 8px 10px;
  cursor: pointer;
}

@media (max-width: 940px) {

  .nav,
  .masthead-end .btn-ghost {
    display: none;
  }

  .burger {
    display: inline-flex;
  }

  /* The account menu stays at every width — it is the only way to reach the
     member area now that the drawer no longer repeats it. Tighter gaps keep
     brand + avatar + button + burger inside a narrow viewport. */
  .masthead-in {
    gap: 12px;
  }

  .masthead-end {
    gap: 8px;
  }

  /* Positioning context for the account panel below this width — the panel
     itself is repositioned in section 18, next to the rest of its rules. */
  .masthead-in {
    position: relative;
  }
}

/* Signed in, the masthead has to carry the wordmark, the avatar, the CTA and
   the burger — 330px of content in the 272px of shell a 320px screen gives,
   and still 3px short at 375. One of them has to go below ~400px.

   It is the CTA, and only for signed-in members: the drawer's first entry is
   "Make a Chart" and the logo goes to the home page, where the workbench is
   the hero, so nothing becomes unreachable. A guest has no avatar, their row
   fits, and they keep the button at every width — they are the ones the CTA
   is for.

   `.has-acct` is set in the Blade rather than matched with :has(), so the rule
   does not depend on selector support for something this load-bearing. */
@media (max-width: 400px) {
  .masthead-end.has-acct .btn-primary {
    display: none;
  }
}

.drawer {
  display: none;
  border-bottom: 1px solid var(--rule);
  background: var(--panel);
  padding: 8px var(--gut) 20px;
}

.drawer.open {
  display: block;
}

.drawer a {
  display: block;
  padding: 11px 2px;
  border-bottom: 1px solid var(--rule-soft);
  text-decoration: none;
  font-family: var(--display);
  font-weight: 500;
}

.drawer .drawer-group {
  font-size: .78rem;
  color: var(--ink-3);
  padding-top: 16px;
  font-family: var(--display);
  letter-spacing: .02em;
}

/* --- 7. Hero + workbench ------------------------------------------------- */

.hero {
  padding-top: clamp(40px, 4.4vw, 58px);
  padding-bottom: clamp(36px, 5vw, 56px);
  background:
    linear-gradient(180deg, #F4F6F7 0%, var(--paper) 62%),
    var(--paper);
  border-bottom: 1px solid var(--rule);
  position: relative;
  overflow: hidden;
}

/* faint plot grid behind the hero */
.hero::before {
  content: "";
  position: absolute;
  inset: 0;
  background-image:
    linear-gradient(to right, rgba(15, 29, 43, .045) 1px, transparent 1px),
    linear-gradient(to bottom, rgba(15, 29, 43, .045) 1px, transparent 1px);
  background-size: 56px 56px;
  mask-image: linear-gradient(to bottom, #000, transparent 78%);
  -webkit-mask-image: linear-gradient(to bottom, #000, transparent 78%);
  pointer-events: none;
}

.hero>* {
  position: relative;
}

.hero h1 {
  max-width: 21ch;
}

.hero .lede {
  max-width: 54ch;
}

.hero-copy {
  max-width: 720px;
}

.kicker {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  font-family: var(--display);
  font-size: .84rem;
  font-weight: 500;
  color: var(--ink-2);
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: 100px;
  padding: 5px 13px 5px 8px;
  margin-bottom: 22px;
  text-decoration: none;
}

.kicker b {
  color: var(--ink);
  font-weight: 600;
}

.kicker .dot {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  background: var(--s3);
  flex: none;
  margin-left: 4px;
}

/* The workbench: prompt + rendered chart */
.workbench {
  margin-top: 34px;
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  box-shadow: var(--lift);
  overflow: hidden;
}

.wb-bar {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 10px 12px;
  border-bottom: 1px solid var(--rule);
  background: linear-gradient(180deg, #FCFDFD, #F6F8F9);
}

.wb-dots {
  display: flex;
  gap: 6px;
  padding-left: 4px;
}

.wb-dots i {
  width: 10px;
  height: 10px;
  border-radius: 50%;
  background: var(--rule);
  display: block;
}

.wb-title {
  font-family: var(--display);
  font-size: .85rem;
  color: var(--ink-2);
  font-weight: 500;
}

.wb-status {
  margin-left: auto;
  font-size: .78rem;
  color: var(--ink-3);
  font-family: var(--mono);
}

.wb-form {
  padding: 18px;
  border-bottom: 1px solid var(--rule-soft);
}

/* A column, not a row: the box is sized for pasting a table, and the submit
   button sits inside it at the bottom so the focus ring wraps the whole
   composer. */
.wb-input-wrap {
  display: flex;
  flex-direction: column;
  gap: 10px;
  border: 1px solid var(--rule);
  border-radius: var(--radius);
  padding: 14px;
  background: var(--panel);
  transition: border-color .15s ease, box-shadow .15s ease;
}

.wb-submit-row {
  display: flex;
  align-items: center;
  justify-content: flex-end;
  gap: 14px;
}

.wb-kbd-hint {
  font-size: .8rem;
  color: var(--ink-3);
}

.wb-input-wrap:focus-within {
  border-color: var(--s1);
  box-shadow: 0 0 0 3px var(--s1-wash);
}

.wb-input {
  border: 0;
  outline: 0;
  resize: none;
  font: inherit;
  font-size: 1rem;
  line-height: 1.55;
  background: transparent;
  min-height: 132px;
  max-height: 300px;
  padding: 0;
  color: var(--ink);
}

.wb-input::placeholder {
  color: var(--ink-3);
}

/* An empty field still shows its placeholder, and the placeholder is taller
   than the two rows the box starts at. Chrome treats that as overflow and
   renders a real scrollbar on an untouched input -- which also steals 15px of
   width from it. Only allow scrolling once there is something to scroll. */
.wb-input:placeholder-shown {
  overflow-y: hidden;
}

.wb-hints {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  margin-top: 14px;
  align-items: center;
}

.wb-hints .label {
  font-size: .84rem;
  color: var(--ink-3);
  margin-right: 2px;
}

.chip {
  border: 1px solid var(--rule);
  background: var(--paper);
  color: var(--ink-2);
  border-radius: 100px;
  padding: 6px 13px;
  font-size: .855rem;
  cursor: pointer;
  transition: border-color .15s ease, color .15s ease, background-color .15s ease;
  font-family: var(--display);
}

.chip:hover {
  border-color: var(--s1);
  color: var(--s1);
  background: var(--s1-wash);
}

.wb-stage {
  padding: 20px;
  background: #FBFCFC;
}

.wb-canvas {
  min-height: 340px;
  display: flex;
  align-items: center;
  justify-content: center;
  border: 1px solid var(--rule-soft);
  border-radius: var(--radius);
  background: var(--panel);
  padding: 20px 18px 14px;
}

.wb-canvas svg {
  width: 100%;
  height: auto;
}

/* Empty state. Sits inside .wb-canvas, so ChartGPT.render() — which clears the
   node before drawing — removes it the moment a chart arrives. */
.wb-empty {
  display: flex;
  flex-direction: column;
  align-items: center;
  text-align: center;
  gap: 10px;
  padding: 24px 16px;
}

.wb-empty svg {
  height: 54px;
  width: auto;
  opacity: .45;
  margin-bottom: 4px;
}

.wb-empty-title {
  font-family: var(--display);
  font-size: 1.05rem;
  font-weight: 500;
  color: var(--ink-2);
  margin: 0;
}

.wb-empty-hint {
  font-size: .92rem;
  color: var(--ink-3);
  margin: 0;
  max-width: 34ch;
}

.wb-empty .btn {
  margin-top: 8px;
}

.wb-foot {
  display: flex;
  flex-wrap: wrap;
  gap: 12px;
  align-items: center;
  justify-content: space-between;
  padding: 14px 20px;
  border-top: 1px solid var(--rule-soft);
  background: var(--panel);
}

/* An author-level display beats the UA sheet's [hidden] rule, so the toolbar
   needs this to actually stay hidden before the first chart. */
.wb-foot[hidden] {
  display: none;
}

@media (max-width: 560px) {
  .wb-submit-row {
    flex-direction: column-reverse;
    align-items: stretch;
    gap: 8px;
  }

  .wb-submit-row .btn {
    width: 100%;
    justify-content: center;
  }

  .wb-kbd-hint {
    text-align: center;
  }

  .wb-input {
    min-height: 116px;
  }
}

.wb-types {
  display: flex;
  flex-wrap: wrap;
  gap: 4px;
}

.wb-type {
  border: 1px solid transparent;
  background: none;
  padding: 6px 11px;
  border-radius: var(--radius);
  font-size: .86rem;
  color: var(--ink-2);
  cursor: pointer;
  font-family: var(--display);
}

.wb-type:hover {
  background: var(--paper);
  color: var(--ink);
}

.wb-type[aria-pressed="true"] {
  background: var(--ink);
  color: #fff;
}

.wb-actions {
  display: flex;
  gap: 8px;
  align-items: center;
}

.wb-note {
  font-size: .8rem;
  color: var(--ink-3);
  padding: 0 20px 16px;
}

/* Chart skeleton while generating */
.wb-canvas.is-busy {
  position: relative;
}

.wb-canvas.is-busy::after {
  content: "";
  position: absolute;
  inset: 0;
  background: linear-gradient(100deg, transparent 20%, rgba(255, 255, 255, .75) 50%, transparent 80%);
  background-size: 200% 100%;
  animation: sweep 1.15s linear infinite;
  border-radius: var(--radius);
}

@keyframes sweep {
  from {
    background-position: 140% 0;
  }

  to {
    background-position: -40% 0;
  }
}

/* --- 8. Grids & tiles ---------------------------------------------------- */

.grid {
  display: grid;
  gap: 1px;
  background: var(--rule);
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  overflow: hidden;
}

.grid-3 {
  grid-template-columns: repeat(3, 1fr);
}

.grid-4 {
  grid-template-columns: repeat(4, 1fr);
}

.grid>* {
  background: var(--panel);
  padding: 26px 24px;
}

.cols {
  display: grid;
  gap: 28px;
}

.cols-2 {
  grid-template-columns: repeat(2, 1fr);
}

.cols-3 {
  grid-template-columns: repeat(3, 1fr);
}

.cols-4 {
  grid-template-columns: repeat(4, 1fr);
}

.cols-side {
  grid-template-columns: minmax(0, 1fr) 340px;
  gap: 56px;
  align-items: start;
}

@media (max-width: 900px) {

  /* minmax(0, 1fr), not 1fr: a bare `1fr` floors at min-content, so one long
     unbreakable line (a <pre>, a URL) drags the column wider than the screen. */
  .grid-3,
  .grid-4,
  .cols-2,
  .cols-3,
  .cols-4,
  .cols-side {
    grid-template-columns: minmax(0, 1fr);
  }

  .cols-side {
    gap: 40px;
  }
}

@media (max-width: 620px) {
  .grid {
    border-radius: var(--radius);
  }
}

.feature h3 {
  margin-bottom: 8px;
}

.feature p {
  color: var(--ink-2);
  font-size: .95rem;
  margin: 0;
}

.feature .mark {
  display: block;
  width: 26px;
  height: 3px;
  margin-bottom: 18px;
  background: var(--s1);
}

.feature:nth-child(2) .mark {
  background: var(--s2);
}

.feature:nth-child(3) .mark {
  background: var(--s3);
}

.feature:nth-child(4) .mark {
  background: var(--s4);
}

.feature:nth-child(5) .mark {
  background: var(--s5);
}

.feature:nth-child(6) .mark {
  background: var(--ink-3);
}

/* Chart type tiles — glyph + name, flat, no shadow */
.type-tile {
  display: flex;
  flex-direction: column;
  gap: 14px;
  text-decoration: none;
  color: var(--ink);
  transition: background-color .15s ease;
}

.type-tile:hover {
  background: #FAFCFD;
}

.type-tile svg {
  height: 46px;
  width: auto;
  align-self: flex-start;
}

.type-tile b {
  font-family: var(--display);
  font-weight: 600;
  font-size: 1rem;
  letter-spacing: -.015em;
}

.type-tile span {
  color: var(--ink-2);
  font-size: .88rem;
  line-height: 1.5;
}

/* Steps — genuinely sequential, so numbering is earned */
.steps {
  counter-reset: step;
  display: grid;
  gap: 0;
}

.step {
  display: grid;
  grid-template-columns: 58px 1fr;
  gap: 22px;
  padding: 26px 0;
  border-top: 1px solid var(--rule);
  align-items: start;
}

.step:last-child {
  border-bottom: 1px solid var(--rule);
}

.step::before {
  counter-increment: step;
  content: counter(step);
  font-family: var(--mono);
  font-size: .95rem;
  color: var(--s1);
  padding-top: 3px;
}

.step h3 {
  margin-bottom: 6px;
}

.step p {
  color: var(--ink-2);
  margin: 0;
  max-width: 62ch;
}

/* --- 9. Pricing ---------------------------------------------------------- */

.plans {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 0;
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  overflow: hidden;
  background: var(--panel);
}

.plan {
  padding: 32px 28px;
  border-right: 1px solid var(--rule);
  display: flex;
  flex-direction: column;
}

.plan:last-child {
  border-right: 0;
}

.plan-feature {
  background: var(--ink);
  color: #DEE7EE;
}

.plan-feature h3,
.plan-feature .price {
  color: #fff;
}

.plan-feature .plan-list li {
  color: #C2D2DE;
}

.plan-feature .plan-list li::before {
  background: var(--s2);
}

.plan h3 {
  margin-bottom: 4px;
}

.plan .plan-for {
  color: var(--ink-2);
  font-size: .9rem;
  min-height: 44px;
  margin-bottom: 18px;
}

.plan-feature .plan-for {
  color: #A9BCCB;
}

.price {
  font-family: var(--display);
  font-size: 2.5rem;
  font-weight: 600;
  letter-spacing: -.035em;
  line-height: 1;
}

.price small {
  font-size: .92rem;
  font-weight: 450;
  color: var(--ink-2);
  letter-spacing: 0;
}

.plan-feature .price small {
  color: #A9BCCB;
}

.plan-cycle {
  font-size: .84rem;
  color: var(--ink-3);
  margin: 10px 0 22px;
}

.plan-list {
  list-style: none;
  margin: 22px 0 0;
  padding: 0;
  display: grid;
  gap: 10px;
  font-size: .92rem;
}

.plan-list li {
  position: relative;
  padding-left: 22px;
  color: var(--ink-2);
}

.plan-list li::before {
  content: "";
  position: absolute;
  left: 0;
  top: .55em;
  width: 9px;
  height: 9px;
  border-radius: 2px;
  background: var(--s1);
}

.plan .btn {
  margin-top: 26px;
  width: 100%;
}

.plan-spacer {
  flex: 1;
}

@media (max-width: 900px) {
  .plans {
    grid-template-columns: minmax(0, 1fr);
  }

  .plan {
    border-right: 0;
    border-bottom: 1px solid var(--rule);
  }
}

.ctable {
  width: 100%;
  border-collapse: collapse;
  font-size: .93rem;
}

.ctable th,
.ctable td {
  text-align: left;
  padding: 13px 16px;
  border-bottom: 1px solid var(--rule);
  vertical-align: top;
}

.ctable thead th {
  font-family: var(--display);
  font-size: .84rem;
  color: var(--ink-2);
  font-weight: 500;
  background: var(--paper);
}

.ctable td:not(:first-child),
.ctable th:not(:first-child) {
  text-align: center;
  width: 17%;
}

.ctable tbody th {
  font-weight: 500;
}

.ctable .yes {
  color: var(--s3);
  font-weight: 600;
}

.ctable .no {
  color: var(--ink-3);
}

.table-scroll {
  overflow-x: auto;
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  background: var(--panel);
}

.table-scroll .ctable tr:last-child td,
.table-scroll .ctable tr:last-child th {
  border-bottom: 0;
}

/* --- 10. Editorial / prose ---------------------------------------------- */

.prose {
  font-size: 1.03rem;
  line-height: 1.75;
  color: #1B2E3D;
  max-width: 68ch;
}

.prose h2 {
  font-size: 1.62rem;
  margin-top: 2.1em;
}

.prose h3 {
  font-size: 1.2rem;
  margin-top: 1.8em;
}

.prose h2:first-child,
.prose h3:first-child {
  margin-top: 0;
}

.prose ul,
.prose ol {
  padding-left: 1.25em;
  margin: 0 0 1.2em;
}

.prose li {
  margin-bottom: .5em;
}

.prose li::marker {
  color: var(--ink-3);
}

.prose a {
  color: var(--s1);
  text-decoration-color: rgba(27, 75, 224, .35);
}

.prose blockquote {
  margin: 1.6em 0;
  padding: 4px 0 4px 22px;
  border-left: 3px solid var(--s2);
  font-size: 1.1rem;
  line-height: 1.55;
  color: var(--ink);
}

.prose code {
  font-family: var(--mono);
  font-size: .86em;
  background: var(--paper-deep);
  padding: 2px 5px;
  border-radius: 4px;
}

.prose pre {
  background: var(--ink);
  color: #DDE7EF;
  padding: 18px 20px;
  border-radius: var(--radius);
  overflow-x: auto;
  font-size: .84rem;
  line-height: 1.6;
}

.prose pre code {
  background: none;
  padding: 0;
  color: inherit;
}

.prose hr {
  border: 0;
  border-top: 1px solid var(--rule);
  margin: 2.4em 0;
}

/* Article bodies are CKEditor HTML imported from another CMS, so the prose
   block has to survive arbitrary markup: oversized images, wide tables and
   pasted URLs that would otherwise push the page sideways on mobile. */
.prose {
  overflow-wrap: anywhere;
}

.prose img {
  max-width: 100%;
  width: 100%;
  height: auto;
  display: block;
  margin: 1.5em 0;
  border-radius: var(--radius);
}

.prose figure {
  margin: 1.5em 0;
}

.prose figure img {
  margin: 0;
}

.prose figcaption {
  font-size: .86rem;
  color: var(--ink-3);
  margin-top: 8px;
}

.prose iframe,
.prose video,
.prose embed,
.prose object {
  max-width: 100%;
}

/* Article tables ---------------------------------------------------------
   Two shapes exist in the imported content, and both have to look right:

     1. <table><thead><tr><th>…            41 of 575 tables
     2. <table><tbody><tr><td><strong>…   534 of 575 — no thead, no th; the
                                          header is only implied by bold text

   Every one of them is wrapped in CKEditor's <figure class="table">, so the
   figure is the scroll container and the table stays a real table (rather than
   display:block, which stops columns distributing).
   ------------------------------------------------------------------------ */

.prose figure.table {
  margin: 1.7em 0;
  overflow-x: auto;
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  background: var(--panel);
  -webkit-overflow-scrolling: touch;
}

.prose figure.table > table {
  margin: 0;
}

.prose table {
  width: 100%;
  border-collapse: collapse;
  font-size: .92rem;
  line-height: 1.55;
  margin: 1.7em 0;
}

/* A hand-written table with no figure around it still must not widen the page. */
.prose > table {
  display: block;
  overflow-x: auto;
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  background: var(--panel);
}

.prose th,
.prose td {
  padding: 12px 16px;
  text-align: left;
  vertical-align: top;
  border-bottom: 1px solid var(--rule-soft);
  /* A floor per column, so a wide table scrolls instead of being crushed
     into unreadable slivers on a phone. */
  min-width: 7.5rem;
}

.prose tbody tr:last-child > th,
.prose tbody tr:last-child > td {
  border-bottom: 0;
}

.prose tbody tr:nth-child(even) {
  background: #F6F8F9;
}

.prose tbody tr:hover {
  background: var(--s1-wash);
}

/* The header row: a real <thead>, or — when the table has none — the first row,
   but only if it is bold, which is what marks it as a header in shape 2. The
   `tbody:first-child` part is the discriminator: with a <thead> present the
   tbody is no longer the table's first child, so this cannot double-apply.
   The 70 tables whose first row is plain data are left as body rows. */
.prose thead > tr > th,
.prose thead > tr > td,
.prose table > tbody:first-child > tr:first-child:has(> td strong, > td b) > td {
  font-family: var(--display);
  font-weight: 600;
  font-size: .85rem;
  letter-spacing: -.005em;
  color: var(--ink);
  background: var(--paper-deep);
  border-bottom: 1px solid var(--rule);
  vertical-align: middle;
}

/* The bold tag is what identified the header; it should not also embolden it. */
.prose table > tbody:first-child > tr:first-child:has(> td strong, > td b) > td strong,
.prose table > tbody:first-child > tr:first-child:has(> td strong, > td b) > td b {
  font-weight: inherit;
}

/* Header rows never take the zebra or hover treatment. */
.prose thead > tr:hover,
.prose table > tbody:first-child > tr:first-child:has(> td strong, > td b):hover {
  background: var(--paper-deep);
}

@media (max-width: 620px) {
  .prose th,
  .prose td {
    padding: 10px 12px;
    min-width: 6.5rem;
  }
}

/* --- 11. Blog ------------------------------------------------------------ */

.post-list {
  border-top: 1px solid var(--rule);
}

.post-row {
  display: grid;
  grid-template-columns: 150px 1fr;
  gap: 32px;
  padding: 30px 0;
  border-bottom: 1px solid var(--rule);
  text-decoration: none;
  color: var(--ink);
  align-items: start;
}

.post-row:hover h3 {
  color: var(--s1);
}

.post-meta {
  font-size: .82rem;
  color: var(--ink-3);
  font-family: var(--mono);
  padding-top: 5px;
}

.post-row h3 {
  margin-bottom: 7px;
  max-width: 30ch;
}

.post-row p {
  color: var(--ink-2);
  margin: 0;
  font-size: .95rem;
  max-width: 68ch;
}

.post-tag {
  display: inline-block;
  font-family: var(--display);
  font-size: .78rem;
  color: var(--ink-2);
  border: 1px solid var(--rule);
  border-radius: 100px;
  padding: 2px 10px;
  margin-top: 12px;
  background: var(--panel);
}

@media (max-width: 720px) {
  .post-row {
    grid-template-columns: minmax(0, 1fr);
    gap: 10px;
  }

  .post-meta {
    padding-top: 0;
  }
}

.byline {
  display: flex;
  align-items: center;
  gap: 12px;
  margin: 26px 0 0;
}

.avatar {
  width: 40px;
  height: 40px;
  border-radius: 50%;
  background: var(--ink);
  color: #fff;
  display: grid;
  place-items: center;
  font-family: var(--display);
  font-weight: 600;
  font-size: .9rem;
  line-height: 1;
  letter-spacing: .01em;
  flex: none;
  overflow: hidden;
  text-transform: uppercase;
  user-select: none;
}

img.avatar {
  object-fit: cover;
}

.byline div {
  line-height: 1.35;
}

.byline b {
  font-family: var(--display);
  font-size: .93rem;
}

/* Scoped to the meta line. A bare `.byline span` also matched the initials
   avatar and, being more specific than `.avatar`, stripped its grid centring
   and white text — leaving the initials grey and jammed to the top-left. */
.byline>div>span {
  display: block;
  color: var(--ink-3);
  font-size: .82rem;
}

/* Article cards — used by every blog listing */
.card-grid {
  display: grid;
  /* min(100%, 300px): the 300px floor must never exceed the track itself, or a
     320px screen (272px after gutters) overflows by the difference. */
  grid-template-columns: repeat(auto-fill, minmax(min(100%, 300px), 1fr));
  gap: 28px;
}

.card {
  display: flex;
  flex-direction: column;
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  overflow: hidden;
  color: var(--ink);
  transition: border-color .15s ease, transform .15s ease;
}

.card:hover {
  border-color: var(--ink-3);
  transform: translateY(-2px);
}

.card:hover .card-title {
  color: var(--s1);
}

.card-shot {
  display: block;
  aspect-ratio: 16 / 9;
  background: var(--paper-deep);
  overflow: hidden;
}

.card-shot img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}

.card-title {
  color: inherit;
  text-decoration: none;
  transition: color .15s ease;
}

.card-title:hover {
  color: var(--s1);
}

.card-shot-none {
  width: 100%;
  height: 100%;
  display: grid;
  place-items: center;
  background: linear-gradient(135deg, var(--paper-deep), var(--paper));
  color: var(--ink-3);
}

.card-body {
  padding: 20px 22px 22px;
  display: flex;
  flex-direction: column;
  flex: 1;
  gap: 10px;
  align-items: flex-start;
  /* stop the tag stretching the full card width */
}

.card-body h3 {
  font-size: 1.05rem;
  margin: 0;
  line-height: 1.35;
}

.card-body p {
  color: var(--ink-2);
  font-size: .9rem;
  margin: 0;
}

.card-foot {
  margin-top: auto;
  padding-top: 12px;
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 8px;
  font-size: .8rem;
  color: var(--ink-3);
  font-family: var(--mono);
}

.card-foot .dot {
  width: 3px;
  height: 3px;
  border-radius: 50%;
  background: var(--ink-3);
  flex: none;
}

.card-author {
  color: var(--ink-2);
  text-decoration: none;
}

.card-author:hover {
  color: var(--s1);
  text-decoration: underline;
}

/* Category tag on a card. Hugs its text — .card-body is a flex column, so
   without align-self it would stretch edge to edge. */
.card-tag {
  align-self: flex-start;
  display: inline-block;
  font-family: var(--display);
  font-size: .78rem;
  line-height: 1.4;
  color: var(--ink-2);
  border: 1px solid var(--rule);
  border-radius: 100px;
  padding: 3px 11px;
  background: var(--panel);
  text-decoration: none;
  transition: border-color .15s ease, color .15s ease, background .15s ease;
}

a.card-tag:hover {
  border-color: var(--s1);
  color: var(--s1);
  background: var(--s1-wash);
}

.card-tag.is-static {
  color: var(--ink-3);
}

/* Category chips */
.cat-bar {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  margin-bottom: 32px;
}

.cat-chip {
  font-family: var(--display);
  font-size: .85rem;
  padding: 6px 14px;
  border: 1px solid var(--rule);
  border-radius: 100px;
  background: var(--panel);
  color: var(--ink-2);
  text-decoration: none;
  transition: border-color .15s ease, color .15s ease;
}

.cat-chip:hover {
  border-color: var(--ink-3);
  color: var(--ink);
}

.cat-chip.is-here {
  background: var(--ink);
  border-color: var(--ink);
  color: #fff;
}

.cat-chip span {
  color: var(--ink-3);
  font-size: .78rem;
  margin-left: 4px;
}

.cat-chip.is-here span {
  color: rgba(255, 255, 255, .6);
}

/* Search box */
.searchbar {
  display: flex;
  gap: 10px;
  max-width: 560px;
}

.searchbar input {
  flex: 1;
  min-width: 0;
  font: inherit;
  font-size: .96rem;
  padding: 12px 16px;
  border: 1px solid var(--rule);
  border-radius: var(--radius);
  background: var(--panel);
  color: var(--ink);
}

.searchbar input:focus {
  outline: 2px solid var(--s1);
  outline-offset: -1px;
  border-color: var(--s1);
}

/* Article hero image */
.article-shot {
  width: 100%;
  border-radius: var(--radius-lg);
  border: 1px solid var(--rule);
  display: block;
  margin-bottom: 34px;
}

/* Author card */
.author-card {
  display: flex;
  gap: 20px;
  align-items: flex-start;
  flex-wrap: wrap;
  padding: 24px;
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
}

.author-face {
  width: 68px;
  height: 68px;
  border-radius: 50%;
  flex: none;
  background: var(--ink);
  color: #fff;
  display: grid;
  place-items: center;
  font-family: var(--display);
  font-weight: 600;
  font-size: 1.3rem;
  line-height: 1;
  text-transform: uppercase;
  overflow: hidden;
  user-select: none;
}

img.author-face {
  object-fit: cover;
}

.author-card h3 {
  margin: 0 0 3px;
  font-size: 1.1rem;
}

.author-card .role {
  color: var(--ink-3);
  font-size: .87rem;
  margin: 0 0 10px;
}

.author-card p {
  color: var(--ink-2);
  font-size: .93rem;
  margin: 0;
  max-width: 62ch;
}

.author-links {
  display: flex;
  gap: 14px;
  margin-top: 12px;
  font-size: .87rem;
}

/* --- 11b. Pagination ----------------------------------------------------- */

.pager {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 10px;
  flex-wrap: wrap;
  margin-top: 48px;
}

.pager-list {
  display: flex;
  align-items: center;
  gap: 4px;
  list-style: none;
  margin: 0;
  padding: 0;
}

.pager-num,
.pager-step {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  font-family: var(--display);
  font-size: .9rem;
  font-weight: 500;
  text-decoration: none;
  color: var(--ink-2);
  border: 1px solid var(--rule);
  border-radius: var(--radius);
  background: var(--panel);
  transition: border-color .15s ease, color .15s ease, background .15s ease;
}

.pager-num {
  min-width: 38px;
  height: 38px;
  justify-content: center;
  padding: 0 10px;
}

.pager-step {
  height: 38px;
  padding: 0 14px;
}

.pager-num:hover,
.pager-step:hover {
  border-color: var(--ink-3);
  color: var(--ink);
}

.pager-num.is-here {
  background: var(--ink);
  border-color: var(--ink);
  color: #fff;
  cursor: default;
}

.pager-step.is-off {
  opacity: .42;
  cursor: not-allowed;
}

.pager-step.is-off:hover {
  border-color: var(--rule);
  color: var(--ink-2);
}

.pager-gap {
  display: inline-grid;
  place-items: center;
  min-width: 26px;
  height: 38px;
  color: var(--ink-3);
}

.pager-count {
  text-align: center;
  margin-top: 14px;
  font-size: .84rem;
  color: var(--ink-3);
  font-family: var(--mono);
}

@media (max-width: 560px) {

  .pager-step span,
  .pager-step {
    padding: 0 10px;
  }

  .pager-list {
    order: -1;
    width: 100%;
    justify-content: center;
  }
}

/* Empty state for listings that return nothing */
.nothing {
  text-align: center;
  padding: 60px 24px;
  border: 1px dashed var(--rule);
  border-radius: var(--radius-lg);
  background: var(--panel);
}

.nothing h3 {
  margin-bottom: 8px;
}

.nothing p {
  color: var(--ink-2);
  margin: 0 auto;
  max-width: 46ch;
}

/* --- 12. Careers --------------------------------------------------------- */

.job {
  display: flex;
  flex-wrap: wrap;
  gap: 14px;
  align-items: center;
  justify-content: space-between;
  padding: 22px 24px;
  border: 1px solid var(--rule);
  border-radius: var(--radius);
  background: var(--panel);
  margin-bottom: 12px;
  text-decoration: none;
  color: var(--ink);
  transition: border-color .15s ease;
}

.job:hover {
  border-color: var(--ink-3);
}

.job h3 {
  margin: 0 0 4px;
  font-size: 1.08rem;
}

.job .job-meta {
  color: var(--ink-2);
  font-size: .89rem;
}

.job .job-summary {
  color: var(--ink-2);
  font-size: .92rem;
  margin: 8px 0 0;
  max-width: 62ch;
}

.job .job-go {
  font-family: var(--display);
  font-size: .9rem;
  color: var(--s1);
  font-weight: 500;
  white-space: nowrap;
}

/* --- 13. Panels, notes, FAQ --------------------------------------------- */

.panel {
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  padding: 28px;
}

.panel-flat {
  border-radius: var(--radius);
  padding: 22px;
}

.note {
  border-left: 3px solid var(--s2);
  background: #FFF9EF;
  padding: 16px 20px;
  border-radius: 0 var(--radius) var(--radius) 0;
  font-size: .94rem;
  color: #4A3A1E;
}

.faq {
  border-top: 1px solid var(--rule);
}

.faq details {
  border-bottom: 1px solid var(--rule);
}

.faq summary {
  cursor: pointer;
  padding: 20px 40px 20px 0;
  font-family: var(--display);
  font-weight: 500;
  font-size: 1.05rem;
  list-style: none;
  position: relative;
}

.faq summary::-webkit-details-marker {
  display: none;
}

.faq summary::after {
  content: "";
  position: absolute;
  right: 8px;
  top: 50%;
  width: 11px;
  height: 11px;
  border-right: 1.5px solid var(--ink-3);
  border-bottom: 1.5px solid var(--ink-3);
  transform: translateY(-70%) rotate(45deg);
  transition: transform .18s ease;
}

.faq details[open] summary::after {
  transform: translateY(-30%) rotate(-135deg);
}

.faq .faq-body {
  padding: 0 60px 22px 0;
  color: var(--ink-2);
}

.faq .faq-body p:last-child {
  margin-bottom: 0;
}

/* Definition rows (about, security, legal contacts) */
.deflist {
  border-top: 1px solid var(--rule);
}

.defrow {
  display: grid;
  grid-template-columns: 220px 1fr;
  gap: 28px;
  padding: 20px 0;
  border-bottom: 1px solid var(--rule);
}

.defrow>b {
  font-family: var(--display);
  font-weight: 500;
}

.defrow>div {
  color: var(--ink-2);
}

@media (max-width: 720px) {
  .defrow {
    grid-template-columns: minmax(0, 1fr);
    gap: 6px;
  }
}

/* --- 14. Forms ----------------------------------------------------------- */

.field {
  margin-bottom: 18px;
}

.field label {
  display: block;
  font-family: var(--display);
  font-size: .9rem;
  font-weight: 500;
  margin-bottom: 6px;
}

.field .hint {
  font-size: .83rem;
  color: var(--ink-3);
  margin-bottom: 8px;
}

/* Match the workbench rather than inheriting each browser's own grey. The
   label carries the meaning; the placeholder is only an example. */
.input::placeholder,
.textarea::placeholder {
  color: var(--ink-3);
  opacity: 1;
}

.input,
.textarea,
.select {
  width: 100%;
  border: 1px solid var(--rule);
  border-radius: var(--radius);
  padding: 11px 13px;
  font: inherit;
  font-size: .97rem;
  background: var(--panel);
  color: var(--ink);
  transition: border-color .15s ease, box-shadow .15s ease;
}

.input:focus,
.textarea:focus,
.select:focus {
  outline: 0;
  border-color: var(--s1);
  box-shadow: 0 0 0 3px var(--s1-wash);
}

.textarea {
  min-height: 150px;
  resize: vertical;
  line-height: 1.6;
}

.error-text {
  color: #C2334F;
  font-size: .85rem;
  margin-top: 6px;
}

.flash {
  border: 1px solid #9FD9D0;
  background: var(--s3-wash);
  color: #0A6A5F;
  padding: 14px 18px;
  border-radius: var(--radius);
  margin-bottom: 24px;
  font-size: .95rem;
}

/* --- 15. Footer ---------------------------------------------------------- */

.footer {
  /* One step deeper than --ink so the footer separates from a dark CTA band
     instead of merging into one slab. Still reads as the same family. */
  background: #0A1622;
  color: #93A9BA;
  padding-top: 64px;
  font-size: .91rem;
}

/* Separator between the footer and whatever sits above it. The CTA band is the
   last child of <main>, and the footer is a sibling of <main> — not of the band
   — so `.band-ink + .footer` never matches. `:has()` reaches across instead.
   Against a light section the hairline reads as the footer's own top edge;
   against the dark CTA it is the seam that stops the two merging. */
.footer {
  border-top: 1px solid #223444;
}

/* Two dark blocks back to back need less air than a dark block after a light
   one, or the seam floats in the middle of an empty area. */
main:has(> .band-ink:last-child) + .footer {
  padding-top: 52px;
}

.footer h4 {
  color: #fff;
  font-size: .8rem;
  font-weight: 600;
  letter-spacing: .01em;
  margin-bottom: 14px;
}

.footer ul {
  list-style: none;
  margin: 0;
  padding: 0;
  display: grid;
  gap: 9px;
}

.footer a {
  color: #93A9BA;
  text-decoration: none;
}

.footer a:hover {
  color: #fff;
}

.footer-grid {
  display: grid;
  grid-template-columns: 1.5fr repeat(4, 1fr);
  gap: 40px 28px;
  padding-bottom: 52px;
  border-bottom: 1px solid #22384A;
}

.footer-brand .brand {
  color: #fff;
}

.footer-brand p {
  color: #7E96A9;
  max-width: 30ch;
  margin: 16px 0 0;
  font-size: .9rem;
}

.footer-base {
  display: flex;
  flex-wrap: wrap;
  gap: 12px 26px;
  align-items: center;
  padding: 24px 0 40px;
  font-size: .84rem;
  color: #7E96A9;
}

.footer-base nav {
  display: flex;
  flex-wrap: wrap;
  gap: 18px;
  margin-left: auto;
}

.social {
  display: flex;
  gap: 12px;
  margin-top: 22px;
}

.social a {
  border: 1px solid #2A4157;
  border-radius: var(--radius);
  padding: 7px;
  display: grid;
  place-items: center;
}

.social a:hover {
  border-color: #587A94;
}

@media (max-width: 900px) {
  .footer-grid {
    grid-template-columns: 1fr 1fr;
  }
}

@media (max-width: 560px) {
  /* Footer links are 18px of text with a 9px gap — a 27px pitch that is easy to
     mis-tap. Padding raises each target past the 24px minimum, and the gap is
     pulled in so the column keeps roughly its original rhythm. */
  .footer ul {
    gap: 2px;
  }

  .footer ul a {
    padding-block: 5px;
  }

  .footer-base nav a {
    padding-block: 4px;
  }

  .footer-grid {
    grid-template-columns: minmax(0, 1fr);
    gap: 30px;
  }

  .footer-base nav {
    margin-left: 0;
  }
}

/* --- 16. Page head ------------------------------------------------------- */

.pagehead {
  padding-block: clamp(38px, 4.6vw, 60px) clamp(22px, 2.6vw, 34px);
  border-bottom: 1px solid var(--rule);
  background: linear-gradient(180deg, #F5F7F8, var(--paper));
}

.pagehead h1 {
  max-width: 20ch;
}

.pagehead .lede {
  margin-top: 6px;
}

/* A band directly under a page head does not need a full section's worth of
   air above it: the head already ends in its own bottom padding, and the two
   stacking put ~150px of nothing between the title and the first content.
   `.band-tight` needs this too — it is a separate class, not a `.band`
   modifier, so it was missing the rule and the ten workbench pages kept the
   full 64px on top of the head's own 34px. */
.pagehead+.band,
.pagehead+.band-tight {
  padding-block-start: clamp(26px, 3vw, 40px);
}

/* The ten workbench pages go tighter still. The tool is the point of those
   pages, so the head's bottom padding is pulled in as well — together that
   takes the gap between the subhead and the composer from ~134px to ~50px of
   padding, which is what lifts the input box above the fold on a laptop.
   Applied as modifier classes in chart/shell.blade.php rather than with
   :has(), matching .pagehead-article / .pagehead-author. */
.pagehead-tool {
  padding-block-end: clamp(14px, 1.6vw, 22px);
}

.pagehead+.band-workbench {
  padding-block-start: clamp(18px, 2vw, 28px);
}

/* Article heads carry a byline and lead straight into the piece, so the title
   is set a step down from the marketing h1 and given a wider measure — at 20ch
   a normal headline wrapped to three lines of 56px type for no reason. */
/* An author name sits beside a 68px avatar, so the marketing h1 (up to 56px)
   overpowers it. This is a label, not a headline. */
.pagehead-author h1 {
  font-size: clamp(1.55rem, 2.7vw, 2.1rem);
  letter-spacing: -.022em;
  max-width: 100%;
}

/* A quieter section head, for listings that sit under a profile rather than
   opening a marketing section. */
.sec-head-sm h2 {
  font-size: clamp(1.15rem, 1.8vw, 1.4rem);
  letter-spacing: -.015em;
}

.pagehead-article h1 {
  font-size: clamp(1.95rem, 3.5vw, 2.75rem);
  max-width: 100%;
}

.pagehead-article .byline {
  margin-top: 20px;
}

.crumb {
  font-size: .85rem;
  color: var(--ink-3);
  margin-bottom: 18px;
  font-family: var(--display);
}

.crumb a {
  color: var(--ink-2);
  text-decoration: none;
}

.crumb a:hover {
  color: var(--s1);
}

/* --- 17. Utilities ------------------------------------------------------- */

.stack-6 {
  display: grid;
  gap: 6px;
}

.stack-12 {
  display: grid;
  gap: 12px;
}

.stack-20 {
  display: grid;
  gap: 20px;
}

.stack-32 {
  display: grid;
  gap: 32px;
}

.mt-8 {
  margin-top: 8px;
}

.mt-16 {
  margin-top: 16px;
}

.mt-24 {
  margin-top: 24px;
}

.mt-32 {
  margin-top: 32px;
}

.mt-40 {
  margin-top: 40px;
}

.mb-0 {
  margin-bottom: 0;
}

.mb-24 {
  margin-bottom: 24px;
}

.center {
  text-align: center;
}

.sr-only {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
  border: 0;
}

.skip {
  position: absolute;
  left: -9999px;
  top: 0;
  z-index: 100;
  background: var(--ink);
  color: #fff;
  padding: 12px 18px;
  border-radius: 0 0 var(--radius) 0;
}

.skip:focus {
  left: 0;
}

/* Sidebar nav used on legal and chart-maker pages.

   The nav itself must NOT be sticky. On both layouts the <aside> holds a panel
   below the nav; pinning only the nav left that panel in normal flow, so it
   scrolled up and rendered over the pinned links. The whole sidebar sticks as
   one unit instead — see .cols-side > aside below. */
.side-nav {
  font-size: .92rem;
}

.side-nav h4 {
  font-family: var(--display);
  font-size: .82rem;
  color: var(--ink-3);
  margin-bottom: 12px;
}

.side-nav ul {
  list-style: none;
  margin: 0;
  padding: 0;
  display: grid;
  gap: 2px;
  border-left: 1px solid var(--rule);
}

.side-nav a {
  display: block;
  padding: 6px 0 6px 16px;
  margin-left: -1px;
  border-left: 1px solid transparent;
  text-decoration: none;
  color: var(--ink-2);
}

.side-nav a:hover {
  color: var(--ink);
  border-left-color: var(--s1);
}

/* The sidebar sticks as a whole, so the nav and the panel under it travel
   together and can never overlap. */
.cols-side > aside {
  position: sticky;
  top: 90px;
  /* Never pin something taller than the screen: a sticky box does not scroll
     with the page, so anything past the fold would be unreachable. */
  max-height: calc(100vh - 110px);
  overflow-y: auto;
  overscroll-behavior: contain;
}

@media (max-width: 900px) {
  .cols-side > aside {
    position: static;
    max-height: none;
    overflow: visible;
  }

  .side-nav {
    margin-bottom: 8px;
  }
}

/* Logo strip / trust row without fake customer logos */
.metrics {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 1px;
  background: var(--rule);
  border-block: 1px solid var(--rule);
}

.metrics div {
  background: var(--paper);
  padding: 22px 24px;
}

.metrics b {
  display: block;
  font-family: var(--display);
  font-size: 1.5rem;
  font-weight: 600;
  letter-spacing: -.03em;
}

.metrics span {
  font-size: .87rem;
  color: var(--ink-2);
}

@media (max-width: 780px) {
  .metrics {
    grid-template-columns: 1fr 1fr;
  }
}

/* Draw-in for the hero chart: one orchestrated moment, nothing else */
.draw-line {
  stroke-dasharray: var(--len);
  stroke-dashoffset: var(--len);
  animation: draw 1.1s cubic-bezier(.22, .61, .36, 1) forwards;
}

@keyframes draw {
  to {
    stroke-dashoffset: 0;
  }
}

.grow-bar {
  transform-origin: bottom;
  animation: grow .62s cubic-bezier(.22, .61, .36, 1) backwards;
}

@keyframes grow {
  from {
    transform: scaleY(0);
  }
}

@media (prefers-reduced-motion: reduce) {
  .draw-line {
    stroke-dashoffset: 0;
    animation: none;
  }

  .grow-bar {
    animation: none;
  }
}

@media print {

  .masthead,
  .footer,
  .wb-form,
  .drawer {
    display: none;
  }

  body {
    background: #fff;
  }
}
/* --- 18. Accounts, auth and forms ---------------------------------------- */

/* Error counterpart to .flash. The contact page carried these three values as
   an inline style; they belong here now that five more pages need them. */
.flash-bad {
  border-color: #E4A9B6;
  background: #FDEEF1;
  color: #8E2436;
}

.flash-list {
  margin: 0;
  padding-left: 18px;
}

.flash-list li+li {
  margin-top: 4px;
}

/* A label with something on the right of it — "Password / Forgotten it?" */
.field-row {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 12px;
}

.field-aside {
  font-size: .85rem;
}

.check {
  display: flex;
  align-items: flex-start;
  gap: 10px;
  margin-bottom: 18px;
  font-size: .92rem;
  line-height: 1.5;
  color: var(--ink-2);
}

.check input {
  flex: none;
  width: 16px;
  height: 16px;
  margin-top: 3px;
  accent-color: var(--s1);
}

.form-legend {
  font-family: var(--display);
  font-size: 1.02rem;
  margin-bottom: 16px;
}

.btn-block {
  width: 100%;
  justify-content: center;
}

/* Comment boxes: .textarea's own 150px is taller than a comment needs. */
.textarea-sm {
  min-height: 96px;
}

.avatar-row {
  display: flex;
  align-items: center;
  gap: 14px;
}

/* min-width:0 or the file input's intrinsic width pushes the row wider than
   its column — the same floor that made the mobile grids overflow. */
.avatar-row .input {
  flex: 1;
  min-width: 0;
}

/* ---- The five account pages ---- */

.band-auth {
  padding-block: clamp(36px, 5vw, 64px);
}

.auth-card {
  max-width: 440px;
  margin-inline: auto;
  padding: clamp(24px, 3vw, 34px);
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
  box-shadow: var(--lift);
}

.auth-head {
  margin-bottom: 22px;
}

/* A form title, not a marketing headline — the layout's h1 runs to 56px. */
.auth-head h1 {
  font-size: clamp(1.5rem, 2.6vw, 1.9rem);
  margin-bottom: 8px;
}

.auth-sub {
  margin: 0;
  font-size: .94rem;
  color: var(--ink-2);
}

.auth-note {
  margin: 16px 0 0;
  font-size: .86rem;
  color: var(--ink-3);
}

.auth-alt {
  max-width: 440px;
  margin: 18px auto 0;
  text-align: center;
  font-size: .9rem;
  color: var(--ink-2);
}

/* ---- Member area ---- */

.pagehead-account h1 {
  font-size: clamp(1.55rem, 2.7vw, 2.1rem);
}

.stat-row {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: 12px;
}

.stat {
  display: block;
  padding: 16px 18px;
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius);
  text-decoration: none;
}

.stat:hover {
  border-color: var(--s1);
}

.stat b {
  display: block;
  font-family: var(--display);
  font-size: 1.6rem;
  font-weight: 600;
  letter-spacing: -.03em;
  color: var(--ink);
}

.stat span {
  font-size: .85rem;
  color: var(--ink-2);
}

@media (max-width: 640px) {
  .stat-row {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }
}

.badge {
  display: inline-block;
  padding: 3px 8px;
  border: 1px solid;
  border-radius: 100px;
  font-family: var(--display);
  font-size: .74rem;
  font-weight: 500;
  letter-spacing: .01em;
}

.badge-ok {
  color: #0A6A5F;
  background: var(--s3-wash);
  border-color: #9FD9D0;
}

.badge-warn {
  color: #7A4708;
  background: #FDF1E1;
  border-color: #EFCB97;
}

.badge-bad {
  color: #8E2436;
  background: #FDEEF1;
  border-color: #E4A9B6;
}

.contrib-list {
  display: grid;
  gap: 12px;
}

.contrib {
  padding: 16px 18px;
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius);
}

.contrib-top {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 10px;
  margin-bottom: 10px;
}

.contrib-meta {
  font-size: .83rem;
  color: var(--ink-3);
}

.contrib-text {
  margin: 0 0 10px;
  font-size: .95rem;
  overflow-wrap: anywhere;
}

.contrib-on {
  margin: 0;
  font-size: .86rem;
  color: var(--ink-2);
}

.contrib-note {
  margin: 10px 0 0;
  font-size: .83rem;
  color: var(--ink-3);
}

/* ---- Account menu in the masthead ---- */

.avatar-sm {
  width: 34px;
  height: 34px;
  font-size: .78rem;
}

/* The wrapper must not lay its button out on a text baseline.
   .acct is the flex item .masthead-end centres, and as a block container it
   established a line box: the trigger holds no text, so as an inline-flex box
   its baseline is its bottom edge, and the parent strut's descender was landing
   below it — a 41px button in a 48.7px wrapper, which centred the wrapper and
   left the avatar sitting 3.9px above both buttons beside it.

   The chart-makers .nav-item does not need this: its trigger has text, so its
   own baseline absorbs the descender. Scoped here rather than onto .nav-item
   so a working component is left alone. */
.acct {
  display: flex;
  align-items: center;
}

/* The trigger is the avatar and nothing else — no name, no chevron. 41px is
   the height of the "Make a chart" button beside it, so the two line up. */
.acct-trigger {
  padding: 0;
  border-radius: 50%;
  line-height: 0;
  transition: box-shadow .15s ease;
}

.acct-trigger .avatar {
  width: 41px;
  height: 41px;
  font-size: .82rem;
}

/* .nav-trigger signals hover and open with a background, which an avatar
   filling the button would cover. A ring reads through it. */
.acct-trigger:hover,
.acct-trigger:focus-visible,
.acct-trigger[aria-expanded="true"] {
  background: none;
  box-shadow: 0 0 0 2px var(--paper), 0 0 0 4px var(--rule);
}

.acct-trigger[aria-expanded="true"] {
  box-shadow: 0 0 0 2px var(--paper), 0 0 0 4px var(--s1);
}

/* The chart-makers panel sits inside .nav, so it picks up the
   `text-decoration: none` from `.nav a`. The account panel lives in
   .masthead-end, where that rule never reaches — which is why its links came
   out underlined. Scope it to the component so the panel stops depending on
   which ancestor it happens to be under. */
.nav-panel a,
.nav-panel button {
  text-decoration: none;
}

/* .nav-panel is a two-column 480px menu built for the chart makers; the
   account menu is a single narrow column, right-aligned to its trigger. */
.nav-panel-acct {
  min-width: 244px;
  left: auto;
  right: -12px;
  grid-template-columns: 1fr;
  padding: 8px;
}

/* Repeats the trigger — avatar, name, address — so the panel opens with a
   header rather than straight into a list of links. */
.acct-head {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 8px 10px 12px;
  margin: 0 0 6px;
  border-bottom: 1px solid var(--rule-soft);
  /* min-width:0 lets the long address ellipsize instead of widening the panel */
  min-width: 0;
}

.acct-head div {
  min-width: 0;
}

.acct-head b {
  display: block;
  font-family: var(--display);
  font-weight: 600;
  font-size: .92rem;
  line-height: 1.25;
  color: var(--ink);
}

.acct-head small {
  display: block;
  font-size: .78rem;
  line-height: 1.35;
  color: var(--ink-3);
  margin-top: 1px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.nav-panel-acct a {
  font-size: .92rem;
  font-weight: 500;
  color: var(--ink-2);
  padding: 9px 10px;
}

.nav-panel-acct a:hover {
  color: var(--ink);
}

/* Signing out is a different kind of action from navigating, so it is set
   apart rather than left as the fifth item in the list. */
.acct-out {
  margin-top: 6px;
  padding-top: 6px;
  border-top: 1px solid var(--rule-soft);
}

/* The panel is 244px wide and hangs off the trigger's right edge. On a phone
   the trigger sits well inboard — the CTA and the burger are to its right — so
   that anchor pushed the panel off the left of the screen (measured
   left: -51px at 375). Below the nav breakpoint it hangs from the masthead row
   instead, which .masthead-in { position: relative } in section 6 sets up.

   This block has to live HERE, after the base .nav-panel-acct rule, not in
   section 6's media query: a media query adds no specificity, so the later
   base rule was simply winning and the override did nothing. */
@media (max-width: 940px) {
  .acct {
    position: static;
  }

  .nav-panel-acct {
    top: calc(100% + 6px);
    right: var(--gut);
    left: auto;
  }
}

/* Sign out is a form button, so it has to be dressed as the links beside it. */
.nav-panel form button {
  display: block;
  width: 100%;
  text-align: left;
  padding: 9px 10px;
  border: 0;
  background: none;
  border-radius: var(--radius);
  font: inherit;
  font-family: var(--display);
  font-size: .92rem;
  font-weight: 500;
  color: var(--ink-2);
  cursor: pointer;
}

.nav-panel form button:hover {
  background: var(--paper);
  color: var(--ink);
}

/* --- 19. Discussion ------------------------------------------------------ */

.cmt-count {
  display: inline-block;
  margin-left: 6px;
  padding: 2px 9px;
  border-radius: 100px;
  background: var(--paper-deep);
  font-size: .7em;
  font-weight: 500;
  color: var(--ink-2);
  vertical-align: middle;
}

.cmt-form {
  padding: 16px;
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
}

.cmt-form-foot {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 12px;
  margin-top: 10px;
}

.cmt-gate {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 16px;
}

.cmt-gate-actions {
  display: flex;
  flex: none;
  gap: 8px;
}

.cmt-list {
  display: grid;
  gap: 18px;
  margin-top: 26px;
}

.cmt {
  padding: 16px 18px;
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--radius-lg);
}

/* Only its author sees this, so it should not look like everything else. */
.cmt.is-pending {
  border-style: dashed;
  background: transparent;
}

.cmt-top {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-bottom: 10px;
}

.cmt-who b {
  display: block;
  font-family: var(--display);
  font-size: .95rem;
  font-weight: 600;
}

.cmt-meta {
  font-size: .82rem;
  color: var(--ink-3);
}

.cmt-body {
  font-size: .96rem;
  line-height: 1.65;
  color: var(--ink-2);
  /* Pasted URLs must wrap rather than widen the page, as in .prose. */
  overflow-wrap: anywhere;
}

/* <details> rather than a scripted toggle, so replying still works with no JS. */
.cmt-reply {
  margin-top: 12px;
}

.cmt-reply>summary {
  display: inline-block;
  cursor: pointer;
  padding: 4px 10px;
  border: 1px solid var(--rule);
  border-radius: 100px;
  font-family: var(--display);
  font-size: .84rem;
  color: var(--ink-2);
  list-style: none;
}

.cmt-reply>summary::-webkit-details-marker {
  display: none;
}

.cmt-reply>summary:hover {
  color: var(--ink);
  border-color: var(--ink-3);
}

.cmt-form-inline {
  margin-top: 12px;
  padding: 0;
  border: 0;
  background: none;
}

.cmt-children {
  display: grid;
  gap: 14px;
  margin-top: 16px;
  padding-left: 16px;
  border-left: 2px solid var(--rule-soft);
}

/* A reply is nested inside a card already — it does not need a second one. */
.cmt-child,
.cmt-child.is-pending {
  padding: 0;
  border: 0;
  border-radius: 0;
  background: none;
}

.cmt-child.is-pending .cmt-body {
  color: var(--ink-3);
}

.nothing-sm {
  padding: 34px 24px;
  margin-top: 26px;
}

@media (max-width: 560px) {

  .cmt-gate,
  .cmt-gate-actions {
    display: block;
  }

  .cmt-gate-actions .btn {
    margin: 10px 8px 0 0;
  }
}
