/* AppTheme parity (SPEC §8 / pixelizer/scripts/app/AppTheme.gd). Palette ported verbatim:
   Godot Color(r,g,b) 0-1 → CSS rgb(0-255). Geometry: 1px borders, 3-4px radius, font 14.
   UI scale is driven by --ui-scale (1.0 = 100%); all sizes are in rem so root font-size
   scales the whole UI (see applyUiScale in theme.ts). Set src/ui/* code against these vars. */
:root {
  --ui-scale: 1;

  /* ── palette (AppTheme.gd constants, RGB 0-1 → 0-255) ──
     UX/UI rework Part III: neutral true-gray chrome (spec/ux-ui-rework/SPEC.md §16-19). */
  --bg-card: #2e2e2e; /* BG_CARD   0.18,0.18,0.18 */
  --bg-header: #383838; /* BG_HEADER 0.22,0.22,0.22 */
  --bg-widget: #262626; /* BG_WIDGET 0.15,0.15,0.15 */
  --border: #424242; /* BORDER    0.26,0.26,0.26 */
  --accent: #6b8fb8; /* BORDER_FCS 0.42,0.561,0.722 steel blue (focus / selection / slider fill) */
  --accent-fill: #6b8fb8; /* slider fill — solid, no alpha (§16 a11y fix) */
  --accent-sel: #6b8fb8; /* selection — solid, no alpha (§16 a11y fix) */
  --text: rgb(224, 224, 224); /* TEXT     0.88,0.88,0.88 */
  --text-dim: #a3a3a3; /* TEXT_DIM  0.64,0.64,0.64 (§16 a11y fix, was 0.50,0.52,0.55) */

  /* widget / field backgrounds (AppTheme LineEdit + HSlider track) — neutralized, no blue tint */
  --bg-field: #1f1f1f; /* LineEdit field ≈0.12,0.12,0.12 */
  --bg-app: #212121; /* window bg, matches status-bar luminance */
  --bg-status: #212121; /* StatusBarPanel ≈0.13,0.13,0.13 */
  --bg-popup: #242424; /* PopupMenu ≈0.14,0.14,0.14 */
  --bg-tab-unsel: #242424; /* TabBar tab_unselected ≈0.14,0.14,0.14 */
  --bg-tab-hover: #2e2e2e; /* tab_hovered ≈0.18,0.18,0.18 */
  --bg-tooltip: rgba(23, 23, 23, 0.97); /* tooltip 0.09,0.09,0.09 @0.97 */
  --border-tooltip: #474747; /* tooltip border ≈0.28,0.28,0.28 */

  /* ── per-panel left-border accent colors (SPEC §8; muted set §18) ── */
  --accent-base: #c78c80;
  --accent-height: #85b88c;
  --accent-normal: #8a80c7;
  --accent-orm: #d1b873;
  --accent-tileable: #a18dcf;

  /* status feedback colors (MainController validation + Process button) */
  --status-error: rgb(255, 89, 76); /* 1.0,0.35,0.3 */
  --status-warn: rgb(255, 191, 51); /* 1.0,0.75,0.2 */
  --process-red: rgb(217, 77, 77); /* 0.85,0.30,0.30 */
  --process-red-bg: rgb(56, 26, 26); /* 0.22,0.10,0.10 */

  /* ── geometry ── */
  --radius: 4px;
  --radius-sm: 3px;
  --border-w: 1px;
  --font-size: calc(14rem / 16); /* default_font_size 14, scaled via root rem */
  --font-size-section: calc(12rem / 16);
  --font-size-title: calc(15rem / 16);
  --gap: calc(4rem / 16);
  --pad-card: calc(8rem / 16);
  --label-col: calc(160rem / 16); /* PanelBase.LABEL_COL_W — sized for "Boundary Protection" / dual-labels at 14px, no wrap */

  font-size: calc(16px * var(--ui-scale)); /* rem anchor — applyUiScale sets --ui-scale */
}

* {
  box-sizing: border-box;
}

