/* ============================================================================
   JULES  ·  COMPONENT LAYER  ·  return 2, 16 Aug 2026
   Loads after kin.css and jules-tokens.css. TOKEN REFERENCES ONLY, no literals.
   Every class here is new in return 2 or is a return 1 component restated
   because return 2 changed it. Nothing here restyles a k- class.
   ========================================================================== */

/* --- 1. CO-BRANDING ------------------------------------------------------
   The hierarchy, and it is a decision, not an average:
   KIN HOLDS THE PRODUCT POSITION. jules and kin wordmarks, grounds, type,
   structure, the olive action, the focus ring. Read first, top left, always.
   FUSION LINE HOLDS THE OPERATOR POSITION. One fixed lockup, real artwork,
   on its own navy plate, under the label OPERATED WITH. Never in the header
   lead slot. Never in the same container as a Kin mark. Never resized to
   match one. Clear space: 24px minimum from any Kin mark.
   ------------------------------------------------------------------------ */
.j-operator {
  display: inline-grid; gap: 8px; justify-items: start;
  padding: 12px 16px 14px;
  background: var(--plate);
  border: 1px solid var(--plate-line);
  border-radius: var(--r-ctl);
}
.j-operator > .j-operator-label {
  margin: 0; font-family: var(--font-mono); font-size: 9.5px;
  letter-spacing: 0.18em; text-transform: uppercase; color: var(--plate-label);
}
.j-operator > img { display: block; height: 20px; width: auto; }
.j-operator > .j-operator-note {
  margin: 0; font-size: 12.5px; line-height: 1.5; color: var(--sand);
  max-width: 38ch; opacity: 0.86;
}
.j-operator--lg { padding: 16px 20px 18px; }
.j-operator--lg > img { height: 26px; }
.j-operator--sm { padding: 9px 12px; gap: 6px; }
.j-operator--sm > img { height: 14px; }
.j-operator--bare { background: transparent; border-color: transparent; padding: 0; }

/* The FL entity badge. Marks an engagement that is held by Fusion Line.
   It is information about a person's engagement, never decoration. */
.j-entity {
  display: inline-flex; align-items: center; gap: 7px; height: 22px;
  padding: 0 9px; border-radius: var(--r-pill);
  background: var(--plate); border: 1px solid var(--human-24);
  color: var(--human); font-family: var(--font-mono); white-space: nowrap;
  font-size: 9.5px; letter-spacing: 0.16em; text-transform: uppercase;
}

/* The seam. ONE per composition, at the join the two companies actually make.
   Three stacked strokes: 20px bloom at 10%, 8px halo at 30%, the core on top. */
