/* Caso Abierto — hoja de estilo única.
   Dos materiales: el expediente (papel, serif, cálido) y la consola (pantalla,
   monoespaciada, fría). El contraste entre ambos es toda la dirección de arte;
   todo lo demás es contención. */

:root {
  /* Papel carbón, no azul de pantalla: el negro tira a betún y la tinta a
     marfil, como un expediente bajo un flexo. El acento es manila de carpeta;
     el rojo, de sello de goma. */
  --bg:        #0c0b09;
  --bg-2:      #14120f;
  --panel:     #191612;
  --panel-2:   #211d18;
  --line:      #302a22;
  --line-soft: #26211b;
  --ink:       #ebe3d1;
  --ink-dim:   #a69d8b;
  /* #6f675a daba 3.0–3.5:1 sobre los cuatro fondos del juego: por debajo de
     AA en las 64 reglas que lo usan —contadores, rótulos, pies de foto, el
     aviso de filas recortadas—. Subido a 4.7–5.5:1 sin salir del tono apagado
     que la dirección de arte pide. */
  --ink-faint: #8f8676;
  --amber:     #e2b15a;
  --amber-dim: #8d6d33;
  --jade:      #5fbb96;
  --violet:    #a891d9;
  --red:       #cf4a3c;
  /* El mismo rojo de sello no vale como texto: sobre el bloque de error da
     3.8:1. Éste es para leer; `--red` se queda para sellos y bordes. */
  --red-claro: #e7685a;
  --paper:     #e9e1cf;
  --paper-ink: #201d18;
  --paper-dim: #6b6455;
  --accent:    var(--amber);

  /* Tres voces tipográficas, ninguna de sistema: un titular condensado de
     cartel, una romana de periódico para leer y una máquina de escribir para
     rótulos, datos y SQL. Van empaquetadas (static/fonts, OFL). */
  --display: "Big Shoulders Display", "Oswald", Impact, "Arial Narrow", sans-serif;
  --serif: "Newsreader", "Iowan Old Style", Palatino, Georgia, serif;
  --sans: system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;
  --mono: "Courier Prime", "Courier New", Courier, monospace;

  --r: 4px;
  --safe-b: env(safe-area-inset-bottom, 0px);
}

@font-face { font-family: "Big Shoulders Display"; font-style: normal; font-weight: 500 900; font-display: swap; src: url("fonts/BigShouldersDisplay.woff2") format("woff2"); }
@font-face { font-family: "Newsreader"; font-style: normal; font-weight: 400 700; font-display: swap; src: url("fonts/Newsreader.woff2") format("woff2"); }
@font-face { font-family: "Newsreader"; font-style: italic; font-weight: 400 700; font-display: swap; src: url("fonts/Newsreader-Italic.woff2") format("woff2"); }
@font-face { font-family: "Courier Prime"; font-style: normal; font-weight: 400; font-display: swap; src: url("fonts/CourierPrime.woff2") format("woff2"); }
@font-face { font-family: "Courier Prime"; font-style: normal; font-weight: 700; font-display: swap; src: url("fonts/CourierPrime-Bold.woff2") format("woff2"); }
@font-face { font-family: "Courier Prime"; font-style: italic; font-weight: 400; font-display: swap; src: url("fonts/CourierPrime-Italic.woff2") format("woff2"); }

* { box-sizing: border-box; }

/* Un `display` explícito en una clase gana al atributo `hidden`, y entonces el
   modal y la barra de sugerencias aparecen siempre. Esta regla lo zanja para
   todo el documento. */
[hidden] { display: none !important; }

html, body {
  margin: 0; padding: 0;
  background: var(--bg);
  color: var(--ink);
  font-family: var(--sans);
  -webkit-text-size-adjust: 100%;
  overscroll-behavior-y: none;
}

body {
  min-height: 100dvh;
  background-image:
    radial-gradient(1200px 700px at 50% -14%, rgba(226,177,90,.09), transparent 60%),
    radial-gradient(900px 600px at 100% 110%, rgba(0,0,0,.5), transparent 60%);
  background-attachment: fixed;
}
body.sin-scroll { overflow: hidden; }

/* Grano de película. Un SVG inline: ni una petición de red por una textura. */
.grain {
  position: fixed; inset: 0; pointer-events: none; z-index: 999; opacity: .16;
  background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='140' height='140'><filter id='n'><feTurbulence type='fractalNoise' baseFrequency='.85' numOctaves='3'/></filter><rect width='140' height='140' filter='url(%23n)' opacity='.5'/></svg>");
  mix-blend-mode: overlay;
}

/* Lluvia: dos capas de gradientes repetidos que se DESPLAZAN POR TRANSFORMACIÓN.
   La versión anterior animaba `background-position`, y eso obliga a repintar
   la pantalla entera sesenta veces por segundo; en un teléfono se ve como
   saltos. Una transformación la mueve el compositor sin tocar un píxel.
   Cada capa se traslada exactamente un periodo de su patrón, así que el bucle
   no tiene costura. */
.rain { position: fixed; inset: 0; pointer-events: none; z-index: 1; opacity: .16; overflow: hidden; }
.rain::before, .rain::after {
  content: ""; position: absolute; left: -12%; right: -12%; top: -720px; bottom: -720px;
  background-image: repeating-linear-gradient(104deg, transparent 0 22px, rgba(190,215,255,.55) 22px 23px, transparent 23px 46px);
  background-size: 460px 460px;
  animation: llueve-a 1.1s linear infinite; will-change: transform;
}
.rain::after {
  background-image: repeating-linear-gradient(99deg, transparent 0 38px, rgba(190,215,255,.35) 38px 39px, transparent 39px 74px);
  background-size: 700px 700px;
  animation: llueve-b 1.7s linear infinite;
}
@keyframes llueve-a { to { transform: translate3d(-110px, 460px, 0); } }
@keyframes llueve-b { to { transform: translate3d(-160px, 700px, 0); } }
@media (prefers-reduced-motion: reduce) {
  .rain::before, .rain::after { animation: none; }
  .rain { opacity: .08; }
}
/* En pantallas táctiles el grano no se mezcla: `mix-blend-mode` sobre toda
   la página obliga a componer cada fotograma otra vez. Se queda como una capa
   translúcida normal, que se ve casi igual y no cuesta nada. */
@media (pointer: coarse) {
  .grain { mix-blend-mode: normal; opacity: .07; }
}

button, input, textarea { font: inherit; color: inherit; }
h1, h2, h3 { margin: 0 0 .4em; line-height: 1.15; }
a { color: var(--accent); }

/* ---------- barra superior ---------- */
.topbar {
  position: sticky; top: 0; z-index: 50;
  display: flex; align-items: center; gap: 12px;
  padding: 10px 16px; padding-top: calc(10px + env(safe-area-inset-top, 0px));
  background: rgba(10,12,15,.86);
  backdrop-filter: blur(14px);
  border-bottom: 1px solid var(--line-soft);
}
/* `margin-right:auto` en la marca y no `margin-left:auto` en el botón del
   manual: así TODO lo que va detrás forma un solo grupo a la derecha. Con el
   auto en el ☰, el botón de ahorro se quedaba suelto en mitad de la barra
   —pegado a la marca— mientras los otros dos controles estaban en la esquina. */
