/* ---------------------------------------------------------------------------
   page.css — the inner pages: legal, reporting, beta.

   Everything that is not the home page shares one shell, and the shell is the
   home page's: the same floating nav pill, the same footer, the same type
   scale. This file holds only what a *reading* page needs and the marketing
   page does not — a titled head band, a white document surface, long-form
   prose rhythm, and form controls on a light ground.

   Load order is brand.css → layout.css → components.css → landing.css →
   page.css, so the nav and the footer arrive from landing.css unchanged. That
   is the point: the chrome has one definition. Before this file the legal and
   reporting pages each carried their own <style> block with their own masthead,
   which is how they ended up on a different --ink from the rest of the site.

   Nothing here spells a colour or a container width of its own —
   test/core/utils/brand_css_parity_test.dart and
   scripts/build/test_landing_build.py both fail on a raw hex or a :root block
   anywhere under hosting_landing/.

   The marketing site has no Figma frame for any of these pages (the file is
   four 1440-wide keyframes of the home page and nothing else), so every
   measurement below is derived from the home page's own scale rather than
   transcribed. Where a value is a decision rather than a derivation it says so.
   --------------------------------------------------------------------------- */

/* ── One ground, painted once ──────────────────────────────────────────────
   The head band, the document and the footer are one surface on these pages,
   so the washes are painted on the page rather than on each of the three.

   They used to be per-section: the band carried the hero's pair over
   --surface-lift, .page-body was a flat --surface, and the footer carried the
   footer's pair. On the home page that reads as a sequence of sections; on a
   reading page the band is 390px tall, which cut the hero's washes off at
   full strength and put a hard line across the page where the two base
   colours met.

   Painted on body, so the positioning area is the whole document and the two
   pairs meet in the middle of it instead of at a section boundary. The
   vertical radii are lengths rather than percentages for the same reason a
   short band was the problem: a percentage here would resolve against the
   document, so the glow would be twice the size on the privacy policy and
   half of it on this page. The horizontal radii stay percentages — those do
   resolve against the viewport's width, which is what they did before.

   The angles and the colours are the ones the home page uses: violet right
   and amber left at the top, mirrored at the bottom, so the chrome still
   reads as the same site. */
body {
  background:
    radial-gradient(54% 420px at 74.4% 24px, var(--wash-violet), transparent),
    radial-gradient(100% 760px at 26.6% 10px, var(--wash-amber), transparent),
    radial-gradient(99% 420px at 73.8% 100%, var(--wash-violet), transparent),
    radial-gradient(89% 400px at 25.6% 100%, var(--wash-amber), transparent),
    var(--surface);
  background-repeat: no-repeat;
  /* A short page — the 404, a route list — would otherwise end above the fold
     and anchor the footer's pair somewhere up the screen. */
  min-height: 100vh;
}

/* ── The head band ─────────────────────────────────────────────────────────
   A band tall enough to clear the floating pill and no taller. A full hero
   would be the wrong promise on a privacy policy: the page's job is to be
   read, and the title is a label on it rather than a pitch. Its wash comes
   from the page now, so all this holds is the space. */
.page-head {
  padding-inline: var(--page-padding);
  /* The band and the document under it are one continuous read, so the space
     between them is a paragraph break rather than a section break — the two
     halves of it are 40 and 40, against the --section-pad-md the marketing page
     puts between things that are genuinely separate. */
  padding-block: calc(var(--nav-clear) + 40px) 40px;
  background: transparent;
}

.page-head__inner {
  display: flex;
  flex-direction: column;
  gap: 16px;
  max-width: var(--container-large);
  margin-inline: auto;
}

/* Running text caps at the measure token; a title does not, because a heading
   that wraps at 560px reads as a column of fragments. */
.page-head .lede { max-width: var(--max-width-md); }

.page-head__meta {
  font-family: var(--font-body);
  font-size: var(--text-sm);
  line-height: 1.5;
  color: var(--muted-soft);
  margin: 0;
}

/* ── The body ──────────────────────────────────────────────────────────────
   One column on --surface, so the white document surface separates from the
   page the way a card does on the home page. */