html,
body {
  margin: 0;
  height: 100%;
  background: var(--bg-app);
  color: var(--text);
  font-family: system-ui, sans-serif;
  font-size: var(--font-size);
}
/* #app must carry the viewport height: .pz-app is height:100% and resolves against this.
   Without it #app is auto-height → the app grows to fit the left column (page scrolls down)
   and the flex-filled preview area collapses to 0 (2D canvas draws nothing). */
#app {
  height: 100%;
}

/* ── App shell layout (SPEC §8) ──────────────────────────────────────────── */
.pz-app {
  display: flex;
  flex-direction: column;
  height: 100%;
  overflow: hidden;
  position: relative; /* anchor for the bottom-right software-adapter warning overlay */
}
/* Software-WebGPU warning, right-aligned over the status bar. */
.pz-status-warn-right {
  position: absolute;
  right: calc(8rem / 16);
  bottom: calc(4rem / 16);
  z-index: 50;
  color: var(--status-warn);
  font-size: var(--font-size);
  pointer-events: none;
}
.pz-menu-row {
  display: flex;
  align-items: center;
  gap: calc(8rem / 16);
  padding: calc(4rem / 16) calc(8rem / 16);
  background: var(--bg-header);
  border-bottom: var(--border-w) solid var(--border);
  flex: 0 0 auto;
}
.pz-menubar {
  display: flex;
  gap: calc(4rem / 16); /* spacing rhythm 4/6/8 (R4) — was off-scale 2 */
}
.pz-body {
  display: flex;
  flex: 1 1 auto;
  min-height: 0; /* allow children to scroll */
}
/* Left pane = fixed-width column: scroll area (flex:1) + pinned Export footer (flex:0) — R2. */
.pz-left-pane {
  display: flex;
  flex-direction: column;
  flex: 0 0 auto;
  width: calc(360rem / 16); /* fixed sidebar — preview absorbs window growth (R1) */
}
.pz-left-scroll {
  flex: 1 1 auto;
  min-height: 0; /* let the scroll area shrink so the footer stays pinned */
  overflow-y: auto;
  overflow-x: hidden; /* rows compress, never pan sideways (R: no permanent h-scrollbar) */
  padding: calc(8rem / 16);
}
.pz-left-col {
  display: flex;
  flex-direction: column;
  gap: calc(8rem / 16);
}
.pz-left-footer {
  flex: 0 0 auto;
  padding: calc(8rem / 16);
  border-top: var(--border-w) solid var(--border);
}
.pz-split-divider {
  flex: 0 0 calc(6rem / 16);
  background: var(--border);
  cursor: col-resize;
  touch-action: none;
}
.pz-split-divider:hover,
.pz-app.is-resizing-split .pz-split-divider {
  background: var(--accent);
}
.pz-app.is-resizing-split {
  cursor: col-resize;
  user-select: none;
}
.pz-right {
  display: flex;
  flex-direction: column;
  flex: 1 1 auto;
  min-width: calc(320rem / 16); /* divider/flex can't crush the preview (R: RightPanel min 320) */
}
/* ONE merged preview header (R3): [channel tabs (expand)] [stale-badge slot] [view switcher]. */
.pz-preview-header {
  display: flex;
  align-items: center;
  flex: 0 0 auto;
  background: var(--bg-header);
  border-bottom: var(--border-w) solid var(--border);
}
.pz-channel-tabs {
  display: flex;
  flex: 1 1 auto;
  min-width: 0;
  overflow: hidden; /* at narrow widths tabs clip rather than wrapping the row */
}
.pz-stale-slot {
  display: flex;
  align-items: center;
  flex: 0 0 auto;
}
.pz-view-tabs {
  display: flex;
  flex: 0 0 auto;
  margin-left: auto; /* pin to the right end; stays put when channel tabs hide in 3D */
}
.pz-preview-area {
  flex: 1 1 auto;
  min-height: 0;
  position: relative;
  overflow: hidden;
}
.pz-view {
  position: absolute;
  inset: 0;
}
.pz-view[hidden] {
  display: none;
}
.pz-status-bar {
  flex: 0 0 auto;
  background: var(--bg-status);
  border-top: var(--border-w) solid var(--border);
  padding: calc(4rem / 16) calc(8rem / 16);
  font-size: var(--font-size);
}