.j-seam {
  height: 20px; border: 0; margin: 0; width: 100%; flex: none;
  background:
    linear-gradient(to bottom, transparent 46%, var(--seam-core) 48%, var(--seam-core) 52%, transparent 54%),
    linear-gradient(to bottom, transparent 26%, var(--seam-halo) 50%, transparent 74%),
    linear-gradient(to bottom, transparent 0%, var(--seam-bloom) 50%, transparent 100%);
  -webkit-mask-image: linear-gradient(to right, transparent, #000 14%, #000 86%, transparent);
  mask-image: linear-gradient(to right, transparent, #000 14%, #000 86%, transparent);
}
.j-seam--v {
  width: 20px; height: 100%;
  background:
    linear-gradient(to right, transparent 46%, var(--seam-core) 48%, var(--seam-core) 52%, transparent 54%),
    linear-gradient(to right, transparent 26%, var(--seam-halo) 50%, transparent 74%),
    linear-gradient(to right, transparent 0%, var(--seam-bloom) 50%, transparent 100%);
  -webkit-mask-image: linear-gradient(to bottom, transparent, #000 14%, #000 86%, transparent);
  mask-image: linear-gradient(to bottom, transparent, #000 14%, #000 86%, transparent);
}

/* The attribution block. Decided once, used on every surface, in this wording.
   Worker facing and candidate facing pages lead with Fusion Line, because that
   is who those people work through. Admin surfaces lead with Kin. */
.j-attrib { display: grid; gap: 4px; }
.j-attrib p {
  margin: 0; font-family: var(--font-mono); font-size: 11px;
  letter-spacing: 0.1em; color: var(--sage);
}
.j-attrib p b { font-weight: 400; color: var(--sand); }

/* A navy plate. An object on a graphite ground, never a ground itself. */
.j-plate { background: var(--plate); border: 1px solid var(--plate-line); border-radius: var(--r-panel); }

/* --- 1b. THE WIDTH CONTAINER --------------------------------------------
   Every Jules page root carries .j-frame. In production its width IS the
   viewport width, so a container query and a media query say the same thing.
   On this return sheet it lets a 390 composition and a 1440 composition sit
   on one page and each behave truthfully. One source of truth, no forks.
   ------------------------------------------------------------------------ */
.j-frame { container-type: inline-size; }

/* --- 2. THE FRONT DOOR --------------------------------------------------- */
/* MESH, 19 AUG 2026: move the seam right so the hero gets the room and the sign
   in side stops reading as empty. It was 1.06fr, a seam at 51.5 percent, and the
   sign in card is capped at 400px sitting in the middle of whatever is left, so
   on a wide screen the right pane was mostly air around a small card. 1.63fr
   puts the seam near 62 percent, which is his 20 percent move.

   THE ANIMATION NEEDS NO SEPARATE CHANGE. `.j-hero` is inset 0 over the whole
   pane and `<jules-sequence>` is `width:100%;height:100%` inside it, so the
   sequence already takes whatever the pane is. `--door-aperture` belongs to
   `.j-aperture`, which this page does not use.

   THE SPLIT ONLY APPLIES WHERE THERE IS ROOM FOR IT. At 1000px, 38 percent is
   380px and the pane's own padding is 40px a side, which leaves 300px for a
   card designed at 400px. So the wide split starts at 1200px and everything
   between 900 and 1200 keeps the original proportion. Widening a hero must
   never squeeze the one thing on the page a person came to click. */
.j-door { display: grid; grid-template-columns: 1.06fr 20px 1fr; min-height: 100vh; background: var(--void); }
@media (min-width: 1200px) { .j-door { grid-template-columns: 1.63fr 20px 1fr; } }
.j-door-hero { position: relative; display: grid; align-content: space-between; gap: var(--s6); padding: var(--s7) var(--s7) var(--s6); background: var(--void); overflow: hidden; }
/* CENTRED IN ITS PANE, 19 Aug 2026 (Mesh). The card is capped at 400px and was
   pinned to the left edge of the pane, so the gap on its right was always bigger
   than the gap on its left. Moving the seam made that asymmetry obvious. The
   text inside stays left aligned, because centred body copy is harder to read
   and the design return set it that way; what is centred is the block. */
.j-door-pane { display: grid; align-content: center; justify-items: center; gap: var(--s5); padding: var(--s7) var(--s7); background: var(--carbon); }
.j-door-inner { display: grid; gap: var(--s5); width: 100%; max-width: 400px; }
.j-aperture { position: relative; width: min(var(--door-aperture), 62vh); aspect-ratio: 1; margin: 0 auto; border-radius: 50%; }
.j-aperture > img { width: 100%; height: 100%; border-radius: 50%; object-fit: cover; }
.j-aperture::before { content: ""; position: absolute; inset: -14px; border-radius: 50%; border: 1px solid var(--edge); box-shadow: 0 0 90px -20px color-mix(in oklab, var(--olive) 55%, transparent); }
.j-aperture::after { content: ""; position: absolute; inset: 0; border-radius: 50%; border: 1px solid var(--line-soft); }
/* The hero mount. The table is a layer under the whole left pane, not an
   object inside a box: it has to run under the wordmark and off the edges. */
.j-hero { position: absolute; inset: 0; z-index: 0; pointer-events: none; }
.j-door-hero > *:not(.j-hero) { position: relative; z-index: 1; }
.j-hero--inline { position: relative; inset: auto; width: 100%; height: min(560px, 58vh); }
.j-seam[data-lit] { animation: j-seam-lit 1500ms cubic-bezier(0.2, 0.7, 0.2, 1) 1; }
@keyframes j-seam-lit { 0% { filter: none; } 26% { filter: brightness(1.9) saturate(1.08); } 100% { filter: none; } }
@media (prefers-reduced-motion: reduce) { .j-seam[data-lit] { animation: none; } }

/* The Google action. The official Google mark is supplied by the build,
   under Google's own brand rules. Do not redraw it here. */
.j-google { width: 100%; justify-content: center; min-height: 48px; font-size: 15px; }
.j-google[aria-disabled="true"] { pointer-events: none; }
@container (max-width: 900px) {
  .j-door { grid-template-columns: minmax(0, 1fr); min-height: 0; }
  .j-door-hero { padding: var(--s6) var(--s5) var(--s5); gap: var(--s5); min-height: 330px; }
  .j-door-pane { padding: var(--s6) var(--s5) var(--s7); justify-items: stretch; }
  .j-door-inner { max-width: none; }
  .j-aperture { width: min(300px, 62vw); }
}

/* --- 3. WORKER PORTAL ----------------------------------------------------
   One scrolling page in the order of the day. Not the admin desk with panels
   removed: no rail, one column, larger type, fewer hairlines, more air. --- */
.j-me { max-width: var(--portal-max); margin: 0 auto; padding: 0 var(--portal-pad) var(--s8); display: grid; gap: var(--s5); }
.j-card { background: var(--ink); border: 1px solid var(--line); border-radius: var(--r-panel); padding: var(--s5) var(--s5) var(--s6); display: grid; gap: var(--s4); }
.j-card > header { display: flex; align-items: baseline; justify-content: space-between; gap: var(--s3); }
.j-card h2 { margin: 0; font-family: var(--font-body); font-weight: 600; font-size: 17px; letter-spacing: 0; }
.j-card-link { font-family: var(--font-mono); font-size: 11px; letter-spacing: 0.1em; text-transform: uppercase; color: var(--sage); }
.j-card-link:hover { color: var(--olive-lift); }
/* A line of the record: label left, fact right, both readable at arm's length */
.j-line { display: flex; align-items: center; justify-content: space-between; gap: var(--s4); min-height: 44px; padding: 6px 0; border-bottom: 1px solid var(--line-soft); }
.j-line:last-child { border-bottom: 0; }
.j-line-k { display: grid; gap: 2px; min-width: 0; }
.j-line-k b { font-weight: 500; font-size: 15px; color: var(--sand); }
.j-line-k span { font-size: 12.5px; color: var(--sage); }
.j-line-v { display: flex; align-items: center; gap: 10px; flex: none; }
/* An honest blank. Used when Jules HAS no number, never when the number is 0. */
.j-blank { display: grid; gap: 6px; padding: var(--s4); border: 1px dashed var(--rc-unknown); border-radius: var(--r-ctl); background: var(--void); }
.j-blank p { margin: 0; font-size: 13.5px; line-height: 1.55; color: var(--rc-unknown-ink); }
.j-blank p b { color: var(--sand); font-weight: 600; }
/* A fact that is zero. Reads as a number, because it IS a number. */
.j-zero { font-family: var(--font-mono); font-weight: 700; font-size: 15px; color: var(--sand); font-variant-numeric: tabular-nums; }

/* Attendance chip set, carried forward from return 1 unchanged, now a class.
   26px pill, mono 9.5, border is the token at 38%, fill is always --fill-faint. */
.j-att { display: inline-flex; align-items: center; height: 26px; padding: 0 10px; border-radius: var(--r-pill); background: var(--fill-faint); border: 1px solid var(--line); font-family: var(--font-mono); font-size: 9.5px; letter-spacing: 0.1em; text-transform: uppercase; white-space: nowrap; }
.j-att--worked  { color: var(--att-worked);  border-color: color-mix(in srgb, var(--att-worked) 38%, transparent); }
.j-att--extra   { color: var(--att-extra);   border-color: color-mix(in srgb, var(--att-extra) 38%, transparent); }
.j-att--short   { color: var(--att-short);   border-color: color-mix(in srgb, var(--att-short) 30%, transparent); }
.j-att--covered { color: var(--att-covered); border-color: color-mix(in srgb, var(--att-covered) 38%, transparent); }
.j-att--review  { color: var(--att-review);  border-color: color-mix(in srgb, var(--att-review) 38%, transparent); }

/* The person band. The one place on a worker's page where a person is the
   subject, so it is the one place the human layer owns. */
.j-person { display: flex; align-items: center; gap: var(--s4); flex-wrap: wrap; }
.j-avatar { flex: none; width: 52px; height: 52px; border-radius: 50%; background: var(--human-14); border: 1px solid var(--human-38); color: var(--human); display: grid; place-items: center; font-family: var(--font-mono); font-size: 14px; font-weight: 700; overflow: hidden; }
.j-avatar img { width: 100%; height: 100%; object-fit: cover; }

/* Document evidence. Signed is not verified, and the design must not collapse it. */
.j-ev { display: inline-flex; align-items: center; gap: 7px; font-family: var(--font-mono); font-size: 10.5px; letter-spacing: 0.12em; text-transform: uppercase; white-space: nowrap; }
.j-ev::before { content: ""; width: 7px; height: 7px; border-radius: 50%; flex: none; }
.j-ev--verified { color: var(--olive-lift); }
.j-ev--verified::before { background: var(--olive-lift); }
.j-ev--signed { color: var(--amber); }
.j-ev--signed::before { background: transparent; border: 1.5px solid var(--amber); }
.j-ev--waiting { color: var(--sand); }
.j-ev--waiting::before { background: transparent; border: 1.5px dashed var(--sage); }

/* --- 4. LIFECYCLE STEP ROW ----------------------------------------------
   State, attempt count and receipt on one row. The mark carries the state,
   the receipt carries the proof, the reason carries the human. ---------- */
.j-answers { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 1px; background: var(--line); border: 1px solid var(--line); border-radius: var(--r-ctl); overflow: hidden; }
.j-answer { background: var(--ink); padding: var(--s4) var(--s5); display: grid; gap: 8px; align-content: start; }
.j-answer > .k-label { color: var(--sage); }
.j-answer > p { margin: 0; font-size: 15px; line-height: 1.45; color: var(--sand); }
.j-answer[data-tone="ask"] > p { color: var(--amber); }
.j-answer[data-tone="settled"] > p { color: var(--olive-lift); }
@container (max-width: 768px) { .j-answers { grid-template-columns: minmax(0, 1fr); } }

.j-step { display: grid; grid-template-columns: 26px minmax(0, 1fr) auto; gap: var(--s4); padding: 14px 16px 14px 13px; border-bottom: 1px solid var(--line-soft); position: relative; }
.j-step:last-child { border-bottom: 0; }
.j-step-mark { position: relative; width: 22px; height: 22px; margin-top: 1px; border-radius: 50%; border: 1px solid var(--line-strong); background: var(--carbon); display: grid; place-items: center; }
.j-step-mark > i { width: 8px; height: 8px; border-radius: 50%; background: var(--st-pending); }
/* the spine, so eleven steps read as one ordered run */
.j-step::before { content: ""; position: absolute; left: 23px; top: 34px; bottom: -1px; width: 1px; background: var(--line); }
.j-step:last-child::before { display: none; }
.j-step-b { display: grid; gap: 6px; min-width: 0; }
.j-step-b > h3 { margin: 0; font-family: var(--font-body); font-weight: 600; font-size: 14.5px; color: var(--sand); }
.j-step-b > p { margin: 0; font-size: 13.5px; line-height: 1.55; color: var(--sage); }
.j-step-meta { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; }
.j-receipt { display: inline-flex; align-items: center; gap: 7px; padding: 3px 8px; border-radius: 5px; background: var(--fill-faint); border: 1px solid var(--line); font-family: var(--font-mono); font-size: 10.5px; letter-spacing: 0.06em; color: var(--sage); white-space: nowrap; }
.j-attempts { font-family: var(--font-mono); font-size: 10.5px; letter-spacing: 0.1em; text-transform: uppercase; color: var(--sage); }
.j-step-r { display: grid; gap: 8px; justify-items: end; align-content: start; }
.j-owner { display: inline-flex; align-items: center; gap: 7px; font-size: 13px; color: var(--sand); white-space: nowrap; }
.j-owner > span { width: 22px; height: 22px; border-radius: 50%; background: var(--human-14); border: 1px solid var(--human-24); color: var(--human); display: grid; place-items: center; font-family: var(--font-mono); font-size: 8.5px; font-weight: 700; }

.j-step[data-state="done"]    .j-step-mark > i { background: var(--st-done); }
.j-step[data-state="running"] .j-step-mark { border-color: var(--olive-lift); }
.j-step[data-state="running"] .j-step-mark > i { background: var(--st-running); box-shadow: 0 0 0 3px var(--rec-ring); animation: k-breathe var(--d-live) var(--e-in-out) infinite; }
.j-step[data-state="failed"]  .j-step-mark { border-color: color-mix(in oklab, var(--clay) 55%, transparent); }
.j-step[data-state="failed"]  .j-step-mark > i { background: var(--st-failed); }
.j-step[data-state="needs_human"] .j-step-mark { border-color: color-mix(in oklab, var(--amber) 60%, transparent); }
.j-step[data-state="needs_human"] .j-step-mark > i { background: var(--st-human); }
.j-step[data-state="skipped"] .j-step-mark > i { background: transparent; border: 1.5px solid var(--st-skipped); width: 9px; height: 9px; }
.j-step[data-state="pending"] .j-step-b > h3 { color: var(--sage); }
.j-step[data-state="needs_human"], .j-step[data-state="failed"] { background: var(--fill-faint); }
.j-step[data-blocking="true"] { box-shadow: inset 3px 0 0 var(--amber); }
@container (max-width: 768px) {
  .j-step { grid-template-columns: 26px minmax(0, 1fr); }
  .j-step-r { grid-column: 2; justify-items: start; }
}

/* --- 5. ACCESS GRANT, TWO AXES ------------------------------------------
   State and reconciliation are independent and are drawn independently.
   The row edge is set by the PAIR. A single chip would lie. -------------- */
.j-grant { display: grid; grid-template-columns: minmax(0, 1.5fr) 150px 190px minmax(0, 1.3fr); gap: var(--s4); align-items: center; padding: 13px 16px 13px 13px; border-bottom: 1px solid var(--line-soft); }
.j-grant:last-child { border-bottom: 0; }
.j-grant[data-verdict="open"]    { box-shadow: inset 3px 0 0 var(--vd-open); background: var(--fill-faint); }
.j-grant[data-verdict="ask"]     { box-shadow: inset 3px 0 0 var(--vd-ask); }
.j-grant[data-verdict="blank"]   { box-shadow: inset 3px 0 0 var(--vd-blank); }
.j-grant[data-verdict="settled"] { box-shadow: none; }
.j-sys { display: grid; gap: 3px; min-width: 0; }
.j-sys b { font-weight: 600; font-size: 14px; color: var(--sand); }
.j-sys span { font-family: var(--font-mono); font-size: 10.5px; letter-spacing: 0.08em; color: var(--sage); }
/* axis one: what Jules was asked to do */
.j-st { display: inline-flex; align-items: center; gap: 7px; height: 26px; padding: 0 10px; border-radius: var(--r-pill); background: var(--fill-faint); border: 1px solid var(--line-strong); font-family: var(--font-mono); font-size: 9.5px; letter-spacing: 0.1em; text-transform: uppercase; color: var(--sage); white-space: nowrap; }
.j-st--active  { color: var(--sand); }
.j-st--pending { color: var(--amber); border-color: color-mix(in oklab, var(--amber) 38%, transparent); }
.j-st--revoked { color: var(--sage); }
/* axis two: what the system actually reports. A FACT, not a status. */
.j-rc { display: inline-flex; align-items: center; gap: 8px; font-family: var(--font-mono); font-size: 10.5px; letter-spacing: 0.1em; text-transform: uppercase; white-space: nowrap; }
.j-rc::before { content: ""; width: 9px; height: 9px; flex: none; }
.j-rc--present  { color: var(--rc-present); }
.j-rc--present::before  { background: var(--rc-present); }
.j-rc--absent   { color: var(--rc-absent); }
.j-rc--absent::before   { background: transparent; border: 1.5px solid var(--rc-absent); }
.j-rc--mismatch { color: var(--rc-mismatch); }
.j-rc--mismatch::before { background: transparent; border: 1.5px solid var(--rc-mismatch); transform: rotate(45deg); }
/* the honest blank: no fill, no colour, no tick nobody verified */
.j-rc--unknown  { color: var(--rc-unknown-ink); }
.j-rc--unknown::before  { background: transparent; border: 1px dashed var(--rc-unknown); border-radius: 50%; }
.j-consequence { margin: 0; font-size: 13px; line-height: 1.5; color: var(--sage); }
.j-consequence b { color: var(--sand); font-weight: 600; }
@container (max-width: 900px) {
  .j-grant { grid-template-columns: minmax(0, 1fr) auto; gap: 10px 14px; padding: 14px 16px 16px 13px; }
  .j-grant > .j-rc { grid-column: 1 / -1; }
  .j-grant > .j-consequence { grid-column: 1 / -1; }
}

/* --- 6. ROLE SCOPED NAVIGATION ------------------------------------------
   Three compositions, not one rail with items removed. -------------------- */
.j-rail { width: var(--rail); flex: none; display: grid; align-content: start; gap: var(--s5); padding: var(--s5) var(--s4); border-right: 1px solid var(--line); background: var(--carbon); }
.j-navgroup { display: grid; gap: 2px; }
.j-navgroup > .k-label { padding: 0 var(--s3) 6px; }
.j-navitem { display: flex; align-items: center; gap: var(--s3); min-height: 40px; padding: 9px var(--s3); border-radius: 6px; font-size: var(--t-small); font-weight: 600; color: var(--sage); }
.j-navitem:hover { color: var(--sand); background: var(--hover); }
.j-navitem[aria-current="page"] { color: var(--sand); background: var(--raised); box-shadow: inset 3px 0 0 var(--olive); }
.j-navitem[aria-disabled="true"] { color: var(--sage); opacity: 0.42; pointer-events: none; }
.j-navitem svg { flex: none; }
.j-mob { display: flex; align-items: stretch; height: 62px; border-top: 1px solid var(--line); background: var(--carbon); }
.j-mob a { flex: 1; display: grid; place-items: center; gap: 4px; min-height: 44px; padding: 9px 4px; font-family: var(--font-mono); font-size: 9.5px; letter-spacing: 0.1em; text-transform: uppercase; color: var(--sage); }
.j-mob a[aria-current="page"] { color: var(--sand); }
.j-mob a[aria-current="page"] svg { color: var(--olive-lift); }

/* --- 7. VIDEO CAPTURE ---------------------------------------------------
   Six states, all of them honest. Nothing here scores a face. ------------ */
.j-cap { display: grid; gap: var(--s4); max-width: var(--portal-max); margin: 0 auto; }
.j-stage { position: relative; aspect-ratio: 3 / 4; border-radius: var(--r-panel); background: var(--void); border: 1px solid var(--line); overflow: hidden; display: grid; place-items: center; }
.j-stage[data-state="recording"] { border-color: color-mix(in oklab, var(--olive-lift) 55%, transparent); }
.j-stage[data-state="failed"] { border-color: color-mix(in oklab, var(--clay) 45%, transparent); }
.j-stage-bar { position: absolute; left: 0; right: 0; top: 0; display: flex; align-items: center; justify-content: space-between; gap: var(--s3); padding: 12px 14px; }
.j-stage-foot { position: absolute; left: 0; right: 0; bottom: 0; display: grid; gap: 10px; padding: 14px; }
.j-rec { display: inline-flex; align-items: center; gap: 8px; height: 26px; padding: 0 11px; border-radius: var(--r-pill); background: var(--void); border: 1px solid var(--line-strong); font-family: var(--font-mono); font-size: 10.5px; letter-spacing: 0.12em; text-transform: uppercase; color: var(--sand); }
.j-rec > i { width: 8px; height: 8px; border-radius: 50%; background: var(--rec); box-shadow: 0 0 0 3px var(--rec-ring); animation: k-breathe var(--d-live) var(--e-in-out) infinite; }
.j-timer { font-family: var(--font-mono); font-weight: 700; font-size: 15px; font-variant-numeric: tabular-nums; color: var(--sand); }
.j-timer--think { color: var(--amber); }
.j-takes { display: inline-flex; align-items: center; gap: 6px; }
.j-takes > i { width: 18px; height: 4px; border-radius: 2px; background: var(--take-left); }
.j-takes > i[data-used="true"] { background: var(--take-used); }
.j-progress { display: flex; gap: 4px; }
.j-progress > i { flex: 1; height: 4px; border-radius: 2px; background: var(--raised); }
.j-progress > i[data-done="true"] { background: var(--olive-lift); }
.j-progress > i[data-current="true"] { background: var(--signal); }

/* --- 8. FOCUS AND REDUCED MOTION, on every new interactive element ------- */
.j-navitem:focus-visible, .j-card-link:focus-visible, .j-google:focus-visible,
.j-mob a:focus-visible, .j-step:focus-visible, .j-grant:focus-visible {
  outline: 2px solid var(--focus); outline-offset: 2px; border-radius: 4px;
}
@media (prefers-reduced-motion: reduce) {
  .j-step[data-state="running"] .j-step-mark > i,
  .j-rec > i { animation: none; }
  .j-step[data-state="running"] .j-step-mark > i { box-shadow: 0 0 0 3px var(--rec-ring); }
}

/* --- 9. THE LIVE INTERVIEW, 20 Aug 2026 ---------------------------------
   The approved Claude Design return owns the live picture. The mobile target
   is 390 by 760. The desktop target is 16 by 9. The existing portal column,
   controls and page order stay unchanged around it. */
.j-live-presence {
  position: relative; width: 100%; aspect-ratio: 390 / 760; overflow: hidden;
  border-radius: var(--r-panel); border: 1px solid var(--line); background: var(--void);
}
@media (min-width: 720px) {
  .j-live-presence { aspect-ratio: 16 / 9; }
}

/* The preparation page keeps its approved card. Once the candidate starts,
   Claude Design's interview room becomes the whole viewport. */
body.j-room-active { overflow: hidden; }
.j-call-room[data-room-active="true"] {
  position: fixed; inset: 0; width: 100vw; height: 100dvh; z-index: 1000;
  padding: 0; margin: 0; background: #071426;
}
.j-call-room[data-room-active="true"] .j-live-presence {
  position: absolute; inset: 0; width: 100%; height: 100%; aspect-ratio: auto;
  border: 0; border-radius: 0;
}

/* WHO IS TALKING, in words, because a colour alone is not an accessible state
   and somebody with the sound low needs to know she is listening to them. */
.j-who { display: inline-flex; align-items: center; gap: 8px; height: 28px; padding: 0 12px; border-radius: var(--r-pill); background: var(--fill-faint); border: 1px solid var(--line); font-family: var(--font-mono); font-size: 10px; letter-spacing: 0.14em; text-transform: uppercase; color: var(--sage); }
.j-who > i { width: 7px; height: 7px; border-radius: 50%; background: var(--edge); }
.j-who[data-state="listening"] > i { background: var(--human); box-shadow: 0 0 0 3px var(--human-24); }
.j-who[data-state="speaking"] > i { background: var(--olive-lift); box-shadow: 0 0 0 3px rgba(155, 176, 104, 0.24); animation: k-breathe var(--d-live) var(--e-in-out) infinite; }

/* HER LAST LINE, so a candidate who missed a word can read it. Deliberately
   only Charlotte's words: transcribing the candidate back at herself while she
   is mid sentence is the fastest way to make somebody self conscious, and she
   is already nervous. */
.j-caption { min-height: 44px; margin: 0; font-size: 15px; line-height: 1.55; color: var(--sand); }
.j-caption:empty::before { content: ""; }

/* The mirrored camera check. `scaleX(-1)` is the whole fix for the lane that
   died: a preview that is not mirrored looks wrong to everybody, because a
   mirror is the only version of your own face you have ever practised in. */
.j-selfie { position: absolute; inset: 0; width: 100%; height: 100%; object-fit: cover; transform: scaleX(-1); }

@media (prefers-reduced-motion: reduce) {
  .j-who[data-state="speaking"] > i { animation: none; }
}

/* THE TASK PANEL, 14 Sep 2026. During the typed tasks of the main assessment
   the approved interview room stays the stage and the task sits beside it on
   a desktop, below it on a phone, on the same card tokens the portal already
   uses. Nothing here restyles the room; it gives the room a place to put the
   rules card, the task and the candidate's own words. */
.j-task-panel { display: none; }
.j-call-room[data-room-active="true"] .j-task-panel[data-open="true"] {
  /* align-content: start keeps the rules at the top at their own height. The
     default stretched six rules down a 960 px panel (first trial, 15 Sep). */
  display: grid; gap: var(--s4); align-content: start; position: absolute; z-index: 1200;
  right: 16px; top: 16px; bottom: 16px; width: min(440px, 44vw);
  overflow-y: auto; padding: var(--s5); background: var(--ink);
  border: 1px solid var(--line); border-radius: var(--r-panel);
  box-shadow: 0 26px 60px -26px #000;
}
.j-call-room[data-room-active="true"] .j-task-panel[data-open="true"] .k-textarea {
  min-height: 220px; resize: vertical; font-size: 14px; line-height: 1.55;
}
.j-task-rules { display: grid; gap: 6px; margin: 0; padding: 0 0 0 18px; }
.j-task-rules li { font-size: 13px; line-height: 1.5; color: var(--sand); }
@media (max-width: 760px) {
  .j-call-room[data-room-active="true"] .j-task-panel[data-open="true"] {
    right: 8px; left: 8px; top: auto; bottom: 8px; width: auto; max-height: 58dvh;
    padding: var(--s4);
  }
  .j-call-room[data-room-active="true"] .j-task-panel[data-open="true"] .k-textarea { min-height: 140px; }
}
