/* Cargo — Tradeling's design system, as specified in design.md.
   ------------------------------------------------------------------
   Loaded AFTER each page's own <style> block (and before nav.css), so the
   token values below win over the cream/navy/gold defaults the templates were
   originally written against. Pages keep using the same token names —
   --navy-*, --paper, --line, --ink, --gold — only the values change here, so
   this one file rethemes all of them.

   design.md is the source of truth. If a value here disagrees with it,
   design.md wins.                                                          */

@import url('https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&family=IBM+Plex+Mono:wght@400;500;600&display=swap');

:root{
  /* ---- Cargo primitives ------------------------------------------------ */
  --cg-gray-0:#FFFFFF;
  --cg-gray-50:#F8FAFC;
  --cg-gray-100:#E3E5E7;
  --cg-gray-200:#CECFD1;
  --cg-gray-300:#B9BBBD;
  --cg-gray-400:#A5A7A8;
  --cg-gray-500:#919394;
  --cg-gray-600:#737576;
  --cg-gray-700:#565759;
  --cg-gray-800:#26292F;
  --cg-gray-900:#15171B;
  --cg-gray-950:#0A0B0C;

  --cg-orange-50:#FAF2F0;
  --cg-orange-100:#FAE3DC;
  --cg-orange-200:#FAD0C3;
  --cg-orange-300:#FAAE96;
  --cg-orange-400:#FC7347;
  --cg-orange-500:#F95000;
  --cg-orange-600:#D24200;
  --cg-orange-700:#AC3501;

  --cg-blue-50:#EDF6FA;
  --cg-blue-100:#DCF0FA;
  --cg-blue-300:#91DBFA;
  --cg-blue-500:#06B5EB;
  --cg-blue-600:#0192BD;
  --cg-blue-700:#026C8C;
  --cg-blue-800:#00394D;
  --cg-blue-900:#002A3A;
  --cg-blue-950:#001C28;

  --cg-green-100:#DCFBDA;
  --cg-green-300:#94F794;
  --cg-green-500:#37B237;
  --cg-green-600:#118F11;

  --cg-yellow-100:#FAEBD7;
  --cg-yellow-300:#FAD196;
  --cg-yellow-500:#EBA322;
  --cg-yellow-600:#CC8E1C;

  --cg-red-100:#FAE0DC;
  --cg-red-300:#FCA497;
  --cg-red-500:#EB1A07;
  --cg-red-600:#C21809;

  /* ---- Cargo semantics ------------------------------------------------- */
  --bg-action:var(--cg-orange-500);      /* one most-important action per screen */
  --bg-brand:var(--cg-blue-800);         /* selected / on / brand surfaces */
  --bg-primary:var(--cg-gray-0);
  --bg-secondary:var(--cg-gray-50);
  --bg-tertiary:var(--cg-gray-100);
  --bg-info-light:var(--cg-blue-100);
  --bg-success-light:var(--cg-green-100);
  --bg-warning-light:var(--cg-yellow-100);
  --bg-danger-light:var(--cg-red-100);
  --bg-state-hover:rgba(0,0,0,.08);

  --border-primary:var(--cg-gray-200);
  --border-secondary:var(--cg-gray-300);
  --border-select:var(--cg-blue-800);
  --border-info:var(--cg-blue-300);
  --border-success:var(--cg-green-300);
  --border-warning:var(--cg-yellow-300);
  --border-danger:var(--cg-red-300);

  --text-primary:var(--cg-gray-950);
  --text-secondary:var(--cg-gray-800);
  --text-tertiary:var(--cg-gray-700);
  --text-disabled:var(--cg-gray-400);
  --text-success:var(--cg-green-600);
  --text-warning:var(--cg-yellow-600);
  --text-danger:var(--cg-red-600);
  --text-action:var(--cg-blue-600);
  --text-invert:var(--cg-gray-0);

  /* Cargo radii */
  --rounded-xs:4px;
  --rounded-sm:8px;
  --rounded-md:12px;
  --rounded-lg:16px;
  --rounded-pill:9999px;

  /* ---- Legacy token names, remapped onto Cargo -------------------------
     "navy" is now Cargo blue (deep teal) and "gold" is now the orange action
     colour. The names stay so no page has to be rewritten.               */
  --navy-950:var(--cg-blue-900);
  --navy-900:var(--cg-blue-800);
  --navy-800:var(--cg-blue-700);
  --navy-700:var(--cg-blue-600);

  --paper:var(--cg-gray-50);
  --paper-dim:var(--cg-gray-100);
  --line:var(--cg-gray-200);
  --grid:var(--cg-gray-100);
  --ink:var(--cg-gray-950);
  --ink-soft:var(--cg-gray-700);
  --ink-muted:var(--cg-gray-600);

  --gold:var(--cg-orange-500);
  --gold-soft:var(--cg-orange-200);   /* kickers/eyebrows on the brand masthead */

  --green:var(--cg-green-600);
  --green-bg:var(--cg-green-100);
  --amber:var(--cg-yellow-600);
  --amber-bg:var(--cg-yellow-100);
  --red:var(--cg-red-600);
  --red-bg:var(--cg-red-100);
  --pos:var(--cg-green-600);
  --neg:var(--cg-red-600);

  --font-display:'Inter','Segoe UI',system-ui,sans-serif;
  --font-ui:'Inter','Segoe UI',system-ui,sans-serif;
  --font-mono:'IBM Plex Mono',ui-monospace,monospace;
}