/* ── tabs (TabBar parity: selected = 2px accent bottom border) ───────────── */
.pz-tab {
  background: var(--bg-tab-unsel);
  color: var(--text-dim);
  border: none;
  border-bottom: calc(2rem / 16) solid transparent;
  padding: calc(4rem / 16) calc(10rem / 16);
  font: inherit;
  cursor: pointer;
}
.pz-tab:hover {
  background: var(--bg-tab-hover);
  color: var(--text);
}
.pz-tab.is-selected {
  background: var(--bg-card);
  color: var(--text);
  border-bottom-color: var(--accent);
}

/* ── card / panel (CardPanel + HeaderPanel) ──────────────────────────────── */
.pz-card {
  background: var(--bg-card);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius);
}
.pz-card-header {
  display: flex;
  align-items: center;
  gap: calc(4rem / 16);
  background: var(--bg-header);
  border-top-left-radius: var(--radius);
  border-top-right-radius: var(--radius);
  padding: calc(6rem / 16);
}
.pz-card-title {
  flex: 1 1 auto;
  font-size: var(--font-size-title);
}
.pz-card-body {
  padding: var(--pad-card);
  display: flex;
  flex-direction: column;
  gap: var(--gap);
}
.pz-card-body[hidden] {
  display: none;
}

/* Per-panel accent left border — applied only when :root has .pz-accents
   (Options "Color-code panels" toggle). Class hook, not per-panel JS. */
.pz-accents .pz-card.pz-accent-base_color {
  border-left: calc(2rem / 16) solid var(--accent-base);
}
.pz-accents .pz-card.pz-accent-height {
  border-left: calc(2rem / 16) solid var(--accent-height);
}
.pz-accents .pz-card.pz-accent-normal {
  border-left: calc(2rem / 16) solid var(--accent-normal);
}
.pz-accents .pz-card.pz-accent-orm {
  border-left: calc(2rem / 16) solid var(--accent-orm);
}
.pz-accents .pz-card.pz-accent-tileable {
  border-left: calc(2rem / 16) solid var(--accent-tileable);
}

/* ── widgets ─────────────────────────────────────────────────────────────── */
.pz-row {
  display: flex;
  align-items: center;
  gap: calc(6rem / 16);
}
.pz-label {
  flex: 0 0 var(--label-col);
  color: var(--text);
}
.pz-section-sep {
  border: none;
  border-top: var(--border-w) solid var(--border);
  margin: calc(4rem / 16) 0;
}
.pz-section-title {
  font-size: var(--font-size-section);
  color: var(--text);
}
/* a hidden section/body must stay hidden — only style elements NOT carrying [hidden] */
.pz-section[hidden],
.pz-advanced[hidden] {
  display: none;
}

.pz-btn {
  background: var(--bg-widget);
  color: var(--text);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius-sm);
  padding: calc(3rem / 16) calc(8rem / 16);
  font: inherit;
  cursor: pointer;
}
.pz-btn:hover {
  background: rgb(46, 46, 46);
}
.pz-btn:focus-visible {
  outline: none;
  border-width: calc(2rem / 16); /* §16 a11y: focus stroke widened 1px→2px */
  border-color: var(--accent);
}
.pz-btn:disabled {
  color: var(--text-dim);
  opacity: 0.6;
  cursor: default;
}
.pz-btn.is-flat {
  background: transparent;
  border-color: transparent;
}
.pz-btn.is-icon {
  min-width: calc(24rem / 16);
  padding: calc(3rem / 16) calc(4rem / 16);
}

/* slider: native range styled to the accent fill */
.pz-slider {
  flex: 1 1 auto;
  min-width: 0;
  accent-color: var(--accent);
  height: calc(18rem / 16);
}
/* slider type-in: two-way bound numeric field. TIGHT fixed width — fits "-180.00" (Hue) with a
   little slack, ~8px narrower than .pz-spin so the range keeps room in the fixed 360px sidebar. */
