/* Core components (spec 13). Hand-written, unlike tokens.css, which is generated.
 * Every rule here uses semantic tokens only; harness/design/check_ui.py fails on a raw colour.
 * Class names are ds-<component>, ds-<component>__<part>, ds-<component>--<variant>, and every one
 * is declared in the design-system skill's registry.json. A class that is not declared is a defect,
 * which is how "a work order may not invent a component" is enforced rather than merely requested.
 */

/* --- num: figures that line up ------------------------------------------------------- */
.ds-num { font-variant-numeric: tabular-nums slashed-zero; }
.ds-num__unit {
  font-size: var(--ff-type-scale-12);
  color: var(--ff-text-muted);
  margin-left: 0.25em;
  font-variant-numeric: normal;
}

/* --- badge: filled, one per row, never a link ----------------------------------------- */
.ds-badge {
  display: inline-flex;
  align-items: center;
  padding: 2px var(--ff-space-3);
  border-radius: var(--ff-radius-chip);
  font-size: var(--ff-type-scale-12);
  line-height: var(--ff-type-leading-compact);
  font-weight: 600;
  letter-spacing: var(--ff-type-tracking-label);
  white-space: nowrap;
}
.ds-badge--neutral { background: var(--ff-surface-raised); color: var(--ff-text-muted); }
.ds-badge--ok      { background: var(--ff-fill-ok-soft);   color: var(--ff-status-ok-text); }
.ds-badge--warn    { background: var(--ff-fill-warn-soft); color: var(--ff-status-warn-text); }
.ds-badge--bad     { background: var(--ff-fill-bad-soft);  color: var(--ff-status-bad-text); }
.ds-badge--accent  { background: var(--ff-fill-accent-soft);  color: var(--ff-text-accent); }
.ds-badge--oracle  { background: var(--ff-fill-oracle-soft);  color: var(--ff-oracle-11); }

/* --- dot: a state machine ------------------------------------------------------------- */
.ds-dot {
  display: inline-block;
  width: 7px;
  height: 7px;
  border-radius: var(--ff-radius-full);
  flex: none;
  background: var(--ff-status-idle-dot);
}
.ds-dot--live { background: var(--ff-status-live-dot); animation: ds-pulse 1.8s ease-in-out infinite; }
.ds-dot--ok   { background: var(--ff-status-ok-dot); }
.ds-dot--warn { background: var(--ff-status-warn-dot); }
.ds-dot--bad  { background: var(--ff-status-bad-dot); }
@keyframes ds-pulse { 0%, 100% { opacity: 1 } 50% { opacity: 0.35 } }

/* --- position: a filled chip (decision 5A) -------------------------------------------- */
/* Safe to fill only because no position shares a hue with a status; the generator enforces that.
   The quiet variant is ink on the row for places a filled chip would be too heavy. */
.ds-pos {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 2.25rem;
  padding: 1px var(--ff-space-3);
  border-radius: var(--ff-radius-chip);
  font-size: var(--ff-type-scale-12);
  line-height: var(--ff-type-leading-compact);
  font-weight: 700;
  letter-spacing: var(--ff-type-tracking-label);
  white-space: nowrap;
}
.ds-pos--quiet { background: none; padding-inline: 0; min-width: 0; font-weight: 600; }
/* the bench keeps a hairline so a column of chips reads as a group */
.ds-pos--bench { outline: 1px solid var(--ff-border-strong); outline-offset: -1px; }

.ds-pos--fill.ds-pos--qb  { background: var(--ff-pos-qb-fill);  color: var(--ff-pos-qb-on-fill); }
.ds-pos--fill.ds-pos--rb  { background: var(--ff-pos-rb-fill);  color: var(--ff-pos-rb-on-fill); }
.ds-pos--fill.ds-pos--wr  { background: var(--ff-pos-wr-fill);  color: var(--ff-pos-wr-on-fill); }
.ds-pos--fill.ds-pos--te  { background: var(--ff-pos-te-fill);  color: var(--ff-pos-te-on-fill); }
.ds-pos--fill.ds-pos--k   { background: var(--ff-pos-k-fill);   color: var(--ff-pos-k-on-fill); }
.ds-pos--fill.ds-pos--dst { background: var(--ff-pos-dst-fill); color: var(--ff-pos-dst-on-fill); }

