/* Stellaria institutional design tokens.
   Authored to the Stellaria specification (package not installed in this project).
   One accent, two type families, hairline borders, tint-step elevation, no shadows
   beyond the focus ring, OKLCH palette tinted toward 260deg. */

:root {
  /* ── Palette (OKLCH, tinted toward the institutional blue 260deg) ─────────── */
  --c-bg:          oklch(0.17 0.012 260);   /* off-black canvas, never #000 */
  --c-surface:     oklch(0.21 0.014 260);   /* panel: one tint step up */
  --c-surface-2:   oklch(0.25 0.016 260);   /* raised panel / hover */
  --c-surface-3:   oklch(0.29 0.018 260);   /* control fill */
  --c-border:      oklch(0.34 0.018 260);   /* hairline */
  --c-border-soft: oklch(0.28 0.016 260);   /* fainter hairline */

  --c-white:       oklch(0.97 0.006 260);   /* off-white, never #fff */
  --c-text:        oklch(0.94 0.006 260);
  --c-text-dim:    oklch(0.74 0.010 260);
  --c-text-faint:  oklch(0.63 0.012 260);  /* 0.58 measured 4.2:1 on cards; 0.63 clears 4.5 */

  --c-accent:      oklch(0.62 0.20 260);    /* institutional blue */
  --c-accent-hi:   oklch(0.72 0.19 260);
  --c-accent-dim:  oklch(0.52 0.16 260);
  --c-accent-ghost: oklch(0.62 0.20 260 / 0.12);
  --c-accent-line:  oklch(0.62 0.20 260 / 0.32);

  /* Text/icons sitting ON the solid accent — stays light in both themes. */
  --c-on-accent:   oklch(0.98 0.006 260);
  --c-accent-solid: oklch(0.50 0.19 260);   /* accent for small white text: 6:1, where --c-accent is 3.5:1 */
  --c-danger-solid: oklch(0.53 0.19 25);    /* danger for small white text: 5:1, where --c-danger is 3.3:1 */
  --c-danger-text:  oklch(0.69 0.19 25);    /* red TEXT on a danger tint: 5.1:1, where --c-danger is 4.35 there */

  /* Restrained second telemetry hue for outbound vs inbound differentiation.
     Muted amber, used only paired with a text/label so color is never the sole signal. */
  --c-out:         oklch(0.74 0.12 70);
  --c-out-ghost:   oklch(0.74 0.12 70 / 0.12);

  /* ── Status scale ─────────────────────────────────────────────────────────
     Used for certificate validity (README §30) and dark-vessel confidence
     (§16). Every one of these is always paired with a text label and, for
     certificates, a glyph — colour is never the only signal, so the scale still
     reads for a colour-blind user and in greyscale print.

     --c-unknown is the important one: "we hold no record" is a real state and
     must look distinctly neutral, never like a failure (Rules 4 and 5). */
  --c-ok:          oklch(0.72 0.15 155);   /* valid */
  --c-ok-ghost:    oklch(0.72 0.15 155 / 0.13);
  --c-warn:        oklch(0.78 0.14 75);    /* expiring soon / suspicious */
  --c-warn-ghost:  oklch(0.78 0.14 75 / 0.13);
  --c-danger:      oklch(0.65 0.19 25);    /* expired / probable dark */
  --c-danger-ghost: oklch(0.65 0.19 25 / 0.13);
  /* Measured against the panel it sits on: 0.60 gave 4.49:1, just under AA,
     and the light theme's 0.58 gave 4.22:1. "We hold no record" is one of the
     states this application most needs a reader to actually read, so it is not
     a place to be a hair under the line. 0.66 is 5.70:1 here. The token is only
     ever a foreground or a border - the 10% ghost is the background - so this
     changes nothing that sits under light text. */
  --c-unknown:     oklch(0.66 0.012 260);  /* no record held */
  --c-unknown-ghost: oklch(0.66 0.012 260 / 0.10);

  /* Observed vs inferred — the distinction README §72 calls essential. */
  --c-observed:    oklch(0.70 0.16 235);
  --c-inferred:    oklch(0.76 0.13 320);
  --c-inferred-ghost: oklch(0.76 0.13 320 / 0.14);

  /* ── Chart ground ─────────────────────────────────────────────────────────
     Land against water, for a page that draws a chart rather than a panel. The
     surface steps above are one tint step apart, which is right for a card on a
     background and wrong here: on a chart "which of that is land" is the first
     thing read and has to separate at a glance. In the dark theme these ARE the
     surface steps, which measured well; the light theme needs its own pair,
     because every light surface sits between L 0.855 and 0.995. */
  --c-chart-sea:   var(--c-bg);
  --c-chart-land:  var(--c-surface-2);
  --c-chart-coast: var(--c-border);

  /* And the ink for drawing ON a chart. These two do NOT flip with the theme,
     because the chart's ground does not either: the tile basemap is a light map
     in both themes and the night chart is dark in both, so what reads over it
     has to be chosen from what is underneath rather than from the panels. Same
     values as the strongest foreground of each theme. */
  --c-chart-ink-light: oklch(0.24 0.03 260);   /* over a light chart */
  --c-chart-ink-dark:  oklch(0.97 0.006 260);  /* over a dark chart */

  color-scheme: dark;

  /* ── Type ─────────────────────────────────────────────────────────────────── */
  --font-display: 'Host Grotesk', system-ui, -apple-system, sans-serif;
  --font-mono:    'Geist Mono', ui-monospace, 'SF Mono', Menlo, monospace;

  --fs-eyebrow: 0.6875rem;
  --fs-label:   0.75rem;
  --fs-body:    0.9375rem;
  --fs-lead:    1.0625rem;
  --fs-h3:      1.25rem;
  --fs-h2:      1.625rem;
  --fs-h1:      2.25rem;
  --fs-data-lg: 2rem;
  --fs-data-xl: 2.75rem;

  --measure-body: 66ch;
  --measure-lead: 54ch;

  /* ── Spacing ──────────────────────────────────────────────────────────────── */
  --sp-1: 0.25rem;
  --sp-2: 0.5rem;
  --sp-3: 0.75rem;
  --sp-4: 1rem;
  --sp-5: 1.5rem;
  --sp-6: 2rem;
  --sp-7: 3rem;
  --sp-8: 4rem;

  /* ── Radius (max 8px; pill is the named exception) ────────────────────────── */
  --r-1: 3px;
  --r-2: 5px;
  --r-3: 8px;
  --r-pill: 999px;

  /* ── Focus (the only permitted shadow) ────────────────────────────────────── */
  --shadow-focus: 0 0 0 2px var(--c-bg), 0 0 0 4px var(--c-accent);

  /* ── Motion ───────────────────────────────────────────────────────────────── */
  --ease-out: cubic-bezier(0.16, 1, 0.3, 1);
  --ease-in-out: cubic-bezier(0.65, 0, 0.35, 1);
  --dur-1: 120ms;
  --dur-2: 220ms;
  --dur-3: 420ms;
}