.pz-slider-num {
  flex: 0 0 calc(64rem / 16);
  width: calc(64rem / 16);
  text-align: right;
  background: var(--bg-field);
  color: var(--text);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius-sm);
  padding: calc(3rem / 16) calc(4rem / 16);
  font: inherit;
}
.pz-slider-num:focus {
  outline: none;
  border-width: calc(2rem / 16); /* §16 a11y: focus stroke widened 1px→2px */
  border-color: var(--accent);
}
.pz-slider-num:disabled {
  color: var(--text-dim);
  opacity: 0.6;
}

.pz-select,
.pz-text,
.pz-spin {
  background: var(--bg-field);
  color: var(--text);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius-sm);
  padding: calc(3rem / 16) calc(6rem / 16);
  font: inherit;
}
.pz-select {
  flex: 1 1 auto;
  min-width: 0;
}
.pz-text {
  flex: 1 1 auto;
  min-width: 0;
}
.pz-spin {
  width: calc(72rem / 16);
}
.pz-select:focus,
.pz-text:focus,
.pz-spin:focus {
  outline: none;
  border-width: calc(2rem / 16); /* §16 a11y: focus stroke widened 1px→2px */
  border-color: var(--accent);
}
.pz-text::selection {
  background: var(--accent-sel);
}
.pz-text:read-only {
  background: rgb(26, 26, 26); /* readonly field ~0.10,0.10,0.10 */
  color: var(--text-dim);
}

.pz-check {
  display: flex;
  align-items: center;
  gap: calc(6rem / 16);
  cursor: pointer;
}
.pz-check input {
  accent-color: var(--accent);
}

/* drop target affordance (text field with browse/drag-drop hook) */
.pz-droptarget.is-dragover {
  border-color: var(--accent);
  background: rgba(107, 143, 184, 0.15);
}

/* ── [hidden] guards — any display rule we set must not defeat el.hidden ──── */
.pz-modal-overlay[hidden] { display: none; }
.pz-menu-popup[hidden]    { display: none; }
/* latent: flex from .pz-row / shell init fights el.hidden on compare rows + channel tabs */
.pz-row[hidden]           { display: none; }
.pz-channel-tabs[hidden]  { display: none; }
.pz-cards[hidden]         { display: none; }
.pz-stale-badge[hidden]   { display: none; }

/* ── .pz-cards — left-column wrapper for Input/Output/Export cards ─────────── */
.pz-cards {
  display: flex;
  flex-direction: column;
  gap: var(--gap);
}

/* ── Menus: popup dropdown (pz-menu wraps btn + popup) ──────────────────────
   .pz-menu-btn = .pz-btn.is-flat — already styled; nothing extra needed.
   The popup positions itself under the button via position:absolute. */
.pz-menu {
  position: relative;
}
.pz-menu-popup {
  position: absolute;
  top: 100%;
  left: 0;
  z-index: 100;
  min-width: calc(160rem / 16);
  background: var(--bg-popup);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius);
  padding: calc(4rem / 16);
  display: flex;
  flex-direction: column;
  gap: calc(1rem / 16);
}
.pz-menu-item {
  display: block;
  width: 100%;
  background: transparent;
  color: var(--text);
  border: none;
  border-radius: var(--radius-sm);
  padding: calc(3rem / 16) calc(8rem / 16);
  font: inherit;
  text-align: left;
  cursor: pointer;
  white-space: nowrap;
}
.pz-menu-item:hover {
  background: rgba(107, 143, 184, 0.22); /* pm_hov BG_FCS @0.22 */
  color: var(--text);
}
/* check items: checked = bold prefix "✓", plain indented otherwise — already in the text */
.pz-menu-check { /* inherits .pz-menu-item */ }
.pz-menu-check.is-checked {
  color: var(--text);
}
.pz-menu-sep {
  border: none;
  border-top: var(--border-w) solid var(--border);
  margin: calc(3rem / 16) calc(4rem / 16);
}