.ds-pos--quiet.ds-pos--qb  { color: var(--ff-pos-qb-text); }
.ds-pos--quiet.ds-pos--rb  { color: var(--ff-pos-rb-text); }
.ds-pos--quiet.ds-pos--wr  { color: var(--ff-pos-wr-text); }
.ds-pos--quiet.ds-pos--te  { color: var(--ff-pos-te-text); }
.ds-pos--quiet.ds-pos--k   { color: var(--ff-pos-k-text); }
.ds-pos--quiet.ds-pos--dst { color: var(--ff-pos-dst-text); }

/* --- eligibility: one letter per slot a player may fill -------------------------------- */
.ds-elig { display: inline-flex; gap: 2px; }
.ds-elig__slot {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 1.05rem;
  height: 1.05rem;
  border-radius: 3px;
  font-size: 0.625rem;
  font-weight: 700;
  line-height: 1;
}
.ds-elig__slot.ds-pos--qb  { background: var(--ff-pos-qb-fill);  color: var(--ff-pos-qb-on-fill); }
.ds-elig__slot.ds-pos--rb  { background: var(--ff-pos-rb-fill);  color: var(--ff-pos-rb-on-fill); }
.ds-elig__slot.ds-pos--wr  { background: var(--ff-pos-wr-fill);  color: var(--ff-pos-wr-on-fill); }
.ds-elig__slot.ds-pos--te  { background: var(--ff-pos-te-fill);  color: var(--ff-pos-te-on-fill); }
.ds-elig__slot.ds-pos--k   { background: var(--ff-pos-k-fill);   color: var(--ff-pos-k-on-fill); }
.ds-elig__slot.ds-pos--dst { background: var(--ff-pos-dst-fill); color: var(--ff-pos-dst-on-fill); }

/* --- stat: a number that is not a heading --------------------------------------------- */
.ds-stat__value {
  font-family: var(--ff-type-family-display), system-ui, sans-serif;
  font-size: var(--ff-type-scale-28);
  line-height: var(--ff-type-leading-tight);
  font-weight: 700;
  letter-spacing: var(--ff-type-tracking-heading);
}
.ds-stat__value--ok   { color: var(--ff-status-ok-text); }
.ds-stat__value--warn { color: var(--ff-status-warn-text); }
.ds-stat__value--bad  { color: var(--ff-status-bad-text); }
.ds-stat__label {
  font-size: var(--ff-type-scale-12);
  line-height: var(--ff-type-leading-normal);
  color: var(--ff-text-muted);
  letter-spacing: var(--ff-type-tracking-label);
}

/* --- meter: a level, not a process ---------------------------------------------------- */
.ds-meter__head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: var(--ff-space-3);
  font-size: var(--ff-type-scale-14);
  line-height: var(--ff-type-leading-compact);
}
.ds-meter__label { color: var(--ff-text-muted); }
.ds-meter__track {
  margin-top: var(--ff-space-2);
  height: 4px;                       /* Carbon's inline-in-a-table height */
  border-radius: var(--ff-radius-full);
  background: var(--ff-surface-raised);
  overflow: hidden;
}
.ds-meter__fill { height: 100%; width: 0; border-radius: inherit; }
/* The width comes from data-pct, one rule per whole percent, because the content security policy
   refuses a style attribute (WO-0095). The macro clamps the value to 0..100. */
