/* public/css/galaxy.css — the galaxy layer (2026-10-18). Loaded LAST, over components.css and pages.css: the layout
   underneath is untouched, this file only changes how things look and move. Every colour is a token from tokens.css,
   the same rule as every other sheet, so the light theme gets a pale dawn version of the same design.

   The owner's direction: a real galaxy turning in the background, off to the side; a deep night, not purple; every
   page its own colour (home blue, profit red, tests green); and NO gradients on text or buttons — only the sky may be
   fancy. Charts keep their glow ("the lighting is great"); the hover light is kept faint, as he asked.

   What lives here:
     page colour .... html[data-page] (set by app.js) → --accent; the spiral's arms (js/ui/galaxy.js), the active tab,
                      the primary button, focus and the press ripple all use it
     the sky ........ the canvas from js/ui/galaxy.js, behind everything
     glass .......... cards, tiles, the top bar, dialogs: translucent and blurred over the sky, one hairline edge
     colour ......... tiles, sparklines and lines in the colour of their CONCEPT (--tile-color from js/palette.js)
     motion ......... press ripple, spring on press, lift on hover, page and chart entrances — off under
                      prefers-reduced-motion (base.css), and the glass turns solid under prefers-reduced-transparency */

/* ------------------------------------------------------------------ the colour of the page */
:root { --accent: var(--page-analytics); }
:root[data-page="profit"] { --accent: var(--page-profit); }
:root[data-page="channels"] { --accent: var(--page-channels); }
:root[data-page="cro"] { --accent: var(--page-cro); }
:root[data-page="orders"] { --accent: var(--page-orders); }
:root[data-page="settings"] { --accent: var(--page-settings); }
:root[data-page="health"] { --accent: var(--page-health); }
:root[data-page="studio"] { --accent: var(--page-studio); }
:root {
  --accent-soft: color-mix(in srgb, var(--accent) 16%, transparent);
  --accent-line: color-mix(in srgb, var(--accent) 45%, transparent);
  --accent-glow: color-mix(in srgb, var(--accent) 28%, transparent);
  --focus: var(--accent);
}
/* Inside a page the brand orange follows the page too (the owner, 21.10.2026: on the tests page everything green, no
   orange): the leading card, chips, meters, links, toggles and the first chart series all take --accent. The logo in
   the top bar keeps the real orange: it sits outside main. Dialogs open from a page, so they follow it. */
main.page, .dialog-inner {
  --brand: var(--accent);
  --brand-deep: var(--accent);
  --brand-soft: var(--accent-line);
  --tint: var(--accent-soft);
  --on-brand: var(--on-accent);
}

/* ------------------------------------------------------------------ the sky */
body { background: var(--cosmos-0); }
.galaxy { position: fixed; inset: 0; inline-size: 100vw; block-size: 100vh; z-index: -1; pointer-events: none; display: block; }

/* ------------------------------------------------------------------ glass surfaces */
.card, .kpi {
  background: var(--card-bg);
  border: 1px solid var(--card-edge);
  -webkit-backdrop-filter: blur(14px) saturate(130%); backdrop-filter: blur(14px) saturate(130%);
  box-shadow: var(--shadow-1);
  isolation: isolate;
  transition: border-color var(--dur-base) var(--ease-out), box-shadow var(--dur-base) var(--ease-out), transform var(--dur-base) var(--ease-out), background-color var(--dur-base) var(--ease-out);
}
/* A faint light that follows the pointer (fx.js sets --mx / --my) — kept low, the owner asked for it softer. */
.card::before, .kpi::before {
  content: ""; position: absolute; inset: 0; border-radius: inherit; pointer-events: none; z-index: -1; opacity: 0;
  background: radial-gradient(360px circle at var(--mx, 50%) var(--my, 0%), color-mix(in srgb, var(--accent) 7%, transparent), transparent 65%);
  transition: opacity var(--dur-base) var(--ease-out);
}
@media (hover: hover) {
  .card:hover::before, .kpi:hover::before { opacity: 1; }
}
.card-tint { background: color-mix(in srgb, var(--tint) 70%, transparent); }
.card-flat { box-shadow: none; }