/* ── Modal overlay (Export Options + Help) ───────────────────────────────── */
.pz-modal-overlay {
  position: fixed;
  inset: 0;
  z-index: 200;
  display: flex;
  align-items: center;
  justify-content: center;
  background: rgba(0, 0, 0, 0.55);
}
.pz-modal {
  background: var(--bg-card);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius);
  padding: var(--pad-card);
  display: flex;
  flex-direction: column;
  gap: calc(6rem / 16);
  min-width: calc(320rem / 16);
  max-width: calc(480rem / 16);
  max-height: 85vh;
  overflow-y: auto;
}
.pz-modal-title {
  font-size: var(--font-size-title);
  color: var(--text);
  font-weight: 600;
  padding-bottom: calc(4rem / 16);
  border-bottom: var(--border-w) solid var(--border);
}
.pz-modal-label {
  color: var(--text-dim);
  font-size: var(--font-size-section);
  margin-top: calc(2rem / 16);
}
.pz-modal-close {
  align-self: flex-end;
  margin-top: calc(4rem / 16);
}
/* Export dialog: channel toggles as a 2-column grid instead of a tall stack. */
.pz-modal-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: calc(2rem / 16) calc(12rem / 16);
}
.pz-modal hr {
  border: none;
  border-top: var(--border-w) solid var(--border);
  margin: calc(4rem / 16) 0;
  width: 100%;
}
/* Help dialog: style the raw innerHTML content */
.pz-help h2,
.pz-help h3 {
  margin: calc(8rem / 16) 0 calc(4rem / 16);
  color: var(--text);
  font-size: var(--font-size-title);
}
.pz-help h2 { font-size: calc(16rem / 16); }
.pz-help p,
.pz-help li {
  color: var(--text);
  margin: calc(4rem / 16) 0;
}
.pz-help ol {
  padding-left: calc(20rem / 16);
}
.pz-help pre {
  background: var(--bg-widget);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius-sm);
  padding: calc(6rem / 16) calc(8rem / 16);
  font-size: var(--font-size);
  color: var(--text);
  white-space: pre-wrap;
  overflow-x: auto;
}

/* ── Process button states ───────────────────────────────────────────────── */
/* .pz-btn.is-stale → amber (warn); .is-running → accent blue; .is-errors → red */
.pz-btn.is-stale {
  border-color: var(--status-warn);
  color: var(--status-warn);
}
.pz-btn.is-stale:hover {
  background: rgba(255, 191, 51, 0.12);
}
.pz-btn.is-running {
  border-color: var(--accent);
  color: var(--accent);
}
.pz-btn.is-running:hover {
  background: rgba(107, 143, 184, 0.12);
}
.pz-btn.is-errors {
  border-color: var(--process-red);
  color: var(--process-red);
}
.pz-btn.is-errors:hover {
  background: var(--process-red-bg);
}

/* ── Staleness badge in the status bar ───────────────────────────────────── */
.pz-stale-badge {
  display: inline-block;
  margin-left: calc(8rem / 16);
  color: var(--status-warn);
  font-size: var(--font-size);
}

/* ── input validation ────────────────────────────────────────────────────── */
input.is-invalid {
  border-color: var(--status-error) !important;
  outline: none;
}
/* Inline validation message under the Input card (PRIMARY surface). Autowraps; hidden when clean
   (the `hidden` attribute). Warnings use the dim/warn tone; .has-error switches to the error tone. */
.pz-validation-msg {
  padding: calc(4rem / 16) calc(8rem / 16) 0;
  color: var(--status-warn);
  font-size: var(--font-size-section);
  line-height: 1.35;
  overflow-wrap: anywhere;
}
.pz-validation-msg.has-error {
  color: var(--status-error);
}
/* Always-visible safety net in the pinned Export footer (bug #8). */
.pz-issue-badge.pz-issue-badge {
  margin-top: calc(6rem / 16);
  color: var(--status-error);
  font-size: var(--font-size-section);
  cursor: pointer;
  text-align: left;
}

/* ── Preview 2D ──────────────────────────────────────────────────────────── */
/* Selectable neutral backdrop (SPEC §19) — default 50% gray; a later wave wires the JS
   selector that toggles these on .pz-preview2d / .pz-compare-stage. Never tinted. */