.ds-meter__fill[data-pct="1"]{width:1%}.ds-meter__fill[data-pct="2"]{width:2%}.ds-meter__fill[data-pct="3"]{width:3%}.ds-meter__fill[data-pct="4"]{width:4%}.ds-meter__fill[data-pct="5"]{width:5%}.ds-meter__fill[data-pct="6"]{width:6%}.ds-meter__fill[data-pct="7"]{width:7%}.ds-meter__fill[data-pct="8"]{width:8%}.ds-meter__fill[data-pct="9"]{width:9%}.ds-meter__fill[data-pct="10"]{width:10%}
.ds-meter__fill[data-pct="11"]{width:11%}.ds-meter__fill[data-pct="12"]{width:12%}.ds-meter__fill[data-pct="13"]{width:13%}.ds-meter__fill[data-pct="14"]{width:14%}.ds-meter__fill[data-pct="15"]{width:15%}.ds-meter__fill[data-pct="16"]{width:16%}.ds-meter__fill[data-pct="17"]{width:17%}.ds-meter__fill[data-pct="18"]{width:18%}.ds-meter__fill[data-pct="19"]{width:19%}.ds-meter__fill[data-pct="20"]{width:20%}
.ds-meter__fill[data-pct="21"]{width:21%}.ds-meter__fill[data-pct="22"]{width:22%}.ds-meter__fill[data-pct="23"]{width:23%}.ds-meter__fill[data-pct="24"]{width:24%}.ds-meter__fill[data-pct="25"]{width:25%}.ds-meter__fill[data-pct="26"]{width:26%}.ds-meter__fill[data-pct="27"]{width:27%}.ds-meter__fill[data-pct="28"]{width:28%}.ds-meter__fill[data-pct="29"]{width:29%}.ds-meter__fill[data-pct="30"]{width:30%}
.ds-meter__fill[data-pct="31"]{width:31%}.ds-meter__fill[data-pct="32"]{width:32%}.ds-meter__fill[data-pct="33"]{width:33%}.ds-meter__fill[data-pct="34"]{width:34%}.ds-meter__fill[data-pct="35"]{width:35%}.ds-meter__fill[data-pct="36"]{width:36%}.ds-meter__fill[data-pct="37"]{width:37%}.ds-meter__fill[data-pct="38"]{width:38%}.ds-meter__fill[data-pct="39"]{width:39%}.ds-meter__fill[data-pct="40"]{width:40%}
.ds-meter__fill[data-pct="41"]{width:41%}.ds-meter__fill[data-pct="42"]{width:42%}.ds-meter__fill[data-pct="43"]{width:43%}.ds-meter__fill[data-pct="44"]{width:44%}.ds-meter__fill[data-pct="45"]{width:45%}.ds-meter__fill[data-pct="46"]{width:46%}.ds-meter__fill[data-pct="47"]{width:47%}.ds-meter__fill[data-pct="48"]{width:48%}.ds-meter__fill[data-pct="49"]{width:49%}.ds-meter__fill[data-pct="50"]{width:50%}
.ds-meter__fill[data-pct="51"]{width:51%}.ds-meter__fill[data-pct="52"]{width:52%}.ds-meter__fill[data-pct="53"]{width:53%}.ds-meter__fill[data-pct="54"]{width:54%}.ds-meter__fill[data-pct="55"]{width:55%}.ds-meter__fill[data-pct="56"]{width:56%}.ds-meter__fill[data-pct="57"]{width:57%}.ds-meter__fill[data-pct="58"]{width:58%}.ds-meter__fill[data-pct="59"]{width:59%}.ds-meter__fill[data-pct="60"]{width:60%}
.ds-meter__fill[data-pct="61"]{width:61%}.ds-meter__fill[data-pct="62"]{width:62%}.ds-meter__fill[data-pct="63"]{width:63%}.ds-meter__fill[data-pct="64"]{width:64%}.ds-meter__fill[data-pct="65"]{width:65%}.ds-meter__fill[data-pct="66"]{width:66%}.ds-meter__fill[data-pct="67"]{width:67%}.ds-meter__fill[data-pct="68"]{width:68%}.ds-meter__fill[data-pct="69"]{width:69%}.ds-meter__fill[data-pct="70"]{width:70%}
.ds-meter__fill[data-pct="71"]{width:71%}.ds-meter__fill[data-pct="72"]{width:72%}.ds-meter__fill[data-pct="73"]{width:73%}.ds-meter__fill[data-pct="74"]{width:74%}.ds-meter__fill[data-pct="75"]{width:75%}.ds-meter__fill[data-pct="76"]{width:76%}.ds-meter__fill[data-pct="77"]{width:77%}.ds-meter__fill[data-pct="78"]{width:78%}.ds-meter__fill[data-pct="79"]{width:79%}.ds-meter__fill[data-pct="80"]{width:80%}
.ds-meter__fill[data-pct="81"]{width:81%}.ds-meter__fill[data-pct="82"]{width:82%}.ds-meter__fill[data-pct="83"]{width:83%}.ds-meter__fill[data-pct="84"]{width:84%}.ds-meter__fill[data-pct="85"]{width:85%}.ds-meter__fill[data-pct="86"]{width:86%}.ds-meter__fill[data-pct="87"]{width:87%}.ds-meter__fill[data-pct="88"]{width:88%}.ds-meter__fill[data-pct="89"]{width:89%}.ds-meter__fill[data-pct="90"]{width:90%}
.ds-meter__fill[data-pct="91"]{width:91%}.ds-meter__fill[data-pct="92"]{width:92%}.ds-meter__fill[data-pct="93"]{width:93%}.ds-meter__fill[data-pct="94"]{width:94%}.ds-meter__fill[data-pct="95"]{width:95%}.ds-meter__fill[data-pct="96"]{width:96%}.ds-meter__fill[data-pct="97"]{width:97%}.ds-meter__fill[data-pct="98"]{width:98%}.ds-meter__fill[data-pct="99"]{width:99%}.ds-meter__fill[data-pct="100"]{width:100%}
.ds-meter__fill--accent { background: var(--ff-fill-accent); }
.ds-meter__fill--oracle { background: var(--ff-oracle-9); }
.ds-meter__fill--ok     { background: var(--ff-status-ok-dot); }
.ds-meter__fill--warn   { background: var(--ff-status-warn-dot); }
.ds-meter__fill--bad    { background: var(--ff-status-bad-dot); }

