/* ═══════════════════════════════════════════════════════════════════
   TypeToaster — sistema visual

   Identidad: un cuaderno de lectura, no un cronómetro. Papel, tinta,
   registro. Los números se leen como anotaciones al margen, no como el
   marcador de un videojuego.

   Regla de oro heredada y no negociable: la página del PDF nunca se
   modifica. Todo el feedback vive en capas superpuestas y translúcidas.
   ═══════════════════════════════════════════════════════════════════ */

/* ── escalas ─────────────────────────────────────────────────────── */
:root{
  /* tipografía: una escala, no valores sueltos */
  --t-xs:11px; --t-sm:12.5px; --t-md:14px; --t-lg:16px;
  --t-xl:20px; --t-2xl:27px; --t-3xl:40px; --t-4xl:54px;

  /* espacio: múltiplos de 4 */
  --s1:4px; --s2:8px; --s3:12px; --s4:16px; --s5:24px;
  --s6:32px; --s7:48px; --s8:64px; --s9:96px;

  --r1:6px; --r2:10px; --r3:14px; --r4:20px;

  /* movimiento: una curva y tres duraciones */
  --ease:cubic-bezier(.22,.9,.3,1);
  --t-fast:120ms; --t-base:200ms; --t-slow:340ms;

  --sans:ui-sans-serif,-apple-system,"Segoe UI",Inter,Roboto,sans-serif;
  --mono:ui-monospace,SFMono-Regular,Menlo,"Cascadia Mono",monospace;

  --measure:1080px;                  /* ancho útil de las vistas */
  --page-radius:2px;
}

/* ── tema noche (por defecto) ────────────────────────────────────── */
body.theme-night{
  --bg:#141210;  --bg-2:#1a1714;
  --surface:#201d19; --surface-2:#272320; --surface-3:#2f2a25;
  --line:#332e28; --line-2:#443d35;
  --ink:#ece5da; --ink-2:#a99f92; --ink-3:#786f64;
  --accent:#e0873f; --accent-2:#f2a769;
  --accent-wash:rgba(224,135,63,.13);
  --good:#74ae76; --bad:#e0563f;
  --shadow-1:0 1px 2px rgba(0,0,0,.35);
  --shadow-2:0 8px 24px rgba(0,0,0,.42);
  --shadow-3:0 24px 60px rgba(0,0,0,.55);
  --shadow-paper:0 1px 0 rgba(255,255,255,.04) inset, 0 24px 60px -42px rgba(0,0,0,.7);
  --paper-dim:rgba(164,139,102,.2);   /* velo nocturno suave: la hoja sigue blanca, solo un punto más cálida */
  --hl-ok:#f4c46a; --hl-bad:#ff8f84; --hl-missed:#e03c2b;
  --ink-ok:#ff8c00; --ink-bad:#ff2419; --ink-missed:#b8503a;
  --hl-alpha:.55; --hl-alpha-dark:.3;
  color-scheme:dark;
}

/* ── tema papel ──────────────────────────────────────────────────── */
body.theme-paper{
  --bg:#efe9df;  --bg-2:#e6dfd2;
  --shadow-paper:0 1px 0 rgba(255,255,255,.5) inset, 0 24px 60px -42px rgba(47,31,17,.5);
  --surface:#faf7f1; --surface-2:#f1ebe0; --surface-3:#e8e0d2;
  --line:#ddd4c5; --line-2:#c9beac;
  --ink:#2b2620; --ink-2:#6e6558; --ink-3:#988e81;
  --accent:#bf5f22; --accent-2:#a95217;
  --accent-wash:rgba(191,95,34,.10);
  --good:#3f7d4e; --bad:#c0392b;
  --shadow-1:0 1px 2px rgba(70,55,35,.10);
  --shadow-2:0 8px 24px rgba(70,55,35,.13);
  --shadow-3:0 20px 54px rgba(70,55,35,.18);
  --paper-dim:transparent;
  --hl-ok:#ffd98a; --hl-bad:#ff9c92; --hl-missed:#cf3324;
  --ink-ok:#f26100; --ink-bad:#e6120a; --ink-missed:#b03a24;
  --hl-alpha:.55; --hl-alpha-dark:.3;
  color-scheme:light;
}

/* ── base ────────────────────────────────────────────────────────── */
*{box-sizing:border-box}
[hidden]{display:none !important}
html,body{height:100%}
body{
  margin:0; background:var(--bg); color:var(--ink);
  font:var(--t-md)/1.5 var(--sans);
  overflow:hidden; -webkit-font-smoothing:antialiased; text-rendering:optimizeLegibility;
}
button,input{font:inherit; color:inherit}
button{border:0; background:none; cursor:pointer}
h1,h2,h3,p,ul{margin:0}
ul{list-style:none; padding:0}
b,strong{font-weight:600}
::selection{background:var(--accent-wash)}

.num{font-variant-numeric:tabular-nums; letter-spacing:-.01em}

.ico{
  width:18px; height:18px; flex:0 0 auto; display:block;
  fill:none; stroke:currentColor; stroke-width:1.6;
  stroke-linecap:round; stroke-linejoin:round;
}

kbd{
  font:600 10px/1 var(--mono); padding:3px 5px 2px;
  border:1px solid var(--line-2); border-radius:4px;
  background:var(--surface-2); color:var(--ink-3);
}

.eyebrow{
  display:block; font-size:var(--t-xs); font-weight:600;
  letter-spacing:.09em; text-transform:uppercase; color:var(--ink-3);
  margin-bottom:var(--s1);
}

/* ── botones ─────────────────────────────────────────────────────── */
.btn{
  display:inline-flex; align-items:center; gap:var(--s2);
  padding:9px 15px; border-radius:var(--r1);
  background:var(--surface-2); border:1px solid var(--line);
  font-size:var(--t-sm); font-weight:500; color:var(--ink);
  transition:background var(--t-fast), border-color var(--t-fast), transform var(--t-fast);
}
.btn:hover{background:var(--surface-3); border-color:var(--line-2)}
.btn:active{transform:translateY(1px)}
.btn .ico{width:15px; height:15px; opacity:.75}