.page-body {
  padding-inline: var(--page-padding);
  padding-block: 40px var(--section-pad-md);
  background: transparent;
}

/* landing.css paints the footer's two washes over --surface. On a reading page
   that pair is already in the body background above, anchored to the same
   bottom edge, so leaving this one on would paint it twice and put the hard
   edge back — at the top of the footer this time. The footer keeps its
   spacing, its divider and its type; only the ground is the page's. */
.site-footer { background: transparent; }

.page-body__inner {
  max-width: var(--container-large);
  margin-inline: auto;
}

/* A reading column, not the 1280 container. 760px is about 85 characters of
   Inter at 16.5px, which is the top of the comfortable range and the width
   the policy pages were already set at. */
.page-body--narrow .page-body__inner { max-width: 760px; }

/* The document surface. Deliberately NOT .card: that class is the marketing
   card — a 40px radius and a --border-card hairline sized for artwork that
   bleeds to its edge — and a fourteen-section privacy policy inside one reads
   as a component rather than a document. */
.doc {
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-24);
  box-shadow: var(--shadow-card);
  padding: 44px;
}

.doc > :first-child { margin-top: 0; }
.doc > :last-child  { margin-bottom: 0; }

/* ── Long-form prose ───────────────────────────────────────────────────────
   Scoped under .doc rather than set on the elements, so the marketing page's
   own headings — which are class-driven and live outside any .doc — are never
   reached by it.

   The sizes are the policy pages' own, kept: 15.5px at 1.7 is a deliberately
   denser setting than the marketing body copy, because these pages are read
   rather than scanned and the alternative is a policy four screens longer. */
.doc h2 {
  font-family: var(--font-display);
  font-size: 22px;
  line-height: 1.3;
  font-weight: 700;
  letter-spacing: normal;
  color: var(--ink);
  margin: 40px 0 12px;
}

.doc h3 {
  font-family: var(--font-body);
  font-size: 16.5px;
  font-weight: 700;
  line-height: 1.45;
  color: var(--ink);
  margin: 26px 0 8px;
}

.doc p,
.doc li {
  font-family: var(--font-body);
  font-size: 15.5px;
  line-height: 1.7;
  color: var(--ink-body);
}

.doc p  { margin: 0 0 14px; }
.doc ul,
.doc ol { padding-left: 22px; margin: 0 0 14px; }
.doc li { margin-bottom: 10px; }
.doc li strong,
.doc p strong { color: var(--ink); font-weight: 600; }

.doc a { color: var(--brand); }
.doc a:hover { color: var(--brand-dark); }

/* Every heading a table of contents can reach has to clear the fixed pill.
   landing.css already sets scroll-padding-top on the root for the home page's
   in-page anchors; this is the same number reaching a <section id>. */
.doc section { scroll-margin-top: calc(var(--nav-clear) + 24px); }
.doc section:first-of-type h2 { margin-top: 0; }

/* An address block inside a policy. Named for the document rather than for
   what it holds, because `.contact` is already the home page's CTA section and
   the two would collide the moment a policy page loaded landing.css — which is
   now every policy page. */
.doc-contact {
  font-style: normal;
  margin: 0 0 14px;
  font-family: var(--font-body);
  font-size: 15.5px;
  line-height: 1.7;
  color: var(--ink-body);
}

.doc-contact strong { color: var(--ink); }

/* The copyright line at the foot of a policy, inside the document surface and
   distinct from the site footer below it. */
.doc-footnote,
.doc .doc-footnote {
  margin: 40px 0 0;
  padding-top: 20px;
  border-top: 1px solid var(--border);
  font-family: var(--font-body);
  font-size: 13px;
  line-height: 1.55;
  color: var(--muted);
}

/* ── Table of contents ─────────────────────────────────────────────────────
   Two columns of section links at the top of a policy. Anchors matter here:
   support and the app both need to point at a single clause rather than the
   top of a fourteen-section document. */
.toc {
  background: var(--brand-wash);
  border: 1px solid var(--brand-hairline);
  border-radius: var(--radius-12);
  padding: 20px 24px;
  margin: 0 0 36px;
}