/* ------------------------------------------------------------------ the top bar and navigation */
.topbar { background: var(--glass); border-block-end: 1px solid var(--card-edge); }
.nav-link { position: relative; transition: color var(--dur-fast) var(--ease-out), background-color var(--dur-fast) var(--ease-out), box-shadow var(--dur-fast) var(--ease-out), transform 160ms var(--ease-spring); }
.nav-link:hover { background: var(--well); }
.nav-link[aria-current="page"] { background: var(--accent-soft); box-shadow: inset 0 0 0 1px var(--accent-line), 0 0 18px var(--accent-glow); color: var(--ink); }
.nav-link[aria-current="page"] .icon { color: var(--accent); }
.bottom-nav { background: var(--glass); border-block-start: 1px solid var(--card-edge); }
.bottom-link[aria-current="page"] { color: var(--ink); }
.bottom-link[aria-current="page"] .icon { color: var(--accent); }
/* A crowded top bar on a laptop: the tagline goes before the brand name is cut. */
@media (max-width: 1360px) { .brand-sub { display: none; } .nav-link { padding: 0 11px; } }
/* Laptop and tablet widths: eight labelled links (the Creative Lab joined on 18.10.2026), the brand and the status
   row do not fit on one line, and the row used to push the "advanced" switch off the screen. The links keep their
   icon and their name as a tooltip; the phone layout (≤ 767px) already moves them to the bottom bar. */
@media (min-width: 768px) and (max-width: 1560px) {
  .nav-link .nav-text { position: absolute; inline-size: 1px; block-size: 1px; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; }
  .nav-link { padding: 0 12px; }
  .nav-link .icon { inline-size: 20px; block-size: 20px; }
}
/* The name never gets cut ("rofit Lab", 21.10.2026): the brand keeps its width, and where the bar is tight the word
   "Agadura" folds away first (the link's aria-label still says it in full). */
.topbar .brand { flex: none; overflow: visible; }
@media (max-width: 1600px) { .brand-word { display: none; } }

/* ------------------------------------------------------------------ buttons: solid, with a ripple and a spring */
.btn { overflow: hidden; transition: background-color 150ms var(--ease-out), color 150ms var(--ease-out), box-shadow 200ms var(--ease-out), transform 180ms var(--ease-spring), filter 150ms; }
.btn:active:not(:disabled) { transform: scale(.955); }
.btn-primary { background: var(--accent); color: var(--on-accent); box-shadow: 0 4px 16px var(--accent-glow); }
.btn-primary:hover:not(:disabled) { background: var(--accent); filter: brightness(1.1); box-shadow: 0 6px 22px var(--accent-glow); }
.btn-ghost { background: var(--card-bg); box-shadow: inset 0 0 0 1px var(--card-edge); -webkit-backdrop-filter: blur(10px); backdrop-filter: blur(10px); }
.btn-ghost:hover:not(:disabled) { background: var(--card-bg-hover); box-shadow: inset 0 0 0 1px var(--accent-line); }
.btn-plain { color: var(--ink); }
.btn-plain:hover:not(:disabled) { background: var(--well); }
.fx-host { position: relative; overflow: hidden; }
.fx-ripple {
  position: absolute; border-radius: 50%; pointer-events: none; z-index: 0;
  background: radial-gradient(circle, color-mix(in srgb, var(--accent) 38%, transparent) 0%, transparent 65%);
  transform: scale(0); opacity: .9; animation: fx-ripple 600ms var(--ease-out) forwards;
}
.btn-primary .fx-ripple { background: radial-gradient(circle, color-mix(in srgb, var(--on-accent) 30%, transparent) 0%, transparent 65%); }
@keyframes fx-ripple { to { transform: scale(1); opacity: 0; } }
.btn > .btn-text, .btn > .icon, .nav-link > .icon, .seg-btn > .icon { position: relative; z-index: 1; }