.btn-primary{background:var(--accent); border-color:var(--accent); color:#1a1410}
.btn-primary:hover{background:var(--accent-2); border-color:var(--accent-2)}
.btn-primary kbd{background:rgba(0,0,0,.16); border-color:rgba(0,0,0,.2); color:inherit; opacity:.7}
.btn-primary .ico{opacity:.9}

.btn-lg{padding:12px 20px; font-size:var(--t-md); border-radius:var(--r1)}

.btn-icon{
  width:32px; height:32px; border-radius:var(--r1);
  display:inline-flex; align-items:center; justify-content:center;
  color:var(--ink-2); transition:background var(--t-fast), color var(--t-fast);
}
.btn-icon:hover{background:var(--surface-2); color:var(--ink)}
.btn-icon:active{background:var(--surface-3)}

.btn-ghost{
  display:inline-flex; align-items:center; gap:var(--s2);
  padding:7px 12px; border-radius:var(--r1); font-size:var(--t-sm);
  color:var(--ink-2); transition:background var(--t-fast), color var(--t-fast);
}
.btn-ghost:hover{background:var(--surface-2); color:var(--ink)}
.btn-ghost .ico{width:16px; height:16px}

.link{
  font-size:var(--t-sm); color:var(--ink-3); padding:2px 0;
  border-bottom:1px solid transparent; transition:color var(--t-fast), border-color var(--t-fast);
}
.link:hover{color:var(--accent); border-bottom-color:var(--accent)}

:focus-visible{outline:2px solid var(--accent); outline-offset:2px; border-radius:var(--r1)}

/* ── vistas ──────────────────────────────────────────────────────── */
.view{
  position:fixed; inset:0; display:flex; flex-direction:column;
  opacity:0; visibility:hidden; transform:scale(.994);
  transition:opacity var(--t-base) var(--ease), transform var(--t-base) var(--ease), visibility var(--t-base);
}
body[data-view="home"]   #home,
body[data-view="book"]   #book,
body[data-view="reader"] #reader{opacity:1; visibility:visible; transform:none}
body[data-view="reader"] #reader{z-index:2}

.app-bar{
  flex:0 0 auto; height:56px; display:flex; align-items:center;
  justify-content:space-between; gap:var(--s4);
  padding:0 var(--s5); border-bottom:1px solid transparent;
}
.app-bar-actions{display:flex; align-items:center; gap:var(--s1)}

.brand{display:flex; align-items:center; gap:var(--s2); font-size:var(--t-md); font-weight:600; letter-spacing:-.015em}
.brand-mark{width:20px; height:20px; color:var(--accent); stroke-width:1.5}
.brand em{font-style:normal; color:var(--accent)}

.view-body{
  flex:1; overflow-y:auto; overflow-x:hidden;
  padding:var(--s5) var(--s5) var(--s9);
  scrollbar-gutter:stable;
}
.view-body > *{width:min(var(--measure),100%); margin-inline:auto}
.view-body::-webkit-scrollbar{width:11px}
.view-body::-webkit-scrollbar-thumb{background:var(--line); border-radius:99px; border:3px solid var(--bg)}
.view-body::-webkit-scrollbar-thumb:hover{background:var(--line-2)}

.block{margin-bottom:var(--s7)}
.block-head{
  display:flex; align-items:baseline; justify-content:space-between; gap:var(--s4);
  margin-bottom:var(--s4); padding-bottom:var(--s3); border-bottom:1px solid var(--line);
}
.block-head h2{font-size:var(--t-md); font-weight:600; letter-spacing:-.01em}
.block-note{font-size:var(--t-sm); color:var(--ink-3)}

/* ── primera vez ─────────────────────────────────────────────────── */
.first-run{display:grid; place-items:center; min-height:calc(100vh - 140px)}
.fr-inner{width:min(560px,100%); text-align:center}
.display{
  font-size:var(--t-3xl); font-weight:600; line-height:1.12;
  letter-spacing:-.032em; margin-bottom:var(--s4);
}
.lede{
  font-size:var(--t-md); line-height:1.65; color:var(--ink-2);
  max-width:46ch; margin:0 auto var(--s6);
}
.dropzone{
  display:grid; place-items:center; gap:var(--s2);
  padding:var(--s7) var(--s5); cursor:pointer;
  border:1.5px dashed var(--line-2); border-radius:var(--r3);
  background:var(--surface); transition:border-color var(--t-base), background var(--t-base), transform var(--t-base);
}
.dropzone:hover,.dropzone.over{border-color:var(--accent); background:var(--surface-2); box-shadow:var(--shadow-2)}
.dz-ico{width:26px; height:26px; color:var(--ink-3); margin-bottom:var(--s1)}
.dropzone:hover .dz-ico,.dropzone.over .dz-ico{color:var(--accent)}
.dz-title{font-size:var(--t-md); font-weight:550}
.dz-sub{font-size:var(--t-sm); color:var(--ink-3)}
.fr-points{
  display:flex; flex-wrap:wrap; justify-content:center; gap:var(--s3) var(--s5);
  margin-top:var(--s6); font-size:var(--t-sm); color:var(--ink-3);
}
.fr-points li{display:flex; align-items:center; gap:var(--s2)}
.fr-points .ico{width:14px; height:14px; color:var(--good); stroke-width:2}

/* ── continuar ───────────────────────────────────────────────────── */
.resume{margin-bottom:var(--s7)}
.resume-card{
  display:flex; gap:var(--s5); align-items:center;
  padding:var(--s5); border-radius:var(--r3);
  background:var(--surface); border:1px solid var(--line); box-shadow:var(--shadow-paper);
}
.resume-cover{
  flex:0 0 auto; width:96px; aspect-ratio:.7; border-radius:2px 4px 4px 2px;
  overflow:hidden; background:var(--surface-3); box-shadow:var(--shadow-2); position:relative;
}
.resume-cover img{width:100%; height:100%; object-fit:cover; object-position:50% 0; display:block}
.resume-cover::after{
  content:""; position:absolute; inset:0;
  background:linear-gradient(90deg,rgba(0,0,0,.26) 0%,rgba(0,0,0,.1) 3%,rgba(255,255,255,.08) 7%,transparent 15%);
}
.resume-body{flex:1; min-width:0}
.resume-title{
  font-size:var(--t-xl); font-weight:600; letter-spacing:-.02em; line-height:1.25;
  margin-bottom:var(--s1); overflow:hidden; text-overflow:ellipsis; white-space:nowrap;
}
.resume-meta{font-size:var(--t-sm); color:var(--ink-2); margin-bottom:var(--s3)}
.resume-meta b{color:var(--ink); font-weight:600}
.resume-actions{display:flex; gap:var(--s2); margin-top:var(--s4)}

.bar{height:4px; border-radius:99px; background:var(--surface-3); overflow:hidden}
.bar i{display:block; height:100%; background:var(--accent); border-radius:99px;
  transition:width var(--t-slow) var(--ease)}

/* ── fichas de dato ──────────────────────────────────────────────── */
.stat-row{display:grid; grid-template-columns:repeat(4,1fr); gap:0; margin-bottom:var(--s4);
  border-top:1px solid var(--line); border-bottom:1px solid var(--line)}
.stat{padding:var(--s4) var(--s4) var(--s4) var(--s5); border-left:1px solid var(--line)}
.stat:first-child{border-left:0; padding-left:var(--s1)}
.stat-head{display:flex; align-items:center; gap:6px; color:var(--ink-3); margin-bottom:var(--s2)}
.stat-head .ico{width:13px; height:13px}
.stat-head span{font-size:var(--t-xs); font-weight:600; letter-spacing:.07em; text-transform:uppercase}
.stat b{
  display:block; font-size:var(--t-2xl); font-weight:600; line-height:1;
  letter-spacing:-.03em; font-variant-numeric:tabular-nums;
}
.stat b small{font-size:var(--t-md); font-weight:500; color:var(--ink-3); letter-spacing:0; margin-left:5px}
.stat i{display:block; font-style:normal; font-size:var(--t-sm); color:var(--ink-3); margin-top:5px}
.stat.accent b{color:var(--accent)}
.stat i.up{color:var(--good)}
.stat i.down{color:var(--bad)}

/* ── mapa de calor ───────────────────────────────────────────────── */
.heatmap{
  display:flex; flex-direction:column; gap:var(--s3);
  width:fit-content; max-width:100%;      /* el panel mide lo que tus datos */
  padding:var(--s4); border-radius:var(--r2);
  background:var(--surface); border:1px solid var(--line);
}
.hm-grid{
  display:grid; grid-auto-flow:column; grid-template-rows:repeat(7,1fr);
  grid-auto-columns:1fr; gap:3px;
  max-width:calc(var(--cols,53) * 20px);   /* celdas de 20 px como techo */
}
.hm-months{
  display:grid; grid-auto-flow:column; grid-auto-columns:1fr; gap:3px;
  font-size:10px; color:var(--ink-3); margin-bottom:5px; height:13px;
  max-width:calc(var(--cols,53) * 20px);
}
.hm-months span{grid-row:1; white-space:nowrap; text-transform:capitalize}
.hm-cell{
  aspect-ratio:1; border-radius:2.5px; background:var(--surface-3); min-width:0;
  transition:transform var(--t-fast), outline-color var(--t-fast);
  outline:1.5px solid transparent; outline-offset:1px;
}
.hm-cell[data-l="1"]{background:color-mix(in srgb,var(--accent) 26%,var(--surface-3))}
.hm-cell[data-l="2"]{background:color-mix(in srgb,var(--accent) 48%,var(--surface-3))}
.hm-cell[data-l="3"]{background:color-mix(in srgb,var(--accent) 72%,var(--surface-3))}
.hm-cell[data-l="4"]{background:var(--accent)}
.hm-cell:hover{transform:scale(1.35); outline-color:var(--ink-2)}
.hm-foot{display:flex; align-items:center; justify-content:space-between; gap:var(--s5);
  font-size:var(--t-xs); color:var(--ink-3)}
.hm-scale{display:flex; align-items:center; gap:4px}
.hm-scale i{width:10px; height:10px; border-radius:2px; display:block}

/* ── estantería ──────────────────────────────────────────────────── */
.shelf{display:grid; gap:var(--s5) var(--s4); grid-template-columns:repeat(auto-fill,minmax(122px,1fr))}
.book-card{cursor:pointer; text-align:left; position:relative}
.book-cover{
  position:relative; aspect-ratio:.7; border-radius:2px 5px 5px 2px;
  background:var(--surface-2); overflow:hidden;
  box-shadow:var(--shadow-2);
  transition:transform var(--t-base) var(--ease), box-shadow var(--t-base) var(--ease);
}
.book-card:hover .book-cover,.book-card:focus-visible .book-cover{box-shadow:var(--shadow-3)}
.book-cover img{width:100%; height:100%; object-fit:cover; object-position:50% 0; display:block}
.book-cover::after{
  content:""; position:absolute; inset:0; pointer-events:none;
  background:linear-gradient(90deg,rgba(0,0,0,.28) 0%,rgba(0,0,0,.1) 3%,rgba(255,255,255,.1) 7%,transparent 15%);
}
.book-ph{position:absolute; inset:0; display:grid; place-items:center; color:var(--ink-3)}
.book-ph .ico{width:26px; height:26px}
.book-cover img ~ .book-ph{display:none}
.book-prog{position:absolute; left:0; right:0; bottom:0; height:3px; background:rgba(0,0,0,.34); z-index:2}
.book-prog i{display:block; height:100%; background:var(--accent)}
.book-badge{
  position:absolute; top:6px; left:6px; z-index:3;
  font-size:10px; font-weight:600; letter-spacing:.04em;
  padding:2px 6px; border-radius:99px;
  background:rgba(0,0,0,.55); color:#fff; backdrop-filter:blur(4px);
}
.book-del{
  position:absolute; top:5px; right:5px; z-index:3;
  width:24px; height:24px; border-radius:var(--r1); color:#fff;
  background:rgba(0,0,0,.5); backdrop-filter:blur(4px);
  opacity:0; transition:opacity var(--t-fast), background var(--t-fast);
}
.book-card:hover .book-del{opacity:1}
.book-del:hover{background:var(--bad)}
.book-del.armed{opacity:1; background:var(--bad); animation:armar 1.2s ease-in-out infinite}
@keyframes armar{0%,100%{transform:scale(1)}50%{transform:scale(1.12)}}
.book-del .ico{width:14px; height:14px}
.book-card.away .book-cover{opacity:.4; filter:grayscale(.6)}
.book-name{
  font-size:var(--t-sm); line-height:1.35; margin-top:var(--s3); font-weight:500;
  display:-webkit-box; -webkit-line-clamp:2; -webkit-box-orient:vertical; overflow:hidden;
}
.book-meta{font-size:var(--t-xs); color:var(--ink-3); margin-top:3px; font-variant-numeric:tabular-nums}

.storage-line{font-size:var(--t-xs); color:var(--ink-3); margin-top:var(--s5)}

/* ── vacíos ──────────────────────────────────────────────────────── */
.empty{
  display:grid; place-items:center; gap:var(--s2); text-align:center;
  padding:var(--s7) var(--s5); border:1px dashed var(--line); border-radius:var(--r2);
  color:var(--ink-3);
}
.empty .ico{width:22px; height:22px; opacity:.6}
.empty b{font-size:var(--t-sm); font-weight:550; color:var(--ink-2)}
.empty p{font-size:var(--t-sm); max-width:38ch}

/* ── ficha del libro ─────────────────────────────────────────────── */
.book-hero{display:flex; gap:var(--s5); margin-bottom:var(--s7)}
.hero-cover{
  flex:0 0 auto; width:132px; aspect-ratio:.7; border-radius:2px 5px 5px 2px;
  overflow:hidden; background:var(--surface-2); box-shadow:var(--shadow-3); position:relative;
}
.hero-cover img{width:100%; height:100%; object-fit:cover; object-position:50% 0; display:block}
.hero-cover::after{
  content:""; position:absolute; inset:0;
  background:linear-gradient(90deg,rgba(0,0,0,.28) 0%,rgba(0,0,0,.1) 3%,rgba(255,255,255,.1) 7%,transparent 15%);
}
.hero-body{flex:1; min-width:0; display:flex; flex-direction:column}
.hero-title{font-size:var(--t-2xl); font-weight:600; letter-spacing:-.028em; line-height:1.2; margin-bottom:var(--s2)}
.hero-meta{font-size:var(--t-sm); color:var(--ink-2); margin-bottom:var(--s4)}
.hero-meta b{color:var(--ink)}
.hero-actions{display:flex; gap:var(--s2); margin-top:auto; flex-wrap:wrap; align-items:center}
.hero-actions .danger{margin-left:auto; background:none; border-color:transparent; color:var(--ink-3)}
.hero-actions .danger:hover{background:var(--surface-2); border-color:var(--line); color:var(--bad)}
.hero-stats{display:grid; grid-template-columns:repeat(4,1fr); gap:var(--s3); margin-bottom:var(--s6)}

/* ── mapa de páginas ─────────────────────────────────────────────── */
.pagemap{
  display:flex; flex-wrap:wrap; gap:3px;
  width:fit-content; max-width:100%;
  padding:var(--s4); border-radius:var(--r2);
  background:var(--surface); border:1px solid var(--line);
}
.pm-cell{
  width:14px; height:18px; border-radius:2px; background:var(--surface-3);
  cursor:pointer; position:relative;
  transition:transform var(--t-fast), outline-color var(--t-fast);
  outline:1.5px solid transparent; outline-offset:1px;
}
.pm-cell[data-l="1"]{background:color-mix(in srgb,var(--accent) 30%,var(--surface-3))}
.pm-cell[data-l="2"]{background:color-mix(in srgb,var(--accent) 52%,var(--surface-3))}
.pm-cell[data-l="3"]{background:color-mix(in srgb,var(--accent) 76%,var(--surface-3))}
.pm-cell[data-l="4"]{background:var(--accent)}
.pm-cell:hover{transform:scale(1.3); outline-color:var(--ink-2); z-index:2}
.pm-cell.current{outline-color:var(--ink); outline-width:2px}
.pm-cell.just{animation:pmPop 700ms var(--ease)}
@keyframes pmPop{
  0%{transform:scale(1); box-shadow:0 0 0 0 var(--accent)}
  35%{transform:scale(1.7); box-shadow:0 0 0 4px var(--accent-wash)}
  100%{transform:scale(1); box-shadow:0 0 0 0 transparent}
}
.pagemap-mini{padding:var(--s3); gap:2px; background:var(--surface-3); border-color:transparent}
.pagemap-mini .pm-cell{width:8px; height:11px; border-radius:1.5px; cursor:default}
/* una pagina sin teclear se pinta con el mismo gris que el fondo de este
   cuadro: dentro del mapa pequeno hay que separarlas o no se ve el libro */
.pagemap-mini .pm-cell[data-l="0"]{background:color-mix(in srgb,var(--ink) 10%,transparent)}
.pagemap-mini .pm-cell:hover{transform:none; outline-color:transparent}

.map-legend{
  display:flex; align-items:center; gap:var(--s4);
  margin-top:var(--s3); font-size:var(--t-xs); color:var(--ink-3);
}
.map-legend .hm-scale i{width:11px; height:13px; border-radius:2px}

/* ── gráficas ────────────────────────────────────────────────────── */
.chart{
  display:block; width:100%; height:190px;
  border-radius:var(--r2); background:var(--surface); border:1px solid var(--line);
}
.chart-sm{height:104px; border:0; background:transparent}

/* ── sesiones ────────────────────────────────────────────────────── */
.session-list{display:flex; flex-direction:column}
.session{
  display:flex; align-items:center; gap:var(--s4);
  padding:var(--s3) var(--s2); border-bottom:1px solid var(--line);
}
.session:last-child{border-bottom:0}
.session-when{flex:0 0 132px; font-size:var(--t-sm); color:var(--ink-2)}
.session-when b{display:block; color:var(--ink); font-weight:550; text-transform:capitalize}
.session-when span{font-size:var(--t-xs); color:var(--ink-3)}
.session-pages{flex:0 0 auto; display:flex; gap:2px}
.session-pages i{width:6px; height:14px; border-radius:1.5px; background:var(--accent); opacity:.35}
.session-figs{margin-left:auto; display:flex; gap:var(--s5); font-size:var(--t-sm); color:var(--ink-2);
  font-variant-numeric:tabular-nums}
.session-figs b{color:var(--ink); font-weight:600}

/* ═══════════════════════════════════════════════════════════════════
   LECTURA — la parte que no se toca sin motivo
   ═══════════════════════════════════════════════════════════════════ */
.reader-bar{
  position:fixed; inset:0 0 auto 0; height:52px; z-index:40;
  background:color-mix(in srgb,var(--bg) 90%,transparent);
  backdrop-filter:blur(12px); border-bottom:1px solid transparent;
  transition:opacity var(--t-base), transform var(--t-base), border-color var(--t-base);
}
.reader-bar.hidden{opacity:0; transform:translateY(-100%); pointer-events:none}
.reader-bar.scrolled{border-bottom-color:var(--line)}
.rb-left,.rb-center,.rb-right{display:flex; align-items:center; gap:var(--s1); min-width:0}
.rb-left{flex:1}
.rb-right{flex:1; justify-content:flex-end}
.rule{width:1px; height:18px; background:var(--line); margin:0 var(--s2)}

.book-chip{
  display:flex; align-items:center; gap:var(--s2); min-width:0;
  padding:5px 10px; border-radius:var(--r1); color:var(--ink-2);
  font-size:var(--t-sm); transition:background var(--t-fast), color var(--t-fast);
}
.book-chip:hover{background:var(--surface-2); color:var(--ink)}
.book-chip span{overflow:hidden; text-overflow:ellipsis; white-space:nowrap; max-width:30vw}
.chip-ico{width:14px; height:14px; opacity:0; transition:opacity var(--t-fast)}
.book-chip:hover .chip-ico{opacity:.7}

.pagebox{
  display:flex; align-items:center; gap:3px; padding:4px 10px;
  font-size:var(--t-sm); color:var(--ink-3); font-variant-numeric:tabular-nums;
  background:var(--surface-2); border-radius:var(--r1);
}
#pageInput{
  width:3.2em; border:0; background:none; text-align:right; outline:none;
  color:var(--ink); font-variant-numeric:tabular-nums;
}

#stage{position:absolute; inset:0}
#scroller{
  position:absolute; inset:0; overflow:auto;
  padding:76px var(--s5) 30vh; display:flex; justify-content:center;
  overscroll-behavior:contain;
}
#scroller::-webkit-scrollbar{width:11px}
#scroller::-webkit-scrollbar-thumb{background:var(--line); border-radius:99px; border:3px solid var(--bg)}

/* La hoja. */
#pageWrap{
  position:relative; flex:0 0 auto; align-self:flex-start; isolation:isolate;
  background:#fff; border-radius:var(--page-radius); box-shadow:var(--shadow-3);
  transition:opacity var(--t-base);
}
#pageWrap.loading{opacity:0}
#pageCanvas{display:block; border-radius:var(--page-radius)}

#fxCanvas,#inkCanvas{
  position:absolute; inset:0; width:100%; height:100%;
  opacity:1; pointer-events:none; border-radius:var(--page-radius);
}
/* El marcador sí es una mezcla: multiply sólo oscurece, así que se lee como
   un rotulador translúcido sobre el papel. */
#fxCanvas{z-index:1; mix-blend-mode:multiply}

/* La tinta NO usa mezcla. El color se recorta a la silueta real de los
   glifos (ver `_construirMascara` en pageview.js) y se pinta opaco encima:
   la letra queda exactamente del color pedido, con su antialiasing, y el
   papel no se toca. Sin mezclas no hay nada que depender de la polaridad. */
/* z-index 4: por ENCIMA del velo nocturno. Ese velo baja la lámpara sobre
   el papel; las letras que ya has tecleado son anotación tuya y conservan
   toda su intensidad. Es lo que hace que el color destaque de verdad. */
#inkCanvas{z-index:4; mix-blend-mode:normal}

/* Página de fondo oscuro (PDF en modo noche). El marcador sí tiene que
   invertirse, porque multiply sobre negro no se ve. */