/* ── Light theme ────────────────────────────────────────────────────────────────
   Only the palette flips; type, spacing, radius and motion are shared. The accent
   is nudged slightly darker so it reads on a light ground. Applied when the root
   carries data-theme="light" (set from the user's saved preference). */
:root[data-theme="light"] {
  --c-bg:          oklch(0.955 0.008 260);  /* light gray-blue canvas */
  --c-surface:     oklch(0.995 0.003 260);  /* near-white panel */
  --c-surface-2:   oklch(0.975 0.006 260);  /* raised panel / hover */
  --c-surface-3:   oklch(0.945 0.009 260);  /* control fill */
  --c-border:      oklch(0.855 0.014 260);  /* hairline */
  --c-border-soft: oklch(0.905 0.011 260);  /* fainter hairline */

  --c-white:       oklch(0.24 0.03 260);    /* strongest foreground (now dark) */
  --c-text:        oklch(0.31 0.024 260);
  --c-text-dim:    oklch(0.44 0.02 260);   /* 0.47 measured 4.0:1 on a warn-tinted cell */
  --c-text-faint:  oklch(0.52 0.016 260);  /* darker than 0.58 so small labels clear 4.5 on white */

  --c-accent:      oklch(0.52 0.22 260);    /* institutional blue, darker for light */
  --c-accent-hi:   oklch(0.45 0.22 260);
  --c-accent-dim:  oklch(0.62 0.15 260);
  --c-accent-solid: oklch(0.48 0.22 260);
  --c-danger-solid: oklch(0.48 0.20 25);
  --c-danger-text:  oklch(0.52 0.20 25);
  --c-accent-ghost: oklch(0.52 0.22 260 / 0.10);
  --c-accent-line:  oklch(0.52 0.22 260 / 0.22);

  /* --c-on-accent stays light (white on blue) — inherited from :root. */

  --c-out:         oklch(0.56 0.14 60);
  --c-out-ghost:   oklch(0.56 0.14 60 / 0.12);

  /* Status scale, darkened so each still carries against a light ground. */
  --c-ok:          oklch(0.47 0.14 155);   /* 0.52 was 4.15:1 as small text on the ok tint (axe, light theme); 0.47 is 5.0 */
  --c-ok-ghost:    oklch(0.52 0.15 155 / 0.12);
  --c-warn:        oklch(0.50 0.12 70);    /* 0.58 amber read 2.6:1 as a value and 3.9:1 in a note */
  --c-warn-ghost:  oklch(0.58 0.13 70 / 0.13);
  --c-danger:      oklch(0.52 0.20 25);
  --c-danger-ghost: oklch(0.52 0.20 25 / 0.11);
  --c-unknown:     oklch(0.50 0.014 260);  /* 5.91:1 on the light panel */
  --c-unknown-ghost: oklch(0.50 0.014 260 / 0.10);

  --c-observed:    oklch(0.50 0.17 235);
  --c-inferred:    oklch(0.52 0.16 320);
  --c-inferred-ghost: oklch(0.52 0.16 320 / 0.12);

  /* Chart ground: a pale blue for the water and a quiet warm grey for the land,
     the one place this palette leaves 260deg — a mariner reads land and sea
     apart before anything else, and two neutrals a tint step apart do not. The
     coast is the darker hairline between them. */
  --c-chart-sea:   oklch(0.905 0.030 240);
  --c-chart-land:  oklch(0.800 0.014 100);
  --c-chart-coast: oklch(0.520 0.020 100);

  color-scheme: light;
}