/* ------------------------------------------------------------------ segmented controls */
.seg { background: var(--well); box-shadow: inset 0 0 0 1px var(--card-edge); }
.seg-indicator {
  background: color-mix(in srgb, var(--accent) 24%, var(--paper));
  box-shadow: inset 0 0 0 1px var(--accent-line), 0 2px 12px var(--accent-glow);
  transition: transform 320ms var(--ease-spring), width 320ms var(--ease-spring), opacity 150ms;
}
.seg-btn { overflow: hidden; }
.seg-btn[aria-checked="true"] { color: var(--ink); }

/* ------------------------------------------------------------------ KPI tiles in the colour of what they measure */
.kpi { --tile-color: var(--accent); position: relative; }
.metric-tile { border-block-start: 2px solid color-mix(in srgb, var(--tile-color) 70%, transparent); }
.metric-tile .kpi-label::before {
  content: ""; display: inline-block; inline-size: 8px; block-size: 8px; border-radius: 50%; margin-inline-end: 7px; vertical-align: 1px;
  background: var(--tile-color); box-shadow: 0 0 8px var(--tile-color);
}
@media (hover: hover) {
  .metric-tile:hover { transform: translateY(-2px); box-shadow: var(--shadow-2), 0 0 16px color-mix(in srgb, var(--tile-color) 12%, transparent); border-color: color-mix(in srgb, var(--tile-color) 30%, var(--card-edge)); }
}
.metric-tile .spark, .metric-tile[data-tone] .spark { color: var(--tile-color); }
.metric-spark { opacity: 1; }
.spark-line { stroke: var(--tile-color, currentColor); stroke-width: 2; opacity: 1; filter: drop-shadow(0 0 4px color-mix(in srgb, var(--tile-color, currentColor) 70%, transparent)); stroke-dasharray: 1; stroke-dashoffset: 1; animation: line-draw 1100ms var(--ease-out) 120ms forwards; }
.spark-stop-top { stop-color: var(--tile-color, currentColor); stop-opacity: .36; }
.spark-stop-bottom { stop-color: var(--tile-color, currentColor); stop-opacity: 0; }
.spark-area { animation: fade-in 900ms var(--ease-out) 300ms both; }
.spark-dot { fill: var(--tile-color, currentColor); stroke: var(--paper); stroke-width: 1.5; filter: drop-shadow(0 0 6px var(--tile-color, currentColor)); }
.spark-cursor { stroke: color-mix(in srgb, var(--tile-color, currentColor) 60%, transparent); }
.spark-readout { -webkit-backdrop-filter: blur(10px); backdrop-filter: blur(10px); }
.metric-pin.is-on { color: var(--accent); background: var(--accent-soft); }
.metric-zoom:hover, .metric-pin:hover { background: color-mix(in srgb, var(--tile-color) 16%, transparent); color: var(--ink); }

/* ------------------------------------------------------------------ charts */
.chart-svg .chart-line { stroke-width: 2.75; filter: drop-shadow(0 0 5px var(--accent-glow)); }
.chart-svg .chart-line.is-draw { animation-duration: 1100ms; }
.chart-svg .chart-area { animation: fade-in 900ms var(--ease-out) 250ms both; }
.chart-svg .grid line { stroke: var(--rule); }
.chart-svg .points.is-dense .chart-point { opacity: 0; }
.chart-svg .points.is-dense .chart-point:hover, .chart-svg .points.is-dense .chart-point:focus-visible { opacity: 1; }
.chart-svg .chart-point { stroke: var(--paper); stroke-width: 1.5; }
.chart-svg .chart-segment { transition: filter var(--dur-fast) var(--ease-out); }
.chart-svg .chart-segment:hover { filter: brightness(1.12); }
.chart-tooltip { background: var(--glass); border: 1px solid var(--card-edge); -webkit-backdrop-filter: blur(14px); backdrop-filter: blur(14px); box-shadow: var(--shadow-2); color: var(--ink); }
.chart-expanded .chart-body svg { inline-size: 100%; block-size: auto; }
.metric-zoom-controls { display: flex; justify-content: flex-start; margin-block-end: 12px; }
.dialog-chart { width: min(1120px, calc(100vw - 32px)); }