.pz-preview2d,
.pz-compare-stage {
  background-color: #808080; /* default backdrop: gray 0.5,0.5,0.5 */
}
.pz-backdrop-gray {
  background-color: #808080; /* 0.5,0.5,0.5 */
}
.pz-backdrop-dark {
  background-color: #1f1f1f; /* 0.12,0.12,0.12 */
}
.pz-backdrop-light {
  background-color: #d9d9d9; /* 0.85,0.85,0.85 */
}
/* Checkerboard is opt-in, ONLY for alpha (never forced, never tinted) — main.ts toggles .pz-checker
   on the 2D surface when the displayed image has alpha. NEUTRAL #474747/#333333 regardless of the
   selected backdrop (SPEC §19): background-color #333333 here (later, equal specificity) overrides
   the .pz-backdrop-* color while checker is on, keeping this in lockstep with drawChecker() so the
   2D CSS surface and the compare canvas render the identical two grays. */
.pz-checker,
.pz-has-alpha {
  background-color: #333333; /* checker's second gray — wins over .pz-backdrop-* when checker is on */
  background-image:
    linear-gradient(45deg, #474747 25%, transparent 25%),
    linear-gradient(-45deg, #474747 25%, transparent 25%),
    linear-gradient(45deg, transparent 75%, #474747 75%),
    linear-gradient(-45deg, transparent 75%, #474747 75%);
  background-size: 32px 32px;
  background-position: 0 0, 0 16px, 16px -16px, -16px 0px;
}
/* Normal panel body de-emphasis when the Height stage is off (R7) — the Enabled toggle stays fully
   interactive above this; only the stage body dims to signal the dependency (no ticked-disabled trap). */
.pz-degraded,
.is-degraded {
  opacity: 0.55;
}
/* Toolbar pinned bottom-right over the canvas; position:absolute is inlined by the TS */
.pz-preview2d-toolbar {
  display: flex;
  gap: calc(2rem / 16);
  padding: calc(4rem / 16);
  background: rgba(33, 33, 33, 0.80);
  border-top-left-radius: var(--radius);
  pointer-events: auto;
}

/* ── Compare view ────────────────────────────────────────────────────────── */
.pz-compare {
  /* flex column + fill are inlined by TS; chrome only here */
}
.pz-compare-toolbar {
  flex: 0 0 auto;
  display: flex;
  align-items: center;
  gap: calc(8rem / 16);
  padding: calc(4rem / 16) calc(8rem / 16);
  background: var(--bg-header);
  border-bottom: var(--border-w) solid var(--border);
}
.pz-compare-row {
  flex: 0 0 auto;
  padding: calc(3rem / 16) calc(8rem / 16);
  background: var(--bg-header);
  border-bottom: var(--border-w) solid var(--border);
}
.pz-compare-stage {
  /* position:relative + flex + min-height:0 are inlined; nothing extra */
}

/* ── Shared canvas ───────────────────────────────────────────────────────── */
/* pz-view-canvas: position/inset/display/imageRendering all inlined by CanvasSurface */
.pz-view-canvas {
  cursor: crosshair;
}

/* ── 3D overlay — floating control strip top-left of the 3D canvas ──────── */
/* position:absolute is not inlined; mount3d is position:absolute (pz-view), so overlay floats over it */
.pz-3d-overlay {
  position: absolute;
  top: calc(8rem / 16);
  left: calc(8rem / 16);
  z-index: 10;
  display: flex;
  flex-direction: column;
  align-items: stretch;
  gap: calc(4rem / 16);
  padding: calc(6rem / 16) calc(8rem / 16);
  background: rgba(33, 33, 33, 0.82);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius);
  pointer-events: auto;
  font-size: calc(12rem / 16);
}
/* One control per row: fixed-width label | control | value readout. */
.pz-3d-overlay-row {
  display: flex;
  align-items: center;
  gap: calc(6rem / 16);
}
.pz-3d-overlay-row > span:first-child {
  flex: 0 0 calc(52rem / 16);
  color: var(--text-dim, #bbb);
}
.pz-3d-overlay-row > span:last-child:not(:first-child) {
  flex: 0 0 calc(28rem / 16);
  text-align: right;
  font-variant-numeric: tabular-nums;
}
.pz-3d-overlay-row > select,
.pz-3d-overlay-row > input[type="range"] {
  flex: 1 1 auto;
  min-width: 0;
}
/* Bare <select> and <input[type=range]> inside the overlay — no .pz-* class */
.pz-3d-overlay select {
  background: var(--bg-field);
  color: var(--text);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius-sm);
  padding: calc(2rem / 16) calc(4rem / 16);
  font: inherit;
}
.pz-3d-overlay select:focus {
  outline: none;
  border-width: calc(2rem / 16); /* §16 a11y: focus stroke widened 1px→2px */
  border-color: var(--accent);
}
.pz-3d-overlay input[type="range"] {
  accent-color: var(--accent);
  width: calc(80rem / 16);
}

/* ── stage-chip nav (UX rework 2): pinned 4×2 grid above the scroll column ─── */
.pz-stage-nav-slot {
  flex: 0 0 auto;
  padding: calc(8rem / 16) calc(8rem / 16) 0;
}
.pz-stage-grid {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: calc(2rem / 16);
  background: var(--bg-header);
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius);
  padding: calc(2rem / 16);
}
.pz-stage-chip {
  appearance: none;
  border: none;
  background: transparent;
  color: var(--text-dim);
  font: inherit;
  padding: calc(5rem / 16) calc(4rem / 16);
  border-radius: calc(3rem / 16);
  border-bottom: calc(3rem / 16) solid transparent;
  cursor: pointer;
  overflow: hidden;
  white-space: nowrap;
  text-overflow: ellipsis;
}
.pz-stage-chip:hover {
  color: var(--text);
}
.pz-stage-chip.is-active {
  background: var(--bg-card);
  color: var(--text);
  border-bottom-color: var(--chip-accent, var(--accent));
}
.pz-stage-chip.is-disabled {
  opacity: 0.4;
}

/* ── header enable checkbox (mirror Godot PanelBase enabled_prop) ──────────── */
.pz-header-enable {
  margin: 0 calc(4rem / 16) 0 0;
  accent-color: var(--accent);
}

/* ── pass cards: collapsed summary rows + single expansion ─────────────────── */
.pz-empty-hint {
  color: var(--text-dim);
  font-size: var(--font-size-section);
  padding: calc(6rem / 16) calc(2rem / 16);
}
.pz-pass-card {
  border: var(--border-w) solid var(--border);
  border-radius: var(--radius);
  background: var(--bg-header);
}
.pz-pass-card.is-active {
  background: var(--bg-card);
  border-color: var(--accent);
}
.pz-pass-header {
  display: flex;
  align-items: center;
  gap: calc(6rem / 16);
  padding: calc(4rem / 16) calc(6rem / 16);
}
.pz-pass-header.is-clickable {
  cursor: pointer;
}
.pz-pass-disclosure {
  flex: 0 0 auto;
  width: calc(12rem / 16);
  color: var(--text-dim);
}
.pz-pass-enable {
  flex: 0 0 auto;
  accent-color: var(--accent);
}
.pz-pass-summary {
  flex: 1 1 auto;
  overflow: hidden;
  white-space: nowrap;
  text-overflow: ellipsis;
}
.pz-pass-details {
  display: flex;
  flex-direction: column;
  gap: calc(4rem / 16);
  padding: 0 calc(6rem / 16) calc(6rem / 16);
}

/* ── subordinate sub-section (Sampling / Cleanup inside a pass card) ───────── */
.pz-subsection {
  display: flex;
  flex-direction: column;
  gap: calc(4rem / 16);
  margin-top: calc(2rem / 16);
}
.pz-subsection-body {
  display: flex;
  flex-direction: column;
  gap: calc(4rem / 16);
}

/* ── link-aspect padlock ───────────────────────────────────────────────────── */
.pz-padlock {
  color: var(--text-dim);
}
.pz-padlock.is-locked {
  color: var(--text);
}