/* ── Touch targets ──────────────────────────────────────────────────────────
   44px is the smallest thing a finger hits reliably, and the controls below are
   half that at rest: sort headers 17px tall, segmented filters 28px, icon
   buttons 32px square. Raised only where the pointer is coarse, so no desktop
   layout moves.

   These live here, in the one stylesheet every page loads, because they were in
   app.css — which only the globe loads, so the dashboard, the dark-vessel list,
   the vessel record and the Bridge never got them. A minimum target size is a
   property of the design system rather than of one page.

   Every selector carries a leading `:root` on purpose. This file is loaded
   first on every page, so a rule of equal specificity in app.css, dashboard.css
   or intel.css — `.segmented button { min-height: 28px }` — would win on order
   alone, and these rules would apply to nothing at all. `:root` adds the one
   point of specificity that settles it without reaching for !important. */
/* A calm notice across the top of a page (js/lib/notices.js): amber ground, one paragraph, a close button. */
.notice-bar {
  display: flex; align-items: flex-start; gap: var(--sp-3);
  padding: var(--sp-3) var(--sp-5);
  background: var(--c-warn-ghost); border-bottom: 1px solid var(--c-warn);
  color: var(--c-text); font-size: var(--fs-label); line-height: 1.5;
}
.notice-bar p { margin: 0; flex: 1; }
.notice-bar__close {
  flex: none; width: 28px; height: 28px; display: grid; place-items: center;
  background: transparent; border: 1px solid transparent; border-radius: var(--r-2);
  color: var(--c-text-dim); font-size: 1.2rem; line-height: 1; cursor: pointer;
}
.notice-bar__close:hover { color: var(--c-text); border-color: var(--c-border); }
@media print { .notice-bar { display: none; } }