#pageWrap.dark-page #fxCanvas{mix-blend-mode:screen}
/* no hay lámpara que bajar: la hoja ya es oscura */
#pageWrap.dark-page::after{background:transparent}
#pageWrap.dark-page{background:#111}
/* y la tinta necesita más luz para leerse sobre negro */
#pageWrap.dark-page{--ink-ok:#ffa31a; --ink-bad:#ff3d2e; --ink-missed:#cc6a4a}

/* De noche el papel sigue siendo papel: por defecto no se invierte, se le
   baja la lámpara con un velo cálido que multiplica sobre TODA la hoja. Si
   el lector quiere la hoja oscura de verdad, «Invertir hoja» en la barra la
   invierte por luminancia conservando el tono (pageview.js). */
#pageWrap::after{
  content:""; position:absolute; inset:0; z-index:3; pointer-events:none;
  border-radius:var(--page-radius); background:var(--paper-dim);
  mix-blend-mode:multiply; transition:background var(--t-slow);
}

#textLayer{
  position:absolute; inset:0; z-index:2; overflow:hidden; line-height:1;
  text-align:initial; user-select:none; -webkit-user-select:none;
  border-radius:var(--page-radius);
}
#textLayer span{position:absolute; white-space:pre; transform-origin:0% 0%; color:transparent; cursor:default}

/* El cursor marca el hueco entre dos letras, así que tiene que ser fino:
   un filo, no una barra. Un halo muy corto lo despega del papel blanco y
   de una página negra sin llegar a tapar el glifo que viene. */
#caret{
  position:absolute; z-index:6; width:2px; left:0; top:0; height:0;
  background:var(--ink-ok); border-radius:1px; pointer-events:none; opacity:0;
  box-shadow:0 0 3px color-mix(in srgb,var(--ink-ok) 60%,transparent);
  transition:left 70ms var(--ease), top var(--t-fast) var(--ease), height var(--t-fast);
}
#caret.on{opacity:1}
#caret.blink{animation:blink 1.05s steps(1,end) infinite}
@keyframes blink{0%,49%{opacity:1}50%,100%{opacity:.12}}

/* Antes de la primera tecla: el cursor se delata. Un filo de 2 px en una
   página llena de letras es difícil de encontrar, y al volver a una
   página a medias puede estar en cualquier renglón. El halo se expande y
   se apaga hasta que se escribe; entonces desaparece y ya no estorba.
   Va detrás de .blink a propósito: misma especificidad, gana el último,
   y mientras late no debe parpadear —parpadear lo hace desaparecer medio
   segundo de cada uno, justo lo contrario de lo que se busca. */
#caret.buscame{animation:none; opacity:1; width:3px}
#caret.buscame::after{
  content:''; position:absolute; inset:-5px -6px;
  border-radius:7px; pointer-events:none;
  box-shadow:0 0 0 2px color-mix(in srgb,var(--ink-ok) 60%,transparent);
  animation:buscarCursor 1.6s var(--ease) infinite;
}
@keyframes buscarCursor{
  0%   {transform:scale(.55); opacity:0}
  18%  {opacity:.95}
  100% {transform:scale(1.9); opacity:0}
}
@media (prefers-reduced-motion:reduce){
  #caret.buscame::after{animation:none; opacity:.85; transform:scale(1)}
}

#pageWrap.shake{animation:shake .16s}
@keyframes shake{0%,100%{transform:translateX(0)}30%{transform:translateX(-2px)}70%{transform:translateX(2px)}}
#pageWrap.done{animation:settle .6s var(--ease)}
@keyframes settle{0%{transform:scale(1)}30%{transform:scale(.994)}100%{transform:scale(1)}}

/* esqueleto de carga: una hoja en blanco con renglones, no un disco girando */
.skeleton{
  position:absolute; top:76px; left:50%; transform:translateX(-50%);
  width:min(660px,86%); padding:var(--s8) var(--s7);
  background:var(--surface); border-radius:var(--page-radius); box-shadow:var(--shadow-3);
  display:flex; flex-direction:column; gap:14px;
}
.sk-line{height:9px; border-radius:3px; background:var(--surface-3); animation:pulse 1.4s ease-in-out infinite}
.sk-gap{height:var(--s5)}
.sk-line:nth-child(2){animation-delay:.08s} .sk-line:nth-child(3){animation-delay:.16s}
.sk-line:nth-child(4){animation-delay:.24s} .sk-line:nth-child(6){animation-delay:.32s}
.sk-line:nth-child(7){animation-delay:.4s}  .sk-line:nth-child(8){animation-delay:.48s}
.sk-line:nth-child(9){animation-delay:.56s}
@keyframes pulse{0%,100%{opacity:.5}50%{opacity:1}}

#progress{position:fixed; top:0; left:0; right:0; height:2px; z-index:50}
#progressFill{height:100%; width:0; background:var(--accent); transition:width var(--t-fast) linear; opacity:.9}

/* El pie no flota sobre el papel: la hoja se disuelve en la mesa y los
   números descansan en la madera. */
#hud{
  position:fixed; left:0; right:0; bottom:0; height:72px; z-index:45;
  display:flex; align-items:flex-end; gap:var(--s5); padding:0 var(--s5) 14px;
  pointer-events:none;
  background:linear-gradient(to top,var(--bg) 0%,var(--bg) 38%,
    color-mix(in srgb,var(--bg) 50%,transparent) 70%,transparent 100%);
}
.hud-main{display:flex; align-items:baseline; gap:5px; transition:opacity var(--t-slow)}
.hud-main b{font-size:var(--t-2xl); font-weight:600; letter-spacing:-.03em; font-variant-numeric:tabular-nums}
.hud-main span{font-size:var(--t-xs); font-weight:600; letter-spacing:.08em; text-transform:uppercase; color:var(--ink-2)}
.hud-sub{
  display:flex; align-items:baseline; gap:var(--s4); padding-bottom:5px;
  font-size:var(--t-md); color:var(--ink-2); transition:opacity var(--t-slow);
}
.hud-sub i{font-style:normal; color:var(--ink-2); font-variant-numeric:tabular-nums}
.hud-page{margin-left:auto}
#hud.idle .hud-main{opacity:.5} #hud.idle .hud-sub{opacity:.5}
#hud.typing .hud-main{opacity:.95} #hud.typing .hud-sub{opacity:.65}
#hud.away .hud-main,#hud.away .hud-sub{opacity:0}

.hint{
  position:fixed; left:50%; bottom:var(--s5); transform:translateX(-50%); z-index:44;
  display:flex; align-items:center; gap:var(--s2);
  font-size:var(--t-sm); color:var(--ink-3);
  background:color-mix(in srgb,var(--surface) 85%,transparent);
  padding:8px 14px; border-radius:var(--r2); border:1px solid var(--line);
  transition:opacity var(--t-slow), transform var(--t-slow); pointer-events:none;
  backdrop-filter:blur(8px);
}
.hint.gone{opacity:0; transform:translate(-50%,6px)}

.paused{
  position:fixed; left:50%; top:50%; transform:translate(-50%,-50%); z-index:47;
  display:flex; align-items:center; gap:var(--s4); max-width:min(520px,92vw);
  padding:var(--s5); border-radius:var(--r3);
  background:var(--surface); border:1px solid var(--line-2);
  box-shadow:var(--shadow-3); animation:rise var(--t-base) var(--ease);
}
.paused > .ico{width:24px; height:24px; color:var(--accent); flex:0 0 auto}
.paused b{display:block; font-size:var(--t-lg); font-weight:600; margin-bottom:3px}
.paused p{font-size:var(--t-sm); color:var(--ink-3); line-height:1.5}
.paused .btn{flex:0 0 auto}
/* mientras está en pausa la hoja se aparta un poco de la vista */
#pageWrap.pausada{filter:saturate(.55) brightness(.82); transition:filter var(--t-slow)}

.notice{
  position:fixed; left:50%; bottom:var(--s7); transform:translateX(-50%); z-index:46;
  display:flex; align-items:center; gap:var(--s4); max-width:min(560px,92vw);
  padding:var(--s4) var(--s4) var(--s4) var(--s5);
  background:var(--surface); border:1px solid var(--line); border-radius:var(--r3);
  box-shadow:var(--shadow-3); animation:rise var(--t-base) var(--ease);
}
.notice > .ico{width:22px; height:22px; color:var(--ink-3); flex:0 0 auto}
.notice b{display:block; font-size:var(--t-sm); font-weight:600; margin-bottom:2px}
.notice p{font-size:var(--t-sm); color:var(--ink-3)}
.notice .btn{flex:0 0 auto}

/* ═══ superposiciones ══════════════════════════════════════════════ */
.sheet{
  position:fixed; inset:0; z-index:60; display:flex;
  align-items:flex-end; justify-content:center;
  background:color-mix(in srgb,var(--bg) 62%,transparent);
  backdrop-filter:blur(4px); animation:fade var(--t-base) ease;
}
@keyframes fade{from{opacity:0}}
.sheet-inner{
  width:min(560px,100%); max-height:92vh; overflow-y:auto;
  background:var(--surface); border:1px solid var(--line); border-bottom:0;
  border-radius:var(--r4) var(--r4) 0 0; padding:var(--s5) var(--s5) var(--s5);
  box-shadow:0 -24px 70px rgba(0,0,0,.28);
  animation:rise var(--t-slow) var(--ease);
}
.sheet-wide{width:min(760px,100%)}
@keyframes rise{from{transform:translateY(28px); opacity:0}}

.sheet-head{display:flex; align-items:flex-start; justify-content:space-between; gap:var(--s4); margin-bottom:var(--s5)}
.sheet-head h2{font-size:var(--t-xl); font-weight:600; letter-spacing:-.022em}
.sheet-actions{display:flex; gap:var(--s2); justify-content:flex-end; flex-wrap:wrap; margin-top:var(--s5)}

/* resumen de página */
.res-headline{display:grid; grid-template-columns:1fr 1fr; gap:0; margin-bottom:var(--s4)}
.metric{padding:var(--s3) var(--s4); position:relative}
.metric b{display:block; font-size:var(--t-xl); font-weight:600; line-height:1;
  letter-spacing:-.03em; font-variant-numeric:tabular-nums}
.metric span{display:block; font-size:var(--t-xs); font-weight:600; letter-spacing:.07em;
  text-transform:uppercase; color:var(--ink-3); margin-top:6px}
.metric-lg{padding:var(--s4) var(--s5) var(--s4) 0}
.metric-lg + .metric-lg{border-left:1px solid var(--line); padding-left:var(--s5)}
.metric-lg b{font-size:var(--t-3xl); color:var(--accent)}
.metric-grid{grid-column:1/-1; display:grid; grid-template-columns:repeat(4,1fr); gap:0;
  border-top:1px solid var(--line); border-bottom:1px solid var(--line)}