/* Pages painted a cream gradient behind the content; Cargo's canvas is a flat
   near-white. Declared here so those gradients are replaced, not layered. */
body{
  background:var(--bg-secondary);
  -webkit-font-smoothing:antialiased;
}

/* Fraunces carried its own optical sizing at display sizes. Inter needs the
   tracking pulled in by hand or large headings read loose. */
h1,h2,
.title,
.panel-title,
.report-name,
.kpi-value{letter-spacing:-.012em}

/* Shared shell chrome. Each page declares these classes itself with
   token-driven colours (the masthead's accent rule is already var(--gold),
   which is the action orange now); only details hardcoded to the old palette
   are restated here. */
/* The masthead logo is the reversed (knockout) mark, so no white plate
   behind it — see tl-logo-reverse.svg. */
.logo-chip{background:transparent}

/* Page-action buttons live on the brand-teal page header: light neutral,
   orange on hover. Orange stays reserved for one action, so these are ghost
   until pointed at. */
.nav-link{
  color:var(--cg-gray-800);
  border-color:var(--cg-gray-200);
}
.nav-link:hover{
  color:var(--cg-orange-700);
  border-color:var(--cg-orange-500);
  background:var(--cg-orange-50);
}

/* Cargo's "don't mix rounded and sharp corners in the same view" — the shared
   surfaces were drawn at 3px, which reads as neither. Snap them to rounded.sm
   and the small pills to rounded.xs. */
.report-card,
.panel,
.kpi-card{border-radius:var(--rounded-sm)}
.badge,
.chip{border-radius:var(--rounded-xs)}