@media (pointer: coarse) {
  :root .segmented button { min-height: 44px; padding-inline: var(--sp-3); }
  :root .th-sort { min-height: 44px; }
  :root .btn, :root .icon-btn, :root .homebtn, :root .btn--sm { min-height: 44px; }
  /* The top bar's own ways home: the Globe link was 33px wide and the logo 30px square, a finger's width short of the 40px the
     handbook promises for every control there. */
  :root .homebtn, :root .brandlink { min-width: 44px; justify-content: center; }
  :root .brandlink { min-height: 44px; }
  :root .btn--sm { padding-inline: var(--sp-3); }
  /* The Bridge and the voyage optimiser name their own controls, and the
     sign-in page is the first screen a phone ever sees. */
  :root .cb-hbtn, :root .cb-home, :root .cb-refuge-btn, :root .hdr-back { min-width: 44px; min-height: 44px; }
  :root .auth-input, :root .input, :root select { min-height: 44px; }
  :root .pw-toggle { min-width: 44px; min-height: 44px; }
  /* "Forgot your password?" and "Create an account" were 16px-tall words and the vessel record's tabs
     40px: a thumb's worth of hit area around them, with the negative margin keeping the layout as it was. */
  :root .auth-alt a { display: inline-block; padding: 14px 8px; margin: -14px -8px; }
  :root .sheet__tab { min-height: 44px; }
  :root .notice-bar__close { width: 44px; height: 44px; }
  /* A 16px-tall slider is a 16px-tall target; the thumb is what the finger
     finds, so the track is given room around it rather than made thicker. */
  :root input[type="range"] { min-height: 44px; }
  :root .tip-help { min-width: 28px; min-height: 28px; }
  :root input[type="checkbox"], :root input[type="radio"] { width: 20px; height: 20px; }
  :root label:has(> input[type="checkbox"]), :root label:has(> input[type="radio"]) {
    min-height: 44px; display: flex; align-items: center;
  }
}


/* Forced colours (Windows High Contrast): the box-shadow focus ring is dropped by the browser, so the ring is an outline.
   The colour is the system's (Highlight), which the mode would force anyway. */
@media (forced-colors: active) {
  :focus-visible { outline: 2px solid Highlight !important; outline-offset: 2px; }
  /* A selected tab was a tint or an accent underline. The mode keeps weight, underline and border width. */
  [role="tab"][aria-selected="true"] { font-weight: 700; text-decoration: underline; text-decoration-thickness: 2px; text-underline-offset: 5px; border-bottom: 3px solid Highlight; }
  /* Bars, dots, swatches and switches are drawn with a background colour and nothing else; they keep the colour they were
     given. (Their numbers and labels are text, which the mode leaves alone.) */
  .hbar__seg, .legend i, .brow__track, .brow__fill, .wrow__track, .wrow__fill, .bar-inline, .jobbar__track, .jobbar__fill,
  .dot, .tl-row__dot, .confidence__dot, .viz-key__swatch, .cb-badge__dot, .cb-gauge__bar, .cb-gauge__fill, .cb-progress,
  .cb-progress__bar, .cb-bars__bar, .cb-oil-bar, .cb-oil-bar > i, .cb-oil-swatch, .mp-track, .mp-track__win, .mp-progress__bar,
  .mp-progress__fill, .im-dot, .im-bar, .im-bar__fill, .im-score__track, .im-score__fill, .pw-meter, .pw-meter__bar,
  .progress-track, .progress-bar, .tab-dot, .toggle-track, .toggle-knob { forced-color-adjust: none; }
}

/* Read, not seen. For the text that has to exist for a screen reader beside a
   picture that carries the same meaning for everyone else — a strength bar, an
   icon-only state. Not `display: none`, which removes it from the reading too. */
.sr-only {
  position: absolute;
  width: 1px; height: 1px;
  margin: -1px; padding: 0; border: 0;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
}