.brand { display: flex; align-items: center; gap: 10px; min-width: 0; margin-right: auto; }
.brand-mark {
  display: grid; place-items: center;
  width: 34px; height: 34px; flex: 0 0 34px;
  border: 1px solid var(--amber-dim); border-radius: 3px;
  color: var(--amber); font-family: var(--mono); font-size: 13px; letter-spacing: .06em;
  background: linear-gradient(160deg, rgba(216,162,74,.16), transparent);
}
.brand-text { display: flex; flex-direction: column; min-width: 0; }
.brand-text strong { font-family: var(--serif); font-size: 17px; letter-spacing: .01em; }
.brand-text span {
  font-size: 10.5px; color: var(--ink-faint); text-transform: uppercase; letter-spacing: .13em;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.score {
  font-family: var(--mono); font-size: 12px; color: var(--ink-dim);
  border: 1px solid var(--line); border-radius: 999px; padding: 5px 11px; white-space: nowrap;
}
.icon-btn {
  background: none; border: 1px solid var(--line); color: var(--ink-dim);
  width: 34px; height: 34px; flex: 0 0 34px; border-radius: 8px; cursor: pointer; font-size: 15px;
  display: grid; place-items: center; position: relative; transition: color .12s, border-color .12s;
}
.icon-btn:hover { color: var(--ink); border-color: var(--amber-dim); }
.manual-btn { margin-left: 0; }
/* El ☰ solo no decía «manual»: quien buscaba una referencia no lo encontraba.
   Con sitio, lleva la palabra; en pantallas estrechas vuelve a ser el icono. */
.manual-rotulo { display: none; }
@media (min-width: 760px) {
  .manual-btn { width: auto; flex: 0 0 auto; padding: 0 10px; display: inline-flex; align-items: center; gap: 6px; font-size: 13px; }
  .manual-rotulo { display: inline; font-family: var(--mono); letter-spacing: .04em; }
}
.enlace-manual { margin-left: 6px; }
.enlace-manual b { color: var(--ink); font-weight: 600; }
#manual-body .patron.resaltado { outline: 2px solid var(--accent); outline-offset: 4px; border-radius: 6px; transition: outline-color .6s; }
.manual-count {
  position: absolute; top: -6px; right: -6px;
  background: var(--accent); color: #17130a; font-family: var(--mono); font-size: 9.5px;
  min-width: 16px; height: 16px; border-radius: 999px; display: grid; place-items: center;
  padding: 0 4px; font-weight: 700;
}
.manual-count:empty { display: none; }

/* ---------- archivo ---------- */
.view { max-width: 1500px; margin: 0 auto; padding: 26px 16px 90px; position: relative; z-index: 2; }
.hero { max-width: 680px; margin: 22px 0 38px; }
.hero-kicker {
  font-family: var(--mono); font-size: 10.5px; letter-spacing: .2em; text-transform: uppercase;
  color: var(--amber-dim); margin: 0 0 10px;
}
.hero h1 {
  font-family: var(--serif); font-size: clamp(32px, 6.5vw, 52px); font-weight: 500;
  letter-spacing: -.015em; margin-bottom: .25em;
}
.hero-lead { color: var(--ink-dim); line-height: 1.68; margin: 0; font-size: 15.5px; }
.hero-stats { display: flex; flex-wrap: wrap; gap: 22px; margin-top: 26px; }
.hero-stat { display: flex; flex-direction: column; gap: 2px; }
.hero-stat b { font-family: var(--mono); font-size: 22px; color: var(--amber); font-weight: 500; }
.hero-stat span {
  font-size: 10.5px; color: var(--ink-faint); text-transform: uppercase; letter-spacing: .12em;
}

/* ---------- el archivo: cajones, carpetas y fotos ----------
 *
 * Una sala de archivo, no una cuadrícula web. Cada temporada es un cajón con
 * su placa; cada caso es una carpeta con una foto de evidencia pegada con
 * cinta —el primer plano de su introducción, pintado— y un sello. Las carpetas
 * cerradas van atadas con cordel y sin foto. Nada aquí es un rectángulo con
 * sombra por defecto: todo tiene una razón de ser dentro del mundo del juego.
 */

.cajon {
  display: flex; align-items: flex-end; justify-content: space-between; gap: 16px; flex-wrap: wrap;
  margin: 44px 0 20px; padding-bottom: 12px; border-bottom: 1px solid var(--line);
  animation: ui-fundir .5s ease-out both;
}
.cajon-placa { display: flex; flex-direction: column; gap: 3px; min-width: 0; }
.cajon-num { font-family: var(--mono); font-size: 10px; letter-spacing: .24em; text-transform: uppercase; color: var(--accent); }
.cajon h2 { font-family: var(--serif); font-weight: 500; font-size: clamp(22px, 3vw, 30px); margin: 0; letter-spacing: -.01em; }
.cajon-sub { font-family: var(--serif); font-style: italic; color: var(--ink-faint); font-size: 13.5px; margin: 2px 0 0; max-width: 52ch; }
.cajon-carpetas { display: flex; gap: 5px; align-items: flex-end; padding-bottom: 4px; }
.cajon-carpetas i { display: block; width: 13px; height: 10px; border: 1px solid var(--ink-faint); border-radius: 1px 4px 1px 1px; opacity: .5; }
.cajon-carpetas i.ok { background: var(--accent); border-color: var(--accent); opacity: 1; }
.cajon-carpetas i.medio { border-color: var(--accent); opacity: .9; }

.carpetas { display: grid; gap: 16px; grid-template-columns: repeat(auto-fill, minmax(320px, 1fr)); }
.carpetas > * { min-width: 0; }
@media (max-width: 400px) { .carpetas { grid-template-columns: 1fr; } }

.carpeta {
  position: relative; display: grid; grid-template-columns: 150px minmax(0, 1fr); gap: 0 16px; align-items: start;
  text-align: left; cursor: pointer; color: inherit;
  padding: 30px 16px 18px 14px;
  background: linear-gradient(170deg, #1a2029 0%, #131820 60%, #10151c 100%);
  border: 1px solid var(--line); border-radius: 3px 10px 10px 10px;
  box-shadow: inset 0 1px 0 rgba(255,255,255,.035), 0 10px 26px rgba(0,0,0,.38);
  transform: rotate(var(--giro, 0deg));
  transition: transform .2s cubic-bezier(.2,.8,.2,1), border-color .2s, box-shadow .2s;
}
/* La textura de la cartulina: líneas casi invisibles. */
.carpeta::after {
  content: ""; position: absolute; inset: 0; border-radius: inherit; pointer-events: none;
  background: repeating-linear-gradient(94deg, transparent 0 7px, rgba(255,255,255,.012) 7px 8px);
}
.carpeta:hover:not(.locked), .carpeta:focus-visible:not(.locked) {
  transform: rotate(0deg) translateY(-4px); border-color: var(--amber-dim);
  box-shadow: 0 22px 44px rgba(0,0,0,.55); outline: none;
}
.carpeta:hover:not(.locked) .foto { transform: rotate(0deg) scale(1.02); }
.pestana {
  position: absolute; top: 0; left: 0; padding: 5px 12px 4px 14px;
  font-family: var(--mono); font-size: 10px; letter-spacing: .18em; color: var(--ink-dim);
  background: var(--panel-2); border-right: 1px solid var(--line); border-bottom: 1px solid var(--line);
  border-radius: 3px 0 8px 0;
}
.carpeta.estado-en_curso .pestana { color: var(--amber); }
.carpeta.estado-resuelto .pestana { color: var(--jade); }
.carpeta.estado-rendido  .pestana { color: var(--red); }

.foto {
  position: relative; width: 150px; aspect-ratio: 4 / 3; box-sizing: border-box;
  padding: 5px 5px 16px; background: var(--paper);
  box-shadow: 0 8px 18px rgba(0,0,0,.55), 0 1px 0 rgba(255,255,255,.2) inset;
  transform: rotate(var(--foto-giro, -2deg)); transition: transform .25s cubic-bezier(.2,.8,.2,1);
}
.foto::before {
  /* la cinta que la sujeta */
  content: ""; position: absolute; top: -7px; left: 50%; width: 30px; height: 11px; margin-left: -15px;
  background: rgba(216,162,74,.62); border-radius: 1px; transform: rotate(-4deg);
  box-shadow: 0 1px 2px rgba(0,0,0,.4);
}
.foto .pintado, .foto .escena-viva {
  display: block; width: 100%; height: 100%; object-fit: cover;
  background: var(--bg-2); opacity: 0; transition: opacity .55s ease;
}
.foto .pintado.lista, .foto .escena-viva { opacity: 1; }
.foto .escena-viva svg { width: 100%; height: 100%; display: block; }
.foto-pie { position: absolute; left: 6px; right: 6px; bottom: 2px; font-family: var(--mono); font-size: 8.5px; letter-spacing: .12em; color: #6a6559; text-transform: uppercase; text-align: center; overflow: hidden; white-space: nowrap; text-overflow: ellipsis; }

/* Hueco abajo para el sello, que va en absoluto: sin él las etiquetas se le
   metían debajo. */
.carpeta-texto { display: flex; flex-direction: column; gap: 6px; min-width: 0; padding: 2px 0 30px; }
.carpeta h3 { font-family: var(--serif); font-weight: 500; font-size: 17.5px; line-height: 1.2; margin: 0; letter-spacing: -.005em; text-wrap: balance; }
.carpeta .lema { color: var(--ink-dim); font-size: 13px; line-height: 1.5; margin: 0; font-family: var(--serif); font-style: italic; }
.carpeta .dificultad { font-family: var(--mono); font-size: 10px; letter-spacing: .1em; color: var(--amber); }
.carpeta .etiquetas { display: flex; flex-wrap: wrap; gap: 5px; margin-top: 4px; }
.carpeta .etiquetas .chip { font-size: 10px; }

.sello {
  position: absolute; right: 14px; bottom: 12px; padding: 3px 9px;
  font-family: var(--mono); font-size: 9.5px; letter-spacing: .16em; text-transform: uppercase;
  border: 1.5px solid currentColor; border-radius: 3px; transform: rotate(-6deg);
  color: var(--ink-faint); opacity: .9; mix-blend-mode: normal;
}
.carpeta.estado-en_curso .sello { color: var(--amber); }
.carpeta.estado-resuelto .sello { color: var(--jade); }
.carpeta.estado-rendido  .sello { color: var(--red); }
.carpeta .medalla { position: absolute; right: 14px; top: 10px; font-size: 14px; line-height: 1; }
.medalla.med-oro { color: #e2b45e; } .medalla.med-plata { color: #c8d0da; } .medalla.med-bronce { color: #b07a4a; }

/* `opacity` sobre el botón entero dejaba el título a 2.8:1 y las etiquetas
   a 1.8:1: una carpeta bloqueada debe verse apagada, no ilegible. */
.carpeta.locked { cursor: not-allowed; opacity: 1; color: var(--ink-dim); background: linear-gradient(170deg, #15191f 0%, #11151b 100%); }
.carpeta.locked h3 { color: var(--ink-dim); }
.carpeta.locked .lema, .carpeta.locked .dificultad, .carpeta.locked .sello, .carpeta.locked .pestana { color: var(--ink-faint); }
/* Una carpeta bloqueada no es un caso: es un hueco con nombre. Ocupa lo que
   ocupa un nombre —sin foto y, salvo la primera de cada temporada, sin la
   frase de la regla— y se alinea arriba para no estirarse hasta la altura de
   los casos jugables de su fila. */
.carpeta.locked { grid-template-columns: minmax(0, 1fr); align-self: start; padding: 28px 14px 12px; }
.carpeta.locked .foto { display: none; }
.carpeta.locked .carpeta-texto { padding-bottom: 26px; }
.carpeta.locked h3 { font-size: 16px; }
.carpeta.locked .sello { bottom: 10px; }
.carpeta.locked .foto { background: #1b2028; box-shadow: none; }
.carpeta.locked .foto::before { display: none; }
.carpeta.locked .foto .cordel {
  position: absolute; inset: 0;
  background:
    linear-gradient(38deg, transparent 49%, var(--ink-faint) 49% 51%, transparent 51%),
    linear-gradient(-38deg, transparent 49%, var(--ink-faint) 49% 51%, transparent 51%);
  opacity: .6;
}
.carpeta.locked h3 { color: var(--ink-dim); }

@media (max-width: 560px) {
  .carpeta { grid-template-columns: 112px minmax(0, 1fr); gap: 0 12px; padding: 28px 12px 16px 12px; }
  .foto { width: 112px; padding: 4px 4px 13px; }
  .carpetas { grid-template-columns: 1fr; }
}

/* El fondo de la sala: la portada, oscurecida, quieta detrás de todo. */
#archivo-fondo { position: fixed; inset: 0; z-index: 0; pointer-events: none; opacity: .32; }
#archivo-fondo .pintado { width: 100%; height: 100%; object-fit: cover; display: block; opacity: 0; transition: opacity 1s ease; }
#archivo-fondo .pintado.lista { opacity: 1; }
#archivo-fondo::after {
  content: ""; position: absolute; inset: 0;
  background: linear-gradient(to bottom, rgba(10,12,15,.35) 0%, rgba(10,12,15,.9) 55%, rgba(10,12,15,.98) 100%);
}
#view-archivo { position: relative; z-index: 1; }

/* Imágenes pintadas en la portada, el caso activo y las viñetas de la intro. */
#titulo-escena .pintado, .activo .activo-escena .pintado, .plano-capa .pintado {
  width: 100%; height: 100%; object-fit: cover; display: block; opacity: 0; transition: opacity .6s ease;
}
#titulo-escena .pintado.lista, .activo .activo-escena .pintado.lista, .plano-capa .pintado.lista { opacity: 1; }
.plano-capa .pintado { position: absolute; inset: 0; will-change: transform; }
.escena-marco .pintado { width: 100%; height: 100%; object-fit: cover; display: block; opacity: 0; transition: opacity .6s ease; }
.escena-marco .pintado.lista { opacity: 1; }

.season { margin-bottom: 44px; }
.chip {
  font-family: var(--mono); font-size: 10px; letter-spacing: .06em;
  border: 1px solid var(--line); border-radius: 4px; padding: 3px 6px; color: var(--ink-faint);
}
.state { font-family: var(--mono); font-size: 10px; letter-spacing: .14em; text-transform: uppercase; margin-left: auto; }
.state.resuelto { color: var(--jade); }
.state.rendido  { color: var(--red-claro); }
.state.en_curso { color: var(--amber); }
.state.bloqueado{ color: var(--ink-faint); }

/* ---------- vista de caso ---------- */
/* La rejilla del caso vive más abajo, en «el puesto de trabajo». */
.pane-title {
  font-family: var(--mono); font-size: 11px; letter-spacing: .16em; text-transform: uppercase;
  color: var(--ink-faint); margin: 0;
}

/* El expediente: papel de verdad, tipografía de máquina de escribir. */
.dossier {
  background: var(--paper); color: var(--paper-ink);
  border-radius: 4px; padding: 22px 22px 18px;
  box-shadow: 0 14px 34px rgba(0,0,0,.5);
  background-image: linear-gradient(180deg, rgba(0,0,0,.03), transparent 120px);
  position: relative;
}
.dossier::after {
  content: ""; position: absolute; inset: 0; border-radius: 4px; pointer-events: none;
  box-shadow: inset 0 0 60px rgba(120,100,60,.14);
}
.dossier-head {
  display: flex; align-items: center; gap: 10px;
  border-bottom: 1px solid rgba(0,0,0,.18); padding-bottom: 8px; margin-bottom: 14px;
}
.dossier-num { font-family: var(--mono); font-size: 11px; letter-spacing: .16em; color: var(--paper-dim); }
.dossier-stamp {
  margin-left: auto; transform: rotate(-6deg);
  font-family: var(--mono); font-size: 11px; letter-spacing: .18em; text-transform: uppercase;
  border: 2px solid currentColor; border-radius: 3px; padding: 2px 7px; opacity: .82;
}
.dossier-stamp:empty { border: 0; }
.dossier-stamp.resuelto { color: #2c7a5a; }
.dossier-stamp.rendido  { color: #a33c36; }
.dossier-stamp.en_curso { color: #8a6c33; }
/* El sello cae de golpe: es el único momento de recompensa del caso. */
.dossier-stamp.sellando { animation: sellar .45s cubic-bezier(.2,1.6,.4,1); }
@keyframes sellar {
  0%   { transform: rotate(-22deg) scale(2.6); opacity: 0; }
  60%  { transform: rotate(-4deg)  scale(.94); opacity: 1; }
  100% { transform: rotate(-6deg)  scale(1); }
}
.dossier h2 { font-family: var(--serif); font-size: 25px; font-weight: 600; letter-spacing: -.01em; }
.dossier-tagline { font-family: var(--serif); font-style: italic; color: var(--paper-dim); margin: 0 0 16px; line-height: 1.45; }
.dossier-body { font-family: var(--serif); font-size: 15.5px; line-height: 1.68; overflow-wrap: anywhere; }
.dossier-body p { margin: 0 0 .85em; }
.dossier-body strong { font-weight: 700; }
.dossier-body code {
  font-family: var(--mono); font-size: .86em; background: rgba(0,0,0,.07);
  padding: 1px 4px; border-radius: 3px;
}
.dossier-body ol, .dossier-body ul { margin: 0 0 .85em; padding-left: 1.3em; }
.dossier-body li { margin-bottom: .3em; }
.dossier-body blockquote {
  margin: 0 0 .85em; padding-left: 12px; border-left: 3px solid rgba(0,0,0,.2);
  font-style: italic; color: var(--paper-dim);
}

.objective {
  margin: 16px 0 12px; padding: 12px 14px;
  background: rgba(0,0,0,.055); border-left: 3px solid var(--amber-dim); border-radius: 0 4px 4px 0;
}
.objective-label {
  font-family: var(--mono); font-size: 10px; letter-spacing: .18em; text-transform: uppercase; color: var(--paper-dim);
}
.objective p { margin: 4px 0 0; font-family: var(--serif); font-size: 16px; font-weight: 600; line-height: 1.45; }
.skills { display: flex; flex-wrap: wrap; gap: 6px; }
.skills span {
  font-family: var(--mono); font-size: 10px; color: var(--paper-dim);
  border: 1px solid rgba(0,0,0,.16); border-radius: 3px; padding: 2px 6px;
}

/* barra de estadísticas del caso */
.statbar {
  display: flex; flex-wrap: wrap; gap: 6px 18px; margin: 12px 2px 0;
  font-family: var(--mono); font-size: 11px; color: var(--ink-faint);
}
.statbar .stat b { color: var(--ink-dim); font-weight: 600; }

/* pistas */
/* `minmax(0, 1fr)` y no el `auto` implícito: un grid item tiene `min-width:
   auto`, así que se estira hasta el contenido más ancho que lleve dentro —una
   línea de SQL sin espacios, por ejemplo— y se sale de su columna. Como la
   consola de al lado está pegada y tiene fondo, el texto desbordado no se ve
   cortado: desaparece debajo. Mismo motivo en el historial y en el manual. */
.hints { margin-top: 14px; display: grid; grid-template-columns: minmax(0, 1fr); gap: 10px; }
.hints > * { min-width: 0; }
.hint {
  background: var(--panel); border: 1px solid var(--line); border-left: 3px solid var(--accent);
  border-radius: 0 var(--r) var(--r) 0; padding: 13px 15px;
  animation: aparece .3s ease;
}
@keyframes aparece { from { opacity: 0; transform: translateY(-6px); } }
.hint h4 {
  margin: 0 0 6px; font-family: var(--mono); font-size: 11px; letter-spacing: .12em;
  text-transform: uppercase; color: var(--accent);
}
.hint-body { font-size: 14px; line-height: 1.62; color: var(--ink); overflow-wrap: anywhere; }
.hint-body p { margin: 0 0 .7em; }
.hint-body p:last-child { margin-bottom: 0; }
.hint-body code, .solution-body code, .patron-nota code {
  font-family: var(--mono); font-size: .88em; background: var(--bg); padding: 1px 4px; border-radius: 3px;
}
/* El SQL de pistas, soluciones y manual ENVUELVE en vez de scrollear: la
   columna del expediente es estrecha y en el móvil lo es más, y una barra de
   scroll horizontal dentro de un bloque de texto que se está leyendo es peor
   que una línea partida. `pre-wrap` conserva la indentación, que es la mitad
   de lo que hace legible una consulta. El `overflow-x` se queda como red por
   si algo no puede partirse. */
.hint-body pre, .solution pre, .patron pre {
  max-width: 100%;
  background: var(--bg); border: 1px solid var(--line); border-radius: 8px;
  padding: 12px; overflow-x: auto; font-family: var(--mono); font-size: 12.5px; line-height: 1.55;
  margin: 0 0 .8em;
  white-space: pre-wrap; overflow-wrap: break-word;
}

/* cuaderno */
.notepad {
  margin-top: 14px; background: var(--panel); border: 1px solid var(--line); border-radius: var(--r);
  overflow: hidden;
}
.notepad summary {
  cursor: pointer; padding: 11px 14px; list-style: none;
  font-family: var(--mono); font-size: 11px; letter-spacing: .14em; text-transform: uppercase; color: var(--ink-dim);
}
.notepad summary::-webkit-details-marker { display: none; }
.notepad summary::before { content: "▸ "; color: var(--ink-faint); }
.notepad[open] summary::before { content: "▾ "; }
.notepad textarea {
  width: 100%; min-height: 130px; resize: vertical; padding: 0 14px 8px;
  background: transparent; border: 0; outline: none; color: var(--ink);
  font-family: var(--serif); font-size: 14.5px; line-height: 1.6;
}
.notepad-state {
  display: block; padding: 0 14px 10px; font-family: var(--mono);
  font-size: 10px; color: var(--ink-faint);
}

/* acusación */
.accuse {
  margin-top: 14px; background: var(--panel); border: 1px solid var(--line);
  border-radius: var(--r); padding: 15px;
}
.accuse h3 { font-family: var(--mono); font-size: 11px; letter-spacing: .16em; text-transform: uppercase; color: var(--ink-dim); margin: 0; }
/* El título no se parte: «Tablero de / hechos» en dos líneas con la píldora
   al lado se leía como un descuadre. Si no caben juntos, baja la píldora. */
.accuse-head { display: flex; flex-wrap: wrap; justify-content: space-between; align-items: baseline; gap: 6px 10px; margin-bottom: 12px; }
.accuse-head h3 { white-space: nowrap; }
.hechos-cuenta { font-family: var(--mono); font-size: 11px; color: var(--ink-faint); }
.hechos-cuenta.ok { color: var(--jade); }

/* La prueba: la consulta que sostiene la acusación. Va prellenada con la
   última que corrió, así que en el flujo normal no cuesta ni un clic. */
.prueba { margin: 12px 0 12px; padding-top: 12px; border-top: 1px dashed var(--line); }
.prueba label { display: block; font-family: var(--mono); font-size: 10.5px; letter-spacing: .14em; text-transform: uppercase; color: var(--ink-dim); margin-bottom: 6px; }
.prueba select {
  width: 100%; padding: 9px 10px; border-radius: 8px; font: inherit; font-family: var(--mono); font-size: 12px;
  background: var(--bg-2); border: 1px solid var(--line); color: var(--ink);
}
.prueba select:focus { outline: none; border-color: var(--accent); }
.prueba select:disabled { color: var(--ink-faint); }
.prueba-nota { margin: 6px 0 0; font-size: 12.5px; color: var(--ink-dim); min-height: 1em; }
.prueba.sin .prueba-nota { color: var(--ink-faint); }

/* Evidencias: celdas fijadas de un resultado. Sirven para rellenar los hechos
   sin volver a la consola a copiar. */
.evidencias { margin: 2px 0 12px; display: grid; gap: 6px; }
.evidencias-titulo { font-family: var(--mono); font-size: 10.5px; letter-spacing: .14em; text-transform: uppercase; color: var(--ink-dim); }
.evidencias-vacio { margin: 0; padding: 8px 10px; font-size: 12.5px; line-height: 1.45; color: var(--ink-dim);
  background: var(--bg-2); border: 1px dashed var(--line); border-radius: 8px; }
.evid { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; padding: 7px 10px; background: var(--bg-2); border: 1px solid var(--line-soft); border-radius: 8px; font-size: 12.5px; }
.evid code { font-family: var(--mono); color: var(--ink); background: none; padding: 0; }
.evid .de { color: var(--ink-faint); font-family: var(--mono); font-size: 10.5px; }
.evid .usos { display: flex; gap: 4px; flex-wrap: wrap; margin-left: auto; }
.evid .usos button, .evid .quitar {
  font: inherit; font-size: 11px; padding: 3px 8px; border-radius: 6px; cursor: pointer;
  background: var(--panel-2); border: 1px solid var(--line); color: var(--ink-dim);
}
.evid .usos button:hover { border-color: var(--amber-dim); color: var(--ink); }
.evid .quitar { padding: 3px 7px; }

/* En la tabla de resultados una celda se puede fijar como evidencia. */
#results td.fijable { cursor: pointer; }
#results td.fijable:hover { outline: 1px solid var(--amber-dim); outline-offset: -1px; }
#results td.seleccionada { outline: 2px solid var(--amber); outline-offset: -2px; background: rgba(216,162,74,.08); }
.evid-bar {
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap;
  padding: 8px 12px; margin-top: 8px; border: 1px solid var(--amber-dim); border-radius: 8px;
  background: rgba(216,162,74,.06); font-size: 12.5px;
}
.evid-bar code { font-family: var(--mono); background: none; padding: 0; color: var(--ink); }
.evid-bar .btn { padding: 5px 10px; font-size: 12px; }
.field { margin-bottom: 10px; }
.field label { display: block; font-size: 12px; color: var(--ink-dim); margin-bottom: 5px; }
.field input {
  width: 100%; padding: 10px 12px; border-radius: 8px;
  background: var(--bg-2); border: 1px solid var(--line); color: var(--ink);
}
.field input:focus { outline: none; border-color: var(--accent); }
.field.ok input { border-color: var(--jade); }
.field.bad input { border-color: var(--red); animation: tiembla .3s; }
@keyframes tiembla { 25% { transform: translateX(-4px); } 75% { transform: translateX(4px); } }
.verdict { margin: 10px 0 0; font-size: 14px; min-height: 1.2em; }
.verdict.ok { color: var(--jade); }
.verdict.bad { color: var(--red-claro); }

/* Tres botones en fila fluida se apilaban a lo ancho de la columna en cuanto
   ésta se estrechaba, y las dos salidas de emergencia acababan pesando lo
   mismo que pedir una pista. Rejilla: la pista ocupa la fila entera, las
   otras dos se reparten la siguiente. */
.danger-zone { display: grid; grid-template-columns: 1fr 1fr; gap: 8px; margin-top: 14px; }
.danger-zone > #btn-hint, .danger-zone > #btn-reset { grid-column: 1 / -1; }
.danger-zone .btn { min-width: 0; }

.btn {
  border-radius: 8px; padding: 10px 16px; cursor: pointer; border: 1px solid transparent;
  font-size: 14px; transition: background .12s, border-color .12s, color .12s, transform .08s;
}
.btn:active { transform: translateY(1px); }
.btn-primary { background: var(--accent); color: #17130a; font-weight: 600; }
.btn-primary:hover { filter: brightness(1.08); }
.btn-ghost { background: transparent; border-color: var(--line); color: var(--ink-dim); }
.btn-ghost:hover { color: var(--ink); border-color: var(--amber-dim); }
.btn-quiet { font-size: 13px; color: var(--ink-faint); }
/* `opacity: .45` dejaba el texto entre 1.6:1 y 2.9:1: ilegible. Un botón
   apagado se reconoce por el color plano y el borde apagado, no por ser
   transparente. */
.btn:disabled { opacity: .7; cursor: not-allowed; color: var(--ink-faint); border-color: var(--line-soft); }
.btn:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }

/* solución */
.solution {
  margin-top: 16px; background: var(--panel); border: 1px solid var(--jade);
  border-radius: var(--r); padding: 16px; animation: aparece .35s ease;
}
.solution h3 { font-family: var(--mono); font-size: 11px; letter-spacing: .16em; text-transform: uppercase; color: var(--jade); }
.solution-body { font-size: 14.5px; line-height: 1.68; color: var(--ink); overflow-wrap: anywhere; }
.solution-body p { margin: 0 0 .8em; }
.solution-body ul { margin: 0 0 .9em; padding-left: 1.2em; }
.solution-body blockquote {
  margin: 0 0 .9em; padding: 10px 14px; border-left: 3px solid var(--jade);
  background: rgba(70,195,156,.06); border-radius: 0 6px 6px 0;
}
.epilogue { font-family: var(--serif); font-style: italic; color: var(--ink-dim); border-top: 1px solid var(--line); padding-top: 12px; margin-top: 4px; }

.case-nav {
  display: flex; justify-content: space-between; gap: 12px; margin-top: 18px;
  font-size: 13px; font-family: var(--mono);
}
.case-nav a { color: var(--ink-dim); text-decoration: none; }
.case-nav a:hover { color: var(--accent); }
.nav-locked { color: var(--ink-faint); opacity: .6; }

/* ---------- consola ---------- */
.editor-wrap { background: var(--panel); border: 1px solid var(--line); border-radius: var(--r); overflow: hidden; }
.editor-head {
  display: flex; align-items: center; gap: 10px; padding: 9px 13px;
  border-bottom: 1px solid var(--line-soft); background: var(--bg-2);
}
.editor-title { font-family: var(--mono); font-size: 10.5px; letter-spacing: .14em; text-transform: uppercase; color: var(--ink-faint); }
.editor-hint { margin-left: auto; font-family: var(--mono); font-size: 10.5px; color: var(--ink-faint); }

/* Resaltado: un <pre> pintado debajo y un <textarea> transparente encima.
   Las dos capas comparten métrica exacta o el cursor se desalinea. */
.editor { position: relative; }
/* CodeMirror vive aquí. Sus colores y tipografía vienen de las variables del
   juego (ver app/src/editor-cm.js); esto sólo le da el marco. */
.editor .cm-editor { border-bottom: 1px solid var(--line-soft); }
.editor .cm-editor.cm-focused { box-shadow: inset 0 -2px 0 var(--amber-dim); }
.tok-op  { color: var(--ink-dim); }
.tok-kw  { color: #7fb2ff; font-weight: 600; }
.tok-fn  { color: #c58cf0; }
.tok-str { color: #93d68a; }
.tok-num { color: #e8b45e; }
.tok-com { color: var(--ink-faint); font-style: italic; }

.tokenbar {
  position: relative; display: flex; flex-wrap: wrap; gap: 6px; padding: 8px 10px;
  border-top: 1px solid var(--line-soft);
  /* Dos filas visibles; el resto, plegado. 2 × (alto del chip 26 px + hueco 6). */
  max-height: calc(8px + 26px * 2 + 6px + 8px); overflow: hidden;
  /* Y hueco reservado a la derecha para el chip «más», que va en absoluto:
     sin esto se echaba encima del último atajo de la segunda fila y lo dejaba
     cortado a la mitad —«LI» por «LIKE»—. La sombra que llevaba no lo tapaba,
     lo emborronaba. */
  padding-right: 88px;
}
.tokenbar.abierta { padding-right: 10px; }
.tokenbar.abierta { max-height: none; }
.tokenbar button {
  flex: 0 0 auto; height: 26px; padding: 0 9px; border-radius: 6px; cursor: pointer;
  font-family: var(--mono); font-size: 11px; letter-spacing: .02em;
  background: var(--panel-2); border: 1px solid var(--line); color: var(--ink-dim);
}
.tokenbar button:hover { border-color: var(--amber-dim); color: var(--ink); }
.tokenbar button:active { background: var(--accent); color: #17130a; }
/* Los comparadores, un poco más anchos y más claros: son los que más se buscan. */
.tokenbar button[title="="], .tokenbar button[title="<"], .tokenbar button[title=">"],
.tokenbar button[title="<="], .tokenbar button[title=">="], .tokenbar button[title="<>"] {
  min-width: 34px; font-size: 13px; color: var(--ink); padding: 0 8px;
}
.tokenbar .tok-mas {
  position: absolute; right: 8px; bottom: 8px; color: var(--amber); border-color: var(--amber-dim);
  background: var(--panel);
}
.tokenbar.abierta .tok-mas { position: static; box-shadow: none; margin-left: auto; }

.editor-actions { display: flex; align-items: center; gap: 8px; padding: 11px 13px; border-top: 1px solid var(--line-soft); flex-wrap: wrap; }
.run-meta { margin-left: auto; font-family: var(--mono); font-size: 11px; color: var(--ink-faint); text-align: right; }

.results { margin-top: 14px; }
.results-empty { color: var(--ink-faint); font-style: italic; font-size: 14px; }
.error {
  background: rgba(210,86,79,.08); border: 1px solid rgba(210,86,79,.4);
  border-radius: var(--r); padding: 13px 15px;
}
.error.vacio { background: transparent; border-color: var(--line); }
.error strong { color: var(--red-claro); display: block; margin-bottom: 5px; font-size: 13px; }
.error.vacio strong { color: var(--amber); }
.error pre { margin: 0; font-family: var(--mono); font-size: 12.5px; white-space: pre-wrap; color: var(--ink); }
.error .fix { margin: 9px 0 0; font-size: 13px; color: var(--amber); }
.error .fix.archivo {
  display: flex; flex-wrap: wrap; align-items: baseline; gap: 6px 10px;
  color: var(--ink); padding: 9px 12px; border-left: 3px solid var(--amber-dim);
  background: rgba(216,162,74,.06); border-radius: 0 8px 8px 0;
}
.error .fix.archivo b { font-family: var(--mono); font-size: 10.5px; letter-spacing: .14em; color: var(--amber); }
.error .fix.archivo span { flex: 1 1 24ch; line-height: 1.5; }
.error .fix.archivo .btn { padding: 4px 10px; font-size: 12px; }
/* Con traducción, el error del motor pasa a nota al pie. */
.error.con-lectura .fix.archivo { margin-top: 2px; }
.error.con-lectura .fix.archivo span { font-size: 14px; }
.error.con-lectura pre {
  margin-top: 11px; padding-top: 9px; border-top: 1px dashed var(--line);
  font-size: 11.5px; color: var(--ink-faint);
}

.results-bar {
  display: flex; align-items: center; gap: 8px; flex-wrap: wrap;
  font-family: var(--mono); font-size: 11px; color: var(--ink-faint); padding: 0 2px 8px;
}
.results-bar .btn { padding: 4px 10px; }
.results-bar span:first-child { margin-right: auto; }

/* La tabla se desplaza de lado cuando hay más columnas de las que caben, y
   hasta ahora no lo decía: en el teléfono la columna `hora` quedaba cortada
   en «2» y parecía un dato roto. Dos sombras ancladas a la caja y dos tapas
   ancladas al contenido: la sombra sólo se ve por el lado que queda por
   recorrer. Sin JavaScript y sin barra siempre visible. */
.table-wrap {
  overflow: auto; max-height: 58vh;
  border: 1px solid var(--line); border-radius: var(--r);
  background-color: var(--panel);
  background-image:
    linear-gradient(to right, var(--panel), rgba(0,0,0,0)),
    linear-gradient(to left,  var(--panel), rgba(0,0,0,0)),
    linear-gradient(to right, rgba(0,0,0,.55), rgba(0,0,0,0)),
    linear-gradient(to left,  rgba(0,0,0,.55), rgba(0,0,0,0));
  background-position: 0 0, 100% 0, 0 0, 100% 0;
  background-repeat: no-repeat;
  background-size: 26px 100%, 26px 100%, 15px 100%, 15px 100%;
  background-attachment: local, local, scroll, scroll;
}
table { border-collapse: collapse; width: 100%; font-family: var(--mono); font-size: 12.5px; }
thead th {
  position: sticky; top: 0; z-index: 2; text-align: left; white-space: nowrap;
  background: var(--panel-2); color: var(--accent); font-weight: 600;
  padding: 9px 12px; border-bottom: 1px solid var(--line); cursor: pointer; user-select: none;
}
thead th:hover { background: var(--line-soft); }
thead th.ordenada { color: var(--ink); }
tbody td { padding: 7px 12px; border-bottom: 1px solid var(--line-soft); white-space: nowrap; color: var(--ink); }
tbody tr:hover td { background: rgba(216,162,74,.05); }
td.null { color: var(--ink-faint); font-style: italic; }
td.num { text-align: right; font-variant-numeric: tabular-nums; }

/* historial */
.history {
  margin-top: 14px; background: var(--panel); border: 1px solid var(--line);
  border-radius: var(--r); overflow: hidden;
}
.history summary {
  cursor: pointer; padding: 11px 14px; list-style: none;
  font-family: var(--mono); font-size: 11px; letter-spacing: .14em; text-transform: uppercase; color: var(--ink-dim);
}
.history summary::-webkit-details-marker { display: none; }
.history summary::before { content: "▸ "; color: var(--ink-faint); }
.history[open] summary::before { content: "▾ "; }
.history-count { color: var(--ink-faint); letter-spacing: 0; }
#history { padding: 0 12px 12px; display: grid; grid-template-columns: minmax(0, 1fr); gap: 6px; }
#history > * { min-width: 0; }
.hist-item {
  display: flex; flex-direction: column; gap: 3px; align-items: flex-start; text-align: left;
  background: var(--bg-2); border: 1px solid var(--line-soft); border-radius: 7px;
  padding: 8px 10px; cursor: pointer; width: 100%;
}
.hist-item:hover { border-color: var(--amber-dim); }
.hist-item code { font-family: var(--mono); font-size: 11.5px; color: var(--ink); word-break: break-word; }
.hist-item span { font-family: var(--mono); font-size: 10px; color: var(--ink-faint); }
.hist-item.err span { color: var(--red-claro); }

/* ---------- esquema ---------- */
.schema-head { display: flex; flex-direction: column; gap: 8px; margin-bottom: 10px; }
#schema-filter {
  width: 100%; padding: 8px 11px; border-radius: 8px;
  background: var(--panel); border: 1px solid var(--line); color: var(--ink); font-size: 13px;
}
#schema-filter:focus { outline: none; border-color: var(--amber-dim); }
.tbl { background: var(--panel); border: 1px solid var(--line); border-radius: var(--r); margin-bottom: 10px; overflow: hidden; }
.tbl summary { cursor: pointer; padding: 11px 13px; list-style: none; display: flex; align-items: center; gap: 8px; }
.tbl summary::-webkit-details-marker { display: none; }
.tbl summary b { font-family: var(--mono); font-size: 13px; color: var(--accent); font-weight: 600; }
.tbl summary .rows { margin-left: auto; font-family: var(--mono); font-size: 10.5px; color: var(--ink-faint); }
.tbl .tbl-comment { padding: 0 13px 10px; font-size: 12.5px; color: var(--ink-dim); font-style: italic; margin: -4px 0 0; }
.cols { border-top: 1px solid var(--line-soft); padding: 8px 0; }
.col { display: grid; grid-template-columns: 1fr auto; gap: 4px 10px; padding: 6px 13px; }
.col:hover { background: rgba(255,255,255,.02); }
.col .cname { font-family: var(--mono); font-size: 12px; color: var(--ink); cursor: pointer; }
.col .cname:hover { color: var(--accent); }
.col .ctype { font-family: var(--mono); font-size: 10px; color: var(--ink-faint); text-transform: lowercase; }
.col .ccomment { grid-column: 1 / -1; font-size: 11.5px; color: var(--ink-faint); line-height: 1.45; }
.tbl-actions { display: flex; gap: 6px; flex-wrap: wrap; padding: 8px 13px 2px; }
.tbl-actions .btn { padding: 6px 10px; font-size: 12px; }

/* ---------- manual ---------- */
.modal {
  position: fixed; inset: 0; z-index: 200; display: grid; place-items: center;
  background: rgba(5,7,9,.78); backdrop-filter: blur(6px); padding: 20px;
}

/* La confirmación del juego: sustituye al `confirm()` del navegador, que saca
   de la pantalla completa y en un iframe sin `allow-modals` ni aparece. */
.modal-confirmar { z-index: 700; place-items: center; padding: 20px; }
.confirmar-caja {
  width: min(440px, 100%); padding: 22px 22px 18px;
  background: var(--panel); border: 1px solid var(--amber-dim); border-radius: var(--r);
  box-shadow: 0 24px 60px rgba(0,0,0,.6);
}
.confirmar-caja p { margin: 0 0 18px; font-family: var(--serif); font-size: 16px; line-height: 1.5; color: var(--ink); }
.confirmar-botones { display: flex; gap: 10px; justify-content: flex-end; flex-wrap: wrap; }
#confirmar-area {
  width: 100%; min-height: 118px; margin: 0 0 16px; resize: vertical;
  font-family: var(--mono); font-size: 12.5px; line-height: 1.5; color: var(--ink);
  background: var(--bg-2); border: 1px solid var(--line); border-radius: var(--r); padding: 10px;
}
/* Los creditos son 2.700 lineas de avisos de licencia, no un codigo de cuatro
   caracteres para copiar: el mismo cuadro necesita altura o el aviso viaja
   pero no se puede leer. */
#confirmar-area.larga { min-height: min(52dvh, 460px); }
.modal-card {
  background: var(--panel); border: 1px solid var(--line); border-radius: 14px;
  width: min(760px, 100%); max-height: 88dvh; overflow-y: auto; padding: 22px;
  box-shadow: 0 24px 70px rgba(0,0,0,.6);
}
.modal-head { display: flex; align-items: center; gap: 12px; }
.modal-head h2 { font-family: var(--serif); font-weight: 500; font-size: 24px; margin: 0; }
.modal-head .icon-btn { margin-left: auto; }
.modal-intro { color: var(--ink-dim); font-size: 14px; line-height: 1.6; margin: 8px 0 20px; }
.modal-body { display: grid; grid-template-columns: minmax(0, 1fr); gap: 14px; }
.modal-body > * { min-width: 0; }
.patron {
  background: var(--bg-2); border: 1px solid var(--line-soft); border-radius: var(--r);
  border-left: 3px solid var(--accent); padding: 14px 16px;
}
.patron h3 { font-family: var(--serif); font-size: 17px; font-weight: 600; margin: 0 0 4px; }
.patron-cuando { color: var(--ink-dim); font-size: 13px; line-height: 1.55; margin: 0 0 10px; }
.patron-nota { color: var(--ink-dim); font-size: 13px; line-height: 1.6; margin: 0; overflow-wrap: anywhere; }
.patron.cerrado { border-left-color: var(--line); opacity: .5; }
.patron.primero-cerrado { margin-top: 22px; padding-top: 20px; border-top: 1px solid var(--line); }
.patron.cerrado h3 { color: var(--ink-faint); }
.patron.cerrado .patron-cuando { font-style: italic; margin: 0; }

/* ---------- pestañas móviles ---------- */
.tabbar { display: none; }
@media (max-width: 860px) {
  .view { padding: 16px 12px calc(76px + var(--safe-b)); }
  /* `1fr` a secas y los hijos con `min-width:auto` dejaban que el editor de
   CodeMirror fijara el ancho de la columna: en un teléfono de 390 px la
   página entera medía 555 y se desplazaba de lado, con la tabla, los chips y
   los botones cortados por el borde. `minmax(0, 1fr)` + `min-width: 0` es lo
   que obliga a cada panel a caber y a desplazarse por dentro. */
.case-grid { display: grid; grid-template-columns: minmax(0, 1fr); gap: 12px; }
.case-grid > * { min-width: 0; }
  /* Las columnas se disuelven y cada bloque va a su pestaña. */
  .zona { display: contents; }
  .zona-rotulo { display: none !important; }
  .case-grid [data-tab] { display: none; }
  .case-grid [data-tab].active { display: block; }
  .case-grid [data-tab][hidden] { display: none !important; }
  /* El orden de lectura del expediente en una sola columna. */
  .case-grid .dossier { order: 1; } .case-grid .estado { order: 2; } .case-grid .hints { order: 3; }
  .case-grid .notepad { order: 4; } .case-grid .accuse { order: 5; } .case-grid .danger-zone { order: 6; }
  .case-grid .solution { order: 7; } .case-grid .case-nav { order: 8; }
  .case-grid .results { margin-top: 0; }
  .tabbar {
    position: fixed; left: 0; right: 0; bottom: 0; z-index: 60;
    display: grid; grid-template-columns: repeat(3, 1fr); gap: 0;
    background: rgba(10,12,15,.94); backdrop-filter: blur(14px);
    border-top: 1px solid var(--line);
    padding-bottom: var(--safe-b);
  }
  .tabbar button {
    background: none; border: 0; color: var(--ink-faint); padding: 14px 4px;
    font-size: 12px; letter-spacing: .06em; text-transform: uppercase; cursor: pointer;
    border-top: 2px solid transparent;
  }
  .tabbar button.active { color: var(--accent); border-top-color: var(--accent); }
  .editor-hl, .editor textarea { min-height: 160px; font-size: 13px; }
  .card-escena { height: 104px; }
  .dossier { padding: 18px 16px 16px; }
  .table-wrap { max-height: 50vh; }
  .hero { margin: 8px 0 28px; }
  .hero-stats { gap: 16px; }
  .modal { padding: 0; }
  .modal-card { max-height: 100dvh; border-radius: 0; border: 0; padding: 18px 16px calc(24px + var(--safe-b)); }
  /* En móvil el título del caso puede ser largo; la barra superior no es sitio
     para leerlo entero: se lee en el propio expediente. */
  .brand-text strong {
    white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
    max-width: 44vw; font-size: 15px;
  }
  .score { display: none; }
}

/* ---------- toast ---------- */
.toast {
  position: fixed; left: 50%; transform: translateX(-50%);
  /* Por encima de la celebración (500): un aviso disparado durante ella era
     invisible y se perdía sin que nadie lo viera. */
  bottom: calc(88px + var(--safe-b)); z-index: 600;
  background: var(--panel-2); border: 1px solid var(--amber-dim); color: var(--ink);
  padding: 11px 18px; border-radius: 999px; font-size: 13.5px;
  box-shadow: 0 8px 28px rgba(0,0,0,.5);
  animation: aparece .2s ease;
}

/* En escritorio la consola y el esquema se quedan pegados: el expediente es
   largo y no tiene sentido perder de vista la herramienta mientras se lee. */
@media (min-width: 861px) {
  .pane-console, .pane-schema {
    position: sticky; top: 70px;
    max-height: calc(100dvh - 86px);
    overflow-y: auto;
    scrollbar-width: thin;
  }
  .pane-console::-webkit-scrollbar, .pane-schema::-webkit-scrollbar { width: 8px; }
  .pane-console::-webkit-scrollbar-thumb, .pane-schema::-webkit-scrollbar-thumb {
    background: var(--line); border-radius: 4px;
  }
}

/* Temporada 2: la paleta se vuelve verde pantalla. Temporada 3: violeta de
   sótano de archivo. */
body[data-season="t2_mercados"] { --accent: var(--jade); --amber: var(--jade); --amber-dim: #2e7d64; }
body[data-season="t3_forense"]  { --accent: var(--violet); --amber: var(--violet); --amber-dim: #5f4b87; }

/* ---------- oferta de quitar anuncios (sólo en la app) ---------- */
.compra { margin: 8px 0 40px; }
.compra-card {
  display: flex; align-items: center; gap: 16px; flex-wrap: wrap;
  background: linear-gradient(168deg, var(--panel-2), var(--panel));
  border: 1px solid var(--amber-dim); border-radius: var(--r); padding: 16px 18px;
}
.compra-card strong { font-family: var(--serif); font-size: 17px; font-weight: 600; }
.compra-card p { margin: 4px 0 0; color: var(--ink-dim); font-size: 13.5px; line-height: 1.5; }
.compra-card .btn { margin-left: auto; white-space: nowrap; }

/* ---------- comportamiento táctil ----------
   En el navegador de escritorio da igual, pero dentro de la app un toque sobre
   una tarjeta abría el menú de selección de texto ("Copiar / Compartir / Leer
   en voz alta") en vez de abrir el expediente. Una app no se lee como una
   página: el texto no se selecciona salvo donde de verdad quieras copiarlo. */
body {
  -webkit-user-select: none; user-select: none;
  -webkit-touch-callout: none;
  -webkit-tap-highlight-color: transparent;
}
/* Y donde sí interesa copiar: la consola, lo que devuelve, el SQL de las
   soluciones y las notas propias. */
#sql, .table-wrap, .results, .solution pre, .hint-body pre, .patron pre,
#notas, .dossier-body, .hint-body, .solution-body, .field input, #schema-filter {
  -webkit-user-select: text; user-select: text;
}
/* Sin el retardo de 300 ms que el navegador reserva por si viene un doble
   toque: en una app, un botón responde al instante o parece rota. */
button, .card, .tabbar button, summary, [data-insert], [data-peek] {
  touch-action: manipulation;
}

/* ================= ESCENAS DE LOS CASOS =================
   Arte vectorial animado con CSS. Todo lo que se mueve aquí usa `transform` y
   `opacity`, que el compositor resuelve sin repintar: en un WebView de móvil
   cualquier otra propiedad animada se nota en el desplazamiento. */

.escena-marco {
  position: relative; overflow: hidden;
  border-radius: 4px 4px 0 0;
  margin: -22px -22px 16px;
  height: 148px;
  background: var(--bg);
}
.escena { display: block; width: 100%; height: 100%; }
/* El papel del expediente empieza justo debajo: un degradado funde la escena
   con él para que no parezca una estampa pegada encima. */
.escena-marco::after {
  content: ""; position: absolute; left: 0; right: 0; bottom: -1px; height: 42px;
  background: linear-gradient(transparent, var(--paper));
}

@keyframes esc-flotar { 50% { transform: translateY(-4px); } }
@keyframes esc-latir { 0%, 100% { opacity: .28; } 50% { opacity: .9; } }
@keyframes esc-girar { to { transform: rotate(360deg); } }
@keyframes esc-barrer { 0% { transform: translateY(0); opacity: 0; }
                        12% { opacity: 1; } 88% { opacity: 1; }
                        100% { transform: translateY(78px); opacity: 0; } }
@keyframes esc-temblar { 25% { transform: rotate(-7deg); } 75% { transform: rotate(7deg); } }
@keyframes esc-subir { 0% { transform: translateY(0); opacity: 0; }
                       30% { opacity: .9; } 100% { transform: translateY(-26px); opacity: 0; } }
@keyframes esc-deslizar { to { stroke-dashoffset: -32; } }
@keyframes esc-caer { 0%, 62% { transform: translateY(-16px); }
                      74% { transform: translateY(0); } 100% { transform: translateY(-16px); } }
@keyframes esc-entrar { from { opacity: 0; transform: translateY(8px); } }
@keyframes esc-apagarse { 0%, 100% { opacity: .38; } 50% { opacity: .08; } }
@keyframes esc-inclinar { 0%, 100% { transform: rotate(-7deg); } 50% { transform: rotate(4deg); } }

.c-motivo .m-flotar { animation: esc-flotar 6s ease-in-out infinite; }
.c-luna { animation: esc-latir 9s ease-in-out infinite; }
.m-ventana { animation: esc-latir 4s ease-in-out infinite; }
.m-carpeta { animation: esc-flotar 4.2s ease-in-out infinite; }
.m-escaneo { animation: esc-barrer 3.4s ease-in-out infinite; }
.m-timbre { animation: esc-temblar .28s ease-in-out 6; transform-origin: 200px 93px; }
.m-ondas { animation: esc-latir 1.6s ease-in-out infinite; }
.m-burbuja { animation: esc-subir 3.2s ease-in-out infinite; }
.m-burbuja.m-b2 { animation-delay: 1.1s; }
.m-aguja { animation: esc-girar 6s linear infinite; }
.m-luzpuerta { animation: esc-latir 5s ease-in-out infinite; }
.m-vagon { animation: esc-flotar 3s ease-in-out infinite; }
.m-haz { animation: esc-latir 7s ease-in-out infinite; transform-origin: 200px 71px; }
.m-haz2 { animation-delay: 3.5s; }
.m-vela { animation: esc-entrar .5s ease-out both; }
.m-gota { animation: esc-flotar 2.4s ease-in-out infinite; }
.m-reflejo { animation: esc-latir 3.6s ease-in-out infinite; }
.m-flecha { stroke-dasharray: 4 6; animation: esc-deslizar 1.6s linear infinite; }
.m-flecha.m-f2 { animation-direction: reverse; }
.m-hueco { animation: esc-latir 2.2s ease-in-out infinite; }
.m-congelada { stroke-dasharray: 5 4; animation: esc-deslizar 3s linear infinite; }
.m-pulso { animation: esc-latir 1.4s ease-in-out infinite; }
.m-adelanto { animation: esc-flotar 3.4s ease-in-out infinite; }
.m-cancel { animation: esc-latir 1.8s steps(1) infinite; }
.m-pared { animation: esc-apagarse 3.2s ease-in-out infinite; }
.m-barrera { transform-origin: 222px 108px; animation: esc-inclinar 4.5s ease-in-out infinite; }
.m-moneda { animation: esc-subir 2.8s ease-in-out infinite; }
.m-flujo { animation: esc-deslizar 1.4s linear infinite; }
.m-hoja { animation: esc-entrar .5s ease-out both; }
.m-x4 { animation: esc-latir 2.4s ease-in-out infinite; }
.m-copia { animation: esc-flotar 5s ease-in-out infinite; }
.m-sellar { animation: esc-caer 3.2s ease-in-out infinite; }
.m-balancear { animation: esc-inclinar 5s ease-in-out infinite; }
.m-hora-repetida { transform-origin: 200px 96px; animation: esc-girar 8s steps(12) infinite; }
.m-borrarse { animation: esc-apagarse 4s ease-in-out infinite; }
.c-niebla { animation: esc-latir 11s ease-in-out infinite; }

/* ---------- introducción: una viñeta por párrafo ----------
   La primera versión era un texto que crecía sobre una imagen fija y leía como
   un libro. Ahora cada párrafo trae su propio plano a pantalla completa y el
   anterior se funde por debajo: el montaje es lo que dramatiza, no la
   tipografía. */
.intro {
  position: fixed; inset: 0; z-index: 400; overflow: hidden;
  background: var(--bg); cursor: pointer;
  animation: intro-abrir .5s ease both;
}
.intro.cerrando { animation: intro-cerrar .45s ease both; }
@keyframes intro-abrir  { from { opacity: 0; } }
@keyframes intro-cerrar { to { opacity: 0; transform: scale(1.04); } }

/* El lienzo ocupa toda la pantalla; las capas se apilan y se funden. */
.intro-lienzo { position: absolute; inset: 0; }
.plano-capa {
  position: absolute; inset: 0;
  animation: plano-entrar .9s ease both;
}
@keyframes plano-entrar { from { opacity: 0; } }
.plano { width: 100%; height: 100%; display: block; }

/* Movimiento de cámara: cuatro recorridos que se alternan para que dos planos
   seguidos nunca se muevan igual. Lentos a propósito — se tienen que notar
   sólo cuando la viñeta lleva unos segundos delante. */
@keyframes cam-a { from { transform: scale(1.16) translate(2%, 1%); }  to { transform: scale(1.02) translate(0, 0); } }
@keyframes cam-b { from { transform: scale(1.03) translate(-2%, 0); }  to { transform: scale(1.18) translate(1%, -2%); } }
@keyframes cam-c { from { transform: scale(1.14) translate(-3%, -1%); } to { transform: scale(1.03) translate(1%, 1%); } }
@keyframes cam-d { from { transform: scale(1.05) translate(1%, 2%); }  to { transform: scale(1.16) translate(-2%, 0); } }
.plano.cam-a { animation: cam-a 15s ease-out both; }
.plano.cam-b { animation: cam-b 15s ease-out both; }
.plano.cam-c { animation: cam-c 15s ease-out both; }
.plano.cam-d { animation: cam-d 15s ease-out both; }

/* Cartel de apertura, centrado sobre el primer plano. Se retira en cuanto
   empieza el relato. */
.intro-titulo {
  position: absolute; inset: 0; display: grid; align-content: center; justify-items: center;
  text-align: center; padding: 0 28px;
  background: radial-gradient(closest-side, rgba(10,12,15,.72), rgba(10,12,15,.35) 70%, transparent);
  transition: opacity .5s ease, transform .5s ease;
}
.intro.en-relato .intro-titulo { opacity: 0; transform: translateY(-18px); pointer-events: none; }

.intro-num {
  font-family: var(--mono); font-size: 11px; letter-spacing: .2em; color: var(--accent);
  margin: 0 0 14px; display: inline-block; overflow: hidden; white-space: nowrap;
  border-right: 2px solid var(--accent);
  animation: intro-teclear 1.4s steps(30, end) .3s both, intro-cursor .7s step-end 5;
}
@keyframes intro-teclear { from { width: 0; } to { width: 100%; } }
@keyframes intro-cursor { 50% { border-color: transparent; } }
.intro-titulo h2 {
  font-family: var(--serif); font-size: clamp(30px, 8vw, 54px); font-weight: 500;
  letter-spacing: -.02em; margin: 0 0 10px; text-shadow: 0 4px 26px rgba(0,0,0,.8);
  animation: intro-subir .9s ease-out 1.3s both;
}
.intro-tagline {
  font-family: var(--serif); font-style: italic; color: var(--ink-dim);
  font-size: clamp(14px, 3.6vw, 18px); margin: 0; text-shadow: 0 2px 14px rgba(0,0,0,.9);
  animation: intro-subir .9s ease-out 1.8s both;
}
@keyframes intro-subir { from { opacity: 0; transform: translateY(16px); } }

/* El pie: la viñeta de texto y los controles, sobre un velo que garantiza que
   el texto se lea encima de cualquier plano. */
.intro-pie {
  position: absolute; left: 0; right: 0; bottom: 0;
  padding: 60px 20px calc(14px + var(--safe-b));
  background: linear-gradient(transparent, rgba(8,10,13,.86) 38%, rgba(8,10,13,.97));
}
.intro-viñeta {
  width: min(660px, 100%); margin: 0 auto 14px;
  animation: vineta-entrar .5s cubic-bezier(.2,.8,.3,1) both;
}
@keyframes vineta-entrar { from { opacity: 0; transform: translateY(16px); } }
.intro-viñeta:empty { display: none; }

.v-texto {
  font-family: var(--serif); font-size: clamp(16px, 4.4vw, 21px); line-height: 1.55;
  color: var(--ink); margin: 0; text-shadow: 0 2px 12px rgba(0,0,0,.7);
}
.v-nombre {
  display: block; font-family: var(--mono); font-size: 11px; letter-spacing: .18em;
  text-transform: uppercase; color: var(--voz, var(--accent)); margin-bottom: 6px;
}
.intro-viñeta.con-voz {
  border-left: 2px solid var(--voz, var(--ink-faint)); padding-left: 16px;
}
.intro-viñeta.con-voz .v-texto {
  font-style: italic; color: var(--ink-dim); font-size: clamp(15px, 4.1vw, 19px);
}
.intro-viñeta[data-voz="pericial"]     { --voz: #7fb2ff; }
.intro-viñeta[data-voz="centralita"] { --voz: #e2705a; }
.intro-viñeta[data-voz="archivo"]    { --voz: #d8a24a; }
.intro-viñeta[data-voz="internos"]   { --voz: #9a7fd0; }
.intro-viñeta[data-voz="instruccion"]     { --voz: #46c39c; }
.intro-viñeta[data-voz="guardia"]     { --voz: #8b96a5; }
.intro-viñeta[data-voz="fiscalia"]   { --voz: #c9a227; }

.intro-pasos {
  display: flex; justify-content: center; gap: 5px;
  width: min(660px, 100%); margin: 0 auto 12px;
}
.intro-pasos i {
  flex: 0 1 16px; min-width: 5px; height: 2px; border-radius: 1px;
  background: var(--ink-faint); opacity: .28; transition: opacity .3s ease, background-color .3s ease;
}
.intro-pasos i.vista { opacity: .9; background: var(--accent); }
.intro-pasos:empty { display: none; }
.intro-controles {
  display: flex; align-items: center; gap: 14px;
  width: min(660px, 100%); margin: 0 auto;
}
.intro-avanzar {
  flex: 1; text-align: center; margin: 0;
  font-family: var(--mono); font-size: 10.5px; letter-spacing: .16em;
  text-transform: uppercase; color: var(--ink-faint);
  animation: intro-latir 2.4s ease-in-out infinite both;
}
@keyframes intro-latir { 0%, 100% { opacity: .35; } 50% { opacity: .85; } }

/* Volver a ver la introducción. Va justo debajo de la ilustración, no al final
   del expediente: quien abrió el caso con una versión anterior no tiene otra
   forma de enterarse de que existe. */
.dossier-intro {
  display: block; width: 100%; margin: 0 0 14px;
  background: transparent; border: 1px solid rgba(0,0,0,.16);
  color: var(--paper-dim); font-size: 13px;
  font-family: var(--mono); letter-spacing: .04em;
}
.dossier-intro:hover { color: var(--paper-ink); border-color: rgba(0,0,0,.4); }
/* Sin ver todavía: se señala, pero sin gritar. */
.dossier-intro.sin-ver {
  color: #7a5c1f; border-color: rgba(122,92,31,.5);
  background: rgba(216,162,74,.10);
}

/* Las animaciones del interior de los planos, heredadas del catálogo. */
.p-ventana  { animation: esc-latir 4s ease-in-out infinite; }
.p-halo     { animation: esc-latir 6s ease-in-out infinite; }
.p-lampara  { animation: esc-latir 5s ease-in-out infinite; }
.p-linea    { stroke-dasharray: 90; animation: esc-deslizar 3s linear infinite; }
.p-flujo    { stroke-dasharray: 4 6; animation: esc-deslizar 1.6s linear infinite; }
.p-sumidero { animation: esc-latir 2.4s ease-in-out infinite; }
.p-hoja     { animation: esc-entrar .6s ease-out both; }
.p-aguja    { animation: esc-girar 30s linear infinite; }

@media (prefers-reduced-motion: reduce) {
  .plano, .plano-capa, .intro-num, .intro-titulo h2, .intro-tagline,
  .intro-avanzar, .intro-viñeta, .p-ventana, .p-halo, .p-lampara, .p-linea,
  .p-flujo, .p-sumidero, .p-hoja, .p-aguja {
    animation-duration: .01s !important; animation-delay: 0s !important;
    animation-iteration-count: 1 !important;
  }
}

/* ================= CAPA DE JUEGO ================= */

/* Rango del jugador, en la portada */
.rango { margin-top: 26px; max-width: 380px; }
.rango-cab { display: flex; align-items: baseline; gap: 10px; flex-wrap: wrap; margin-bottom: 7px; }
.rango-cab strong {
  font-family: var(--serif); font-size: 18px; font-weight: 600; color: var(--accent);
}
.rango-cab span { font-size: 12px; color: var(--ink-faint); }
.rango-barra { height: 3px; background: var(--line-soft); border-radius: 3px; overflow: hidden; }
.rango-barra div {
  height: 100%; background: var(--accent); border-radius: 3px;
  transition: width .8s cubic-bezier(.2,.8,.3,1);
}

/* Medalla en la tarjeta del archivo */
.medalla { font-size: 13px; line-height: 1; }
.med-bronce { color: #b07a4a; }
.med-plata  { color: #aab4c0; }
.med-oro    { color: var(--amber); text-shadow: 0 0 8px rgba(216,162,74,.55); }

/* Objetivos secundarios del caso */
.objetivos { list-style: none; margin: 10px 0 0; padding: 0; display: grid; gap: 5px; }
.objetivos li {
  display: flex; align-items: baseline; gap: 8px;
  font-size: 12.5px; color: var(--ink-faint);
  font-family: var(--mono);
}
.objetivos li em { color: var(--ink-faint); opacity: .7; font-style: normal; font-size: 11px; }
.objetivos li.ok { color: var(--jade); }
.objetivos li.fallado { opacity: .45; text-decoration: line-through; text-decoration-thickness: 1px; }
.obj-icono { width: 12px; text-align: center; }

/* ---------- pantalla de caso resuelto ---------- */
.celebracion {
  position: fixed; inset: 0; z-index: 500;
  display: grid; place-items: center; padding: 20px;
  background: rgba(5,7,9,.82); backdrop-filter: blur(8px);
  animation: cel-entrar .35s ease both;
}
@keyframes cel-entrar { from { opacity: 0; } }

.cel-caja {
  position: relative; z-index: 2;
  width: min(460px, 100%); max-height: 88dvh; overflow-y: auto;
  background: var(--panel); border: 1px solid var(--line); border-radius: 14px;
  padding: 26px 24px 22px; text-align: center;
  box-shadow: 0 30px 80px rgba(0,0,0,.7);
  animation: cel-subir .45s cubic-bezier(.2,.9,.3,1) both;
}
@keyframes cel-subir { from { opacity: 0; transform: translateY(22px) scale(.97); } }

.cel-sello {
  width: 128px; height: 128px; margin: 4px auto 16px;
  display: grid; place-items: center; border-radius: 50%;
  border: 3px solid currentColor; color: var(--jade);
  font-family: var(--mono); font-size: 15px; letter-spacing: .14em; line-height: 1.35;
  transform: rotate(-9deg);
  animation: cel-sellar .55s cubic-bezier(.2,1.7,.4,1) .12s both;
}
/* El sello cae de golpe, como en la carpeta: es el mismo gesto, más grande. */
@keyframes cel-sellar {
  0%   { transform: rotate(-30deg) scale(2.4); opacity: 0; }
  55%  { transform: rotate(-6deg) scale(.92); opacity: 1; }
  100% { transform: rotate(-9deg) scale(1); }
}
.cel-sello.cel-bronce { color: #b07a4a; }
.cel-sello.cel-plata  { color: #aab4c0; }
.cel-sello.cel-oro    { color: var(--amber); box-shadow: 0 0 34px rgba(216,162,74,.34); }

.cel-caja h2 { font-family: var(--serif); font-size: 23px; font-weight: 500; margin: 0 0 2px; }
.cel-medalla {
  font-family: var(--mono); font-size: 11px; letter-spacing: .18em; text-transform: uppercase;
  color: var(--ink-faint); margin: 0 0 18px;
}

.cel-objetivos { list-style: none; margin: 0 0 18px; padding: 0; display: grid; gap: 7px; text-align: left; }
.cel-objetivos li {
  display: flex; align-items: baseline; gap: 9px;
  font-size: 13px; color: var(--ink-faint);
  background: var(--bg-2); border: 1px solid var(--line-soft); border-radius: 8px; padding: 8px 11px;
  animation: cel-fila .4s ease both;
}
.cel-objetivos li:nth-child(1) { animation-delay: .5s; }
.cel-objetivos li:nth-child(2) { animation-delay: .62s; }
.cel-objetivos li:nth-child(3) { animation-delay: .74s; }
@keyframes cel-fila { from { opacity: 0; transform: translateX(-10px); } }
.cel-objetivos li.ok { color: var(--jade); border-color: rgba(70,195,156,.35); }
.cel-objetivos li em { margin-left: auto; font-style: normal; font-size: 11px; opacity: .7; }
.cel-icono { width: 14px; text-align: center; }

.cel-etiqueta {
  display: block; font-family: var(--mono); font-size: 10px; letter-spacing: .16em;
  text-transform: uppercase; color: var(--ink-faint); margin-bottom: 4px;
}
.cel-patron {
  background: rgba(216,162,74,.07); border: 1px solid var(--amber-dim);
  border-radius: 9px; padding: 11px 13px; margin-bottom: 16px; text-align: left;
  animation: cel-fila .45s ease .9s both;
}
.cel-patron strong { display: block; font-family: var(--serif); font-size: 15.5px; }
.cel-patron strong + strong { margin-top: 4px; }

.cel-rango { text-align: left; margin-bottom: 20px; animation: cel-fila .45s ease 1s both; }
.cel-barra { height: 3px; background: var(--line-soft); border-radius: 3px; overflow: hidden; margin: 6px 0 6px; }
.cel-barra div { height: 100%; background: var(--accent); animation: cel-barra 1s ease 1.1s both; }
@keyframes cel-barra { from { width: 0 !important; } }
.cel-rango p { margin: 0; font-size: 12.5px; color: var(--ink-faint); }

/* Papeles de archivo cayendo por detrás de la tarjeta */
.cel-papeles { position: absolute; inset: 0; overflow: hidden; pointer-events: none; }
.cel-papeles i {
  position: absolute; top: -14%; display: block;
  background: var(--paper); opacity: .85; border-radius: 1px;
  box-shadow: inset 0 0 0 1px rgba(0,0,0,.12);
  animation-name: cel-caer; animation-timing-function: linear; animation-iteration-count: 1;
  animation-fill-mode: both;
}
@keyframes cel-caer {
  0%   { transform: translateY(0) rotate(0); opacity: 0; }
  8%   { opacity: .9; }
  100% { transform: translateY(112vh) rotate(var(--giro)); opacity: 0; }
}

@media (prefers-reduced-motion: reduce) {
  .cel-papeles { display: none; }
  .cel-sello, .cel-caja, .cel-objetivos li, .cel-patron, .cel-rango, .cel-barra div {
    animation-duration: .01s !important; animation-delay: 0s !important;
  }
}

/* ---------- micro-animaciones de la interfaz ----------
   Cortas y sólo a la entrada. Nada que se repita mientras se lee, y nada que
   retrase un toque: si una animación hace esperar para actuar, sobra. */

@keyframes ui-entrar { from { opacity: 0; transform: translateY(10px); } }
@keyframes ui-fundir { from { opacity: 0; } }

.carpetas .carpeta { animation: ui-entrar .42s cubic-bezier(.2,.8,.3,1) both; }
/* El escalonado se corta a la sexta: más allá, quien llega abajo tras
   desplazarse encontraría tarjetas todavía apareciendo. */
.carpetas .carpeta:nth-child(1) { animation-delay: .02s; }
.carpetas .carpeta:nth-child(2) { animation-delay: .06s; }
.carpetas .carpeta:nth-child(3) { animation-delay: .10s; }
.carpetas .carpeta:nth-child(4) { animation-delay: .14s; }
.carpetas .carpeta:nth-child(5) { animation-delay: .18s; }
.carpetas .carpeta:nth-child(n+6) { animation-delay: .2s; }

.hero { animation: ui-entrar .5s ease-out both; }
.season { animation: ui-fundir .5s ease-out both; }

.case-grid > .pane { animation: ui-entrar .38s cubic-bezier(.2,.8,.3,1) both; }
.case-grid > .pane:nth-child(2) { animation-delay: .06s; }
.case-grid > .pane:nth-child(3) { animation-delay: .12s; }

.results .table-wrap { animation: ui-entrar .3s ease-out both; }
.results-bar { animation: ui-fundir .3s ease-out both; }

/* El botón de ejecutar late mientras trabaja: en el móvil, una consulta de dos
   segundos sin señal de vida parece un toque perdido. */
#btn-run:disabled { animation: ui-latir 1.1s ease-in-out infinite; }
@keyframes ui-latir { 50% { opacity: .55; } }

@media (prefers-reduced-motion: reduce) {
  .carpetas .carpeta, .hero, .cajon, .case-grid > .pane, .results .table-wrap, .results-bar {
    animation: none !important;
  }
  #btn-run:disabled { animation: none; }
}

/* ---------- la línea de una voz ----------
 * Abajo, con el color de la voz, el tiempo justo de leerla. Es el mismo objeto
 * que el coach del tutorial, sin botones: una voz interior, no un aviso. */
.voz-linea {
  position: fixed; left: 12px; right: 12px; bottom: calc(76px + var(--safe-b)); z-index: 320;
  max-width: 520px; margin: 0 auto; cursor: pointer;
  background: rgba(21,26,33,.94); border: 1px solid var(--line); border-left: 3px solid var(--voz, var(--amber));
  border-radius: 10px; padding: 10px 14px 11px 16px; box-shadow: 0 16px 40px rgba(0,0,0,.55);
  backdrop-filter: blur(8px);
  animation: voz-entrar .4s cubic-bezier(.2,.9,.3,1) both;
}
@media (min-width: 900px) { .voz-linea { left: auto; right: 24px; bottom: 24px; max-width: 420px; } }
.voz-linea.saliendo { animation: voz-salir .35s ease both; }
.voz-cab { display: flex; align-items: baseline; gap: 10px; margin-bottom: 4px; }
.voz-quien { font-family: var(--mono); font-size: 10.5px; letter-spacing: .16em; color: var(--voz, var(--amber)); }
.voz-sobre { font-family: var(--mono); font-size: 10px; color: var(--ink-faint); margin-left: auto; text-align: right; }
.voz-texto { margin: 0; font-family: var(--serif); font-size: 14.5px; line-height: 1.45; color: var(--ink); }
@keyframes voz-entrar { from { opacity: 0; transform: translateY(12px); } }
@keyframes voz-salir  { to   { opacity: 0; transform: translateY(-6px); } }
body.con-coach .voz-linea { display: none; }   /* el coach ya habla */
html.ahorro .voz-linea { backdrop-filter: none; }
@media (prefers-reduced-motion: reduce) { .voz-linea, .voz-linea.saliendo { animation: none; } }

/* Los colores de las voces, compartidos por la introducción, el coach, la
   línea y la placa. */
[data-voz="archivo"]    { --voz: #c9a86b; }
[data-voz="pericial"]     { --voz: #7fb2ff; }
[data-voz="internos"]   { --voz: #d2564f; }
[data-voz="instruccion"]     { --voz: #46c39c; }
[data-voz="guardia"]     { --voz: #9a7fd0; }
[data-voz="centralita"] { --voz: #e8b45e; }
[data-voz="fiscalia"]   { --voz: #e07a6f; }

/* Las voces en la placa: siete filas, una marca por técnica. Es la ficha del
   personaje, y el personaje son las voces. */
.voces-ficha { display: grid; gap: 6px; margin-top: 12px; padding-top: 10px; border-top: 1px solid var(--line-soft); }
.voz-fila { display: grid; grid-template-columns: 92px 1fr auto; align-items: center; gap: 8px; }
.voz-fila .voz-quien { font-size: 9.5px; letter-spacing: .14em; }
.voz-marcas { display: flex; gap: 3px; }
.voz-marcas i { display: block; width: 9px; height: 9px; border-radius: 2px; border: 1px solid var(--line); }
.voz-marcas i.on { background: var(--voz, var(--amber)); border-color: transparent; box-shadow: 0 0 6px color-mix(in srgb, var(--voz, var(--amber)) 45%, transparent); }
.voz-fila em { font-style: normal; font-family: var(--mono); font-size: 9.5px; letter-spacing: .08em; color: var(--ink-faint); }
.voz-fila.afilada em { color: var(--voz); }

/* ---------- ajustes de narración ---------- */
.ajustes-voz {
  background: var(--bg-2); border: 1px solid var(--line-soft); border-radius: var(--r);
  padding: 14px 16px; margin-bottom: 18px; display: grid; gap: 10px;
}
.ajuste { display: flex; align-items: center; gap: 12px; font-size: 13px; color: var(--ink-dim); }
.ajuste > span { flex: 0 0 84px; }
.ajuste select, .ajuste input[type="range"] { flex: 1; min-width: 0; }
.ajuste select {
  background: var(--panel); color: var(--ink); border: 1px solid var(--line);
  border-radius: 7px; padding: 7px 9px; font-size: 12.5px;
}
.ajuste input[type="range"] { accent-color: var(--accent); }
.ajustes-nota { color: var(--ink-faint); font-size: 12.5px; line-height: 1.55; margin: 0; }


/* ---------- consumo: que el teléfono no se caliente ----------
 *
 * Tres cosas cuestan de verdad en un móvil y las tres estaban aquí:
 *
 * 1. **Animar dentro de un filtro SVG.** Ya arreglado en `escenas.js`: el
 *    motivo y la luna salieron de los grupos filtrados. Un `feTurbulence`
 *    recalculándose sesenta veces por segundo por tarjeta es todo el
 *    presupuesto térmico del aparato.
 * 2. **Componer lo que no se ve.** El archivo pinta veintidós tarjetas. Ya
 *    estaban congeladas, pero el navegador seguía rasterizando las veintidós
 *    escenas —con sus filtros— aunque en pantalla cupieran tres.
 * 3. **Seguir animando con la app en segundo plano.** Nada lo impedía.
 */

/* Con la app en segundo plano no se anima nada. `paused` en vez de `none`
   para que al volver siga donde estaba y no dé un salto. */
html.pausa *,
html.pausa *::before,
html.pausa *::after { animation-play-state: paused !important; }

/* Ahorro de batería. Se enciende solo en aparatos con poca memoria o pocos
   núcleos, y a mano desde la barra. Quita lo caro y deja el juego intacto:
   el óleo, el grano y la lluvia son atmósfera, no información. */
html.ahorro svg *,
html.ahorro .plano,
html.ahorro .rain { animation: none !important; }
html.ahorro [filter] { filter: none !important; }
html.ahorro .grain { display: none; }
html.ahorro .rain { opacity: .07; }
html.ahorro .cel-papeles { display: none; }
html.ahorro .topbar,
html.ahorro .modal,
html.ahorro .hoja { backdrop-filter: none; }


/* ---------- válvulas anti-atasco ---------- */

/* Un hecho revelado se queda escrito y bloqueado: se pidió ver una pieza, no
   volver a teclearla. */
.field.revelado input { color: var(--ink-dim); border-style: dashed; }
.field.revelado label::after { content: " · revelado"; color: var(--amber-dim); }

/* El empujón de ARCHIVO cuando el jugador lleva consultas sin abrir una tabla
   que importa. Se pinta como una voz interior, no como un aviso del sistema. */
.olfato {
  margin-top: 10px; padding: 10px 14px; border-left: 3px solid var(--amber-dim);
  background: rgba(216,162,74,.06); border-radius: 0 8px 8px 0; font-size: 13.5px;
}
.olfato b { font-family: var(--mono); font-size: 10.5px; letter-spacing: .14em; color: var(--amber); margin-right: 8px; }
.olfato code { font-family: var(--mono); }


/* ---------- pantalla de título ----------
 *
 * Lo primero que se ve. Una portada pintada a pantalla completa con tres
 * capas que se mueven poco y despacio —la escena con paralaje al ratón, la
 * niebla derivando, la viñeta quieta— y el nombre del juego con tipografía
 * propia. Sin barra, sin chrome: el mundo antes que la interfaz.
 */
.titulo {
  position: fixed; inset: 0; z-index: 60; overflow: hidden; background: var(--bg);
  display: grid; place-items: end start; cursor: pointer; user-select: none;
  --px: 0; --py: 0;
}
.titulo-escena {
  position: absolute; inset: -4%; will-change: transform;
  transform: translate(calc(var(--px) * -12px), calc(var(--py) * -8px)) scale(1.04);
  transition: transform .6s cubic-bezier(.2,.8,.2,1);
}
.titulo-escena svg { width: 100%; height: 100%; display: block; }
.titulo-niebla {
  position: absolute; inset: 0; pointer-events: none;
  background:
    radial-gradient(60% 40% at 30% 78%, rgba(30,42,53,.55), transparent 70%),
    radial-gradient(50% 30% at 75% 70%, rgba(30,42,53,.35), transparent 70%);
  animation: niebla-deriva 26s ease-in-out infinite alternate;
  transform: translate(calc(var(--px) * -22px), 0);
}
@keyframes niebla-deriva { from { background-position: 0 0, 0 0; } to { background-position: 60px 0, -80px 0; } }
.titulo-vineta {
  position: absolute; inset: 0; pointer-events: none;
  background:
    linear-gradient(to top, rgba(10,12,15,.92) 0%, rgba(10,12,15,.55) 30%, transparent 60%),
    radial-gradient(90% 70% at 50% 40%, transparent 55%, rgba(10,12,15,.7) 100%);
}
.titulo-bloque {
  position: relative; z-index: 2; padding: 0 clamp(20px, 6vw, 72px) clamp(36px, 8vh, 84px);
  max-width: 720px; animation: ui-entrar .9s .2s cubic-bezier(.2,.8,.2,1) both;
}
.titulo-sobre {
  font-family: var(--mono); font-size: 11px; letter-spacing: .22em; text-transform: uppercase;
  color: var(--amber); margin: 0 0 14px; opacity: .9;
}
.titulo-nombre {
  font-family: var(--serif); font-weight: 500; line-height: .92; margin: 0;
  font-size: clamp(56px, 11vw, 132px); letter-spacing: -.03em; color: var(--paper);
  text-shadow: 0 2px 0 rgba(0,0,0,.35), 0 18px 50px rgba(0,0,0,.6);
}
.titulo-nombre span { display: block; font-size: .42em; letter-spacing: .18em; text-transform: uppercase; font-weight: 400; color: var(--ink-dim); margin-bottom: .1em; }
.titulo-nombre em { font-style: italic; color: var(--paper); }
.titulo-trazo { width: min(300px, 60vw); height: 14px; color: var(--amber); margin: 6px 0 14px; display: block; }
.titulo-lema { font-family: var(--serif); font-style: italic; font-size: clamp(15px, 2vw, 19px); color: var(--ink-dim); margin: 0 0 26px; max-width: 46ch; }
.titulo-menu { display: flex; flex-wrap: wrap; gap: 10px; }
.titulo-btn {
  font: inherit; font-size: 14px; letter-spacing: .04em; cursor: pointer;
  padding: 12px 20px; border-radius: 4px; color: var(--ink);
  background: rgba(21,26,33,.72); border: 1px solid var(--line);
  backdrop-filter: blur(6px); transition: border-color .2s, background .2s, transform .2s;
}
.titulo-btn:hover { border-color: var(--amber-dim); background: rgba(27,33,42,.9); transform: translateY(-1px); }
/* El foco tenía `outline: none` y se confiaba al cambio de borde; en el botón
   primario el borde ya es ámbar, así que con el teclado no pasaba nada
   visible en el botón más importante del juego. El anillo va en color papel
   para que se vea igual sobre el ámbar que sobre el panel oscuro. */
.titulo-btn:focus-visible {
  border-color: var(--amber-dim); transform: translateY(-1px);
  outline: 2px solid var(--paper); outline-offset: 3px;
}
.titulo-btn.primario { background: var(--amber); color: #17130a; border-color: var(--amber); font-weight: 600; }
.titulo-btn.primario:hover { background: #e6b45e; }
.titulo-btn.primario small { display: block; font-weight: 400; font-size: 11.5px; opacity: .8; letter-spacing: .02em; }
.titulo-pie {
  position: absolute; right: clamp(16px, 4vw, 40px); bottom: clamp(14px, 3vh, 28px); z-index: 2; margin: 0;
  font-family: var(--mono); font-size: 10.5px; letter-spacing: .18em; text-transform: uppercase; color: var(--ink-faint);
  animation: ui-latir 3.2s ease-in-out infinite;
}
.titulo .brand-oculta { display: none; }
body.en-titulo .topbar, body.en-titulo .rain { display: none; }

/* ---------- el archivo: caso activo, placa y carpetas ---------- */
.cabecera-archivo {
  display: grid; grid-template-columns: minmax(0, 1.6fr) minmax(260px, .9fr); gap: 18px;
  margin: 8px 0 40px; align-items: stretch; animation: ui-entrar .5s ease-out both;
}
@media (max-width: 860px) { .cabecera-archivo { grid-template-columns: 1fr; } }

/* El caso activo: la escena pintada en grande y el botón de seguir. Es lo
   único que un jugador que vuelve necesita ver antes de decidir nada. */
.activo {
  position: relative; min-height: 260px; border-radius: var(--r); overflow: hidden;
  border: 1px solid var(--line); background: var(--panel); cursor: pointer;
}
.activo .activo-escena { position: absolute; inset: 0; }
.activo .activo-escena svg { width: 100%; height: 100%; display: block; }
.activo .activo-sombra { position: absolute; inset: 0; background: linear-gradient(to top, rgba(10,12,15,.95) 0%, rgba(10,12,15,.6) 45%, rgba(10,12,15,.05) 100%); }
.activo .activo-texto { position: relative; z-index: 1; padding: 28px 26px 24px; display: flex; flex-direction: column; justify-content: flex-end; min-height: 260px; }
.activo-sobre { font-family: var(--mono); font-size: 10.5px; letter-spacing: .2em; text-transform: uppercase; color: var(--amber); margin: 0 0 8px; }
.activo h2 { font-family: var(--serif); font-weight: 500; font-size: clamp(24px, 3.4vw, 36px); margin: 0 0 6px; text-wrap: balance; }
.activo .activo-lema { color: var(--ink-dim); font-style: italic; font-family: var(--serif); margin: 0 0 16px; font-size: 15px; }
.activo .activo-pie { display: flex; align-items: center; gap: 14px; flex-wrap: wrap; }
.activo .activo-pie .meta { font-family: var(--mono); font-size: 11px; color: var(--ink-faint); letter-spacing: .06em; }
.activo:hover .activo-escena { transform: scale(1.02); }
.activo .activo-escena { transition: transform .6s ease; }
/* El motivo del caso queda detrás del texto: se atenúa para que sea fondo y no
   compita con el título. */
.activo .c-motivo { opacity: .7; }

/* La placa: el rango y los números, como la ficha de un policía. */
.ficha {
  border: 1px solid var(--line); border-radius: var(--r); background: var(--panel);
  padding: 18px 20px; display: flex; flex-direction: column; gap: 14px;
  background-image: repeating-linear-gradient(0deg, transparent 0 22px, rgba(255,255,255,.015) 22px 23px);
}
.ficha-sobre { font-family: var(--mono); font-size: 10.5px; letter-spacing: .2em; text-transform: uppercase; color: var(--ink-faint); margin: 0; }
.ficha .rango { margin: 0; }
.ficha-stats { display: grid; grid-template-columns: 1fr 1fr; gap: 10px 16px; margin-top: auto; }
.ficha-stats .hero-stat b { font-size: 20px; }

html.ahorro .titulo-niebla, html.ahorro .titulo-pie { animation: none; }
html.ahorro .titulo-escena, html.ahorro .titulo-niebla { transform: none; transition: none; }
@media (prefers-reduced-motion: reduce) {
  .titulo-niebla, .titulo-pie, .titulo-bloque, .cabecera-archivo { animation: none !important; }
  .titulo-escena, .titulo-niebla { transform: none !important; }
}


/* ---------- el coach del tutorial ----------
 * Una voz interior, no un cuadro de ayuda: mismo color por voz que en la
 * introducción, abajo, sin tapar la consola. */
.coach {
  position: fixed; left: 12px; right: 12px; bottom: calc(66px + var(--safe-b)); z-index: 300;
  max-width: 520px; margin: 0 auto;
  background: rgba(21,26,33,.94); border: 1px solid var(--line); border-left: 3px solid var(--voz, var(--amber));
  border-radius: 10px; padding: 12px 14px 12px 16px; box-shadow: 0 16px 40px rgba(0,0,0,.55);
  backdrop-filter: blur(8px);
}
@media (min-width: 900px) { .coach { left: auto; right: 24px; bottom: 24px; max-width: 420px; } }
.coach.entra { animation: ui-entrar .35s cubic-bezier(.2,.8,.3,1) both; }
.coach-cab { display: flex; align-items: center; gap: 10px; margin-bottom: 6px; }
.coach-voz { font-family: var(--mono); font-size: 10.5px; letter-spacing: .16em; color: var(--voz, var(--amber)); }
.coach-paso { font-family: var(--mono); font-size: 10px; color: var(--ink-faint); margin-left: auto; }
.coach-cerrar { background: none; border: 0; color: var(--ink-faint); cursor: pointer; font-size: 14px; padding: 2px 4px; }
.coach-cerrar:hover { color: var(--ink); }
.coach-texto { margin: 0 0 10px; font-family: var(--serif); font-size: 15px; line-height: 1.5; color: var(--ink); }
.coach-acciones { display: flex; gap: 8px; flex-wrap: wrap; }
.coach-acciones .btn { padding: 7px 12px; font-size: 12.5px; }
/* Los colores por voz están en «la línea de una voz», compartidos. */
@media (prefers-reduced-motion: reduce) { .coach.entra { animation: none; } }

/* Mientras el coach está en pantalla, el expediente deja sitio debajo. */
body.con-coach .case-grid > .zona:last-child > :last-child, body.con-coach .case-grid [data-tab].active:last-of-type { margin-bottom: 190px; }
@media (min-width: 1181px) { body.con-coach .zona-der { padding-bottom: 240px; } body.con-coach .zona-izq { padding-bottom: 0; } }

/* El foco del tutorial: un recorte de luz. La sombra de 9999px apaga el resto
   de la pantalla; el aro ámbar late para que el ojo vaya solo. No bloquea
   toques: es una indicación, no una jaula. */
.foco-tutorial {
  position: fixed; z-index: 290; pointer-events: none; border-radius: 8px;
  box-shadow: 0 0 0 9999px rgba(6, 8, 11, .74), 0 0 0 3px var(--amber), 0 0 26px rgba(216,162,74,.55);
  transition: left .25s ease, top .25s ease, width .25s ease, height .25s ease;
  animation: foco-latir 1.6s ease-in-out infinite;
}
.foco-tutorial.oculto { display: none; }
@keyframes foco-latir {
  50% { box-shadow: 0 0 0 9999px rgba(6, 8, 11, .74), 0 0 0 5px var(--amber), 0 0 34px rgba(216,162,74,.75); }
}
html.ahorro .foco-tutorial { animation: none; }
@media (prefers-reduced-motion: reduce) { .foco-tutorial { animation: none; transition: none; } }


/* ---------- el puesto de trabajo ----------
 *
 * La vista de un caso tiene tres trabajos y se lee de izquierda a derecha en
 * ese orden: LEER el expediente, CONSULTAR los datos, PROBAR lo que se
 * afirma. Cada columna es uno. En pantalla grande la vista ocupa el alto de la
 * ventana y cada columna se desplaza por su cuenta: la consola crece hasta el
 * borde, el tablero de hechos queda siempre a la vista junto a los
 * resultados —fijar una celda y verla aparecer al lado— y el expediente se
 * lee sin arrastrar consigo todo lo demás. En tablet son dos columnas; en el
 * móvil, pestañas (más arriba).
 */
/* Sólo a partir de tablet: en el móvil mandan las pestañas (más arriba). */
@media (min-width: 861px) {
  /* Las laterales eran fijas —400 y 360— y se las pagaba entera la consola:
     en una ventana de 1280 la columna donde se escribe SQL y se leen los
     resultados se quedaba con 456 px, la más estrecha de las tres, siendo
     donde se pasa el 95 % del tiempo. Con `clamp` las laterales ceden en
     pantallas pequeñas y recuperan su tamaño en las grandes. */
  .case-grid { display: grid; gap: 14px; align-items: start;
    grid-template-columns: minmax(0, clamp(320px, 26vw, 400px)) minmax(0, 1fr) minmax(0, clamp(292px, 23vw, 360px)); }
  .zona { min-width: 0; display: flex; flex-direction: column; gap: 12px; }
}
.zona-rotulo {
  font-family: var(--mono); font-size: 10.5px; letter-spacing: .22em; text-transform: uppercase;
  color: var(--ink-faint); margin: 0 0 -4px 2px;
}
.zona-rotulo::before { content: "// "; color: var(--line); }
.case-grid .hints, .case-grid .notepad, .case-grid .accuse, .case-grid .history, .case-grid .results,
.case-grid .solution, .case-grid .danger-zone, .case-grid .case-nav, .case-grid .statbar, .case-grid .objetivos { margin-top: 0; }

/* Tablet: el expediente y la acusación comparten la columna izquierda. */
@media (min-width: 861px) and (max-width: 1180px) {
  .case-grid { grid-template-columns: minmax(0, 360px) minmax(0, 1fr); }
  .zona-izq { grid-column: 1; grid-row: 1; }
  .zona-der { grid-column: 1; grid-row: 2; }
  .zona-centro { grid-column: 2; grid-row: 1 / span 2; }
}

/* Escritorio: la vista cabe en la ventana y las columnas se desplazan solas. */
@media (min-width: 1181px) {
  body.en-caso { height: 100dvh; overflow: hidden; display: flex; flex-direction: column; }
  body.en-caso .topbar { flex: 0 0 auto; }
  body.en-caso .view-caso {
    flex: 1 1 0; min-height: 0; max-width: 1760px; width: 100%;
    padding: 14px 18px 14px; display: flex; flex-direction: column;
  }
  .view-caso .case-grid { flex: 1 1 0; min-height: 0; align-items: stretch; }
  .zona { min-height: 0; overflow-y: auto; overflow-x: hidden; padding: 2px 6px 2px 2px; scrollbar-width: thin; scrollbar-color: var(--line) transparent; }
  .zona::-webkit-scrollbar { width: 8px; }
  .zona::-webkit-scrollbar-thumb { background: var(--line); border-radius: 8px; }
  /* La consola: el editor arriba, fijo; los resultados se quedan el resto. */
  /* Con barra por si aun así no cabe: un contenedor que se desplaza sin
     poder desplazarse a mano deja el editor fuera de la vista para siempre. */
  .zona-centro { overflow-y: auto; }
  /* El editor cede antes que los resultados: con la barra de atajos abierta
     en una ventana baja, lo que se encoge (y se desplaza) es el editor, y la
     tabla conserva sitio para verse. */
  /* El editor mide lo que mide: nunca se recorta ni se desplaza por dentro
     (en una ventana baja dejaba el botón de ejecutar fuera de la vista). Si
     no cabe todo, se desplaza la columna entera, que sí tiene barra. */
  .zona-centro .editor-wrap { flex: 0 0 auto; }
  .zona-centro .results { flex: 1 1 0; min-height: 320px; display: flex; flex-direction: column; }
  .zona-centro .results > .table-wrap { flex: 1 1 0; min-height: 0; max-height: none; }
  .zona-centro .results > .error, .zona-centro .results > .vacio { flex: 0 0 auto; }
  .zona-centro .history { flex: 0 0 auto; }
  .zona-centro .history[open] { max-height: 40%; overflow: auto; }
  .zona-der .datos { flex: 0 0 auto; }
}

/* El editor con algo de cuerpo en el escritorio: tres o cuatro líneas de
   consulta a la vista sin desplazar. */
@media (min-width: 861px) { .editor .cm-editor { min-height: 132px; } }

/* La consola vacía: un empujón, no un hueco. */
.vacio {
  border: 1px dashed var(--line); border-radius: var(--r); padding: 22px 20px;
  background: linear-gradient(180deg, rgba(255,255,255,.015), transparent);
}
.vacio-titulo { margin: 0 0 4px; font-family: var(--serif); font-size: 17px; color: var(--ink); }
.vacio-texto { margin: 0 0 14px; font-size: 13.5px; color: var(--ink-dim); line-height: 1.55; }
.vacio-chips { display: flex; flex-wrap: wrap; gap: 8px; }
.vacio-chip {
  font-family: var(--mono); font-size: 12px; color: var(--ink-dim);
  background: var(--panel); border: 1px solid var(--line); border-radius: 8px; padding: 8px 12px; cursor: pointer;
  transition: border-color .12s, color .12s;
}
.vacio-chip b { color: var(--amber); font-weight: 600; }
.vacio-chip:hover { border-color: var(--amber-dim); color: var(--ink); }

/* El tablero de hechos: es el sitio al que va todo lo demás, y se nota. */
.accuse {
  background: linear-gradient(180deg, var(--panel-2), var(--panel));
  border: 1px solid var(--line); border-top: 2px solid var(--amber-dim);
  border-radius: var(--r); padding: 16px 16px 14px;
}
.accuse h3 { font-family: var(--serif); font-size: 18px; font-weight: 600; letter-spacing: 0; text-transform: none; color: var(--ink); }
.hechos-cuenta { padding: 3px 9px; border: 1px solid var(--line); border-radius: 999px; white-space: nowrap; }
.hechos-cuenta.ok { border-color: var(--jade); }
#btn-answer { width: 100%; padding: 12px 16px; font-weight: 600; letter-spacing: .02em; }
.accuse .field:last-of-type { margin-bottom: 0; }
.prueba { margin: 12px 0; }
.prueba select { text-overflow: ellipsis; }

/* El estado del caso: cuatro cifras y los tres objetivos, no una línea de log. */
.estado { background: var(--panel); border: 1px solid var(--line-soft); border-radius: var(--r); padding: 12px 14px 10px; }
.statbar { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 8px; margin: 0; }
.statbar .stat {
  display: flex; flex-direction: column-reverse; gap: 2px; min-width: 0;
  font-family: var(--mono); font-size: 9.5px; letter-spacing: .1em; text-transform: uppercase; color: var(--ink-faint);
}
.statbar .stat b { font-size: 15px; letter-spacing: 0; color: var(--ink); font-weight: 600; font-variant-numeric: tabular-nums; }
.estado .objetivos { margin: 10px 0 0; padding-top: 10px; border-top: 1px solid var(--line-soft); }
.objetivos li.ok { color: var(--jade); }
.objetivos li.ok .obj-icono { color: var(--jade); }
.objetivos li.fallado { color: var(--ink-faint); text-decoration: line-through; text-decoration-color: rgba(255,255,255,.18); }

/* Los datos: título y filtro en una línea cuando cabe. */
.datos .schema-head { flex-direction: row; align-items: center; justify-content: space-between; gap: 10px; flex-wrap: wrap; }
/* El marcador del filtro se cortaba a media palabra en la columna estrecha.
   Con esta base, cuando no cabe junto al título baja a su propia línea
   entero, en vez de encogerse hasta recortar el texto. */
.datos .schema-head input { flex: 1 1 100%; min-width: 0; }
.datos #schema-filter { width: auto; flex: 1 1 140px; min-width: 120px; }
.danger-zone .btn { padding: 8px 12px; font-size: 13px; }

/* El botón del otro idioma en la portada: presente, discreto. */
.titulo-idioma { opacity: .8; }


/* ---------- el expediente 88-C ----------
 * La serie hecha tangible: un tablero de corcho en el archivo al que cada
 * caso cerrado aporta una nota. Las notas son fichas mecanografiadas,
 * pinchadas con un giro pequeño; los huecos, fichas en blanco. */
.hilo { margin: 0 0 30px; }
.hilo-cab { display: flex; align-items: baseline; gap: 14px; flex-wrap: wrap; margin-bottom: 12px; }
.hilo-cab h2 { font-family: var(--serif); font-size: 24px; font-weight: 600; margin: 0; letter-spacing: -.01em; }
.hilo-cab .hilo-cuenta { font-family: var(--mono); font-size: 11px; letter-spacing: .14em; text-transform: uppercase; color: var(--amber); }
.hilo-cab .hilo-vacio { font-size: 13.5px; color: var(--ink-faint); font-style: italic; margin: 0; }
.corcho {
  position: relative; display: grid; gap: 10px; padding: 16px;
  grid-template-columns: repeat(auto-fill, minmax(170px, 1fr));
  background:
    radial-gradient(circle at 20% 30%, rgba(255,255,255,.03), transparent 40%),
    linear-gradient(180deg, #2a2016, #211a12);
  border: 1px solid #3a2e21; border-radius: var(--r);
  box-shadow: inset 0 0 40px rgba(0,0,0,.45);
}
.nota {
  position: relative; min-height: 96px; padding: 12px 12px 10px;
  background: var(--paper); color: var(--paper-ink);
  font-family: var(--mono); font-size: 11.5px; line-height: 1.45;
  transform: rotate(var(--giro, 0deg));
  box-shadow: 0 6px 14px rgba(0,0,0,.4);
}
.nota::before {
  content: ""; position: absolute; top: -5px; left: 50%; width: 10px; height: 10px; border-radius: 50%;
  background: radial-gradient(circle at 35% 35%, #e6b866, #8a5a1a); box-shadow: 0 2px 3px rgba(0,0,0,.5);
  transform: translateX(-50%);
}
.nota .nota-num { display: block; font-size: 9.5px; letter-spacing: .16em; color: var(--paper-dim); margin-bottom: 5px; }
/* El texto estaba a 2.6:1. Se atenúa la ficha, no su contenido. */
.nota.vacia { background: rgba(232,226,212,.06); color: #8a8172; box-shadow: none; border: 1px dashed rgba(232,226,212,.2); }
.nota.vacia::before { background: rgba(232,226,212,.15); box-shadow: none; }
.nota.vacia .nota-num { color: #736c60; }
.nota.final { grid-column: 1 / -1; background: #f1e8d3; font-size: 12px; }
@media (max-width: 560px) { .corcho { grid-template-columns: repeat(2, minmax(0, 1fr)); padding: 12px; } .nota { font-size: 11px; } }

/* El 88-C vacío: una tira, no un corcho. Veintiocho marcas finas dicen
   «esto se colecciona» sin gastar dos pantallas en fichas en blanco. */
.hilo.hilo-tira { margin-bottom: 22px; }
.hilo-tira .tira {
  display: flex; gap: 5px; flex-wrap: wrap; align-items: center;
  padding: 12px 14px; border: 1px solid #3a2e21; border-radius: var(--r);
  background: linear-gradient(180deg, #2a2016, #211a12);
  box-shadow: inset 0 0 24px rgba(0,0,0,.45);
}
.hilo-tira .tira i {
  flex: 1 1 18px; height: 16px;
  border: 1px dashed rgba(232,226,212,.20); border-radius: 2px;
  background: rgba(232,226,212,.05);
}

/* El turno de noche antes de la primera técnica: sólo los nombres. */
.turno-tira { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 10px; }
.turno-tira span {
  font-family: var(--mono); font-size: 10.5px; letter-spacing: .12em; text-transform: uppercase;
  padding: 4px 8px; border-radius: 3px;
  color: var(--voz, var(--ink-dim)); border: 1px solid currentColor; opacity: .72;
}


/* La revelación usa la maquinaria de la introducción, con su rótulo. */
.intro.revelacion .intro-num { color: var(--jade); }

/* El aviso de logro: como la línea de una voz, en jade. */
.voz-linea.logro { border-left-color: var(--jade); }
.voz-linea.logro .voz-quien { color: var(--jade); }

/* Insignia de demo en la portada y aviso en el archivo. */
.btn-tienda {
  font-family: var(--mono); font-size: 11px; letter-spacing: .18em; text-transform: uppercase;
  color: var(--bg); background: var(--amber); border: 1px solid var(--amber);
  padding: 7px 14px; border-radius: 3px; text-decoration: none; white-space: nowrap;
  box-shadow: 2px 2px 0 var(--amber-dim); transition: transform .08s ease, box-shadow .08s ease;
}
.btn-tienda:hover { transform: translate(1px, 1px); box-shadow: 1px 1px 0 var(--amber-dim); }
.btn-tienda:active { transform: translate(2px, 2px); box-shadow: none; }
@media (max-width: 720px) { .btn-tienda { font-size: 10px; padding: 6px 9px; letter-spacing: .12em; } }

.demo-sello { font-family: var(--mono); font-size: 10.5px; letter-spacing: .24em; color: var(--amber); border: 1px solid var(--amber-dim); padding: 3px 8px; border-radius: 3px; margin-left: 10px; vertical-align: middle; }
.demo-aviso { margin: 18px 0 0; padding: 14px 16px; border: 1px dashed var(--amber-dim); border-radius: var(--r); color: var(--ink-dim); font-size: 13.5px; }

/* La licencia en Ajustes. */
.ajustes-voz.licencia .ok { color: var(--jade); }
.lic-fila { display: flex; gap: 8px; }
.lic-fila input { flex: 1; min-width: 0; padding: 9px 11px; border-radius: 8px; background: var(--panel); border: 1px solid var(--line); color: var(--ink); font-family: var(--mono); font-size: 12.5px; }
.lic-fila input:focus { outline: none; border-color: var(--amber-dim); }
.ajustes-voz.licencia a.btn { display: inline-block; text-decoration: none; }

/* ---------- consejos de SQL ----------
 *
 * Una tira bajo la barra de atajos, con la voz baja de ARCHIVO: rótulo,
 * una frase y el ejemplo, que se pega en el editor con un toque. */
.consejo {
  display: flex; flex-wrap: wrap; align-items: baseline; gap: 6px 10px;
  padding: 9px 12px 9px 14px; border-top: 1px solid var(--line-soft);
  border-left: 3px solid var(--amber-dim); background: rgba(216,162,74,.06);
  font-size: 13px; line-height: 1.5; color: var(--ink-dim); animation: aparece .25s ease;
}
.consejo b { font-family: var(--mono); font-size: 10.5px; letter-spacing: .14em; color: var(--amber); }
.consejo-texto { flex: 1 1 28ch; color: var(--ink); }
.consejo-ej {
  flex: 1 1 100%; text-align: left; cursor: pointer; background: var(--panel-2);
  border: 1px dashed var(--line); border-radius: 6px; padding: 5px 9px; color: var(--ink-dim); font-size: 12px;
}
.consejo-ej code { font-family: var(--mono); white-space: pre-wrap; background: none; padding: 0; }
.consejo-ej:hover { border-color: var(--amber-dim); color: var(--ink); }
.consejo-x { margin-left: auto; background: none; border: 0; color: var(--ink-faint); cursor: pointer; font-size: 13px; padding: 0 2px; }
.consejo-x:hover { color: var(--ink); }

/* ---------- caso cerrado: el siguiente paso, bajo el veredicto ---------- */
.caso-cerrado {
  margin-top: 14px; padding-top: 14px; border-top: 1px dashed var(--line);
  display: flex; flex-direction: column; gap: 8px; animation: aparece .35s ease;
}
/* Los dos eventos que costaban algo y no se veían.
 *
 * Una pista baja el rango al resolver: aparecía de golpe, igual que cualquier
 * otro párrafo, y no se leía como un precio pagado. Y la evidencia fijada
 * aterriza en el tablero, que en pantalla ancha está en otra columna: sin un
 * destello no se ve de dónde salió lo que acaba de llegar.
 *
 * Ninguna de las dos mueve nada de sitio ni retrasa al jugador: se despliegan
 * donde ya estaban, en menos de un segundo, y desaparecen. */
@keyframes pista-abre {
  from { opacity: 0; transform: translateY(-6px); clip-path: inset(0 0 100% 0); }
  to   { opacity: 1; transform: none;             clip-path: inset(0 0 0 0); }
}
.hint.nueva { animation: pista-abre .42s cubic-bezier(.2, .9, .3, 1) both; }

@keyframes evid-fijar {
  0%   { box-shadow: 0 0 0 2px var(--amber); }
  70%  { box-shadow: 0 0 0 2px var(--amber); }
  100% { box-shadow: 0 0 0 0 transparent; }
}
.evid.nueva { animation: evid-fijar .9s ease-out both; }

/* Ni con el ahorro de batería ni con el sistema pidiendo menos movimiento. */
html.ahorro .hint.nueva, html.ahorro .evid.nueva { animation: none; }
@media (prefers-reduced-motion: reduce) {
  .hint.nueva, .evid.nueva { animation: none; }
}

/* El expediente del jugador, dentro del manual. Una lista sobria: la técnica,
   el veredicto y las cifras que lo sostienen. El color sólo marca el estado,
   y «en prueba» va en gris a propósito — no es ni bueno ni malo, es que aún
   no se sabe. */
/* Las pestañas del modal. Tres pisos de información que antes venían
   apilados: el manual, el expediente y los ajustes. */
.modal-tabs { display: flex; gap: 2px; margin: 0 0 18px; border-bottom: 1px solid var(--line); }
.modal-tabs button {
  appearance: none; background: none; border: 0; border-bottom: 2px solid transparent;
  padding: 9px 14px; margin-bottom: -1px; cursor: pointer;
  font-family: var(--mono); font-size: 11.5px; letter-spacing: .16em; text-transform: uppercase;
  color: var(--ink-faint);
}
.modal-tabs button:hover { color: var(--ink-dim); }
.modal-tabs button[aria-selected="true"] { color: var(--amber); border-bottom-color: var(--amber); }
.modal-tabs button:focus-visible { outline: 2px solid var(--amber); outline-offset: 2px; }
.modal-panel[hidden] { display: none !important; }

.expediente { margin: 0 0 22px; padding: 16px 18px; border: 1px solid var(--line); border-radius: var(--r); background: var(--panel); }
.expediente h3 { margin: 0 0 6px; font-family: var(--display); font-size: 20px; letter-spacing: .01em; }
.expediente-nota { margin: 0 0 14px; font-size: 13px; color: var(--ink-faint); max-width: 62ch; }
/* ---------- logros ---------- */
.logros-cuenta { margin: 0 0 12px; font-family: var(--mono); font-size: 11px; letter-spacing: .14em;
  text-transform: uppercase; color: var(--amber); }
.logros-lista { display: grid; gap: 2px; }
.logro-fila {
  display: grid; grid-template-columns: 18px minmax(0, 13rem) minmax(0, 1fr); align-items: baseline;
  gap: 4px 12px; padding: 9px 10px; border-radius: var(--r); border-left: 2px solid var(--line);
}
.logro-fila.ganado { border-left-color: var(--amber); background: rgba(226,177,90,.05); }
.logro-marca { color: var(--ink-faint); font-size: 11px; }
.logro-fila.ganado .logro-marca { color: var(--amber); }
.logro-nombre { font-family: var(--serif); font-size: 15px; color: var(--ink-dim); }
.logro-fila.ganado .logro-nombre { color: var(--ink); font-weight: 600; }
.logro-nota { font-size: 13px; color: var(--ink-faint); line-height: 1.45; }
@media (max-width: 560px) {
  .logro-fila { grid-template-columns: 18px minmax(0, 1fr); }
  .logro-nota { grid-column: 2; }
}

.expediente-vacio { margin: 0; padding: 14px 16px; font-family: var(--serif); font-style: italic;
  font-size: 14px; color: var(--ink-dim); border-left: 2px solid var(--line); background: var(--panel-2); border-radius: 0 var(--r) var(--r) 0; }
.expediente-lista { list-style: none; margin: 0; padding: 0; display: grid; gap: 6px; }
.expediente-lista li { display: grid; grid-template-columns: 1fr auto auto; gap: 12px; align-items: baseline;
  padding: 6px 0; border-bottom: 1px solid var(--line-soft); }
.expediente-lista li:last-child { border-bottom: 0; }
.exp-tecnica { font-family: var(--mono); font-size: 12.5px; color: var(--ink); }
.exp-veredicto { font-family: var(--mono); font-size: 11px; letter-spacing: .14em; text-transform: uppercase; }
.exp-cifras { font-family: var(--mono); font-size: 11.5px; color: var(--ink-faint); font-variant-numeric: tabular-nums; }
.exp-firme    .exp-veredicto { color: var(--jade); }
.exp-flojo    .exp-veredicto { color: var(--red-claro); }
.exp-mezcla   .exp-veredicto { color: var(--amber); }
.exp-oxidado  .exp-veredicto { color: var(--violet); }
.exp-en-prueba .exp-veredicto { color: var(--ink-faint); }

.cerrado-marca {
  margin: 2px 0 14px; font-family: var(--mono); font-size: 12px; letter-spacing: .08em;
  color: var(--ink-dim); font-variant-numeric: tabular-nums;
}

.cerrado-rotulo { margin: 0 0 2px; font-family: var(--mono); font-size: 10.5px; letter-spacing: .16em; text-transform: uppercase; color: var(--jade); }
.caso-cerrado .btn { display: block; text-decoration: none; text-align: center; }
.caso-cerrado .cerrado-siguiente { display: flex; flex-direction: column; align-items: center; gap: 3px; padding: 11px 14px; }
.cerrado-siguiente span { font-family: var(--mono); font-size: 10.5px; letter-spacing: .14em; text-transform: uppercase; opacity: .75; }
.cerrado-siguiente b { font-family: var(--serif); font-size: 15px; font-weight: 500; }
.cerrado-fin { margin: 0; font-size: 13px; color: var(--ink-faint); font-style: italic; }

/* ---------- réplicas del coach y acciones de una voz ---------- */
.coach-replica {
  margin: 10px 0 2px; padding: 8px 0 0; border-top: 1px dashed var(--line);
  color: var(--ink);
}
.coach-replica .coach-voz { display: block; margin-bottom: 3px; }
.coach-replica p { margin: 0; font-family: var(--serif); font-size: 14px; line-height: 1.45; color: var(--ink); }
.coach-replica.entra { animation: aparece .3s ease; }
.voz-acciones { display: flex; gap: 8px; margin-top: 10px; }
.voz-acciones .btn { padding: 7px 12px; font-size: 13px; }
.cerrado-teaser { margin: 0; font-family: var(--serif); font-style: italic; font-size: 13.5px; line-height: 1.45; color: var(--ink-dim); }

/* ---------- pestañas, no barras ----------
 *
 * Las voces, los consejos y las pistas llevaban una barra de color a la
 * izquierda. Es el rasgo más reconocible de las interfaces hechas en serie;
 * aquí todo son carpetas, y una carpeta se distingue por su pestaña. La voz
 * va en una pestaña que asoma por el borde superior, con su color de fondo y
 * tinta oscura, como el rótulo de un archivador. */
.coach, .voz-linea {
  border-left: 1px solid var(--line); border-radius: 4px 10px 10px 10px;
  padding-left: 14px; padding-top: 16px; overflow: visible;
}
.coach-cab, .voz-cab { position: static; }
.coach-voz, .voz-linea .voz-quien {
  position: absolute; top: -11px; left: 12px; z-index: 1;
  background: var(--voz, var(--amber)); color: #0c0e12;
  padding: 4px 9px 3px; border-radius: 3px 3px 0 0; font-weight: 700; letter-spacing: .18em;
  box-shadow: 0 -2px 0 rgba(0,0,0,.25) inset;
}
.coach-replica .coach-voz { position: static; display: inline-block; margin-bottom: 4px; padding: 2px 7px 1px; border-radius: 3px; font-size: 9.5px; }
.voz-linea.logro { border-left-color: var(--line); --voz: var(--jade); }
.consejo, .olfato, .error .fix.archivo, .solution-body blockquote {
  border-left: 0; border-radius: 8px; background: rgba(255,255,255,.025);
  border: 1px solid var(--line-soft); padding-left: 14px;
}
.consejo { border-radius: 0; border-width: 1px 0 0; }
.consejo b, .olfato b, .error .fix.archivo b {
  background: var(--amber); color: #0c0e12; padding: 2px 7px 1px; border-radius: 3px;
  font-weight: 700; letter-spacing: .16em; font-size: 9.5px;
}
.hint { border-left: 1px solid var(--line); border-radius: var(--r); border-top: 3px solid var(--accent); }
.patron { border-left: 1px solid var(--line-soft); border-top: 3px solid var(--accent); }
.patron.cerrado { border-top-color: var(--line); border-left-color: var(--line-soft); }
.intro-viñeta.con-voz { border-left: 0; padding-left: 0; }
.intro-viñeta.con-voz .v-nombre {
  background: var(--voz, var(--amber)); color: #0c0e12; padding: 3px 9px 2px; border-radius: 3px;
  display: inline-block; margin-bottom: 8px; letter-spacing: .18em; font-weight: 700;
}

/* ---------- el expediente del día ---------- */
.diario { margin: 18px 0 6px; }
.diario-carpeta {
  position: relative; width: 100%; text-align: left; cursor: pointer;
  display: grid; grid-template-columns: 1fr auto; gap: 14px 22px; align-items: center;
  padding: 26px 18px 16px 18px; border-radius: 4px 10px 10px 10px;
  background: linear-gradient(180deg, rgba(216,162,74,.10), rgba(216,162,74,.03)), var(--panel);
  border: 1px solid var(--amber-dim); color: var(--ink);
  transition: transform .12s, border-color .12s;
}
.diario-carpeta:hover { transform: translateY(-1px); border-color: var(--amber); }
.diario-carpeta .pestana { color: var(--amber); background: var(--panel); border-color: var(--amber-dim); }
.diario-carpeta.estado-resuelto { border-color: var(--jade); }
.diario-carpeta.estado-resuelto .pestana { color: var(--jade); border-color: var(--jade); }
.diario-texto h3 { font-family: var(--serif); font-size: 19px; font-weight: 600; margin: 4px 0 2px; }
.diario-texto .lema { margin: 0 0 6px; font-family: var(--serif); font-style: italic; color: var(--ink-dim); font-size: 14px; }
.diario-nota { margin: 0; font-size: 12.5px; color: var(--ink-faint); line-height: 1.5; max-width: 60ch; }
.diario-lado { display: flex; flex-direction: column; align-items: flex-end; gap: 4px; }
.diario-racha { font-family: var(--mono); font-size: 12px; letter-spacing: .08em; color: var(--amber); }
.diario-total { font-family: var(--mono); font-size: 10.5px; color: var(--ink-faint); margin-bottom: 6px; }
.diario-lado .btn { pointer-events: none; }
@media (max-width: 640px) {
  .diario-carpeta { grid-template-columns: 1fr; }
  .diario-lado { flex-direction: row; align-items: center; flex-wrap: wrap; justify-content: space-between; }
}

/* ---------- identidad: cartel, periódico, máquina de escribir ----------
 *
 * Titulares condensados en mayúsculas (cartel de comisaría), cuerpo de
 * periódico, rótulos y datos a máquina. Bordes rectos, grano de papel sobre
 * todo, botones con sombra dura de imprenta y nada de cristal esmerilado. */
.brand-text strong { font-family: var(--display); font-weight: 700; font-size: 21px; letter-spacing: .03em; text-transform: uppercase; }
.activo h2, .cajon h2, .cel-caja h2, .modal-head h2, .hilo-cab h2, .diario-texto h3, .archivo-cerrado h2 {
  font-family: var(--display); font-weight: 800; text-transform: uppercase; letter-spacing: .015em; line-height: .96; text-wrap: balance;
}
.activo h2 { font-size: clamp(36px, 4.8vw, 58px); font-weight: 900; }
.cajon h2 { font-size: 30px; }
.cel-caja h2 { font-size: 34px; }
.diario-texto h3 { font-size: 26px; }
.titulo-nombre { font-family: var(--display); font-weight: 900; text-transform: uppercase; letter-spacing: 0; line-height: .86; font-size: clamp(66px, 13.5vw, 156px); }
.titulo-nombre em { font-style: normal; color: var(--amber); }
.titulo-nombre span { font-family: var(--mono); font-weight: 700; letter-spacing: .12em; font-size: .17em; }
.cel-sello-texto { font-family: var(--display); font-weight: 900; letter-spacing: .04em; }
.dossier h2 { font-family: var(--serif); font-weight: 600; font-size: 27px; letter-spacing: -.005em; }
.carpeta h3 { font-family: var(--serif); font-weight: 600; }

/* Rótulos a máquina: menos aire entre letras que un tablero de mandos. */
.zona-rotulo, .ficha-sobre, .pestana, .sello, .coach-voz, .voz-quien, .voz-nombre, .cerrado-rotulo, .solution h3, .hint h4,
.hechos-cuenta, .results-bar, .run-meta, .coach-paso, .voz-sobre, .cajon-num, .activo-sobre, .hero-stat span, .stat, .consejo b, .olfato b, .error .fix.archivo b,
.cerrado-siguiente span, .diario-racha, .diario-total, .intro-num, .cel-etiqueta, .estado-sello, .nav-locked, .case-nav {
  letter-spacing: .07em;
}
.pestana, .sello { font-weight: 700; }

/* Botones: etiqueta a máquina, sombra dura. */
.btn { font-family: var(--mono); font-weight: 700; text-transform: uppercase; letter-spacing: .05em; font-size: 12px; border-radius: 3px; }
.btn-primary { background: var(--amber); color: #16110a; border: 1px solid #0b0906; box-shadow: 2px 2px 0 #060504; }
/* Naranja cableado: en las temporadas 2 y 3 `--amber` es jade o violeta, y
   el botón más pulsado del juego parpadeaba a naranja al pasar el ratón. */
.btn-primary:hover { filter: none; background: #eebd66; }
@supports (background: color-mix(in srgb, red 50%, white)) {
  .btn-primary:hover { background: color-mix(in srgb, var(--amber) 86%, #fff); }
}
.btn-primary:active { transform: translate(1px, 1px); box-shadow: 1px 1px 0 #060504; }
.btn-ghost { border: 1px solid var(--line); background: transparent; }
.btn-ghost:hover { border-color: var(--amber-dim); background: rgba(226,177,90,.06); }
@supports (background: color-mix(in srgb, red 50%, white)) {
  .btn-ghost:hover { background: color-mix(in srgb, var(--amber) 8%, transparent); }
}
.btn-primary:disabled, .btn-primary[disabled] { box-shadow: none; opacity: .45; }

/* Sin cristal: los paneles flotantes son opacos, como una ficha sobre otra. */
.coach, .voz-linea, .tabbar, .topbar, .consejo, .modal, .toast { backdrop-filter: none; -webkit-backdrop-filter: none; }
.coach, .voz-linea { background: #1a1713; box-shadow: 4px 4px 0 #070605, 0 18px 40px rgba(0,0,0,.5); }
.accuse, .hint, .solution, .patron, .ajustes-voz, .diario-carpeta, .cel-caja { border-radius: var(--r); }

/* La consola escribe a máquina. */
.editor .cm-scroller, .editor .cm-content { font-family: var(--mono) !important; font-size: 14px; line-height: 1.5; }
.results table { font-family: var(--mono); font-size: 13px; }

/* Grano de papel sobre todo, muy leve. */
body::after {
  content: ""; position: fixed; inset: 0; pointer-events: none; z-index: 2000; opacity: .07;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='180' height='180'%3E%3Cfilter id='g'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.85' numOctaves='2' stitchTiles='stitch'/%3E%3CfeColorMatrix values='0 0 0 0 1 0 0 0 0 1 0 0 0 0 1 0 0 0 .9 0'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23g)'/%3E%3C/svg%3E");
  background-size: 180px 180px; mix-blend-mode: overlay;
}
html.ahorro body::after { display: none; }

/* ---------- la placa: el turno de noche como mapa de técnicas ---------- */
.turno-nota { margin: 4px 0 10px; font-size: 12.5px; line-height: 1.5; color: var(--ink-dim); }
.voces-ficha { gap: 9px; }
.voz-fila { display: block; }
.voz-cab-fila { display: flex; justify-content: space-between; align-items: baseline; gap: 8px; }
.voz-nombre { font-family: var(--mono); font-size: 10.5px; font-weight: 700; color: var(--voz, var(--amber)); }
.voz-fila em { font-style: normal; font-family: var(--mono); font-size: 10px; letter-spacing: .04em; color: var(--ink-faint); text-align: right; }
.voz-fila.afilada em { color: var(--voz); }
.voz-tecnicas { display: flex; flex-wrap: wrap; gap: 4px; margin-top: 4px; }
.voz-tecnicas span {
  font-family: var(--mono); font-size: 10px; padding: 1px 6px; border-radius: 2px;
  border: 1px dashed var(--line); color: var(--ink-faint);
}
.voz-tecnicas span.on { border-style: solid; border-color: var(--voz); color: var(--voz); background: color-mix(in srgb, var(--voz) 14%, transparent); }

/* ---------- escala de lectura ----------
 *
 * En un portátil de 13 pulgadas los rótulos de 10 px y el cuerpo de 14 se
 * leen con esfuerzo, y la máquina de escribir tiene la x baja: todo sube un
 * punto o dos. El móvil sube menos: allí el sitio manda. */
.brand-text span { font-size: 12px; }
/* `.accuse h3` está fuera de esta lista a propósito: 600 líneas antes se
   declara como título serif de 18 px y esta capa lo devolvía a 12, más
   pequeño que las etiquetas del propio panel que encabeza. */
.zona-rotulo, .ficha-sobre, .cerrado-rotulo, .solution h3, .hint h4, .activo-sobre, .cajon-num, .intro-num, .cel-etiqueta, .hechos-cuenta { font-size: 12px; }
.pestana, .sello { font-size: 11.5px; }
.coach-voz, .voz-linea .voz-quien { font-size: 11px; }
.coach-texto, .voz-texto { font-size: 16.5px; }
.coach-replica p { font-size: 15.5px; }
.coach-acciones .btn, .voz-acciones .btn { font-size: 12.5px; }
.turno-nota { font-size: 14px; }
.voz-nombre { font-size: 12px; }
.voz-fila em { font-size: 11.5px; }
.voz-tecnicas span { font-size: 11.5px; padding: 2px 7px; }
.hero-stat b { font-size: 24px; }
.hero-stat span { font-size: 12px; }
.rango-cab strong { font-size: 24px; }
.rango-cab span { font-size: 14px; }
.tokenbar button { font-size: 12.5px; height: 29px; padding: 0 11px; }
.tokenbar { max-height: calc(8px + 29px * 2 + 6px + 8px); }
.btn { font-size: 13px; }
.btn-quiet { font-size: 12.5px; }
.editor .cm-scroller, .editor .cm-content { font-size: 15px; }
.results table { font-size: 14px; }
.results-bar, .run-meta, .history summary, .stat, .case-nav { font-size: 12.5px; }
.results-empty { font-size: 15px; }
.dossier h2 { font-size: 29px; }
.dossier-tagline { font-size: 16.5px; }
.dossier-body { font-size: 16.5px; }
.objective p { font-size: 17px; }
.hint-body { font-size: 15.5px; }
.solution-body { font-size: 15.5px; }
.epilogue { font-size: 15.5px; }
.field label { font-size: 13.5px; }
.field input { font-size: 15.5px; }
.prueba-nota { font-size: 13.5px; }
.verdict { font-size: 15px; }
.consejo { font-size: 14px; }
.consejo-ej { font-size: 13px; }
.olfato { font-size: 14.5px; }
.error pre { font-size: 13.5px; }
.error strong { font-size: 14px; }
.error .fix.archivo span, .error .fix { font-size: 14px; }
.evid code { font-size: 14px; }
.evid .de { font-size: 11.5px; }
.evid .usos button { font-size: 12px; }
.col .cname { font-size: 13.5px; }
.col .ctype { font-size: 11.5px; }
.col .ccomment { font-size: 12.5px; }
.carpeta h3 { font-size: 18px; }
.carpeta .lema { font-size: 14px; }
.chip { font-size: 11.5px; }
.diario-nota { font-size: 14px; }
.diario-racha { font-size: 13px; }
.diario-total { font-size: 12px; }
.cerrado-teaser, .cerrado-fin { font-size: 14.5px; }
.cerrado-siguiente b { font-size: 17px; }
.ajustes-nota { font-size: 13.5px; }
.ajuste { font-size: 14px; }
.vacio-chip { font-size: 13px; }
@media (max-width: 860px) {
  .tokenbar button { font-size: 12px; height: 28px; }
  .tokenbar { max-height: calc(8px + 28px * 2 + 6px + 8px); }
  .dossier-body { font-size: 16px; }
  .editor .cm-scroller, .editor .cm-content { font-size: 14.5px; }
}

/* ---------- consecuencias, progreso y ajustes nuevos ---------- */
.consecuencia { margin: 12px 0 14px; padding: 10px 14px; border: 1px solid var(--line-soft); border-radius: 6px; font-family: var(--serif); font-size: 15px; line-height: 1.5; color: var(--ink-dim); }
.consecuencia b { font-family: var(--mono); font-size: 9.5px; letter-spacing: .16em; background: #c9a227; color: #0c0e12; padding: 2px 7px 1px; border-radius: 3px; margin-right: 8px; font-weight: 700; }
.ajuste-progreso { align-items: flex-start; }
.ajuste-botones { display: flex; gap: 8px; flex-wrap: wrap; }
#prog-pegar { display: grid; gap: 8px; margin: 6px 0 4px; }
#prog-texto { width: 100%; font-family: var(--mono); font-size: 12px; background: var(--bg); color: var(--ink); border: 1px solid var(--line); border-radius: 6px; padding: 8px; resize: vertical; }

/* ---------- aviso de copyright ---------- */
.titulo-cargando {
  margin: 18px 0 0; font-family: var(--mono); font-size: 12px; letter-spacing: .16em;
  text-transform: uppercase; color: var(--ink-faint);
}
.titulo-btn[disabled] { opacity: .45; cursor: default; }

.titulo-copyright {
  position: absolute; left: 24px; bottom: calc(14px + var(--safe-b)); margin: 0; z-index: 3;
  font-family: var(--mono); font-size: 10.5px; letter-spacing: .06em; color: var(--ink-faint); opacity: .85;
}
@media (max-width: 640px) { .titulo-copyright { left: 16px; bottom: calc(52px + var(--safe-b)); } }
.modal-pie { margin: 18px 0 0; padding-top: 12px; border-top: 1px solid var(--line-soft); font-size: 11.5px; line-height: 1.5; color: var(--ink-faint); }