.toc h2 {
  font-family: var(--font-body);
  font-size: 13px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--muted);
  font-weight: 700;
  margin: 0 0 12px;
}

.toc ol {
  margin: 0;
  padding: 0;
  list-style: none;
  columns: 2;
  column-gap: 32px;
}

.toc li {
  margin: 0 0 8px;
  break-inside: avoid;
  font-size: var(--text-sm);
  line-height: 1.45;
}

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

.toc a:hover { color: var(--brand); text-decoration: underline; }

/* ── A row of destinations ─────────────────────────────────────────────────
   The legal hub and the reporting hub are both a short list of places to go
   next. One treatment, because they are the same thing. */
.route-list {
  display: flex;
  flex-direction: column;
  gap: 12px;
  margin: 28px 0 0;
}

.route {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
  padding: 18px 20px;
  border: 1px solid var(--border);
  border-radius: var(--radius-12);
  text-decoration: none;
  background: var(--card);
  transition: border-color 0.15s ease, box-shadow 0.15s ease;
}

.route:hover {
  border-color: var(--brand);
  box-shadow: var(--shadow-xs);
}

.route__text { display: flex; flex-direction: column; gap: 5px; min-width: 0; }

.route__title {
  font-family: var(--font-body);
  font-weight: 700;
  font-size: 16.5px;
  line-height: 1.4;
  color: var(--ink);
}

.route__desc {
  font-family: var(--font-body);
  font-size: var(--text-sm);
  line-height: 1.55;
  color: var(--muted);
}

/* The chevron is drawn rather than exported: arrow-right.svg is the button
   arrow and is tinted for a 50px text button, and a second SVG request for one
   character is a request nobody needs. */
.route__chevron {
  flex: none;
  color: var(--muted-soft);
  font-size: 20px;
  line-height: 1;
}

/* The way back up one level, under a document rather than over it: a person
   reads the page first and leaves afterwards, and a back link above the title
   competes with the title. */
.backlink-row {
  margin: 22px 0 0;
  font-family: var(--font-body);
  font-size: var(--text-sm);
  line-height: 1.5;
}

.backlink-row a {
  color: var(--brand);
  text-decoration: none;
  font-weight: 600;
}

.backlink-row a:hover { text-decoration: underline; }

/* ── A callout ─────────────────────────────────────────────────────────────
   Something the reader must take in before they act on the page: the NCII
   route's emergency guidance, the counter-notice's jurisdiction warning, the
   beta form's identity-document requirement. */
.callout {
  background: var(--brand-wash);
  border: 1px solid var(--brand-hairline);
  border-radius: var(--radius-12);
  padding: 14px 16px;
  margin: 0 0 24px;
  font-family: var(--font-body);
  font-size: var(--text-sm);
  line-height: 1.55;
  color: var(--ink-body);
}

.callout strong { color: var(--ink); }
.callout a { color: var(--brand); }
.callout :last-child { margin-bottom: 0; }

/* An amber-edged callout is the warning voice. Transparent rather than tinted
   so it does not read as a second brand surface next to the indigo one. */
.callout--warn {
  background: transparent;
  border-color: var(--warning-soft);
}

/* ── Small print under a form or a card ──────────────────────────────────────
   The disclaimer voice, and it is the same size and rhythm as .hint — the two
   are the same kind of line and reading at two different sizes made the one
   under the button look like body copy that had lost its paragraph.

   Scoped under .doc as well as on its own, because `.doc p` is one element
   more specific than a bare class: without the pair this silently took the
   prose size wherever it sat inside a document surface, which is every form on
   the site. Same for .err and .doc-footnote below, and
   test_landing_build.py::test_a_class_on_doc_prose_outranks_the_prose_rule
   fails on the next class that forgets.

   The top margin is deliberately larger than the gap between form rows. It
   follows a full-width button, and small print tight under an action reads as
   a consequence of pressing it. */
.formnote,
.doc .formnote {
  font-family: var(--font-body);
  font-size: 13px;
  line-height: 1.5;
  color: var(--muted);
  margin: 28px 0 0;
}

.formnote a { color: var(--brand); }