/* the cost table and the channel table carry the same colours as the charts */
.cost-label { display: inline-flex; align-items: center; gap: 8px; }
.cost-dot, .channel-dot { inline-size: 10px; block-size: 10px; border-radius: 3px; flex: none; background: var(--dot); box-shadow: 0 0 8px color-mix(in srgb, var(--dot) 60%, transparent); }
.channel-dot { border-radius: 50%; }
.channel-label { display: inline-flex; align-items: center; gap: 8px; }

/* ------------------------------------------------------------------ dialogs, toasts, chips, tables, fields */
.dialog { background: color-mix(in srgb, var(--paper) 90%, transparent); border: 1px solid var(--card-edge); -webkit-backdrop-filter: blur(22px) saturate(130%); backdrop-filter: blur(22px) saturate(130%); box-shadow: var(--shadow-2); }
.dialog::backdrop { background: var(--scrim); -webkit-backdrop-filter: blur(5px); backdrop-filter: blur(5px); }
.dialog[open] { animation: galaxy-dialog-in 340ms var(--ease-spring); }
@keyframes galaxy-dialog-in { from { opacity: 0; transform: translateY(10px) scale(.95); } to { opacity: 1; transform: none; } }
.toast { border: 1px solid var(--card-edge); -webkit-backdrop-filter: blur(14px); backdrop-filter: blur(14px); box-shadow: var(--shadow-2); }
.table tbody tr { transition: background-color var(--dur-fast) var(--ease-out); }
.table tbody tr:hover { background: color-mix(in srgb, var(--accent) 6%, transparent); }
.table th { color: var(--soft-text); }
/* base.css gives every .num inline-block (an LTR island inside RTL text). A header cell carrying .num must stay a table
   cell, or the numeric headers float out of their row — the solid paper cards hid that; glass shows it. */
.table th.num { display: table-cell; }
.input, .select, .textarea { background: color-mix(in srgb, var(--paper) 72%, transparent); }
.input:focus-visible, .select:focus-visible, .textarea:focus-visible { box-shadow: 0 0 0 4px var(--accent-soft); }
.alert-bar { -webkit-backdrop-filter: blur(12px); backdrop-filter: blur(12px); }

/* ------------------------------------------------------------------ page and content entrances */
.page-view { transition: opacity 320ms var(--ease-out), transform 420ms var(--ease-spring); }
.page-view.is-entering { opacity: 0; transform: translateY(12px); }
.reveal { transition: opacity 520ms var(--ease-out), transform 620ms var(--ease-spring); }

/* ------------------------------------------------------------------ preferences */
@media (prefers-reduced-motion: reduce) {
  .fx-ripple { display: none; }
  .spark-line { animation: none; stroke-dashoffset: 0; }
}
@media (prefers-reduced-transparency: reduce) {
  .card, .kpi, .dialog, .btn-ghost, .chart-tooltip, .toast { background: var(--paper) !important; -webkit-backdrop-filter: none !important; backdrop-filter: none !important; }
}

/* ------------------------------------------------------------------ the login page */
/* login.css makes the card transparent on a phone (it was a plain page then). Over the galaxy the title landed on
   the bright core, so on every width the card is glass, like every other card. */
.login-card { background: var(--card-bg); border: 1px solid var(--card-edge); -webkit-backdrop-filter: blur(16px) saturate(130%); backdrop-filter: blur(16px) saturate(130%); box-shadow: var(--shadow-2); }
@media (max-width: 480px) { .login-card { background: var(--card-bg); box-shadow: var(--shadow-1); padding: var(--space-5); } }

/* ------------------------------------------------------------------ phones */
/* A phone's graphics chip pays for every blurred pane on every frame of the moving sky; Safari in particular chokes on
   it. On a touch screen the glass is a solid-looking tint instead — it reads the same at that size, and the page
   stays smooth. */
@media (max-width: 767px), (hover: none) and (pointer: coarse) {
  .card, .kpi, .btn-ghost, .dialog, .chart-tooltip, .toast, .spark-readout, .alert-bar, .login-card {
    -webkit-backdrop-filter: none; backdrop-filter: none;
  }
  .card, .kpi, .login-card { background: color-mix(in srgb, var(--paper) 90%, transparent); }
  .dialog { background: var(--paper); }
  .card::before, .kpi::before { display: none; }
}