/* --- notice --------------------------------------------------------------------------- */
.ds-notice {
  padding: var(--ff-space-4) var(--ff-space-5);
  border-radius: var(--ff-radius-panel);
  border-left: 3px solid var(--ff-border-strong);
  background: var(--ff-surface-panel);
  font-size: var(--ff-type-scale-14);
  line-height: var(--ff-type-leading-normal);
}
.ds-notice__title { margin: 0 0 var(--ff-space-2); font-weight: 650; }
.ds-notice__body { margin: 0; color: var(--ff-text-muted); }
.ds-notice--info   { border-left-color: var(--ff-oracle-9); background: var(--ff-fill-oracle-soft); }
.ds-notice--ok     { border-left-color: var(--ff-status-ok-dot);   background: var(--ff-fill-ok-soft); }
.ds-notice--warn   { border-left-color: var(--ff-status-warn-dot); background: var(--ff-fill-warn-soft); }
.ds-notice--bad    { border-left-color: var(--ff-status-bad-dot);  background: var(--ff-fill-bad-soft); }
/* a callout loads with the page and has no dismiss control, because dismissing it would be a lie */
.ds-notice--callout { border-left-width: 3px; }
.ds-notice--inline  { border-radius: var(--ff-radius-chip); }

/* --- empty ---------------------------------------------------------------------------- */
.ds-empty {
  padding: var(--ff-space-7) var(--ff-space-5);
  text-align: center;
  border: 1px dashed var(--ff-border-default);
  border-radius: var(--ff-radius-panel);
}
/* The three kinds differ in what the reader should do next, so they differ in weight too:
   nothing-yet is quiet, a filtered miss invites a change, blocked is a problem. */
.ds-empty--none { border-color: var(--ff-border-subtle); }
.ds-empty--filtered { border-style: solid; border-color: var(--ff-border-default); }
.ds-empty--blocked { border-style: solid; border-color: var(--ff-status-warn-dot); }
.ds-empty__title { margin: 0; font-weight: 650; }
.ds-empty__body {
  margin: var(--ff-space-2) 0 0;
  color: var(--ff-text-muted);
  font-size: var(--ff-type-scale-14);
}

/* --- row: the list primitive ----------------------------------------------------------- */
.ds-row {
  display: flex;
  align-items: flex-start;
  gap: var(--ff-space-4);
  padding: var(--ff-space-4) 0;
  border-bottom: 1px solid var(--ff-border-subtle);
  color: inherit;
  text-decoration: none;
}
.ds-row:last-child { border-bottom: none; }
a.ds-row:hover { background: var(--ff-surface-panel); }
.ds-row__lead { flex: none; display: flex; align-items: center; gap: var(--ff-space-3); padding-top: 3px; }
.ds-row__body { flex: 1; min-width: 0; }
.ds-row__title {
  font-size: var(--ff-type-scale-14);
  line-height: var(--ff-type-leading-compact);
  font-weight: 600;
}
.ds-row__description {
  font-size: var(--ff-type-scale-12);
  line-height: var(--ff-type-leading-normal);
  color: var(--ff-text-muted);
}
.ds-row__trail { flex: none; display: flex; align-items: center; gap: var(--ff-space-3); }
/* inactive: the row cannot function because something upstream is broken. Not the same as
   disabled, which means the viewer may not use it. */
.ds-row--inactive { opacity: 0.55; }
.ds-row--inactive .ds-row__title { font-weight: 500; }

@media (prefers-reduced-motion: reduce) {
  .ds-dot--live { animation: none; }
}