.metric-grid .metric{padding:var(--s3) var(--s4); border-left:1px solid var(--line)}
.metric-grid .metric:first-child{border-left:0; padding-left:0}
.delta:empty{display:none}
.delta{
  position:absolute; top:var(--s4); right:var(--s4);
  font-style:normal; font-size:var(--t-xs); font-weight:600;
  padding:3px 7px; border-radius:99px; background:var(--surface-3); color:var(--ink-3);
}
.delta.up{background:color-mix(in srgb,var(--good) 18%,transparent); color:var(--good)}
.delta.down{background:color-mix(in srgb,var(--bad) 16%,transparent); color:var(--bad)}
.delta.pb{background:var(--accent); color:#1a1410}

.res-context{display:grid; grid-template-columns:1fr 1fr; gap:var(--s3); margin-bottom:var(--s4)}
.ctx-block{
  display:flex; flex-direction:column;
  padding:var(--s4); border-radius:var(--r2);
  background:var(--surface-2); border:1px solid var(--line);
}
.ctx-foot{margin-top:auto; padding-top:var(--s3)}
.ctx-head{display:flex; align-items:baseline; justify-content:space-between; margin-bottom:var(--s3)}
.ctx-head span{font-size:var(--t-xs); font-weight:600; letter-spacing:.07em; text-transform:uppercase; color:var(--ink-3)}
.ctx-head b{font-size:var(--t-md); font-weight:600; font-variant-numeric:tabular-nums}
.ctx-foot{font-size:var(--t-sm); color:var(--ink-3)}
.ctx-foot b{color:var(--ink-2); font-weight:550}

/* huecos de publicidad: una franja con regla y etiqueta; el anuncio de la
   casa es texto propio, sin iframes ni scripts */
.hueco{margin-top:var(--s6)}
#huecoResumen{margin-top:var(--s4)}
.anuncio-casa{display:flex; align-items:center; gap:var(--s4); padding:var(--s3) var(--s1); min-height:64px;
  border-top:1px solid var(--line); border-bottom:1px solid var(--line); font-size:var(--t-sm); color:var(--ink-2)}
.anuncio-etiqueta{font-size:var(--t-xs); font-weight:600; letter-spacing:.08em; text-transform:uppercase; color:var(--ink-3); flex:0 0 auto}
.anuncio-casa div{flex:1; min-width:0}
.anuncio-casa b{display:block; color:var(--ink); font-weight:600}
.anuncio-casa .btn{flex:0 0 auto; text-decoration:none}
@media (max-width:640px){ .anuncio-casa{flex-wrap:wrap} .anuncio-casa div{flex-basis:100%} }
/* muestras al volver: cuatro a la vista; el resto, al desplegar */
.demo-block .demo-row:not(.abierta) .demo-card:nth-child(n+5){display:none}
.demo-mas{appearance:none; border:0; background:none; color:var(--ink-2); font:inherit; font-size:var(--t-sm); cursor:pointer;
  padding:var(--s3) 0 0; text-decoration:underline; text-underline-offset:3px; text-decoration-color:var(--line-2)}
.demo-mas:hover{color:var(--ink)}
/* filas de aviso (instalar, Premium): una fila con regla, sin caja */
.fila-aviso{display:flex; align-items:center; gap:var(--s3); padding:var(--s3) var(--s1); margin:var(--s4) 0 var(--s6);
  border-top:1px solid var(--line); border-bottom:1px solid var(--line); font-size:var(--t-sm); color:var(--ink-2)}
.fila-aviso + .fila-aviso{margin-top:calc(-1 * var(--s6) - 1px)}
.fila-aviso .ico{width:20px; height:20px; color:var(--accent); flex:0 0 auto}
.fila-aviso div{flex:1; min-width:0}
.fila-aviso b{color:var(--ink); font-weight:600; margin-right:var(--s2)}
@media (max-width:640px){ .fila-aviso{flex-wrap:wrap} .fila-aviso div{flex-basis:100%} }
/* Premium: beneficios con regla, plan como dos opciones, correo opcional */
.premium-lista{list-style:none; margin:0 0 var(--s4); padding:0}
.premium-lista li{padding:var(--s3) 0; border-top:1px solid var(--line); font-size:var(--t-sm); color:var(--ink-2)}
.premium-lista li:first-child{border-top:0; padding-top:0}
.premium-lista b{display:block; color:var(--ink); font-weight:600; margin-bottom:2px}
.premium-nota{font-size:var(--t-sm); color:var(--ink-3); border-top:1px solid var(--line); padding-top:var(--s3); margin:0 0 var(--s4)}
.premium-plan{display:grid; grid-template-columns:1fr 1fr; gap:var(--s2)}
.premium-plan button{appearance:none; text-align:left; border:1px solid var(--line-2); background:transparent; color:var(--ink-2); border-radius:var(--r1); padding:var(--s3) var(--s4); font:inherit; cursor:pointer}
.premium-plan button b{display:block; font-size:var(--t-xl); font-weight:600; color:var(--ink); letter-spacing:-.02em; font-variant-numeric:tabular-nums}
.premium-plan button span{font-size:var(--t-xs); color:var(--ink-3)}
.premium-plan button[aria-checked="true"]{border-color:var(--accent); color:var(--accent)}
.premium-plan button[aria-checked="true"] b{color:var(--accent)}
.premium-plan button:focus-visible{outline:2px solid var(--accent); outline-offset:2px}
.premium-correo{margin-top:var(--s4); border-top:1px solid var(--line); padding-top:var(--s4); font-size:var(--t-sm); color:var(--ink-2)}
.premium-correo p{margin:0 0 var(--s3)}
.premium-campos{display:flex; gap:var(--s2)}
.premium-campos input{flex:1; min-width:0; font:inherit; font-size:var(--t-md); padding:9px 12px; border-radius:var(--r1); border:1px solid var(--line-2); background:var(--surface-2); color:var(--ink)}
.premium-campos input:focus-visible{outline:2px solid var(--accent); outline-offset:1px}
.premium-consent{display:flex; gap:var(--s2); align-items:flex-start; margin-top:var(--s3); font-size:var(--t-xs); color:var(--ink-3)}
.premium-consent input{margin-top:2px}
.premium-consent a{color:var(--ink-2)}
.premium-hecho{margin-top:var(--s4); border-top:1px solid var(--line); padding-top:var(--s4); font-size:var(--t-sm); color:var(--ink-2)}
.premium-hecho p{margin:0 0 var(--s3)}
.premium-hecho i{font-style:normal; color:var(--ink)}
.sr-only{position:absolute; width:1px; height:1px; overflow:hidden; clip:rect(0 0 0 0); white-space:nowrap}
/* recordatorio: un enlace discreto tras la tarea */
.lec-tarea button{appearance:none; border:0; background:none; color:var(--ink-3); font:inherit; font-size:var(--t-xs); cursor:pointer;
  margin-left:var(--s3); text-decoration:underline; text-underline-offset:3px; text-decoration-color:var(--line-2)}
.lec-tarea button:hover{color:var(--ink)}
/* lo que enseña la página: filas con regla, no cajas */
.res-lecciones{font-size:var(--t-sm); color:var(--ink-3); border-top:1px solid var(--line); padding-top:var(--s3)}
.lec-head{font-size:var(--t-xs); font-weight:600; letter-spacing:.07em; text-transform:uppercase; color:var(--ink-3); margin-bottom:var(--s2)}
.lec{display:grid; grid-template-columns:minmax(9em,12em) 1fr; gap:var(--s2) var(--s4); padding:6px 0; border-top:1px solid var(--line)}
.lec:first-of-type{border-top:0}
.lec b{color:var(--ink-2); font-weight:550}
.lec span{color:var(--ink-2); font-variant-numeric:tabular-nums}
.lec-limpia{grid-template-columns:1fr}
.lec-tarea b{color:var(--accent)}
.lec-tarea span{color:var(--ink)}
@media (max-width:560px){ .lec{grid-template-columns:1fr; gap:2px} }
/* tablas de cifras a dos columnas: la regla vertical solo entre las dos */
@media (max-width:640px){
  .stat:nth-child(odd){border-left:0; padding-left:var(--s1)}
  .stat:nth-child(n+3){border-top:1px solid var(--line)}
  .metric-grid{grid-template-columns:1fr 1fr}
  .metric-grid .metric:nth-child(odd){border-left:0; padding-left:0}
  .metric-grid .metric:nth-child(n+3){border-top:1px solid var(--line)}
}
.tramo-fin .tf-leccion{color:var(--ink); font-weight:550}
.tramo-fin .tf-salto{flex-basis:100%; height:0}
.tramo-fin .tf-detalle{color:var(--ink-3)}
.resume-tarea{margin-top:var(--s2); font-size:var(--t-sm); color:var(--ink); font-weight:550}

/* ajustes */
.set-list{display:flex; flex-direction:column}
.set-row{display:flex; align-items:center; justify-content:space-between; gap:var(--s5);
  padding:var(--s3) var(--s1); border-bottom:1px solid var(--line)}
.set-row:last-child{border-bottom:0}
.set-group{
  font-size:var(--t-xs); font-weight:600; letter-spacing:.09em; text-transform:uppercase;
  color:var(--ink-3); padding:var(--s5) var(--s1) var(--s2); border-bottom:1px solid var(--line);
}
.set-group:first-child{padding-top:0}
.set-row .lbl{font-size:var(--t-md); font-weight:450}
.set-row .desc{font-size:var(--t-sm); color:var(--ink-3); margin-top:3px; max-width:44ch; line-height:1.5}
.switch{
  width:38px; height:22px; border-radius:99px; background:var(--surface-3);
  position:relative; flex:0 0 auto; transition:background var(--t-base);
  border:1px solid var(--line);
}
.switch::after{
  content:""; position:absolute; top:2px; left:2px; width:16px; height:16px;
  border-radius:50%; background:var(--ink-3); box-shadow:var(--shadow-1);
  transition:transform var(--t-base) var(--ease), background var(--t-base);
}
.switch.on{background:var(--accent); border-color:var(--accent)}
.switch.on::after{transform:translateX(16px); background:#fff}
.seg-acciones{display:flex; gap:var(--s2); flex:0 0 auto}
.seg{display:flex; gap:2px; padding:2px; border-radius:var(--r1);
  background:var(--surface-2); border:1px solid var(--line); flex:0 0 auto}
.seg button{padding:5px 11px; border-radius:5px; font-size:var(--t-sm); color:var(--ink-3);
  transition:background var(--t-fast), color var(--t-fast)}
.seg button:hover{color:var(--ink)}
.seg button.on{background:var(--surface-3); color:var(--ink); box-shadow:var(--shadow-1)}

/* ── avisos ──────────────────────────────────────────────────────── */
.toast{
  position:fixed; left:50%; top:calc(var(--s5) + 44px); transform:translateX(-50%); z-index:90;
  background:var(--ink); color:var(--bg); padding:10px 18px; border-radius:var(--r2);
  font-size:var(--t-sm); font-weight:500; box-shadow:var(--shadow-3);
  animation:rise var(--t-base) var(--ease);
}
/* Arrastrar un PDF debe responder desde cualquier vista, no sólo desde la
   pantalla de bienvenida. */
.drop-veil{
  position:fixed; inset:0; z-index:88; display:grid; place-items:center;
  background:color-mix(in srgb,var(--bg) 78%,transparent);
  backdrop-filter:blur(6px); animation:fade var(--t-fast) ease;
}
.dv-card{
  display:grid; place-items:center; gap:var(--s2); text-align:center;
  padding:var(--s7) var(--s8); border-radius:var(--r3);
  border:2px dashed var(--accent); background:var(--surface);
  box-shadow:var(--shadow-3); animation:rise var(--t-base) var(--ease);
}
.dv-card .ico{width:30px; height:30px; color:var(--accent); margin-bottom:var(--s1)}
.dv-card b{font-size:var(--t-lg); font-weight:600}
.dv-card span{font-size:var(--t-sm); color:var(--ink-3)}

.splash{position:fixed; inset:0; z-index:95; display:grid; place-items:center;
  background:color-mix(in srgb,var(--bg) 88%,transparent); backdrop-filter:blur(3px)}
.splash-inner{display:flex; flex-direction:column; align-items:center; gap:var(--s4);
  font-size:var(--t-sm); color:var(--ink-2)}
.spinner{
  width:26px; height:26px; border:2px solid var(--line-2);
  border-top-color:var(--accent); border-radius:50%; animation:spin .7s linear infinite;
}
@keyframes spin{to{transform:rotate(360deg)}}

#sink{position:fixed; top:-100px; left:-100px; width:1px; height:1px; opacity:0; border:0}

/* ── adaptación ──────────────────────────────────────────────────── */
@media (max-width:820px){
  .stat-row,.hero-stats{grid-template-columns:repeat(2,1fr)}
  .res-context{grid-template-columns:1fr}
  .metric-grid{grid-template-columns:repeat(2,1fr)}
}
@media (max-width:640px){
  .app-bar{padding:0 var(--s4); height:52px}
  .view-body{padding:var(--s4) var(--s4) var(--s8)}
  .display{font-size:var(--t-2xl)}
  .book-hero{flex-direction:column}
  .hero-cover{width:104px}
  .resume-card{flex-direction:column; align-items:flex-start}
  .res-headline{grid-template-columns:1fr}
  #scroller{padding:64px var(--s2) 32vh}
  .book-chip span{max-width:36vw}
  .session-figs{gap:var(--s3)}
  .session-when{flex-basis:96px}
}
@media (prefers-reduced-motion:reduce){
  *,*::before,*::after{animation-duration:1ms !important; transition-duration:1ms !important}
}


/* ═══ tramos: la unidad de práctica ═══════════════════════════════ */

/* marca del tramo activo sobre la página: un corchete fino en el margen
   y una señal de cierre al final. No tapan nada. */
.tramo-marca{
  position:absolute; width:2px; border-radius:2px; pointer-events:none;
  background:color-mix(in srgb,var(--ink-ok) 55%,transparent);
  transition:top var(--t-base) var(--ease), height var(--t-base) var(--ease), left var(--t-base);
}
.tramo-marca::before,.tramo-marca::after{
  content:''; position:absolute; left:0; width:7px; height:2px; border-radius:2px; background:inherit;
}
.tramo-marca::before{top:0} .tramo-marca::after{bottom:0}
.tramo-cierre{
  position:absolute; width:7px; height:7px; border-radius:50%; pointer-events:none;
  background:color-mix(in srgb,var(--ink-ok) 70%,transparent);
  transform:translate(2px,-50%); transition:left var(--t-base), top var(--t-base);
}

/* resumen breve entre tramos: no es una hoja, no tapa la página, no roba
   el foco; la primera tecla lo cierra */
.tramo-fin{
  position:fixed; left:50%; bottom:104px; transform:translateX(-50%); z-index:46;
  display:flex; align-items:baseline; gap:var(--s2) var(--s4); flex-wrap:wrap; justify-content:center;
  padding:12px 20px; border-radius:var(--r2); pointer-events:none; max-width:min(92vw,760px);
  background:color-mix(in srgb,var(--surface) 92%,transparent); border:1px solid var(--line-2);
  box-shadow:var(--shadow-2); backdrop-filter:blur(10px);
  font-size:var(--t-sm); color:var(--ink-3); animation:rise var(--t-base) var(--ease);
}
.tramo-fin .tf-cual{font-size:var(--t-xs); font-weight:600; letter-spacing:.08em; text-transform:uppercase}
.tramo-fin .tf-cifras{display:inline-flex; align-items:baseline; gap:3px; color:var(--ink)}
.tramo-fin .tf-cifras b{font-size:var(--t-xl); font-weight:600; letter-spacing:-.02em; font-variant-numeric:tabular-nums}
.tramo-fin .tf-cifras b + small{margin-right:var(--s2)}
.tramo-fin .tf-cifras small{font-size:var(--t-xs); font-weight:600; text-transform:uppercase; letter-spacing:.06em; color:var(--ink-3)}
.tramo-fin .tf-detalle i{font-style:normal; color:var(--ink-2); font-variant-numeric:tabular-nums}
.tramo-fin .tf-sigue{color:var(--ink-3)}
.tramo-fin .tf-sigue i{font-style:normal; color:var(--ink-2)}
.tramo-fin kbd{margin-left:4px}
@media (prefers-reduced-motion:reduce){ .tramo-fin{animation:none} .tramo-marca,.tramo-cierre{transition:none} }


/* ═══ prueba con un libro: la demo instantánea ═══════════════════ */
.demo{margin-top:var(--s6)}
.demo-head{display:flex; align-items:baseline; gap:var(--s3); flex-wrap:wrap; margin-bottom:var(--s3)}
.demo-head h2{font-size:var(--t-md); font-weight:600; margin:0}
.demo-head span{font-size:var(--t-xs); color:var(--ink-3)}
.demo-row{display:flex; gap:var(--s4); flex-wrap:wrap}
.demo-card{
  display:flex; align-items:center; gap:var(--s3); text-align:left;
  appearance:none; border:0; border-top:1px solid var(--line); background:transparent; color:var(--ink);
  border-radius:0; padding:10px 14px 10px 10px; cursor:pointer; font:inherit;
  flex:1 1 240px; min-width:0; transition:transform var(--t-fast), border-color var(--t-fast), box-shadow var(--t-fast);
}
.demo-card:hover{border-color:var(--line-2); background:var(--surface)}
.demo-card:focus-visible{outline:2px solid var(--accent); outline-offset:2px}
.demo-card img{width:44px; height:62px; object-fit:cover; border-radius:3px; box-shadow:var(--shadow-1); background:var(--surface-2)}
.demo-card b{display:block; font-size:var(--t-sm); font-weight:600; line-height:1.25}
.demo-card small{display:block; font-size:var(--t-xs); color:var(--ink-3); margin-top:3px}
.demo-card .demo-lang{margin-left:auto; font-size:var(--t-xs); font-weight:600; letter-spacing:.06em; color:var(--ink-3); text-transform:uppercase}
.book-badge.muestra{background:color-mix(in srgb,var(--accent) 18%,var(--surface))}
.first-run .demo{max-width:640px; margin-left:auto; margin-right:auto}

/* botón de luna: encendido cuando la hoja está invertida */
#btnNoche.on{color:var(--accent)}


/* ═══ acentos: el color de la casa, a elegir ═══════════════════════
   Cada acento es una tríada acierto / fallo / saltada, con versión para
   papel claro y para papel oscuro. La paleta adaptativa (pageview.js,
   _elegirPaleta) sigue mandando si el libro escribe en ese color. */
/* el FALLO es siempre rojo, en cualquier acento: su significado no cambia */
body.acento-cian   {--ink-ok:#0090b8; --ink-bad:#d42a13; --ink-missed:#4d8494; --accent:#0090b8}
body.acento-violeta{--ink-ok:#6a35d9; --ink-bad:#d42a13; --ink-missed:#7d6cab; --accent:#6a35d9}
body.acento-verde  {--ink-ok:#00803c; --ink-bad:#d42a13; --ink-missed:#5f8a6b; --accent:#00803c}
body.acento-rosa   {--ink-ok:#c22a86; --ink-bad:#b3200f; --ink-missed:#9a6a86; --accent:#c22a86}
body.theme-night.acento-cian   {--ink-ok:#2ac9e8; --ink-bad:#ff3d2e; --ink-missed:#79aebd; --accent:#2ac9e8}
body.theme-night.acento-violeta{--ink-ok:#a37bff; --ink-bad:#ff3d2e; --ink-missed:#a99ccc; --accent:#a37bff}
body.theme-night.acento-verde  {--ink-ok:#3ad882; --ink-bad:#ff3d2e; --ink-missed:#84bd99; --accent:#3ad882}
body.theme-night.acento-rosa   {--ink-ok:#ff5fb8; --ink-bad:#ff4a2e; --ink-missed:#c98fb4; --accent:#ff5fb8}
body.acento-cian    #pageWrap.dark-page{--ink-ok:#2ac9e8; --ink-bad:#ff3d2e; --ink-missed:#79aebd}
body.acento-violeta #pageWrap.dark-page{--ink-ok:#a37bff; --ink-bad:#ff3d2e; --ink-missed:#a99ccc}
body.acento-verde   #pageWrap.dark-page{--ink-ok:#3ad882; --ink-bad:#ff3d2e; --ink-missed:#84bd99}
body.acento-rosa    #pageWrap.dark-page{--ink-ok:#ff5fb8; --ink-bad:#ff4a2e; --ink-missed:#c98fb4}
.swatch-auto{font-size:var(--t-xs); color:var(--ink-3); margin-left:6px}

/* fila de muestras en Ajustes */
.swatches{display:flex; gap:8px; align-items:center}
.swatch{
  appearance:none; border:2px solid transparent; padding:2px; border-radius:50%; background:transparent; cursor:pointer;
  width:28px; height:28px; display:grid; place-items:center; transition:border-color var(--t-fast), transform var(--t-fast);
}
.swatch i{display:block; width:18px; height:18px; border-radius:50%; background:var(--muestra)}
.swatch:hover{transform:scale(1.08)}
.swatch.on{border-color:var(--ink)}
.swatch:focus-visible{outline:2px solid var(--accent); outline-offset:2px}

/* ═══ modo grabación: la pantalla, limpia para el vídeo ════════════ */
body.grabando #topbar{transform:translateY(-100%); opacity:0; pointer-events:none; transition:transform var(--t-base), opacity var(--t-base)}
body.grabando.barra-asomada #topbar{transform:none; opacity:1; pointer-events:auto}
body.grabando #toast, body.grabando #hint, body.grabando .hud-sub, body.grabando #storageLine{display:none !important}
body.grabando #hud{height:72px}
body.grabando #hud .hud-main{opacity:.95 !important}
body.grabando #caret{width:3px; box-shadow:0 0 6px color-mix(in srgb,var(--ink-ok) 75%,transparent)}
body.grabando #pageWrap::after{opacity:.85}


/* ═══ PWA: sin conexión y actualización ═══════════════════════════ */
.sin-red{
  position:fixed; top:0; left:50%; transform:translateX(-50%); z-index:80;
  font-size:var(--t-xs); font-weight:600; letter-spacing:.02em; color:var(--ink-2);
  background:var(--surface); border:1px solid var(--line-2); border-top:0;
  padding:5px 12px; border-radius:0 0 var(--r2) var(--r2); box-shadow:var(--shadow-2);
}
.actualizacion{
  position:fixed; left:50%; bottom:var(--s6); transform:translateX(-50%); z-index:80;
  display:flex; align-items:center; gap:var(--s3); font-size:var(--t-sm); color:var(--ink);
  background:var(--surface); border:1px solid var(--line-2); border-radius:var(--r2);
  padding:8px 8px 8px 16px; box-shadow:var(--shadow-3);
}
/* papel de verdad: un grano de 7 % sobre el fondo claro (nada en noche) */
@media (prefers-reduced-data:reduce){ body.theme-paper{background-image:none !important} }
body.theme-paper{background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='200' height='200'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.85' numOctaves='2' stitchTiles='stitch'/%3E%3CfeColorMatrix values='0 0 0 0 .25 0 0 0 0 .17 0 0 0 0 .09 0 0 0 .07 0'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E"); background-size:200px 200px}
/* contraste: el naranja de día sobre papel blanco no llegaba a 4,5:1 */
body.theme-paper{--ink-ok:#c64800}
/* movimiento reducido: sin sacudidas ni desplazamientos animados */
@media (prefers-reduced-motion:reduce){ #pageWrap.shake{animation:none !important} html{scroll-behavior:auto} }


/* ═══ postura de móvil ═══════════════════════════════════════════════
   Inicio, biblioteca, ficha y resumen tienen que ir perfectos en una
   columna. El lector se soporta en escritorio y tableta con teclado; en
   un teléfono se avisa, y si se entra igual, la barra se parte en dos
   filas y el control de longitud queda junto al paginador. */
.sheet-movil .sheet-inner{max-width:440px; margin:auto; padding:var(--s6); text-align:left}
.sheet-movil h2{font-size:var(--t-lg); margin:0 0 var(--s3)}
.sheet-movil p{color:var(--ink-2); line-height:1.5; margin:0 0 var(--s5)}
.sheet-actions{display:flex; gap:var(--s3); justify-content:flex-end; flex-wrap:wrap}
@media (max-width:640px){
  .reader-bar{height:auto; flex-wrap:wrap; row-gap:4px; padding-bottom:6px}
  .reader-bar .rb-left{flex:1 1 40%}
  .reader-bar .rb-center{flex:1 1 auto; justify-content:center}
  .reader-bar .rb-right{display:contents}            /* sus hijos pasan a ser filas/items de la barra */
  .reader-bar .book-chip span{display:none}
  .reader-bar .longitud{order:99; flex:1 1 100%; justify-content:center; margin:0 var(--s3)}
  .reader-bar .rule{display:none}
  #hud{padding-left:var(--s4); padding-right:var(--s4)}
  .hint{flex-wrap:wrap; justify-content:center; text-align:center; max-width:calc(100vw - 32px); row-gap:4px}
  .hud-sub{gap:var(--s3)}
  .demo-row{flex-direction:column}
  .demo-card{flex-basis:auto}
  .demo-card{min-width:0}
  .stat-row{grid-template-columns:1fr 1fr}
  .view-body{padding-left:var(--s4); padding-right:var(--s4)}
  html,body{overflow-x:hidden}
}

.sr-only{position:absolute; width:1px; height:1px; padding:0; margin:-1px; overflow:hidden; clip:rect(0,0,0,0); white-space:nowrap; border:0}
@media (max-width:640px){
  #hud{height:auto; min-height:0; padding-top:6px; padding-bottom:6px}
  #hud .hud-main b{font-size:var(--t-lg)}
}

/* barras de sesión: si llevan a una página son botones, con el mismo aspecto */
.session-pages button.session-bar{appearance:none; border:0; padding:0; margin:0; font:inherit; cursor:pointer}
.session-pages button.session-bar:focus-visible{outline:2px solid var(--accent); outline-offset:2px}

/* ajustes: lo avanzado, plegado */
.set-avanzado{margin-top:var(--s5); border-top:1px solid var(--line); padding-top:var(--s3)}
.set-avanzado summary{cursor:pointer; list-style:none; display:flex; align-items:baseline; gap:var(--s3); padding:var(--s2) 0; color:var(--ink-2)}
.set-avanzado summary::-webkit-details-marker{display:none}
.set-avanzado summary::before{content:"›"; display:inline-block; transition:transform var(--t-base); color:var(--ink-3)}
.set-avanzado[open] summary::before{transform:rotate(90deg)}
.set-avanzado summary b{color:var(--ink); font-weight:600}
.set-avanzado summary span{font-size:var(--t-sm); color:var(--ink-3)}
/* la sentada en curso, destacada en la lista de sesiones */
.session.viva{border-left:3px solid var(--accent); padding-left:var(--s3)}
.session.viva .session-when b{color:var(--accent)}

/* el título recibe el foco al abrir un diálogo (para lectores de pantalla); sin recuadro visual */
.sheet h2[tabindex="-1"]:focus{outline:none}

/* ═══ identidad: serif de marca en titulares, ranura en la zona de arrastre ═══ */
:root{--display:"Fraunces",Georgia,"Times New Roman",serif}
.display, .hero-title, .resume-title, #resTitle, .sheet-head h2{font-family:var(--display); font-weight:600; letter-spacing:-.015em}
.brand span{font-family:var(--display); font-weight:700}
.first-run .display{margin-bottom:var(--s6)}
.dropzone{border:0; border-radius:20px 20px 30px 30px; background:linear-gradient(180deg,#e8893d,#c86428); color:#24160d;
  box-shadow:inset 0 -10px 0 rgba(92,45,20,.22), 0 24px 40px -24px rgba(0,0,0,.7); padding:var(--s6) var(--s6) var(--s7); gap:var(--s2)}
.dropzone:hover, .dropzone.over{background:linear-gradient(180deg,#f0954a,#d06c2c)}
.dropzone .dz-ico{display:none}
.dropzone .dz-ranura{display:block; width:min(420px,78%); height:14px; border-radius:99px; background:#332016; box-shadow:inset 0 3px 4px rgba(0,0,0,.4); margin:0 auto var(--s4)}
.dropzone .dz-title{font-family:var(--display); font-size:var(--t-xl); font-weight:600; color:#24160d}
.dropzone .dz-sub{color:#4a2a14; opacity:.85}
body.theme-paper .dropzone{box-shadow:inset 0 -10px 0 rgba(92,45,20,.22), 0 24px 40px -24px rgba(60,35,15,.5)}
/* actividad por madurez */
#activityBlock[hidden]{display:none}
.act-linea{color:var(--ink-2); font-size:var(--t-sm); margin:0 0 var(--s5)}
/* HUD legible */
#hud{color:var(--ink-2)}
#hud .hud-main b{color:var(--ink)}
#activityBlock.sin-cifras #activityCards{display:none}
#activityBlock.sin-mapa #heatmap{display:none}

/* el estado «pulsado / con el puntero encima» del acento se deriva del
   propio acento, para cualquier color elegido: más claro de noche, más
   oscuro de día (antes era un naranja fijo) */
body.theme-night{--accent-2:color-mix(in srgb, var(--accent) 82%, #fff)}
body.theme-paper{--accent-2:color-mix(in srgb, var(--accent) 84%, #000)}

/* invitación al PDF propio, en el resumen de tramo */
.tf-propio{display:inline-flex; align-items:center; gap:var(--s3); margin-left:var(--s4); color:var(--ink)}
.btn-sm{padding:5px 12px; font-size:var(--t-sm)}

/* elección de longitud: antes de empezar (ficha, continuar) y para el siguiente tramo (resumen) */
.longitud-eleccion{display:flex; gap:var(--s2); margin:var(--s3) 0 var(--s4); flex-wrap:wrap}
.longitud-eleccion button{display:flex; flex-direction:column; align-items:flex-start; gap:2px; min-width:140px; padding:8px 12px; border:1px solid var(--line-2); border-radius:6px; background:var(--surface); color:var(--ink-2); cursor:pointer; text-align:left; font:inherit}
.longitud-eleccion button b{color:var(--ink); font-weight:600}
.longitud-eleccion button span{font-size:var(--t-xs); color:var(--ink-3)}
.longitud-eleccion button.on{border-color:var(--accent); box-shadow:inset 0 0 0 1px var(--accent)}
.longitud-eleccion button.on b{color:var(--accent)}
.longitud-eleccion button:focus-visible{outline:2px solid var(--accent); outline-offset:2px}
.tf-longitud{display:inline-flex; align-items:center; gap:var(--s1); margin-left:var(--s4); color:var(--ink-3); font-size:var(--t-sm)}
.tf-longitud button{border:1px solid var(--line-2); background:transparent; color:var(--ink-2); border-radius:6px; padding:3px 8px; font:inherit; font-size:var(--t-xs); cursor:pointer}
.tf-longitud button.on{border-color:var(--accent); color:var(--accent)}

/* ═══ revisión de diseño (r2): sistema ═══════════════════════════════
   Escala menos saltarina, radios menos «card UI», medidas separadas para
   app, panel y lector. Tema papel con más contraste en lo secundario. */
:root{
  --t-xs:11px; --t-sm:12px; --t-md:14px; --t-lg:16px;
  --t-xl:22px; --t-2xl:32px; --t-3xl:44px; --t-4xl:56px;
  --s8:72px; --s9:104px;
  --r1:6px; --r2:8px; --r3:12px; --r4:16px;
  --reader-measure:1240px; --panel-measure:720px;
}
body.theme-paper{--ink-2:#5f5549; --ink-3:#837767; --line:#d3c5b2; --line-2:#b8a992}
body.theme-paper .resume-card{border-radius:10px; box-shadow:0 18px 42px -34px rgba(55,35,18,.45); background:#fbf7ef}

/* primera visita: un control, no un cartel */
.first-run{place-items:start center; min-height:auto; padding-top:112px}
.fr-inner{width:min(620px,100%)}
.first-run .display{font-size:44px; line-height:1.04; margin-bottom:28px}
.dropzone{min-height:164px; border-radius:14px 14px 22px 22px; padding:28px 32px 34px}
.dropzone .dz-ranura{height:10px; width:min(360px,72%); margin-bottom:22px}
.dropzone .dz-title{font-size:26px}
.dropzone .dz-sub{font-size:14px}

/* volver: tablero de continuación (portada · texto · acciones), la tarea con regla de acento */
.resume-card{display:grid; grid-template-columns:104px minmax(0,1fr) 220px; align-items:center; gap:var(--s5) var(--s6); padding:28px 32px; border-radius:10px}
.resume-cover{width:104px}
.resume-body{grid-column:2}
.resume-actions{grid-column:3; grid-row:1; flex-direction:column; align-items:stretch; margin-top:0}
.resume-actions .btn{justify-content:center}
.resume-tarea{border-top:2px solid var(--accent); padding-top:10px; margin-top:var(--s3); color:var(--ink)}
/* en la tarjeta de continuación las acciones van en su propia columna, así que
   la elección de longitud no necesita margen inferior; en la ficha del libro el
   botón va DEBAJO y ese margen es lo que los separa (no quitarlo en global) */
.resume-card .longitud-eleccion{margin:14px 0 0}
.longitud-eleccion button{min-width:112px; padding:8px 10px}
@media (max-width:820px){ .resume-card{grid-template-columns:88px minmax(0,1fr)} .resume-actions{grid-column:1/-1; grid-row:auto; flex-direction:row} }

/* muestras al volver: título primero, portada legible; seis a la vista */
.demo-block .demo-row{display:grid; grid-template-columns:repeat(3,1fr); gap:0 24px}
.demo-block .demo-row:not(.abierta) .demo-card:nth-child(n+5){display:flex}
.demo-block .demo-row:not(.abierta) .demo-card:nth-child(n+7){display:none}
.demo-card{min-height:92px; padding:14px 10px 14px 0; flex-basis:auto; border-top-color:var(--line)}
.demo-card img{width:54px; height:76px}
.demo-card b{font-size:14px}

/* ficha: menos aire arriba, mapa del libro como navegación, cifras con prioridad.
   Acotado a #book a propósito: sin acotar, esta rejilla de ancho completo
   se llevaba por delante el mapa pequeño de la hoja de resultados. */
.book-hero{margin-bottom:40px; padding-top:32px}
#book .pagemap{width:100%; display:grid; grid-template-columns:repeat(auto-fill,minmax(12px,1fr)); gap:4px; padding:18px}
#book .pm-cell{width:auto; height:20px}
.stat-row{grid-template-columns:1.2fr 1.2fr 1fr 1fr}
.stat{padding:18px 20px}
.stat b{font-size:32px}
.stat:first-child b,.stat:nth-child(2) b{font-size:38px}

/* lector: HUD que se lee, cursor fino, barra con grupos */
#hud{height:72px; padding:0 28px 14px; background:linear-gradient(to top,var(--bg) 0%,color-mix(in srgb,var(--bg) 92%,transparent) 52%,transparent)}
.hud-main b{font-size:24px}
.hud-sub{font-size:13px; gap:18px}
#caret{width:1.5px; box-shadow:0 0 2px color-mix(in srgb,var(--ink-ok) 70%,transparent)}
body.grabando #caret{width:2px}
.reader-bar{height:48px; background:color-mix(in srgb,var(--surface) 96%,transparent); border-bottom-color:var(--line)}
.rb-right{gap:4px}
.rule{margin:0 10px; background:var(--line-2)}
.reader-bar .btn-icon{width:30px; height:30px}

/* resumen de tramo: bandeja discreta abajo a la derecha, nunca sobre el centro */
.tramo-fin{left:auto; right:24px; bottom:24px; transform:none; max-width:420px; justify-content:flex-start; padding:12px 14px; border-radius:8px; gap:6px 14px}
.tramo-fin .tf-salto{display:none}
.tramo-fin .tf-detalle{flex-basis:100%}
.tramo-fin .tf-longitud{flex-basis:100%; margin-left:0; padding-top:8px; border-top:1px solid var(--line)}
.tramo-fin .tf-propio{flex-basis:100%; margin-left:0; padding-top:8px; border-top:1px solid var(--line)}
.tramo-fin .tf-sigue{display:block; flex-basis:100%}
@media (max-width:640px){ .tramo-fin{left:12px; right:12px; bottom:12px; max-width:none} }

/* hojas: panel de 620/720, no un tablero encima del PDF */
.sheet{align-items:center; background:rgba(20,18,16,.72); backdrop-filter:blur(8px)}
.sheet-inner{border-radius:16px; border:1px solid var(--line-2); width:min(620px,calc(100% - 32px)); max-height:88vh; padding:28px}
.sheet-wide{width:min(720px,calc(100% - 32px))}
.res-headline{grid-template-columns:1fr 1fr; margin-bottom:20px}
.metric-lg b{font-size:44px}
.res-lecciones{margin-top:20px; padding-top:16px}
.lec{padding:10px 0}

/* Premium: lista con etiqueta y detalle, planes con cuerpo */
.premium-lista li{display:grid; grid-template-columns:150px 1fr; gap:16px; padding:14px 0}
.premium-lista b{margin-bottom:0}
.premium-nota{font-size:13px; line-height:1.45; margin-bottom:18px}
.premium-plan{gap:12px}
.premium-plan button{padding:16px; min-height:86px}
#premium .sheet-actions{margin-top:18px}

/* móvil: cabecera compacta, ranura usable, muestras como lista */
@media (max-width:640px){
  .app-bar{height:48px; padding:0 16px}
  .brand{font-size:15px}
  .btn-ghost{font-size:13px; padding:6px 8px}
  .first-run{padding-top:36px}
  .first-run .display{font-size:38px; line-height:1.04}
  .dropzone{min-height:190px; padding:24px 22px 30px; border-radius:18px}
  .demo{margin-top:48px}
  .demo-block .demo-row{grid-template-columns:1fr}
  .demo-card{min-height:112px; padding:16px 0; gap:16px}
  .demo-card img{width:52px; height:74px}
  .demo-card .demo-lang{font-size:12px; margin-left:8px}
}

/* r3: tablero de continuación: acciones en su propia columna, apiladas */
.resume-card{grid-template-columns:104px minmax(0,1fr)}
.resume-body{display:grid; grid-template-columns:minmax(0,1fr) 220px; column-gap:32px; align-items:start}
.resume-body > *{grid-column:1}
.resume-body .resume-actions{grid-column:2; grid-row:1 / span 7; align-self:center; display:flex; flex-direction:column; gap:var(--s2)}
.resume-body .resume-title{white-space:normal}
@media (max-width:820px){ .resume-body{grid-template-columns:1fr} .resume-body .resume-actions{grid-column:1; grid-row:auto; flex-direction:row} }

/* r3: en el teléfono el HUD sigue encogiéndose (la regla r2 le había fijado 72 px) */
@media (max-width:640px){ #hud{height:auto; padding-bottom:6px} }

/* ═══ revisión de diseño (r4): el color de la interfaz no es el de las letras ═══
   El naranja queda para lo tecleado y la marca; la interfaz activa (CTA,
   selección, progreso) usa un verde salvia apagado. El ajuste «Acento» solo
   cambia el color de las letras acertadas. */
body.theme-night, body.theme-night:is(.acento-cian,.acento-violeta,.acento-verde,.acento-rosa){--accent:#8fa58f; --accent-2:#b3c7b1; --accent-wash:rgba(143,165,143,.14)}
body.theme-paper, body.theme-paper:is(.acento-cian,.acento-violeta,.acento-verde,.acento-rosa){--accent:#5f7150; --accent-2:#7a8d69; --accent-wash:rgba(95,113,80,.12)}
body.theme-night .brand-mark, body.theme-night .brand em{color:#e0873f}
body.theme-paper .brand-mark, body.theme-paper .brand em{color:#c64800}
.btn-primary{color:#f4f1ea}
body.theme-paper .btn-primary{color:#fbf7ef}

/* r4: primera visita móvil compacta */
@media (max-width:640px){
  .first-run{padding-top:24px}
  .first-run .display{font-size:32px; line-height:1.03; max-width:11ch; margin:48px auto 20px}
  .dropzone{min-height:156px; padding:20px 20px 24px; border-radius:16px}
  .dropzone .dz-ranura{height:8px; width:min(300px,68%); margin-bottom:16px}
  .dropzone .dz-title{font-size:22px}
  .dropzone .dz-sub{font-size:13px}
}

/* r4: el aviso flotante fuera del centro visual */
.toast{left:auto; right:24px; top:64px; transform:none; max-width:360px; padding:8px 12px; border-radius:8px}
@media (max-width:640px){ .toast{left:12px; right:12px; top:auto; bottom:12px; max-width:none} }

/* r4: el resumen de página da más peso a lo que enseña */
.res-lecciones{margin-top:12px; padding:14px 0 0; border-top:1px solid var(--line-2); color:var(--ink-2)}
.metric-lg b{font-size:40px}
.metric-grid .metric b{font-size:18px}

/* r5: el botón principal en noche lleva tinta oscura sobre salvia claro (contraste 7:1) */
body.theme-night .btn-primary{color:#141210}
body.theme-night .btn-primary kbd{background:rgba(0,0,0,.12); border-color:rgba(0,0,0,.18)}
body.theme-night .btn-primary:hover{background:var(--accent-2); border-color:var(--accent-2)}

/* r6: tres detalles finales del juez */
.res-lecciones{padding-top:24px; font-size:15px}
.res-lecciones .lec b, .res-lecciones .lec span{font-size:15px}
@media (max-width:640px){ .first-run .display{font-size:clamp(42px,11vw,56px); line-height:.94; max-width:none} }
.tramo-fin{background:rgba(29,26,23,.92); border-color:rgba(239,232,220,.16)}
body.theme-paper .tramo-fin{background:rgba(250,247,241,.94); border-color:rgba(60,45,30,.18)}

/* ═══ identidad 2 · cian, marino, Manrope ═════════════════════════════
   Color principal: el cian de la referencia (#11C6DA). Tinta azul marino.
   Fondos fríos y limpios, sin grano. Una sola familia (Manrope) para
   todo; peso 800 para titulares, 500–600 para interfaz. */
:root{
  --sans:"Manrope",ui-sans-serif,-apple-system,"Segoe UI",Roboto,sans-serif;
  --display:"Manrope",ui-sans-serif,-apple-system,"Segoe UI",Roboto,sans-serif;
  --r1:10px; --r2:12px; --r3:16px; --r4:20px;
}
body{font-family:var(--sans); font-weight:500}
.display, .hero-title, .resume-title, #resTitle, .sheet-head h2{font-family:var(--display); font-weight:800; letter-spacing:-.025em}
h2,h3{font-weight:700}
.brand span{font-family:var(--display); font-weight:800; letter-spacing:-.02em}
b,strong{font-weight:700}

body.theme-night, body.theme-night:is(.acento-cian,.acento-violeta,.acento-verde,.acento-rosa,.acento-naranja){
  --bg:#0C1220; --bg-2:#101828;
  --surface:#141C2C; --surface-2:#1A2436; --surface-3:#223047;
  --line:#233149; --line-2:#33445F;
  --ink:#EEF3F8; --ink-2:#A8B4C6; --ink-3:#7A889C;
  --accent:#11C6DA; --accent-2:#3FDCEC; --accent-wash:rgba(17,198,218,.14);
  --good:#2FD59C; --bad:#FF5A6A;
  --shadow-1:0 1px 2px rgba(0,0,0,.35); --shadow-2:0 10px 30px rgba(0,0,0,.35); --shadow-3:0 24px 60px rgba(0,0,0,.5);
  --shadow-paper:0 1px 0 rgba(255,255,255,.04) inset, 0 24px 60px -42px rgba(0,0,0,.7);
  --paper-dim:rgba(120,140,170,.14);
}
body.theme-paper, body.theme-paper:is(.acento-cian,.acento-violeta,.acento-verde,.acento-rosa,.acento-naranja){
  --bg:#F5F8FA; --bg-2:#EDF2F5;
  --surface:#FFFFFF; --surface-2:#F2F6F9; --surface-3:#E7EDF2;
  --line:#E1E8EE; --line-2:#C9D4DE;
  --ink:#0C1424; --ink-2:#4B5870; --ink-3:#7E8A9C;
  --accent:#11C6DA; --accent-2:#0FB4C7; --accent-wash:rgba(17,198,218,.12);
  --good:#1FB981; --bad:#E23D52;
  --shadow-1:0 1px 2px rgba(12,20,36,.06); --shadow-2:0 10px 30px rgba(12,20,36,.08); --shadow-3:0 24px 60px rgba(12,20,36,.14);
  --shadow-paper:0 1px 0 rgba(255,255,255,.6) inset, 0 20px 50px -34px rgba(12,20,36,.25);
  background-image:none !important;
}
/* letras tecleadas: cian-verdoso legible sobre la hoja blanca (4,5:1); el
   naranja queda como opción, no como valor por defecto */
body.theme-night, body.theme-paper, body.theme-night.acento-cian, body.theme-paper.acento-cian{
  --ink-ok:#0895A8; --ink-bad:#E11D3A; --ink-missed:#B54255;
  --hl-ok:#A6EEF6; --hl-bad:#FFB3BC; --hl-missed:#E23D52;
}
body.theme-night.acento-naranja, body.theme-paper.acento-naranja{--ink-ok:#E8720C; --ink-bad:#E11D3A; --ink-missed:#B8503A; --hl-ok:#FFD08A}
body.theme-night .brand-mark, body.theme-night .brand em, body.theme-paper .brand-mark, body.theme-paper .brand em{color:var(--accent)}
.brand em{color:var(--accent)}

/* botones: cian con tinta marino (contraste 9:1), esquinas de 12 px */
.btn{border-radius:var(--r2); font-weight:600}
.btn-lg{border-radius:var(--r2)}
.btn-primary, body.theme-night .btn-primary, body.theme-paper .btn-primary{background:var(--accent); border-color:var(--accent); color:#0C1424}
.btn-primary:hover, body.theme-night .btn-primary:hover{background:var(--accent-2); border-color:var(--accent-2); color:#0C1424}
.btn-primary kbd, body.theme-night .btn-primary kbd{background:rgba(12,20,36,.12); border-color:rgba(12,20,36,.18); color:#0C1424}
.btn-primary .ico{color:#0C1424}

/* la ranura de la primera visita: tostadora cian */
.dropzone, .dropzone:hover, .dropzone.over{background:linear-gradient(180deg,#2ADAEC,#0FB4C7); border-color:transparent; border-radius:18px 18px 26px 26px}
.dropzone:hover, .dropzone.over{background:linear-gradient(180deg,#45E2F1,#14BFD3)}
.dropzone .dz-ranura{background:#0C1424; box-shadow:inset 0 3px 4px rgba(0,0,0,.45)}
.dropzone .dz-title{color:#0C1424; font-weight:800; letter-spacing:-.02em}
.dropzone .dz-sub{color:rgba(12,20,36,.75)}
.dropzone .dz-ico{color:#0C1424}

/* tarjetas y paneles: blancos, esquinas de 16, sombra suave */
.resume-card, body.theme-paper .resume-card{border-radius:var(--r3); background:var(--surface); border:1px solid var(--line); box-shadow:var(--shadow-paper)}
.sheet-inner{border-radius:var(--r4)}
.ctx-block, .premium-plan button, .longitud-eleccion button{border-radius:var(--r2)}
.tramo-fin, body.theme-paper .tramo-fin{border-radius:var(--r2)}
body.theme-night .tramo-fin{background:rgba(20,28,44,.94); border-color:rgba(238,243,248,.14)}
body.theme-paper .tramo-fin{background:rgba(255,255,255,.96); border-color:var(--line-2)}
.toast{background:var(--ink); color:var(--bg); border-radius:10px; font-weight:600}
.fila-aviso .ico{color:var(--accent)}
.resume-tarea{border-top-color:var(--accent)}
.lec-tarea b{color:var(--accent-2)}
body.theme-night .lec-tarea b{color:var(--accent)}
.premium-plan button[aria-checked="true"]{border-color:var(--accent); background:var(--accent-wash)}
.premium-plan button[aria-checked="true"] b, .premium-plan button[aria-checked="true"]{color:var(--ink)}
.longitud-eleccion button.on, .longitud-eleccion button[aria-checked="true"]{border-color:var(--accent); background:var(--accent-wash); color:var(--ink)}
.tf-longitud button.on{border-color:var(--accent); color:var(--accent)}
.metric-lg b, .stat.accent b{color:var(--accent)}
body.theme-paper .metric-lg b, body.theme-paper .stat.accent b{color:#0895A8}
.hud-main b{color:var(--ink)}

/* ═══ identidad 2 · afinado (juez r4) ═══════════════════════════════ */
/* texto tecleado con contraste AA sobre la hoja (4,9:1) */
body.theme-paper, body.theme-night, body.theme-paper.acento-cian, body.theme-night.acento-cian{--ink-ok:#067B8C; --hl-ok:#A6EEF6}
/* el cian principal es plano, como en la referencia; la profundidad va en la sombra */
.dropzone, .dropzone:hover, .dropzone.over{background:#11C6DA; box-shadow:0 28px 56px -28px rgba(12,20,36,.42), inset 0 -8px 0 rgba(12,20,36,.14); transition:transform 140ms cubic-bezier(.22,.9,.3,1), box-shadow 140ms}
.dropzone.over{transform:translateY(-2px) scale(1.01); box-shadow:0 34px 70px -30px rgba(12,20,36,.45), inset 0 -8px 0 rgba(12,20,36,.14)}
/* marca: baldosa cian con la tostadora en blanco; el nombre en tinta */
.brand-mark, body.theme-night .brand-mark, body.theme-paper .brand-mark{width:26px; height:26px; padding:4px; border-radius:7px; background:#11C6DA; color:#fff; stroke-width:2}
.brand em, body.theme-night .brand em, body.theme-paper .brand em{color:var(--ink)}
/* jerarquía: sin tracking negativo; listas en 700, no 800 */
.display, .hero-title, .resume-title, #resTitle, .sheet-head h2, .brand span, .block-head h2{letter-spacing:0}
.demo-card b, .book-name, .resume-title{font-weight:700}
/* botones: alturas fijas y microinteracción por profundidad */
.btn{min-height:40px; padding-top:0; padding-bottom:0; transition:transform 140ms cubic-bezier(.22,.9,.3,1), background 140ms, border-color 140ms, box-shadow 140ms}
.btn-lg{min-height:48px; padding-left:20px; padding-right:20px}
.btn-sm{min-height:32px}
.btn:hover{transform:translateY(-1px)}
.btn:active{transform:translateY(1px)}
.book-card:hover .book-cover, .resume-cover:hover{transform:scale(1.015)}
.book-card .book-cover, .resume-cover{transition:transform 140ms cubic-bezier(.22,.9,.3,1), box-shadow 140ms}
/* aviso flotante en la retícula; en papel es una tarjeta blanca */
.toast{top:72px; right:24px; border-radius:12px; padding:10px 14px}
body.theme-paper .toast{background:#fff; color:#0C1424; border:1px solid var(--line); box-shadow:0 18px 45px rgba(12,20,36,.12)}
/* filas de aviso (instalar, Premium): tarjeta con un velo cian, no un anuncio injertado */
.fila-aviso{padding:14px 16px; border:1px solid var(--line); border-radius:16px; background:color-mix(in srgb,var(--surface) 88%,var(--accent) 12%)}
.fila-aviso b{font-weight:700}
/* primera visita: centro óptico, no centro absoluto */
.first-run{padding-top:72px; align-items:start}
.first-run .display{margin-bottom:24px}

/* identidad 2: la baldosa de marca en marino, como en las páginas públicas */
.brand-mark, body.theme-paper .brand-mark{background:#0C1424; color:#fff}
body.theme-night .brand-mark{background:#11C6DA; color:#0C1424}

/* ═══ la bienvenida y el inicio: lo tuyo primero ═══════════════════
   El PDF propio es la puerta del producto; las muestras son un apaño
   para quien no tiene uno a mano. El tamaño lo dice sin escribirlo. */
.fr-sub{font-size:var(--t-md); line-height:1.6; color:var(--ink-2); max-width:44ch; margin:0 auto 28px}
#firstRun .demo-head, #firstRun .demo-row{justify-content:center}
.demo-menor{margin-top:40px}
.demo-menor .demo-head h2{font-size:var(--t-sm); font-weight:550; color:var(--ink-2); letter-spacing:0}
/* la estantería propia lleva su propio sitio donde soltar, discreto */
.dropzone-corta{display:flex; align-items:center; justify-content:center; gap:8px;
  padding:14px; margin-top:14px; font-size:var(--t-sm); color:var(--ink-3);
  border-radius:12px; border:1.5px dashed var(--line-2); background:none}
.dropzone-corta .ico{width:16px; height:16px}
.dropzone-corta:hover, .dropzone-corta.over{color:var(--ink-2); background:var(--surface)}
#tusLibros .block-head .btn{flex:0 0 auto}
/* cuatro muestras a la vista: el catálogo dejó de ser el centro */
.demo-block .demo-row:not(.abierta) .demo-card:nth-child(n+5){display:none}

/* ═══ soltar un PDF: el gesto principal, sin disfraz ════════════════
   Era una losa de esmalte cian que gritaba más que la propia página, y
   el cian dejaba de significar nada. Ahora es lo que es: un sitio donde
   soltar, con la piel del lector. El acento vuelve a aparecer sólo
   donde hay que mirar: al arrastrar encima. */
.dropzone, .dropzone:hover, .dropzone.over{
  background:var(--surface); border:1.5px dashed var(--line-2); border-radius:16px;
  box-shadow:none; color:var(--ink); min-height:0; padding:44px 32px;
  transform:none; transition:border-color 140ms, background 140ms, color 140ms;
}
body.theme-paper .dropzone{box-shadow:none}
.dropzone:hover{background:var(--surface-2); border-color:var(--ink-3)}
.dropzone.over{background:var(--surface-2); border-color:var(--accent)}
.dropzone .dz-ranura{display:none}
.dropzone .dz-ico{display:block; width:22px; height:22px; color:var(--ink-3); margin:0 auto 10px}
.dropzone:hover .dz-ico{color:var(--ink-2)}
.dropzone.over .dz-ico{color:var(--accent)}
.dropzone .dz-title{font-family:inherit; font-size:20px; font-weight:700; color:var(--ink); letter-spacing:-.01em}
.dropzone .dz-sub{font-size:13px; color:var(--ink-3)}
/* la de la estantería: la misma idea, en pequeño */
.dropzone-corta, .dropzone-corta:hover, .dropzone-corta.over{
  display:flex; align-items:center; justify-content:center; gap:8px;
  padding:16px; min-height:0; border-radius:12px; font-size:var(--t-sm); color:var(--ink-3); background:none;
}
.dropzone-corta:hover{background:var(--surface); color:var(--ink-2)}
.dropzone-corta.over{background:var(--surface); color:var(--ink-2); border-color:var(--accent)}
.dropzone-corta .ico{width:16px; height:16px}
@media (max-width:620px){
  .dropzone, .dropzone:hover, .dropzone.over{padding:32px 20px}
  .dropzone .dz-title{font-size:18px}
}

/* Con un solo libro, el de «Continuar» ya está arriba: la estantería vacía
   no aporta nada y se retira, pero la zona de soltar se queda. */
#tusLibros.sin-otros #shelf{display:none}
#tusLibros.sin-otros .dropzone-corta{margin-top:0}

/* ── qué cierra el tramo: palabras o tiempo ─────────────────────────
   Va pegado a los valores que cambia, no en Ajustes: escondido allí, el
   modo existía sobre el papel y no en la práctica. */
.medida-eleccion{display:inline-flex; gap:2px; padding:2px; margin:0 8px 0 6px;
  border:1px solid var(--line); border-radius:999px; background:var(--surface); vertical-align:middle}
.medida-eleccion button{appearance:none; border:0; background:none; cursor:pointer; font:inherit;
  font-size:var(--t-xs); color:var(--ink-3); padding:3px 10px; border-radius:999px; line-height:1.4;
  transition:background 140ms, color 140ms}
.medida-eleccion button:hover{color:var(--ink-2)}
.medida-eleccion button.on{background:var(--accent-wash); color:var(--accent); font-weight:600}
.medida-eleccion button:focus-visible{outline:2px solid var(--accent); outline-offset:1px}
/* en la tarjeta de continuar y en la ficha va sobre su propia línea, y sin
   estirarse: dentro de una columna flexible, un inline-flex se ensancha */
.longitud-eleccion{margin-top:8px}
.resume .medida-eleccion, .book-hero .medida-eleccion{margin:14px 0 0; align-self:flex-start; width:fit-content}

/* el hueco de la pausa entre pruebas: cabe en el panel sin empujarlo */
.hueco-tramo{margin:10px 0 0; padding-top:10px; border-top:1px solid var(--line)}
.hueco-tramo .anuncio{gap:10px}

/* ── el estado de la prueba ────────────────────────────────────────
   Grande, en el acento y encima del texto, como en Monkeytype: es lo
   único que se mira de reojo mientras se teclea. Se aparta cuando la
   barra está a la vista para no chocar con ella. */
.prueba-estado{
  position:absolute; top:76px; left:50%; transform:translateX(-50%);
  z-index:30; pointer-events:none;
  font-size:30px; font-weight:600; letter-spacing:-.02em; line-height:1;
  font-variant-numeric:tabular-nums; color:var(--accent);
  transition:opacity var(--t-base), transform var(--t-base);
}
.prueba-estado .pe-de{opacity:.45; font-size:.62em; font-weight:550}
body:not(.escribiendo) .prueba-estado{opacity:.55}
/* con la barra visible, el contador baja para no solaparse */
#topbar:not(.hidden) ~ #stage .prueba-estado{transform:translateX(-50%) translateY(6px)}
@media (max-width:820px){ .prueba-estado{font-size:24px; top:70px} }

/* el selector dentro del resumen de prueba: es lo que decide la siguiente */
.res-longitud{margin-top:var(--s4); padding-top:var(--s4); border-top:1px solid var(--line)}
.res-longitud .medida-eleccion{margin:0 0 10px}
.res-longitud .longitud-eleccion{margin:0; flex-wrap:wrap}

/* Con el selector dentro, la hoja de resultados creció y los botones se
   salían de la pantalla. El pie se queda pegado abajo: la salida principal
   siempre a mano, sin buscarla. */
.sheet-actions{position:sticky; bottom:calc(var(--s5) * -1); z-index:2;
  background:linear-gradient(to top, var(--surface) 62%, transparent);
  padding-top:14px; margin-top:var(--s4)}

/* ═══ movimiento ═══════════════════════════════════════════════════
   Sólo transform, opacity y scale. Todo cae bajo la regla global de
   prefers-reduced-motion. Ver r25-movimiento en el diario. */
@keyframes subir{from{opacity:0; transform:translateY(10px)}}
@keyframes aparecer{from{opacity:0}}
@keyframes pop{0%{opacity:0; transform:scale(.6)} 60%{transform:scale(1.08)} 100%{opacity:1; transform:scale(1)}}
@keyframes tic{35%{scale:1.12}}
@keyframes latido{0%,100%{scale:1} 50%{scale:1.07}}
@keyframes brillo{30%{text-shadow:0 0 24px color-mix(in srgb,var(--accent) 75%,transparent)}}
@keyframes desvanecer{to{opacity:0}}
@keyframes bajar{to{transform:translateY(14px); opacity:0}}
@keyframes tostar{
  0%{box-shadow:inset 0 3px 4px rgba(0,0,0,.45)}
  40%{box-shadow:inset 0 3px 4px rgba(0,0,0,.45), inset 0 0 22px 6px #ff9a3c}
  100%{box-shadow:inset 0 3px 4px rgba(0,0,0,.45)}
}

/* el contador de la prueba */
.prueba-estado.tic{animation:tic 200ms var(--ease)}
.prueba-estado.apremia{color:var(--bad); animation:latido 1s ease-in-out infinite}

/* el resumen: entra por bloques, las cifras suben, el premio salta */
#results .sheet-inner > *{animation:subir 380ms var(--ease) both}
#results .sheet-inner > :nth-child(2){animation-delay:40ms}
#results .sheet-inner > :nth-child(3){animation-delay:80ms}
#results .sheet-inner > :nth-child(4){animation-delay:120ms}
#results .sheet-inner > :nth-child(5){animation-delay:160ms}
#results .sheet-inner > :nth-child(6){animation-delay:200ms}
#results .sheet-inner > :nth-child(7){animation-delay:240ms}
#results .sheet-inner > :nth-child(8){animation-delay:270ms}
#results .sheet-inner > :nth-child(n+9){animation-delay:300ms}
#resAccDelta.up{animation:pop 420ms var(--ease) 420ms both}
#results.record #resWpm{animation:brillo 1.1s ease-out 500ms}

/* salir con un fundido, no desaparecer */
.sheet.saliendo{animation:desvanecer 150ms ease both}
.sheet.saliendo .sheet-inner{animation:bajar 150ms ease both}
.toast.saliendo{animation:desvanecer 200ms ease both}

/* inicio: listas escalonadas, la flecha que se adelanta, la tostadora */
.resume-card{animation:subir 380ms var(--ease) both}
.demo-card, .book-card{animation:subir 360ms var(--ease) both}
.demo-card:nth-child(2), .book-card:nth-child(2){animation-delay:40ms}
.demo-card:nth-child(3), .book-card:nth-child(3){animation-delay:80ms}
.demo-card:nth-child(4), .book-card:nth-child(4){animation-delay:120ms}
.demo-card:nth-child(5), .book-card:nth-child(5){animation-delay:160ms}
.demo-card:nth-child(6), .book-card:nth-child(6){animation-delay:200ms}
.demo-card:nth-child(n+7), .book-card:nth-child(n+7){animation-delay:240ms}
.btn .ico{transition:transform var(--t-fast) var(--ease)}
#resumeGo:hover .ico, #resumeGo:focus-visible .ico{transform:translateX(3px)}
.dropzone{transition:transform var(--t-base) var(--ease), background var(--t-base), border-color var(--t-base), box-shadow var(--t-base)}
.dropzone.over{transform:scale(1.012)}
.dropzone .dz-ranura{transition:box-shadow var(--t-base)}
.dropzone.over .dz-ranura{box-shadow:inset 0 3px 4px rgba(0,0,0,.45), 0 0 0 3px rgba(255,255,255,.35)}
.dropzone.tostando .dz-ranura{animation:tostar 900ms ease-out}

/* ficha y ajustes */
.pagemap .pm-cell:not(.just){animation:aparecer 240ms ease both; animation-delay:calc(min(var(--i,0),90) * 3ms)}
.longitud-eleccion button{transition:border-color var(--t-fast), box-shadow var(--t-fast), background var(--t-fast), transform var(--t-fast)}
.longitud-eleccion button:active, .seg button:active, .medida-eleccion button:active{transform:scale(.97)}
.swatch.on i{animation:pop 320ms var(--ease)}
body{transition:background-color var(--t-slow), color var(--t-slow)}

/* móvil: la tarjeta de continuación en una columna. Con la portada a la
   izquierda quedaban 250 px para título, elección y botones, y el botón
   principal se partía en cuatro líneas. */
@media (max-width:640px){
  .resume-card{grid-template-columns:1fr; padding:20px 18px; gap:var(--s4)}
  .resume-cover{width:84px; grid-column:1}
  .resume-body{grid-column:1}
  .resume-body .resume-actions{flex-direction:column; align-items:stretch}
  .resume-body .resume-actions .btn{justify-content:center}
  .resume-card .longitud-eleccion button{min-width:0; flex:1 1 44%}
}

/* ── reconocimiento de texto (páginas escaneadas) ───────────────────
   La barra vive dentro del cartel «sin texto»: mientras se lee la
   página dice cuánto falta; sin cifra, va y viene. */
.ocr-barra{height:4px; border-radius:2px; background:var(--surface-3); margin-top:10px; overflow:hidden; position:relative}
.ocr-barra i{display:block; height:100%; width:0; background:var(--accent); border-radius:2px; transition:width .25s linear}
.ocr-barra.indeterminada i{width:34%; animation:ocrVaiven 1.1s ease-in-out infinite alternate}
@keyframes ocrVaiven{from{transform:translateX(0)} to{transform:translateX(194%)}}
@media (prefers-reduced-motion:reduce){ .ocr-barra.indeterminada i{animation:none; width:100%; opacity:.5} }

/* ── ficha: nombre y portada editables ─────────────────────────────
   La caja de portada toma la proporción real de la imagen (inline, desde
   coverW/coverH): nada de recortes. La portada es pulsable y lo dice al
   pasar por encima; el título se edita en su sitio. */
/* la ficha es un flex con align-items:stretch: sin esto la caja se estira a
   la altura del cuerpo y la proporción declarada no cuenta */
.hero-cover{cursor:pointer; align-self:flex-start}
.hero-cover .hero-cover-cambiar{
  position:absolute; left:0; right:0; bottom:0; z-index:2; padding:8px 6px;
  font-size:var(--t-xs); font-weight:600; text-align:center; color:#fff;
  background:linear-gradient(180deg,transparent,rgba(0,0,0,.72));
  opacity:0; transition:opacity var(--t-fast); pointer-events:none;
}
.hero-cover:hover .hero-cover-cambiar, .hero-cover:focus-visible .hero-cover-cambiar{opacity:1}
.hero-cover:focus-visible{outline:2px solid var(--accent); outline-offset:3px}
.hero-edit{display:flex; gap:var(--s2); flex-wrap:wrap; margin:-6px 0 var(--s4)}
.hero-edit .btn-ghost{padding:5px 8px; font-size:var(--t-xs); color:var(--ink-3); gap:5px}
.hero-edit .btn-ghost:hover{color:var(--ink)}
.hero-edit .btn-ghost .ico{width:14px; height:14px}
.hero-title-input{
  font:inherit; font-size:var(--t-2xl); font-weight:600; letter-spacing:-.028em; line-height:1.2;
  width:100%; max-width:36ch; margin-bottom:var(--s2); padding:2px 8px; margin-left:-9px;
  color:var(--ink); background:var(--surface-2); border:1px solid var(--accent); border-radius:6px; outline:none;
}

/* el libro recién elegido en la estantería sube a «Continuar» y lo dice */
.resume-card.recien{animation:recienElegido 700ms var(--ease)}
@keyframes recienElegido{0%{box-shadow:0 0 0 0 var(--accent-wash), var(--shadow-paper); transform:translateY(6px); opacity:.6} 45%{box-shadow:0 0 0 6px var(--accent-wash), var(--shadow-paper)} 100%{box-shadow:0 0 0 0 transparent, var(--shadow-paper); transform:none; opacity:1}}
@media (prefers-reduced-motion:reduce){ .resume-card.recien{animation:none} }

/* la nota breve: los valores («30 s», «1 min») no se parten en dos líneas */
.tf-longitud button{white-space:nowrap}

/* ── la hoja cabe en la pantalla ────────────────────────────────────
   El mapa en miniatura tiene el tamaño de celda que le dice `--pm` (lo
   calcula renderPageMap para que el libro entero quepa en ~100 px), y la
   hoja se compacta por pasos (ajustarHoja) hasta no necesitar scroll. */
.pagemap-mini .pm-cell{width:var(--pm,8px); height:calc(var(--pm,8px) * 1.35)}

.sheet-inner.ajuste-1{padding:18px 24px 16px}
.sheet-inner.ajuste-1 .sheet-head{margin-bottom:10px}
.sheet-inner.ajuste-1 .res-headline{margin-bottom:10px}
.sheet-inner.ajuste-1 .metric-lg{padding-top:8px; padding-bottom:8px}
.sheet-inner.ajuste-1 .metric-lg b{font-size:36px}
.sheet-inner.ajuste-1 .metric-grid .metric{padding-top:6px; padding-bottom:6px}
.sheet-inner.ajuste-1 .res-context{margin-bottom:8px}
.sheet-inner.ajuste-1 .ctx-block{padding:10px 12px}
.sheet-inner.ajuste-1 .ctx-head{margin-bottom:6px}
.sheet-inner.ajuste-1 .ctx-foot{padding-top:6px}
.sheet-inner.ajuste-1 .chart-sm{height:64px}
.sheet-inner.ajuste-1 .res-lecciones{margin-top:8px; padding-top:8px}
.sheet-inner.ajuste-1 .lec{padding:4px 0}
.sheet-inner.ajuste-1 .res-longitud{margin-top:8px; padding-top:8px}
.sheet-inner.ajuste-1 .res-longitud .medida-eleccion{margin-bottom:6px}
.sheet-inner.ajuste-1 .sheet-actions{margin-top:6px; padding-top:8px}

.sheet-inner.ajuste-2 .res-context .pagemap, .sheet-inner.ajuste-2 .res-context .chart{display:none}
.sheet-inner.ajuste-2 .res-context{grid-template-columns:minmax(0,1fr) minmax(0,1fr)}
.sheet-inner.ajuste-2 .ctx-block{min-width:0; flex-direction:row; align-items:baseline; justify-content:flex-start; gap:14px; padding:10px 14px}
.sheet-inner.ajuste-2 .ctx-head{margin:0; gap:8px; flex:0 0 auto; white-space:nowrap}
.sheet-inner.ajuste-2 .ctx-foot{margin:0; padding:0; flex:1; min-width:0; white-space:nowrap; overflow:hidden; text-overflow:ellipsis}
/* se queda la cabecera y la primera lección (la cabecera es el primer hijo) */
.sheet-inner.ajuste-2 .lec:nth-child(n+3){display:none}
.sheet-inner.ajuste-2 .metric-lg b{font-size:32px}

.sheet-inner.ajuste-3 .res-context, .sheet-inner.ajuste-3 .res-lecciones, .sheet-inner.ajuste-3 .hueco{display:none}

/* ── franja de la tienda ────────────────────────────────────────────
   Una línea sobria arriba del todo, con el enlace a la tienda y una
   equis para no volver a verla en un mes. No tapa nada: empuja. */
.franja-tienda{
  display:flex; align-items:center; justify-content:center; gap:10px;
  padding:9px 40px 9px 16px; position:relative;
  background:var(--accent); color:#fff;
  font-size:var(--t-sm); font-weight:550; letter-spacing:-.01em;
}
.franja-tienda a{color:#fff; text-decoration:underline; text-underline-offset:3px}
.franja-tienda .franja-x{
  position:absolute; right:8px; top:50%; transform:translateY(-50%);
  background:none; border:0; color:#fff; font-size:18px; line-height:1;
  padding:4px 8px; cursor:pointer; opacity:.8; border-radius:6px;
}
.franja-tienda .franja-x:hover{opacity:1; background:rgba(0,0,0,.15)}
@media (max-width:640px){ .franja-tienda{font-size:var(--t-xs); padding:8px 36px 8px 12px} }

/* ══ portada de teléfono ═════════════════════════════════
   El dominio es el héroe de esta pantalla: quien llegó aquí no puede
   usar la herramienta todavía, y lo único que hay que conseguir es que
   se lo lleve a su ordenador. Por eso va grande, en la tipografía de la
   página escrita, y con el botón pegado debajo. */
.fr-movil{place-items:start center; min-height:auto; padding:40px 0 56px}
.fr-movil .display{font-size:34px; line-height:1.06; max-width:none; margin:0 auto 16px}
.fr-movil .fr-sub{color:var(--ink-2); line-height:1.6; max-width:34ch; margin:0 auto 32px; font-size:var(--t-md)}

.fm-pase{
  display:grid; justify-items:center; gap:14px;
  padding:24px 20px 20px; border-radius:var(--r3);
  background:var(--surface); border:1px solid var(--line-2);
  box-shadow:var(--shadow-1);
}
.fm-dom{
  font-family:var(--mono); font-size:21px; letter-spacing:-.02em;
  color:var(--ink); word-break:break-all; line-height:1.2;
}
.fm-pase .btn{min-height:46px; padding-inline:26px; font-size:var(--t-lg)}
.fm-pista{font-size:var(--t-sm); color:var(--ink-3); max-width:30ch; text-align:center; line-height:1.45}

.fm-otros{display:grid; gap:10px; justify-items:stretch; margin:24px auto 0; max-width:320px}
.fm-otros .btn{min-height:44px; justify-content:center}
.fm-otros .btn-ghost{min-height:40px; justify-content:center; color:var(--ink-3)}

/* La tienda es lo único que sí se puede usar desde un teléfono, así que
   no se queda de huérfana al pie: va tras una línea que la separa de la
   herramienta, con presencia propia pero sin robarle el sitio al pase. */
.fm-tienda{
  display:inline-flex; align-items:center; gap:var(--s2);
  margin-top:32px; padding:13px 22px;
  border-radius:999px; border:1px solid var(--line-2);
  background:var(--surface); color:var(--ink); text-decoration:none;
  font-size:var(--t-md); font-weight:550;
}
.fm-tienda:hover{border-color:var(--accent); color:var(--accent)}
.fm-otros:has(+ .fm-tienda:not([hidden])){
  padding-bottom:28px; border-bottom:1px solid var(--line);
}

@media (min-width:480px){
  .fr-movil .display{font-size:40px}
  .fm-dom{font-size:25px}
}