/* ── Form controls on a light ground ───────────────────────────────────────
   components.css's .field is the CTA card's input and is white-on-dark by
   design — there is no light-background variant of it, because on the home
   page there is no light form. These are that variant, and they are element
   selectors scoped under .doc rather than a second .field class: the two
   would collide by name on any page that loaded both stylesheets, and the
   report pages now do. */
.doc fieldset { border: 0; margin: 0; padding: 0; }

.doc legend {
  font-family: var(--font-body);
  font-weight: 700;
  font-size: 16.5px;
  line-height: 1.45;
  color: var(--ink);
  padding: 0;
  margin-bottom: 14px;
}

.form-row { margin-bottom: 22px; }

.form-row > label,
.form-label {
  display: block;
  font-family: var(--font-body);
  font-weight: 600;
  font-size: 14.5px;
  line-height: 1.5;
  color: var(--ink);
  margin-bottom: 6px;
}

.hint {
  display: block;
  font-weight: 400;
  font-size: 13px;
  line-height: 1.5;
  color: var(--muted);
  margin-top: 3px;
}

.doc input[type="text"],
.doc input[type="email"],
.doc input[type="tel"],
.doc textarea {
  width: 100%;
  font-family: var(--font-body);
  font-size: 15px;
  line-height: 1.5;
  color: var(--ink);
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-8);
  padding: 11px 13px;
}

.doc textarea {
  min-height: 104px;
  resize: vertical;
}

.doc input:focus,
.doc textarea:focus {
  outline: none;
  border-color: var(--brand);
  box-shadow: 0 0 0 3px var(--brand-tint);
}

/* ── A row of radio choices ────────────────────────────────────────────────
   Rendered as cards rather than bare radios: on a phone a 17px radio with a
   label beside it is a target nobody can hit reliably, and the whole row is
   the label here. */
.choices {
  display: flex;
  flex-wrap: wrap;
  gap: 12px;
}

.choice {
  display: flex;
  align-items: center;
  gap: 10px;
  flex: 1 1 180px;
  padding: 13px 16px;
  border: 1px solid var(--border);
  border-radius: var(--radius-12);
  background: var(--card);
  cursor: pointer;
  transition: border-color 0.15s ease, background-color 0.15s ease;
}

.choice input {
  flex: none;
  width: 18px;
  height: 18px;
  margin: 0;
  accent-color: var(--brand);
}

.choice span {
  font-family: var(--font-body);
  font-size: 15px;
  line-height: 1.4;
  color: var(--ink);
}

.choice:hover { border-color: var(--tertiary-border); }
.choice:has(input:checked) {
  border-color: var(--brand);
  background: var(--brand-wash);
}

/* :has() is recent enough to need a fallback that is not "no selected state at
   all" — but only where it is actually missing. Applied unconditionally the
   ring would double up with the card highlight everywhere else, which reads as
   a focus state on a control nobody is focusing. */
@supports not selector(:has(*)) {
  .choice input:checked {
    outline: 2px solid var(--brand);
    outline-offset: 2px;
  }
}

/* ── A checkbox row ────────────────────────────────────────────────────────
   The consent tick on the beta form and the attestations on the three legal
   intake forms are the same control. Larger hit area than a bare checkbox
   because on the intake forms ticking one is a statement under penalty of
   perjury, not a preference. */
.check {
  display: flex;
  gap: 12px;
  align-items: flex-start;
  border: 1px solid var(--border);
  border-radius: var(--radius-12);
  padding: 14px 16px;
  margin-bottom: 14px;
  cursor: pointer;
}

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

.check span {
  font-family: var(--font-body);
  font-size: var(--text-sm);
  line-height: 1.55;
  color: var(--ink-body);
}

.check a { color: var(--brand); }

/* ── The submit button on a light form ─────────────────────────────────────
   Full width and 48 tall rather than the home page's 40px rail: this is the
   only action on the page, and .btn is sized to sit in a nav pill beside a
   wordmark.

   --brand-dark, which is .btn--primary's fill and therefore the nav pill's
   button eight inches above it. The site has one filled indigo action and it
   should be one colour; it used to sit a slot lighter on --brand, which read
   as a second, weaker blue rather than the same button doing a second job.
   Hover is left to .btn's brightness step for that reason too — the old
   override darkened to --brand-dark, which is now where it starts. */