/* ---------------------------------------------------------------------------
   Shared masthead — templates/_masthead.html

   One header for every page: logo left, kicker + title centred, session
   actions right. It is sticky, so it is fixed chrome and only the data below
   it scrolls and refreshes. Declared here rather than per page so all pages
   stay identical; these rules land after each page's own `.masthead` block
   and win on equal specificity.
--------------------------------------------------------------------------- */
.masthead{
  position:sticky;
  top:0;
  z-index:800;
  display:grid;
  grid-template-columns:1fr auto 1fr;
  align-items:center;
  gap:16px;
  padding:14px 24px;
  background:var(--cg-gray-0);
  color:var(--text-primary,#0A0B0C);
  border-bottom:1px solid var(--cg-gray-100);
}

.masthead .logo-chip{
  justify-self:start;
  align-self:center;
  display:flex;
  align-items:center;
  line-height:0;
  margin:0;
  padding:0;
  background:transparent;
  border-radius:0;
}
.masthead .logo-chip a{display:flex;line-height:0}

.masthead .title-block{
  grid-column:2;
  text-align:center;
  min-width:0;
}
.masthead .kicker,
.masthead .brand-eyebrow,
.masthead .eyebrow{
  font-family:var(--font-mono);
  font-size:10.5px;
  letter-spacing:.12em;
  text-transform:uppercase;
  color:var(--cg-gray-600);
  margin:0 0 3px;
  opacity:1;
}
.masthead .title,
.masthead .brand-title,
.masthead h1{
  margin:0;
  font-family:var(--font-display);
  font-size:22px;
  font-weight:600;
  line-height:1.2;
  color:var(--cg-blue-900);
}

.masthead .session-row{
  grid-column:3;
  justify-self:end;
  display:flex;
  align-items:center;
  gap:8px;
  flex-wrap:wrap;
  justify-content:flex-end;
}

/* Data-source notes and caveats used to sit under the title inside the header;
   they belong to the page body now so the bar stays one line tall. */
.page-notes{
  padding:12px 24px 0;
  color:var(--ink-soft);
  font-size:11.5px;
  line-height:1.55;
}
.page-notes .source-note{margin:0}
.page-notes .notes-list{margin-top:6px;font-size:11px;line-height:1.6}

@media (max-width:820px){
  .masthead{
    grid-template-columns:auto 1fr;
    row-gap:10px;
    padding:12px 14px;
  }
  .masthead .title-block{grid-column:1 / -1;order:3;text-align:left}
  .masthead .title,
  .masthead h1{font-size:19px}
  .masthead .session-row{grid-column:2}
  .page-notes{padding:12px 14px 0}
}

/* Page-level controls that used to live inside the header — date pickers,
   filter rows, chart legends. They sit directly under the masthead on a light
   bar so the header itself stays one line tall. */
.page-toolbar{
  display:flex;
  align-items:center;
  flex-wrap:wrap;
  gap:10px 16px;
  padding:10px 24px;
  background:var(--bg-primary);
  border-bottom:1px solid var(--line);
}
.page-toolbar .filter-row,
.page-toolbar .legend-row,
.page-toolbar .asof{
  display:flex;
  align-items:center;
  flex-wrap:wrap;
  gap:8px;
  margin:0;
}
.page-toolbar .filter-row{flex:1 1 auto}
.page-toolbar .filter-group.right{margin-left:auto}
.page-toolbar .source-note,
.page-toolbar .range-note{
  color:var(--ink-soft);
  font-size:11.5px;
  margin:0;
}
/* On the light bar these controls need body ink, not the masthead's knockout. */
.page-toolbar .nav-link,
.page-toolbar .back-link{
  color:var(--text-action);
  border-color:var(--border-primary);
}
.page-toolbar .nav-link:hover,
.page-toolbar .back-link:hover{
  color:var(--text-invert);
  background:var(--gold);
  border-color:var(--gold);
}
.page-toolbar .asof{color:var(--ink-soft);font-size:11px;gap:8px}

@media (max-width:820px){
  .page-toolbar{padding:10px 14px}
}

/* These controls were written for the dark masthead — light ink, translucent
   white borders, brand-teal fills. On the light toolbar they need body ink and
   real borders, so restate the colours (not the geometry) here. */
.page-toolbar .filter-label,
.page-toolbar .range-note,
.page-toolbar .legend-item,
.page-toolbar .asof{color:var(--ink-soft)}
.page-toolbar .asof b{color:var(--ink)}

.page-toolbar .preset-btn,
.page-toolbar .toggle-btn,
.page-toolbar .date-nav-btn,
.page-toolbar .date-select{
  color:var(--ink-soft);
  background:var(--bg-primary);
  border:1px solid var(--border-primary);
}
.page-toolbar .preset-btn:hover,
.page-toolbar .toggle-btn:hover,
.page-toolbar .date-nav-btn:hover,
.page-toolbar .date-select:hover{
  color:var(--ink);
  border-color:var(--border-secondary);
}
/* The selected filter is the one piece of state worth the brand fill. */
.page-toolbar .toggle-btn.active,
.page-toolbar .preset-btn.active{
  background:var(--bg-brand);
  color:var(--text-invert);
  border-color:var(--bg-brand);
}
.page-toolbar .date-input{
  background:var(--bg-primary);
  color:var(--ink);
  border:1px solid var(--border-primary);
}
/* Apply is the primary action on the bar — the one place orange belongs. */
.page-toolbar .apply-btn{
  background:var(--bg-action);
  color:var(--text-invert);
  border:1px solid var(--bg-action);
}

/* Selectable filter chips (DSO) moved to the light bar with the same treatment
   as the buttons above: neutral by default, brand fill when selected. */
.page-toolbar .chip{
  color:var(--ink-soft);
  background:var(--bg-primary);
  border:1px solid var(--border-primary);
}
.page-toolbar .chip:hover{color:var(--ink);border-color:var(--border-secondary)}
.page-toolbar .chip.active{
  background:var(--bg-brand);
  border-color:var(--bg-brand);
  color:var(--text-invert);
}
.page-toolbar .filter-label{opacity:1}
.page-toolbar .filter-sep{background:var(--border-primary)}

/* Page-action buttons in the page header (Refresh, Download, CSV). One box
   for all of them so the row is consistent on pages that never declared
   one. */
/* The shape is shared by every page-action button, in the header or in a
   page's own toolbar (Reset, Dashboard links); the colour rules above and
   nav.css set the palette. */
.nav-link{
  font-family:var(--font-mono);
  font-size:11px;
  letter-spacing:.05em;
  text-transform:uppercase;
  text-decoration:none;
  padding:5px 9px;
  border-radius:var(--rounded-xs);
  border:1px solid var(--cg-gray-200);
  background:none;
  cursor:pointer;
  line-height:1.5;
  white-space:nowrap;
}
.page-toolbar .as-of{color:var(--ink-soft);opacity:1}

/* ---------------------------------------------------------------------------
   Loading state — templates/_loader.html

   A four-dot mark in the brand palette that orbits while each dot breathes,
   the page's message, and a gradient bar sliding underneath. The pages'
   own `.loading` containers get a consistent box here; they still toggle it.
--------------------------------------------------------------------------- */
/* ---- header furniture every page used to restyle locally -----------------
   The as-of stamp and data-source notes were drawn for the old dark header in
   each template; these are the shared versions, so a page template carries
   none of them. */
.as-of{font-family:var(--font-mono);font-size:11px}
.masthead .as-of{text-align:right}
.source-note{font-size:11.5px;line-height:1.5;color:var(--ink-soft)}

/* ---- sibling-view tab strip (templates/_tabs.html) -------------------------
   Header and tabs are pinned together by sticking their shared wrapper, not
   each bar on its own: two bars both pinned to top:0 would land on the same
   line and the tabs would scroll away behind the title. The masthead keeps
   its own position:sticky — inside a wrapper exactly its content's height,
   that resolves to no movement. nav.css recolours the strip for the white
   header and sets the wrapper's offset under the app bar. */
.header-stack{position:sticky;top:0;z-index:800}
/* One rule at the bottom of the whole header: title band and tabs read as a
   single block rather than two stacked bars. */
.header-stack .masthead{border-bottom:none}
.view-tabs{
  display:flex;flex-wrap:wrap;gap:2px;
  padding:0 24px;
  background:var(--navy-950);
  border-bottom:3px solid var(--gold);
  box-shadow:0 6px 14px rgba(10,26,46,.10);
}
.view-tab{
  display:inline-flex;align-items:center;gap:8px;padding:11px 18px 10px;
  font-family:var(--font-ui);font-size:14px;font-weight:500;line-height:1.3;
  color:#FFFFFF;text-decoration:none;white-space:nowrap;
  border-bottom:3px solid transparent;
}
.view-tab:hover{background:rgba(255,255,255,.09)}
.view-tab.current{font-weight:600;background:rgba(255,255,255,.12);border-bottom-color:var(--gold-soft)}
/* A view whose source is not built yet stays clickable — the page it opens
   explains itself — but reads as secondary. */
.view-tab.pending{opacity:.7}
.tab-chip{
  font-family:var(--font-mono);font-size:9px;font-weight:600;letter-spacing:.08em;
  color:var(--gold-soft);border:1px solid rgba(250,208,195,.55);border-radius:2px;padding:1px 4px;
}

.loading{
  padding:56px 20px;
  text-align:center;
  font-family:var(--font-ui);
  font-size:13.5px;
  color:var(--cg-gray-700);
}
.tl-loader{
  display:inline-flex;
  flex-direction:column;
  align-items:center;
  gap:14px;
  min-width:220px;
}
.tl-loader-mark{
  position:relative;
  width:52px;height:52px;
  animation:tl-loader-orbit 2.6s cubic-bezier(.65,.05,.36,1) infinite;
}
.tl-loader-mark span{
  position:absolute;
  width:20px;height:20px;
  border-radius:50%;
  animation:tl-loader-breathe 1.3s ease-in-out infinite;
}
.tl-loader-mark span:nth-child(1){top:0;left:0;background:var(--cg-orange-500)}
.tl-loader-mark span:nth-child(2){top:0;right:0;background:var(--cg-orange-300);animation-delay:.16s}
.tl-loader-mark span:nth-child(3){bottom:0;left:0;background:var(--cg-blue-500);animation-delay:.32s}
.tl-loader-mark span:nth-child(4){bottom:0;right:0;background:var(--cg-blue-800);animation-delay:.48s}
.tl-loader-text{
  font-family:var(--font-display);
  font-size:15px;
  font-weight:600;
  color:var(--cg-blue-900);
  letter-spacing:-.005em;
}
.tl-loader-sub{
  margin-top:-8px;
  font-family:var(--font-mono);
  font-size:11.5px;
  color:var(--cg-gray-600);
}
.tl-loader-sub code{font-family:inherit;background:var(--cg-blue-50);border-radius:3px;padding:1px 5px}
.tl-loader-bar{
  width:168px;height:4px;
  border-radius:2px;
  background:var(--cg-gray-100);
  overflow:hidden;
}
.tl-loader-bar::after{
  content:"";
  display:block;
  width:42%;height:100%;
  border-radius:2px;
  background:linear-gradient(90deg,var(--cg-orange-500),var(--cg-orange-300),var(--cg-blue-500));
  animation:tl-loader-slide 1.4s ease-in-out infinite;
}
@keyframes tl-loader-orbit{to{transform:rotate(360deg)}}
@keyframes tl-loader-breathe{0%,100%{transform:scale(1);opacity:1}50%{transform:scale(.55);opacity:.7}}
@keyframes tl-loader-slide{0%{transform:translateX(-110%)}100%{transform:translateX(340%)}}
@media (prefers-reduced-motion:reduce){
  .tl-loader-mark,.tl-loader-mark span{animation:none}
  .tl-loader-bar::after{animation-duration:2.8s}
}