.btn--submit {
  width: 100%;
  height: 48px;
  background: var(--brand-dark);
  color: var(--card);
  margin-top: 8px;
}
.btn--submit[disabled] { opacity: 0.6; cursor: default; filter: none; transform: none; box-shadow: none; }

/* ── The honeypot ──────────────────────────────────────────────────────────
   Off-screen rather than display:none — some automated fillers skip hidden
   inputs but not positioned ones. aria-hidden and tabindex keep it away from
   anybody using a screen reader or the keyboard. */
.hp {
  position: absolute;
  left: -9999px;
  width: 1px;
  height: 1px;
  overflow: hidden;
}

/* ── Validation feedback ───────────────────────────────────────────────────── */
.err,
.doc .err {
  font-family: var(--font-body);
  color: var(--danger);
  font-size: 13px;
  line-height: 1.5;
  margin: 6px 0 0;
  display: none;
}

.err.show { display: block; }

.form-row.invalid input,
.form-row.invalid textarea { border-color: var(--danger); }
.check.invalid,
.choice.invalid { border-color: var(--danger); }

.summary {
  border: 1px solid var(--danger);
  border-radius: var(--radius-12);
  padding: 14px 16px;
  margin-bottom: 22px;
  display: none;
}

.summary.show { display: block; }

.summary p {
  margin: 0 0 8px;
  font-family: var(--font-body);
  font-weight: 600;
  font-size: 14.5px;
  line-height: 1.5;
  color: var(--danger);
}

.summary ul { margin: 0; padding-left: 20px; }
.summary li { font-size: var(--text-sm); line-height: 1.55; color: var(--ink-body); }

/* A result replaces the form rather than sitting above it: after a successful
   filing there is nothing left to do on the page, and leaving a populated form
   on screen invites a second identical notice. */
.result { display: none; }
.result.show { display: block; }

.result h2 {
  font-family: var(--font-display);
  font-size: 22px;
  line-height: 1.3;
  margin: 0 0 10px;
}

.reference {
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
  font-size: 15px;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius-8);
  padding: 12px 14px;
  margin: 14px 0;
  word-break: break-all;
  color: var(--ink);
}

/* ── Steps ───────────────────────────────────────────────────────────────── */
@media (max-width: 767px) {
  .page-head { padding-block: calc(var(--nav-clear) + 24px) var(--section-pad-md); }

  /* 44px of padding on each side of a 350px page leaves 262 for the text. The
     surface keeps its border and its radius — it is still a document — but it
     stops paying for margins the screen edge is already providing. */
  .doc { padding: 28px 20px; border-radius: var(--radius-12); }

  .toc ol { columns: 1; }
  .toc { padding: 16px 18px; }

  .route { padding: 16px; }

  /* Two 180px choices plus the gap need 372, which overflows a 350px page
     before the document's own padding is paid for. */
  .choices { flex-direction: column; }
  .choice { flex: 0 0 auto; }
}

/* ── Print ─────────────────────────────────────────────────────────────────
   A policy is the one kind of page here that gets printed and filed. The
   chrome goes: a floating nav pill and a marketing footer are furniture, and
   on paper the document is the whole point. */
@media print {
  /* The shorthand clears all four washes. min-height is separate and has to
     go too, or a short page reserves a screenful and prints a blank second
     sheet. */
  body { background: var(--card); min-height: auto; }

  .site-nav,
  .site-footer,
  .skip-link,
  .toc { display: none; }

  /* The head band keeps its title and loses its wash: the h1 is the document's
     name and is the one thing a filed printout must carry. */
  .page-head {
    padding: 0 0 24px;
    background: var(--card);
  }

  .page-body { padding: 0; background: var(--card); }

  .doc {
    border: 0;
    box-shadow: none;
    padding: 0;
  }

  .doc p,
  .doc li { font-size: 11pt; }
  .doc h2 { break-after: avoid; }
}
