/* Nido — estética One UI (Samsung): tipografía del sistema, esquinas muy
   redondeadas, superficies planas. Acento verde salvia con secundario terracota
   sobre fondos hueso: doméstico y cálido, no de app de productividad. */

:root{
  --salvia:#4A6B57; --salvia-deep:#2E4437; --salvia-soft:#E6EEE8; --salvia-ink:#3A5645;
  /* Terracota y ocre bajados hasta pasar AA sobre las tres superficies claras:
     los de antes se quedaban en 4,43 y 3,00 sobre --surface-2, y ahí van textos
     pequeños (la caducidad de la despensa, las etiquetas). En oscuro no hacía
     falta tocar nada: ahí todos pasan de sobra. Medido, no a ojo. */
  --terracota:#A35736; --terracota-soft:#FBEDE6;
  --ocre:#846823; --ocre-soft:#F7EFD9;
  --pizarra:#3F5A6B; --pizarra-soft:#E5EDF1;
  --bg:#F6F3EE; --surface:#FFFFFF; --surface-2:#F1EDE6;
  /* La bola del interruptor apagado. Va por token porque en claro es blanca
     sobre gris claro y en oscuro tiene que ser **clara sobre oscuro**: con
     `--surface` en los dos, en oscuro la bola (#1F1E18) sobre la pista
     (#292821) era invisible y el interruptor no se veía apagado, se veía roto. */
  --sw-bola:#FFFFFF;
  /* La pista y el pulgar de un segmentado (v2.39). La pista es un punto más
     oscura que `--surface-2` para que se lea como caja sobre el hueso de la
     página, y el pulgar es la superficie de una tarjeta. En oscuro se invierte
     el sentido, como con la bola del interruptor: el pulgar tiene que ser **más
     claro** que la pista, o el activo se hunde en vez de levantarse. */
  --pista:#EBE6DD; --pulgar:#FFFFFF;
  --ink:#1A1C19; --ink-2:#4A4E48; --muted:#6B6D64;
  --line:#E6E1D8; --ok:#3B7A55; --danger:#B3261E; --danger-soft:#FBE7E6;
  --sobre-salvia:#FFFFFF;
  --ui:"SamsungOne","One UI Sans",Roboto,system-ui,-apple-system,"Segoe UI",sans-serif;
  --display:"Fraunces",Georgia,serif;
  --r-xl:28px; --r-l:22px; --r-m:16px; --r-s:12px;
  /* ---- escalas (v2.1) ----
     Antes había veinte tamaños de fuente sueltos, ocho de ellos con medio
     píxel, y ni una escala de espaciado. Un tamaño que no está en esta lista
     es un tamaño que alguien eligió a ojo. */
  --t-xs:11px; --t-s:12px; --t-m:13px; --t-b:14px;
  --t:15px; --t-l:16px; --t-xl:17px; --t-xxl:20px;
  /* Los de titular, que van en Fraunces y tienen su propio ritmo. */
  --d-s:21px; --d-m:24px; --d-l:31px;
  /* ---- la voz de las cifras (v2.2) ----
     Fraunces estaba en nueve reglas y **ninguna era un dato**: los titulares de
     cabecera, de sección, de hoja, de cajón, de pantalla, de fallo, de
     bienvenida, del estado vacío… y una sola de contenido. Una serif de titular
     que solo aparece en las cabeceras es decoración; una que aparece en las
     cifras es una voz.
     `opsz` 14 y no el 40 de los titulares: a 20 px el corte óptico de 40 es
     demasiado y se abre. Y `tabular-nums`, o las columnas bailan. */
  --cifra:var(--display); --cifra-opsz:"opsz" 14;
  /* Espaciado, base 4. */
  --e-1:4px; --e-2:8px; --e-3:12px; --e-4:16px; --e-5:20px; --e-6:24px; --e-7:32px;
  /* ---- acentos por familia (v2.1) ----
     Las cuatro áreas ya tenían color; los módulos no tenían ninguno y las ocho
     pantallas `mod-*` se veían idénticas. Cada familia reutiliza un acento que
     ya existe: no se inventa ningún color, porque los del bloque claro están
     medidos para AA sobre las tres superficies.
     Apuntan a los tokens de tema, así que cambian solos en oscuro y **no hay
     que duplicarlos** en los otros dos bloques. */
  --ac-cuerpo:var(--terracota);  --ac-cuerpo-soft:var(--terracota-soft);
  --ac-casa:var(--salvia);       --ac-casa-soft:var(--salvia-soft);
  --ac-vida:var(--pizarra);      --ac-vida-soft:var(--pizarra-soft);
  --ac-compra:var(--ocre);       --ac-compra-soft:var(--ocre-soft);
  /* Elevación. En claro las tarjetas son blancas sobre hueso y la diferencia
     es de tres puntos de luminancia: sin un filo o una sombra, once tarjetas
     seguidas se leen como una sola mancha. `--sombra-1` lleva **las dos cosas**
     (v2.39): el filo de 1 px de `--filo-card`, que estaba declarado y sin usar,
     y la sombra de siempre. */
  --sombra-1:0 0 0 1px var(--filo-card), 0 1px 2px rgba(26,28,25,.05), 0 1px 1px rgba(26,28,25,.04);
  --sombra-2:0 4px 14px rgba(26,28,25,.09);
  --filo-card:rgba(26,28,25,.055);
}
/* Modo oscuro. Se aplica cuando lo dice el sistema —salvo que el usuario haya
   elegido claro a mano— y siempre que haya elegido oscuro. Los valores están
   duplicados a propósito: CSS no permite reutilizar un bloque de tokens. Al
   tocar uno, tócalos en los tres sitios. */
@media (prefers-color-scheme:dark){
  :root:not([data-tema="claro"]){
    /* `--salvia-soft` era #1E2C23 sobre una superficie #1F1E18: dos puntos de
       diferencia, o sea que en oscuro los botones fantasma y las píldoras no
       tenían forma —se leía el texto flotando—. #26382C los devuelve al mundo
       sin encender nada. */
    --salvia:#9CC4A8; --salvia-deep:#7FAE8D; --salvia-soft:#26382C; --salvia-ink:#B4D6BE;
    --terracota:#E09070; --terracota-soft:#33201A;
    --ocre:#D9B45E; --ocre-soft:#2F2716;
    --pizarra:#8FB2C6; --pizarra-soft:#1B2830;
    /* Calentado (v2.2): era `#131512`/`#1C1F1B`, o sea el gris neutro de
       cualquier app de Material — negro con un punto de verde. En claro
       `#F6F3EE` sobre blanco es inconfundible y cálido, y en oscuro ese
       carácter se había ido, que es donde el móvil va la mitad del tiempo.
       Ahora el carbón lleva el mismo tinte de hueso que el fondo claro. Medido
       contra las tres superficies: `--muted` #9A9A8E da 5,9:1 sobre --surface y
       6,6:1 sobre --bg, o sea AA de sobra, como ya pasaba antes. */
    --bg:#15140F; --surface:#1F1E18; --surface-2:#292821;
    --ink:#F1F0E9; --ink-2:#CDCCC2; --muted:#9A9A8E;
    --sw-bola:#CDCCC2;
    --pista:#1F1E18; --pulgar:#35342B;
    --line:#35342B; --ok:#7CC79A; --danger:#F2B8B5; --danger-soft:#3E1F1D;
    --sobre-salvia:#131A15;
    /* En oscuro la separación ya la da el color —#1C1F1B sobre #131512— así que
       la sombra es casi nula y el filo, una luz tenue por arriba. */
    --sombra-1:0 0 0 1px var(--filo-card), 0 1px 2px rgba(0,0,0,.28);
    --sombra-2:0 6px 18px rgba(0,0,0,.42);
    --filo-card:rgba(255,255,255,.045);
  }
}
:root[data-tema="oscuro"]{
    /* `--salvia-soft` era #1E2C23 sobre una superficie #1F1E18: dos puntos de
       diferencia, o sea que en oscuro los botones fantasma y las píldoras no
       tenían forma —se leía el texto flotando—. #26382C los devuelve al mundo
       sin encender nada. */
    --salvia:#9CC4A8; --salvia-deep:#7FAE8D; --salvia-soft:#26382C; --salvia-ink:#B4D6BE;
    --terracota:#E09070; --terracota-soft:#33201A;
    --ocre:#D9B45E; --ocre-soft:#2F2716;
    --pizarra:#8FB2C6; --pizarra-soft:#1B2830;
    /* Calentado (v2.2): era `#131512`/`#1C1F1B`, o sea el gris neutro de
       cualquier app de Material — negro con un punto de verde. En claro
       `#F6F3EE` sobre blanco es inconfundible y cálido, y en oscuro ese
       carácter se había ido, que es donde el móvil va la mitad del tiempo.
       Ahora el carbón lleva el mismo tinte de hueso que el fondo claro. Medido
       contra las tres superficies: `--muted` #9A9A8E da 5,9:1 sobre --surface y
       6,6:1 sobre --bg, o sea AA de sobra, como ya pasaba antes. */
    --bg:#15140F; --surface:#1F1E18; --surface-2:#292821;
    --ink:#F1F0E9; --ink-2:#CDCCC2; --muted:#9A9A8E;
    --sw-bola:#CDCCC2;
    --pista:#1F1E18; --pulgar:#35342B;
    --line:#35342B; --ok:#7CC79A; --danger:#F2B8B5; --danger-soft:#3E1F1D;
    --sobre-salvia:#131A15;
    /* En oscuro la separación ya la da el color —#1C1F1B sobre #131512— así que
       la sombra es casi nula y el filo, una luz tenue por arriba. */
    --sombra-1:0 0 0 1px var(--filo-card), 0 1px 2px rgba(0,0,0,.28);
    --sombra-2:0 6px 18px rgba(0,0,0,.42);
    --filo-card:rgba(255,255,255,.045);
}

/* Los márgenes de las barras del sistema.
   Capacitor 8 quitó `adjustMarginsForEdgeToEdge` y en su lugar el plugin de
   barras del sistema **inyecta** las variables `--safe-area-inset-*` en el
   WebView, porque en Android el `env()` de CSS no es de fiar. De ahí que cada
   margen lleve la variable primero y el `env()` de reserva: así funciona igual
   dentro del APK y en el navegador. Si se deja solo `env()`, en el móvil la
   cabecera se mete debajo del reloj y la barra de abajo, bajo los gestos. */
*{box-sizing:border-box;-webkit-tap-highlight-color:transparent}
/* `hidden` tiene que esconder de verdad. El `[hidden]{display:none}` del
   navegador es de origen UA y **cualquier** `display` de autor lo pisa:
   `.fila{display:flex}`, `.btn{display:inline-flex}`, `.buscador{display:flex}`
   ganaban siempre, así que treinta y tres `x.hidden = …` de app.js no escondían
   nada sobre esos elementos —los botones sobre la lista de la compra vacía, el
   del asistente sin clave, la caja de búsqueda de la despensa—, y solo lo hacían
   sobre los cinco que tenían su regla propia (hoja, cajón, pantalla, fallo,
   aviso). Con esta regla esas cinco sobran. */
[hidden]{display:none!important}
html,body{margin:0;padding:0;overscroll-behavior-y:contain}
body{font-family:var(--ui);background:var(--bg);color:var(--ink);
  font-size:var(--t);line-height:1.5;-webkit-font-smoothing:antialiased;
  /* margen para la barra de gestos: Android 15 dibuja de borde a borde */
  padding-bottom:calc(96px + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)))}
.wrap{max-width:620px;margin:0 auto}
img{max-width:100%;display:block}
a{color:var(--salvia)}

/* ---------- la entrada de la app ----------
   Una sola animación al arrancar: la cabecera, el contenido y la barra suben un
   poco y aparecen, escalonados. Dura menos de medio segundo — más que eso deja
   de parecer cuidado y empieza a parecer lento.

   **La clase `listo` la pone el JS cuando ya ha pintado**, y toda la animación
   cuelga de ella. Es a propósito y es la parte importante: si el arranque falla,
   la clase no llega, no hay animación, y el contenido se ve. Una animación que
   entra desde `opacity:0` sin esa condición deja la app invisible para siempre
   el día que algo reviente antes de tiempo.

   La marca de agua solo escala: su opacidad depende del tema (.06 en claro, .09
   en oscuro) y animarla obligaría a repetir esos números aquí, que es justo la
   forma de que dejen de cuadrar. */
@keyframes nido-entra {
  from { opacity:0; transform:translateY(9px) }
  to   { opacity:1; transform:none }
}
@keyframes nido-marca {
  from { transform:scale(1.05) }
  to   { transform:none }
}
@media (prefers-reduced-motion: no-preference){
  html.listo header,
  html.listo main,
  html.listo nav { animation:nido-entra .4s cubic-bezier(.22,.61,.36,1) both }
  html.listo main { animation-delay:.05s }
  html.listo nav  { animation-delay:.1s }
  /* **El nido se cierra sobre los huevos.** El SVG ya viene partido en cuatro
     grupos —fibras de detrás, contornos de los huevos, huevos, fibras de
     delante—, que es el reparto del que sale toda la profundidad del dibujo.
     Escalonarlos es lo que hace cualquier ilustrador con tres planos: el fondo
     llega primero y las fibras de delante las últimas, y durante 900 ms el nido
     se cierra en vez de escalar en bloque. La opacidad no se toca: depende del
     tema (.06 en claro, .09 en oscuro) y repetir esos números aquí es la forma
     de que dejen de cuadrar. */
  html.listo .marca-agua > g { animation:nido-marca .9s cubic-bezier(.22,.61,.36,1) both }
  html.listo .marca-agua > g:nth-child(2),
  html.listo .marca-agua > g:nth-child(3) { animation-delay:.06s }
  html.listo .marca-agua > g:nth-child(4) { animation-delay:.12s }
}

/* ---------- cabecera ---------- */
header{padding:calc(22px + var(--safe-area-inset-top, env(safe-area-inset-top, 0px))) 22px 18px;position:relative}
.tema{position:absolute;top:calc(20px + var(--safe-area-inset-top, env(safe-area-inset-top, 0px)));right:18px;width:44px;height:44px;
  border:0;border-radius:50%;background:var(--surface);color:var(--ink);
  cursor:pointer;display:grid;place-items:center;line-height:1}
.tema:active{transform:scale(.94)}
.eyebrow{font-size:var(--t-s);letter-spacing:.02em;color:var(--muted);font-weight:600;margin:0 0 3px}
header h1{font-family:var(--display);font-variation-settings:"opsz" 40;font-size:var(--d-l);font-weight:600;
  letter-spacing:-.01em;margin:0;line-height:1.2;padding-right:56px}
header h1 em{font-style:normal;color:var(--salvia)}
.subhead{font-size:var(--t-b);color:var(--ink-2);margin:var(--e-1) 0 0}

main{padding:var(--e-1) var(--e-3) var(--e-2)}
.panel{display:none}
.panel.on{display:block;animation:in .2s cubic-bezier(.2,.9,.3,1)}
@keyframes in{from{opacity:0;transform:translateY(8px)}to{opacity:1;transform:none}}
@media (prefers-reduced-motion:reduce){.panel.on{animation:none}}

/* ---------- la cabecera dice dónde estás (v2.2) ----------
   El `h2.sec` que había debajo de la cabecera decía «Comida» en 24 px mientras
   la cabecera, en 31 px, decía «Buenas tardes» — lo mismo en las cinco
   pestañas. Ahora la cabecera **es** la sección fuera de Hoy y el h2 se ha ido
   del HTML; el filo del acento, que era lo mejor que tenía, sube con ella.

   `body[data-seccion]` lo pone `renderCabecera()`. En Hoy no hay filo: ahí el
   titular es el saludo y no es de ninguna sección. */
body:not([data-seccion="hoy"]) header h1{position:relative;padding-left:var(--e-4)}
body:not([data-seccion="hoy"]) header h1::before{content:"";position:absolute;
  left:0;top:.24em;bottom:.24em;width:5px;border-radius:3px;background:var(--salvia)}
/* cada sección lleva su color, para reconocerla de un vistazo. Casa lo cambia
   por mitad —cocinar es terracota, comprar es ocre, las tareas el salvia de
   reserva—: `data-sub` lo pone `renderCabecera()` junto a `data-seccion`. */
body[data-seccion="casa"][data-sub="cocina"] header h1::before{background:var(--terracota)}
body[data-seccion="casa"][data-sub="compra"] header h1::before{background:var(--ocre)}
body[data-seccion="salud"] header h1::before{background:var(--ac-cuerpo)}
/* Finanzas es de la familia «vida», pizarra: sus subpestañas ya lo eran
   (`#p-finanzas{--ac-seccion}`) y la cabecera se había quedado en el salvia de
   reserva, dos acentos distintos a cuarenta píxeles uno de otro. */
body[data-seccion="finanzas"] header h1::before{background:var(--pizarra)}
/* y sin el h2 la cabecera puede respirar menos por abajo: son los ~48 px que
   ocupaba, más los 6 de su margen. */
body:not([data-seccion="hoy"]) header{padding-bottom:var(--e-3)}
.sub-sec{font-size:var(--t-m);font-weight:700;letter-spacing:.06em;text-transform:uppercase;
  color:var(--muted);margin:var(--e-5) var(--e-1) var(--e-2)}
.hint{font-size:var(--t-m);color:var(--muted);margin:0 var(--e-1) var(--e-4);line-height:1.5}
.vacio{font-size:var(--t-b);color:var(--muted);text-align:center;padding:var(--e-6) var(--e-4);line-height:1.55}

/* ---------- filas de lista ----------
   Ocho componentes distintos repetían el mismo par: filo arriba salvo en la
   primera. Se declara aquí una vez y cada uno se queda con lo suyo —su
   distribución y su altura—, que es lo único en lo que de verdad se
   diferencian.

   Cuidado al añadir una: `:first-of-type` va por **tipo de elemento**, no por
   clase. Una lista que mezcla `<div>` y `<button>` tendrá dos «primeras» y se
   verá un filo de más. Por eso `.filas .fila-aj` usa `:first-child`. */
.item,.linea,.ingr,.momento,.ranura,.tipo-bloque,.fila-sw,.tienda-fila,.todo.llano{
  border-top:1px solid var(--line)}
.item:first-of-type,.linea:first-of-type,.ingr:first-of-type,.momento:first-of-type,
.ranura:first-of-type,.tipo-bloque:first-of-type,.fila-sw:first-child,
.tienda-fila:first-child,.todo.llano:first-of-type{border-top:0}

/* ---------- tarjetas ---------- */
/* El filo de 1 px (`--filo-card`) va **dentro de `--sombra-1`**, no en una
   regla aparte: dos `box-shadow` en reglas distintas no se suman, gana la
   última, y así lo llevan a la vez la tarjeta, la tarea, la receta y todo lo
   que se apoya en la página. */
.card{background:var(--surface);border-radius:var(--r-xl);padding:var(--e-4) var(--e-4);
  margin-bottom:var(--e-3);overflow:hidden;position:relative;box-shadow:var(--sombra-1)}
/* El acento de una tarjeta destacada es **una barra recta**, no un `inset`
   (v2.39). Como sombra interior seguía el radio de 28 px de la tarjeta y se
   curvaba en gancho en las dos esquinas, afinándose hasta desaparecer: se leía
   como un borde mal recortado. La barra es un `::before` que empieza y acaba
   donde la esquina ya es recta, y con eso la sombra de `.card` no hay que
   repetirla aquí. */
.card.hoy::before,.card.alerta::before,.dia-plan.esHoy::before{content:"";position:absolute;
  left:0;top:var(--e-5);bottom:var(--e-5);width:3px;border-radius:0 3px 3px 0;
  background:var(--salvia)}
.card.alerta::before{background:var(--terracota)}
.card-t{display:flex;align-items:center;gap:var(--e-2);margin:0 0 var(--e-3)}
.card-t h3{font-size:var(--t-xl);font-weight:700;margin:0;flex:1;min-width:0;letter-spacing:-.01em}
.card-t .ico{color:var(--salvia)}
.card-t .cuenta{font-size:var(--t-m);font-weight:700;color:var(--muted);font-variant-numeric:tabular-nums}

.item{display:flex;gap:var(--e-3);padding:var(--e-3) 0;align-items:flex-start}
.item:first-of-type{padding-top:2px}
.item .t{flex:0 0 46px;font-size:var(--t-m);font-weight:700;color:var(--salvia);font-variant-numeric:tabular-nums;padding-top:1px}
.item .t.none{color:var(--muted);font-weight:600}
/* El rótulo de un hueco de comida. La columna de 46 px está medida para una
   hora («09:00»); «Desayuno», «Almuerzo» y «Merienda» no caben, la desbordaban
   cada uno en lo suyo y el nombre del plato empezaba en una x distinta en cada
   fila. Con su propio ancho, los cinco platos caen en la misma vertical. */
.item .t.hueco{flex-basis:68px}
.item .b{flex:1;min-width:0}
.item .b strong{display:block;font-size:var(--t);font-weight:600}
.item .b small{display:block;color:var(--muted);font-size:var(--t-m);margin-top:3px;line-height:1.45}
/* El repaso del ticket. La × es **la misma `.quita-linea` de la lista de la
   compra** —quitar una línea es quitar una línea—; lo único propio es
   centrarla, porque `.item` alinea sus hijos arriba. Y la línea ya quitada
   **se queda en gris y tocable** en vez de desaparecer: quitar la que no era y
   no poder deshacerlo obliga a repetir la foto entera. */
.item .quita-linea{align-self:center}
.item.quitada{opacity:.55}
.item.quitada .b strong{text-decoration:line-through;text-decoration-thickness:1px}
/* Una cifra de una cabecera que además se toca para corregirla. Hereda de
   `.cuenta` y solo añade que se note que es un botón. */
.como-chip{border:0;font:inherit;color:inherit;background:var(--surface-2);
  border-radius:var(--r-m);padding:2px var(--e-2)}
.como-chip:active{transform:scale(.96)}
.item .ico-izq{flex:0 0 auto;color:var(--muted);padding-top:2px}
/* `.item` nació como `<div>`. Usada en un `<button>` —para que la fila entera
   sea pulsable— hereda el centrado, el borde y la tipografía del botón, y la
   lista sale con el texto centrado y descuadrada. Este reset es lo que hace que
   las dos formas se vean igual. */
button.item{width:100%;text-align:left;background:none;border:0;cursor:pointer;
  font-family:var(--ui);color:inherit}
button.item:active{background:var(--surface-2)}

/* ---------- etiquetas y chips ----------
   Eran once clases para dos componentes. Lo común se declara una vez aquí y
   cada nombre conserva solo lo que lo distingue, que casi siempre es el color.
   Los nombres se mantienen porque hay miles de líneas de plantilla que los
   usan; lo que se ha unificado es la definición, no la nomenclatura.

     · ETIQUETA — informa, no se toca. Pequeña y de una sola línea.
     · CHIP     — se toca, así que necesita área de dedo (44 px de alto real,
                  aunque el dibujo sea más bajo).
   Si algún día hace falta una decimosegunda, sale de aquí. */
.tag,.pill,.due,.tienda-et,.tipo-libre{
  display:inline-flex;align-items:center;gap:var(--e-1);
  font-size:var(--t-xs);font-weight:600;padding:3px var(--e-2);border-radius:var(--r-l);
  line-height:1.45;white-space:nowrap}
.tag{margin-top:var(--e-2)}
.due{margin-top:var(--e-2);font-weight:600}
.tienda-et{font-weight:700;letter-spacing:.04em;padding:2px var(--e-2);margin-left:var(--e-1)}
.tipo-libre{font-weight:700}
.tag.comida{background:var(--terracota-soft);color:var(--terracota)}
.tag.casa{background:var(--salvia-soft);color:var(--salvia-ink)}
.tag.compra{background:var(--ocre-soft);color:var(--ocre)}
.tag.agenda{background:var(--pizarra-soft);color:var(--pizarra)}
.tag.gris{background:var(--surface-2);color:var(--muted)}
.tag.urg{background:var(--danger-soft);color:var(--danger)}

.acts{display:flex;gap:var(--e-2);margin-top:var(--e-2);flex-wrap:wrap}
/* Los chips que viven **dentro** de un botón —los antojos— no pueden ser un
   <button>: un botón dentro de otro no es HTML válido. Van como
   `span[role="button"]` y se pintan igual, que es lo que ve el usuario. Su rama
   del listener va antes que la del botón que los envuelve, como el chip de
   posponer. */
.acts a,.acts button,.acts [role="button"]{font-size:var(--t-m);font-weight:600;text-decoration:none;border:0;cursor:pointer;min-height:44px;
  border-radius:var(--r-l);padding:var(--e-2) var(--e-3);background:var(--salvia-soft);color:var(--salvia-ink);
  font-family:var(--ui);display:inline-flex;align-items:center;gap:var(--e-1)}
.acts a:active,.acts button:active,.acts [role="button"]:active{background:var(--salvia);color:var(--sobre-salvia)}
/* La acción única de una fila, a su derecha: hermana del cuerpo y no hija. */
.item>.acts{margin-top:0;flex:0 0 auto;align-self:center}

/* ---------- formularios y botones ---------- */
input,textarea,select{font-family:var(--ui);font-size:var(--t);color:var(--ink);border:0;
  border-radius:var(--r-m);padding:var(--e-3) var(--e-3);background:var(--surface-2);width:100%}
input:focus,textarea:focus,select:focus{outline:2px solid var(--salvia);outline-offset:0}
textarea{resize:vertical;line-height:1.5}
label.campo{display:block;margin-bottom:var(--e-2)}
label.campo span{display:block;font-size:var(--t-m);color:var(--muted);font-weight:600;margin-bottom:var(--e-1)}
/* `.fila` es para **parejas de campos** de un formulario: reparte el ancho a
   partes iguales entre sus hijos. Para una fila de icono + texto + interruptor
   no vale, y es un error fácil de cometer: el icono y el interruptor se llevan
   un tercio del ancho cada uno y la fila se ve descuadrada. Para eso está
   `.fila-sw`, aquí debajo. */
.fila{display:flex;gap:var(--e-2)}
.fila>*{flex:1;min-width:0}
.adder{display:flex;gap:var(--e-2);margin-top:var(--e-3)}
.adder input{flex:1;min-width:0}
.adder .btn{flex:0 0 48px;padding:var(--e-3) 0;display:grid;place-items:center}
.btn{background:var(--salvia);color:var(--sobre-salvia);border:0;border-radius:var(--r-l);padding:var(--e-3) var(--e-5);
  font-family:var(--ui);font-weight:600;font-size:var(--t);cursor:pointer;transition:transform .12s;
  display:inline-flex;align-items:center;justify-content:center;gap:var(--e-2)}
.btn:active{transform:scale(.97);background:var(--salvia-deep)}
/* El secundario va **sin relleno y con filo** (v2.39). Iba en `--salvia-soft`
   lleno, y en los módulos casi cada tarjeta acaba en uno a todo el ancho: en
   Vehículos eran cinco seguidos, una pared de botones verdes en la que el
   principal —el único relleno de verdad— no destacaba. El filo es un `inset`,
   así que la caja mide lo mismo y no se mueve nada. */
.btn.ghost{background:none;color:var(--salvia-ink);box-shadow:inset 0 0 0 1px var(--line)}
.btn.ghost:active{background:var(--salvia-soft)}
.btn.peligro{background:var(--danger-soft);color:var(--danger)}
.btn.texto{background:none;color:var(--muted);font-weight:500}
.btn.wide{width:100%;margin-top:var(--e-2)}
.btn.chico{padding:var(--e-2) var(--e-3);font-size:var(--t-b);border-radius:var(--r-m)}

/* ---------- segmentados y subpestañas ---------- */
/* **Un segmentado es una caja con un pulgar dentro** (v2.39). Eran botones
   sueltos y el activo iba relleno del acento: tres bloques de color lleno, uno
   al lado de otro, que pesaban más que la tarjeta que venía debajo. Ahora la
   pista es una sola caja —se lee como un control y no como tres botones— y el
   activo es el pulgar, que se levanta con la sombra de una tarjeta y lleva el
   acento **en el texto**. */
.seg{display:flex;gap:2px;background:var(--pista);border-radius:var(--r-m);padding:3px}
.seg button{flex:1;border:0;background:none;border-radius:var(--r-s);padding:var(--e-2) var(--e-1);
  min-height:38px;
  font-family:var(--ui);font-weight:600;font-size:var(--t-b);color:var(--ink-2);cursor:pointer;
  display:inline-flex;align-items:center;justify-content:center;gap:var(--e-1)}
.seg button.on{background:var(--pulgar);color:var(--salvia-ink);box-shadow:var(--sombra-1)}
/* Cinco rangos de fechas no caben en una fila: en columna se leen y siguen
   siendo del mismo componente, sin inventar otro. */
/* El aviso de que el menú de la sesión del domingo ha cambiado. Filo ocre a la
   izquierda: es un «mira esto», no un error. */
.aviso-cambio{border-left:3px solid var(--ocre);background:var(--surface-2);
  border-radius:var(--r-s);margin:0 0 var(--e-2)}
.item.aviso-cambio{padding:var(--e-3);align-items:center}
.item.aviso-cambio .btn{flex:0 0 auto}

/* El conmutador de semana va pegado arriba de la rejilla y necesita aire por
   debajo: sin él se lee como parte de la tarjeta del resumen. */
#seg-semana{margin:0 0 var(--e-3)}
/* El paso de un periodo al siguiente: dos flechas y el rótulo en medio. Existía
   ya en Agenda → Mes, escrito a mano con estilos en línea, y ahora lo usan
   también las dos semanas de Comida — que eran una **segunda fila de
   segmentado** justo debajo de las subpestañas: dos controles del mismo aspecto
   y de rango distinto pegados, y a los dos pasos ya no se sabía cuál mandaba
   sobre cuál. Un control, un patrón, y `.fila` deja de usarse para algo que no
   es una pareja de campos. */
.nav-periodo{display:flex;align-items:center;gap:var(--e-2);margin:0 var(--e-1) var(--e-3)}
.nav-periodo b{flex:1;text-align:center;font-size:var(--t);font-weight:600}
.nav-periodo button:disabled{opacity:.32;cursor:default}
/* En columna no hay pista: son opciones largas, una por línea, y cada una es
   su propia caja. Aquí el activo sí va relleno, que es lo que dice cuál está
   elegida en una lista. */
.seg.col{flex-direction:column;gap:var(--e-2);background:none;padding:0;border-radius:0}
.seg.col button{flex:none;justify-content:flex-start;padding:var(--e-3) var(--e-4);
  background:var(--surface-2);border-radius:var(--r-m)}
.seg.col button.on{background:var(--salvia);color:var(--sobre-salvia);box-shadow:none}

/* La × de quitar una línea de la compra. Va la última y en gris muy flojo: es
   una salida, no una acción que se ofrezca. El área de toque es la de siempre
   (44 px de alto) aunque el aspa sea pequeña. */
.quita-linea{flex:0 0 auto;background:none;border:0;cursor:pointer;color:var(--muted);
  opacity:.5;padding:var(--e-3) 2px var(--e-3) var(--e-2);display:grid;place-items:center;min-height:44px}
.quita-linea:active{opacity:1;color:var(--danger)}
.linea.done .quita-linea{display:none}

/* La tarjeta del despertar. Lleva un filo de acento arriba para que se lea como
   «lo primero de hoy» sin gritar: es la única tarjeta que aparece y desaparece
   sola, y sin nada que la distinga parece que la app se ha desordenado. */
.card.despertar::before{content:"";position:absolute;top:0;left:var(--e-6);right:var(--e-6);
  height:3px;border-radius:0 0 3px 3px;background:var(--ocre)}

/* ---------- suplementos ----------
   La pantalla era una lista de filas y no se distinguía una recomendación fuerte
   de una floja. Ahora las recomendaciones son fichas en rejilla, con el icono en
   un círculo del color de su nivel de evidencia, y lo que uno ya toma va arriba
   como chips agrupados por momento del día. */
/* `auto-fit` y no dos columnas fijas: con un nombre largo —«magnesio
   bisglicinato»— dos columnas de 460 px partían la palabra por la mitad. */
.rejilla-supl{display:grid;grid-template-columns:repeat(auto-fit,minmax(150px,1fr));
  gap:var(--e-2);margin:0 0 var(--e-4)}
.supl-card{display:flex;flex-direction:column;align-items:flex-start;gap:var(--e-1);
  background:var(--surface);border:0;border-radius:var(--r-l);padding:var(--e-3);
  font-family:var(--ui);text-align:left;cursor:pointer;color:var(--ink);
  box-shadow:var(--sombra-1)}
.supl-card:active{background:var(--surface-2)}
.supl-ico{width:38px;height:38px;border-radius:50%;display:grid;place-items:center;
  margin-bottom:var(--e-1);background:var(--salvia-soft);color:var(--salvia-ink)}
/* El color dice cuánto respaldo tiene, sin tener que leer la etiqueta. */
.supl-card.ev-alta  .supl-ico{background:var(--salvia-soft);color:var(--salvia-ink)}
.supl-card.ev-media .supl-ico{background:var(--ocre-soft);color:var(--ocre)}
.supl-card.ev-floja .supl-ico{background:var(--surface-2);color:var(--muted)}
.supl-nom{font-size:var(--t);font-weight:700;line-height:1.25}
.supl-dosis{font-size:var(--t-s);color:var(--ink-2);font-weight:600}
.supl-por{font-size:var(--t-s);color:var(--muted);line-height:1.4}
.supl-ev{margin-top:var(--e-1);font-size:var(--t-xs);font-weight:700;letter-spacing:.02em;
  text-transform:uppercase;color:var(--muted)}
.supl-card.ev-alta .supl-ev{color:var(--salvia)}

/* Un momento del día con lo que toca tomar. */
.momento{padding:var(--e-2) 0}

.momento-t{display:flex;align-items:center;gap:var(--e-2);font-size:var(--t-m);color:var(--muted);
  font-weight:600;margin:0 0 var(--e-2)}
.momento-t b{margin-left:auto;font-variant-numeric:tabular-nums}
/* Ámbar solo cuando ya pasó la hora y sigue sin tomarse: es lo único de la
   tarjeta que pide algo del usuario. */
.momento.tarde .momento-t{color:var(--ocre)}
.chips{display:flex;flex-wrap:wrap;gap:var(--e-2)}
/* CHIP: el que se toca. El `min-height` es el área de dedo, no el dibujo. */
.chip-supl,.chip-temp,.precio-et,.cad-chip,.dequien{
  display:inline-flex;align-items:center;gap:var(--e-1);border:0;cursor:pointer;
  font-family:var(--ui);font-weight:600;background:var(--surface-2);color:var(--ink-2)}
.chip-supl,.chip-temp{border-radius:var(--r-l);padding:var(--e-2) var(--e-3);font-size:var(--t-m);min-height:38px}
.chip-supl:active,.chip-temp:active,.cad-chip:active,.precio-et:active{transform:scale(.96)}
.chip-supl{}
.chip-supl.on{background:var(--salvia-soft);color:var(--salvia-ink)}
.chip-supl.on{text-decoration:line-through;text-decoration-thickness:1px}

/* Un chip que se marca y se desmarca, para elegir entre varias opciones a la
   vez. Es `.chip-supl` **sin el tachado**: ahí el tachado significa «ya tomado»,
   y aquí marcado significa «sí, quiero este aviso» — con la línea encima se lee
   exactamente al revés de lo que es. */
.chip-elige{display:inline-flex;align-items:center;gap:var(--e-1);border:0;cursor:pointer;
  font-family:var(--ui);font-weight:600;background:var(--surface-2);color:var(--ink-2);
  border-radius:var(--r-l);padding:var(--e-2) var(--e-3);font-size:var(--t-m);min-height:38px}
.chip-elige:active{transform:scale(.96)}
.chip-elige.on{background:var(--salvia);color:var(--sobre-salvia)}

/* El avance del día, encima de las tarjetas de Hoy: una línea y una barra, sin
   tarjeta, que no compite con lo que hay que hacer. */
.avance-dia{margin:0 var(--e-1) var(--e-4)}

/* Lo tachado de una lista sin fecha (Casa → Tareas → Listas). */
.linea .tachado{color:var(--muted);text-decoration:line-through;text-decoration-thickness:1px}

/* La semana de un hábito: siete casillas, de lunes a domingo. Hecho en salvia;
   el día que no toca, más tenue (se puede marcar igual: hacer de más no es un
   error); hoy, con su aro; y el futuro, sin poder tocarse. */
.semana-hab{display:grid;grid-template-columns:repeat(7,1fr);gap:var(--e-1)}
.semana-hab button{aspect-ratio:1;max-height:44px;border:0;border-radius:var(--r-s);background:var(--surface-2);
  color:var(--ink-2);font-family:var(--ui);font-weight:700;font-size:var(--t-m);cursor:pointer;
  display:grid;place-items:center}
.semana-hab button.no-toca{background:none;color:var(--muted)}
.semana-hab button.hoy{outline:2px solid var(--salvia);outline-offset:-2px}
.semana-hab button.on{background:var(--salvia);color:var(--sobre-salvia)}
.semana-hab button:disabled{opacity:.45;cursor:default}

/* ---------- el diario ---------- */
.area{width:100%;background:var(--surface-2);border-radius:var(--r-m);padding:var(--e-3) var(--e-4);
  font-size:var(--t-l);line-height:1.55;min-height:150px;box-sizing:border-box}
.tira-fotos{display:flex;flex-wrap:wrap;gap:var(--e-2);margin:0 0 var(--e-3)}
.foto-diario{position:relative;width:calc(50% - 4px);aspect-ratio:4/3;border-radius:var(--r-m);
  overflow:hidden;background:var(--surface-2)}
.foto-diario img{width:100%;height:100%;object-fit:cover;display:block}
/* La miniatura de una prenda ocupa el hueco del icono de la fila, con el mismo
   tamaño: así una lista con fotos y otra sin ellas se leen igual y no bailan.
   `object-fit:cover` porque una foto de ropa siempre viene con el suelo dentro. */
/* Las barras del dinero. Verde lo que entra y terracota lo que sale, que es el
   par de la casa; y **el mes sin datos se pinta con un guion**, no con una barra
   a cero: un mes sin importar el extracto no es un mes sin gastos. */
.barras-fin{display:flex;gap:var(--e-2);align-items:flex-end;height:110px;margin-top:var(--e-1)}
.barra-mes{flex:1;display:flex;flex-direction:column;align-items:center;gap:var(--e-1);min-width:0}
.barra-mes .par{flex:1;width:100%;display:flex;gap:3px;align-items:flex-end;justify-content:center}
.barra-mes .b-in,.barra-mes .b-out{width:44%;min-height:3px;border-radius:4px 4px 0 0;display:block}
.barra-mes .b-in{background:var(--salvia)}
.barra-mes .b-out{background:var(--terracota)}
.barra-mes .b-vacia{color:var(--muted);font-size:var(--t-m);align-self:center;line-height:1}
.barra-mes small{color:var(--muted);font-size:var(--t-s);white-space:nowrap}

.mini-ropa{flex:0 0 auto;width:34px;height:34px;border-radius:9px;object-fit:cover;
  background:var(--surface-2);display:block}
.foto-prenda{width:100%;max-height:280px;object-fit:cover;border-radius:var(--r-m);
  background:var(--surface-2);display:block;margin:0 0 var(--e-3)}
/* El botón de quitar va **encima** de la foto y con su propio fondo: sobre una
   foto clara, un icono sin fondo no se ve, y ese es justo el que no se puede
   fallar al tocar. */
.quita-foto{position:absolute;top:6px;right:6px;border:0;border-radius:50%;width:28px;height:28px;
  display:grid;place-items:center;background:rgba(20,18,16,.62);color:#fff;cursor:pointer}
/* Las subpestañas son el mismo segmentado con pista, a lo ancho de la página.
   Siguen desplazándose cuando no caben —la pista es la que scrollea, así que
   `marcarDesborde()` y sus máscaras valen tal cual—. */
.subtabs{display:flex;gap:2px;margin:0 var(--e-1) var(--e-4);overflow-x:auto;scrollbar-width:none;
  background:var(--pista);border-radius:var(--r-l);padding:var(--e-1)}
.subtabs::-webkit-scrollbar{display:none}
.subtabs button{flex:1 0 auto;border:0;background:none;border-radius:var(--r-m);padding:var(--e-2) var(--e-3);
  min-height:40px;
  font-family:var(--ui);font-weight:600;font-size:var(--t-b);color:var(--ink-2);cursor:pointer;white-space:nowrap}
/* La subpestaña activa lleva **el acento de su sección**, no el salvia fijo que
   llevaba: en Comida se veía el filo terracota de la cabecera y tres píxeles más
   abajo «La semana» en verde. El sistema de acentos se paraba justo antes del
   único componente que se usa en todas las secciones. `--ac-seccion` lo pone
   cada panel; el que no lo declare se queda en salvia, que es el de casa. */
/* El acento va en el **texto** del activo, no en el relleno: `--terracota`,
   `--ocre`, `--pizarra` y `--salvia` están medidos para AA sobre `--surface`,
   que es lo que vale el pulgar en claro. */
.subtabs button.on{background:var(--pulgar);color:var(--ac-seccion,var(--salvia));
  font-weight:700;box-shadow:var(--sombra-1)}
/* Casa lleva un acento por mitad: la cocina terracota, la compra con su ocre
   de siempre y las tareas el salvia de reserva. El color es lo que dice de qué
   va una pantalla, y la lista de la compra no se ha vuelto terracota por
   haberse mudado. Salud y Finanzas llevan el de su familia. */
#cx-cocina{--ac-seccion:var(--terracota)}
#cx-compra{--ac-seccion:var(--ocre)}
#p-salud{--ac-seccion:var(--ac-cuerpo)}
#p-finanzas{--ac-seccion:var(--pizarra)}

/* El segundo nivel de subpestañas. Comida tiene dos —Cocina y Compra, y dentro
   de cada una las de siempre— y sin distinguirlos son siete chips seguidos sin
   jerarquía: uno no sabe cuál manda sobre cuál. Más pequeño y sin caja propia
   cuando está apagado, que es lo que dice «esto está dentro de lo de arriba». */
/* …y desde la v2.39, **subrayado**: sin pista ni pulgar, con una raya del
   acento bajo el activo y el filo de la página bajo todos. Dos cajas, una
   dentro de otra, volvían a ser dos controles del mismo rango. */
.subtabs.nivel-2{margin-bottom:var(--e-3);background:none;padding:0;border-radius:0;
  gap:var(--e-1);box-shadow:inset 0 -1px 0 var(--line)}
/* Relleno lateral `--e-2` y no `--e-3` (v2.55): con cinco chips —Pendientes,
   Estancias, Listas, Frecuencias, Trucos— el último se salía de un móvil de
   412 px, y una tira que hay que arrastrar sin saber que sigue esconde lo que
   lleva al final. */
.subtabs.nivel-2 button{flex:0 0 auto;padding:var(--e-2) var(--e-2);font-size:var(--t-b);
  border-radius:0;color:var(--muted)}
.subtabs.nivel-2 button.on{background:none;box-shadow:inset 0 -2px 0 var(--ac-seccion,var(--salvia));
  color:var(--ac-seccion,var(--salvia))}
/* Los filtros del recetario no son un segmentado: son nueve, se arrastran y no
   se excluyen de la misma forma que tres pestañas. Chips sueltos, pequeños. */
.subtabs.filtros{background:none;padding:0;border-radius:0;gap:var(--e-2)}
.subtabs.filtros button{flex:0 0 auto;min-height:36px;padding:var(--e-1) var(--e-3);border-radius:999px;
  background:var(--surface);font-size:var(--t-m);color:var(--ink-2);box-shadow:var(--sombra-1)}
.subtabs.filtros button.on{background:var(--ac-seccion,var(--salvia));color:var(--sobre-salvia);
  font-weight:600;box-shadow:none}

/* **El desbordamiento tiene que verse.** Estas tiras llevan `overflow-x:auto` y
   la barra escondida, así que en Salud la quinta pestaña —«Cuerpo»— se cortaba
   a media palabra contra el borde y no había ni una señal de que aquello se
   arrastrase. Esconder la barra está bien; esconderla **y** no marcar el filo es
   esconder la mitad del control. La clase la pone `marcarDesborde()` en JS,
   porque «esto no cabe» no se puede preguntar desde CSS. */
.subtabs.desborda-der,.strip.desborda-der{
  mask-image:linear-gradient(90deg,#000 calc(100% - 26px),transparent)}
.subtabs.desborda-izq,.strip.desborda-izq{
  mask-image:linear-gradient(90deg,transparent,#000 26px)}
.subtabs.desborda-izq.desborda-der,.strip.desborda-izq.desborda-der{
  mask-image:linear-gradient(90deg,transparent,#000 26px,#000 calc(100% - 26px),transparent)}

/* El rango de la pantalla de Salud no es del mismo rango que sus cinco
   subpestañas y no debe parecerlo: eran dos filas de segmentado, una encima de
   la otra, del mismo aspecto. Como chips pequeños alineados a la derecha se lee
   lo que es: un modificador de lo que ya se ha elegido arriba. */
.seg.chips{justify-content:flex-end;gap:var(--e-1);margin-bottom:var(--e-3);
  background:none;padding:0;border-radius:0;flex-wrap:wrap}
.seg.chips button{flex:0 0 auto;padding:var(--e-1) var(--e-3);border-radius:999px;
  min-height:0;background:none;font-size:var(--t-m);color:var(--muted)}
.seg.chips button.on{background:var(--salvia-soft);color:var(--salvia-ink);box-shadow:none}
/* Los mandos de un gráfico van **a la izquierda**, donde empieza el dibujo.
   A la derecha, tres filas de distinto largo dejaban un borde izquierdo en
   escalera encima del gráfico. */
.seg.chips.mandos{justify-content:flex-start}
.sub{display:none}
.sub.on{display:block;animation:in .18s cubic-bezier(.2,.9,.3,1)}

/* ---------- tira de días ---------- */
.strip{display:flex;gap:var(--e-2);overflow-x:auto;padding:2px var(--e-1) var(--e-3);scrollbar-width:none}
.strip::-webkit-scrollbar{display:none}
.chip{flex:0 0 auto;min-width:52px;text-align:center;padding:var(--e-2) var(--e-1) var(--e-2);border:0;
  border-radius:var(--r-m);background:var(--surface);font-size:var(--t-xs);color:var(--muted);
  font-weight:600;cursor:pointer;transition:transform .12s;font-family:var(--ui)}
.chip:active{transform:scale(.94)}
.chip b{display:block;font-size:var(--t-xl);color:var(--ink);font-weight:700;line-height:1.25}
.chip.libre{background:var(--salvia-soft)}
.chip.now{background:var(--salvia);color:var(--sobre-salvia)}
.chip.now b{color:var(--sobre-salvia)}
.chip .pt{display:block;height:4px;width:4px;border-radius:2px;background:var(--terracota);margin:var(--e-1) auto 0}

/* ---------- casillas ---------- */
.todo{display:flex;gap:var(--e-3);background:var(--surface);border-radius:var(--r-l);padding:var(--e-4) var(--e-4);
  margin-bottom:var(--e-2);cursor:pointer;align-items:flex-start;width:100%;text-align:left;border:0;
  font-family:var(--ui);font-size:var(--t);color:var(--ink);box-shadow:var(--sombra-1)}
.todo.llano{background:none;border-radius:0;padding:var(--e-3) 0;margin:0;box-shadow:none}
.todo.llano:first-of-type{padding-top:2px}
.box{flex:0 0 24px;height:24px;border:2px solid var(--muted);border-radius:50%;
  display:grid;place-items:center;margin-top:1px}
.todo.done .box{background:var(--ok);border-color:var(--ok)}
/* La marca es dibujo nuestro: el mismo trazo redondo del juego de iconos. */
.todo.done .box::after{content:"";width:13px;height:13px;
  background:url('data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="none" stroke="white" stroke-width="3.4" stroke-linecap="round" stroke-linejoin="round"><path d="M5 12.6 9.6 17 19 7.4"/></svg>') center/13px no-repeat}
.todo.done .qu,.todo.done .de{opacity:.5;text-decoration:line-through}
/* ---------- acuse de recibo al tocar ----------
   Marcar una tarea o tachar una línea de la compra repintaba y ya: la acción
   en sí no acusaba recibo, y el toast llega después y en otro sitio de la
   pantalla. Es la diferencia entre una app correcta y una que se siente hecha
   por alguien.

   Va en `:active` **a propósito**, y no en una animación tras el clic: el
   repintado por `innerHTML` se lleva por delante cualquier animación en curso
   —el nodo que se estaba animando ya no existe—, mientras que `:active` ocurre
   mientras el dedo sigue puesto, o sea **antes** de que nada repinte. Es el
   único acuse que no se puede perder.

   La casilla se rellena en el propio toque, que es lo que hace que el gesto se
   sienta terminado aunque el repintado tarde un fotograma. */
@media (prefers-reduced-motion: no-preference){
  .todo:active,.linea:active{transition:transform .12s ease, opacity .12s ease}
  .box{transition:background .12s ease, border-color .12s ease}
}
.todo:active{transform:scale(.985)}
.todo:not(.done):active .box{background:var(--salvia);border-color:var(--salvia);opacity:.55}
.casilla:not(.done):active .box{background:var(--salvia);border-color:var(--salvia);opacity:.55}
.linea:has(.casilla:active){opacity:.6}
.todo .cuerpo{flex:1;min-width:0}
.todo .qu{display:block;font-size:var(--t);font-weight:600;line-height:1.35}
.todo .de{display:block;margin:3px 0 0;font-size:var(--t-m);color:var(--muted);line-height:1.45}
.todo .ico-tarea{flex:0 0 auto;color:var(--salvia);margin-top:1px}

/* La casilla suelta de la lista de la compra. No puede ser un `.todo`: eso
   lleva width:100%, y dentro de la fila flex aplastaba el nombre del producto
   hasta dejarlo fuera de la tarjeta. */
.casilla{flex:0 0 auto;background:none;border:0;padding:0;cursor:pointer;
  display:grid;place-items:center}
.casilla .box{width:24px;height:24px}
.casilla.done .box{background:var(--ok);border-color:var(--ok)}
.casilla.done .box::after{content:"";width:13px;height:13px;
  background:url('data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="none" stroke="white" stroke-width="3.4" stroke-linecap="round" stroke-linejoin="round"><path d="M5 12.6 9.6 17 19 7.4"/></svg>') center/13px no-repeat}

/* Marcar «tengo horno» no es tachar una tarea: la línea sigue vigente. */
.todo.sin-tachar.done .qu,.todo.sin-tachar.done .de{opacity:1;text-decoration:none}
.todo.sin-tachar.done .qu{color:var(--salvia)}

/* Los colores de `.due`. La forma la pone la regla de las etiquetas, allá
   arriba: declararla otra vez aquí le quitaba el `inline-flex` y el icono de
   dentro se descolgaba medio píxel. */
.due{background:var(--salvia-soft);color:var(--salvia-ink)}
.due.pronto{background:var(--ocre-soft);color:var(--ocre)}
.due.urg{background:var(--danger-soft);color:var(--danger)}
.todo.done .due{display:none}

/* ---------- comida: rejilla de la semana ---------- */
.semana{display:grid;gap:var(--e-2)}
.dia-plan{background:var(--surface);border-radius:var(--r-l);padding:var(--e-3) var(--e-4);
  position:relative;box-shadow:var(--sombra-1)}
.dia-plan.fuera{opacity:.72}
.dia-cab{display:flex;align-items:baseline;gap:var(--e-2);margin-bottom:var(--e-2)}
.dia-cab b{font-size:var(--t);font-weight:700;text-transform:capitalize}
.dia-cab span{font-size:var(--t-s);color:var(--muted);flex:1}
.dia-cab .kcal{font-size:var(--t-s);color:var(--muted);font-variant-numeric:tabular-nums}
/* El «rehacer este día». Va sin `flex:1` a propósito: los dos `span` de al lado
   sí lo llevan y sin esto el botón se llevaría un tercio de la cabecera. */
.dia-cab button{flex:0 0 auto;background:none;border:0;padding:2px var(--e-1);min-height:44px;
  color:var(--muted);line-height:0;cursor:pointer;border-radius:8px}
.dia-cab button:active{background:var(--surface-2)}
.ranura{display:flex;gap:var(--e-2);align-items:center;padding:var(--e-2) 0;
  width:100%;text-align:left;border-left:0;border-right:0;border-bottom:0;background:none;
  font-family:var(--ui);cursor:pointer;color:var(--ink)}

.ranura .cual{flex:0 0 52px;font-size:var(--t-xs);font-weight:700;letter-spacing:.05em;text-transform:uppercase;color:var(--muted)}
.ranura .qu{flex:1;min-width:0;font-size:var(--t);font-weight:600;line-height:1.35}
.ranura .mm{font-size:var(--t-s);color:var(--muted);font-weight:600;white-space:nowrap;
  display:inline-flex;align-items:center;gap:var(--e-1)}
.ranura.vacia .qu{color:var(--muted);font-weight:500}

/* ---------- comida: recetas ---------- */
/* **Una fila, no una tarjeta con hueco de foto.** El recetario son noventa y
   tres recetas y ninguna tiene foto: el bloque de 96 px con el icono del
   momento repetido se leía como noventa y tres marcadores iguales, y para ver
   seis recetas había que bajar dos pantallas. El cuadro de 56 px lleva el icono
   del aparato —eso sí distingue— y la miniatura de verdad cuando hay foto. */
.receta{display:flex;gap:var(--e-3);align-items:flex-start;width:100%;text-align:left;
  background:var(--surface);border:0;
  border-radius:var(--r-l);padding:var(--e-3) var(--e-4);margin-bottom:var(--e-2);cursor:pointer;font-family:var(--ui);box-shadow:var(--sombra-1)}
.rec-mini{flex:0 0 auto;width:56px;height:56px;border-radius:var(--r-m);overflow:hidden;
  display:grid;place-items:center;background:var(--surface-2)}
.rec-mini.sin{background:var(--terracota-soft);color:var(--terracota)}
.rec-mini img{width:100%;height:100%;object-fit:cover;display:block}
.rec-cuerpo{flex:1;min-width:0}
.receta strong{display:block;font-size:var(--t-l);font-weight:600;color:var(--ink);line-height:1.35}
.receta .meta{display:flex;flex-wrap:wrap;gap:var(--e-1);margin-top:var(--e-1);align-items:center}
.pill{background:var(--surface-2);color:var(--muted)}
.pill.prot{background:var(--terracota-soft);color:var(--terracota)}
.pill.base{background:var(--salvia-soft);color:var(--salvia-ink)}
.pill.mia{background:var(--pizarra-soft);color:var(--pizarra)}
/* La temporada. El verde es el de la casa; lo que está fuera de su mes va en
   gris apagado y no en rojo: no es un error, es un dato. */
.pill.temporada{background:var(--salvia-soft);color:var(--salvia-ink)}
.pill.fuera-temp{background:var(--surface-2);color:var(--muted);font-weight:500}
/* La tarjeta de temporada, en Comida. Los productos van en una tira que se
   desplaza a lo ancho —`.strip`, que además queda fuera del gesto del cajón— y
   lo que entra este mes va en salvia lleno para que se distinga de un vistazo. */
/* La semana de casa: siete columnas dentro de una `.strip`. Van con `flex:0 0`
   y ancho fijo porque siete días tienen que caber a lo ancho de un móvil sin que
   el jueves con tres tareas ensanche su columna y descoloque el resto. */
/* La semana de casa: **una fila por día**. Eran columnas de 88 px en una tira
   que se desplaza a lo ancho, y con un nombre largo —«Desatascar y desinfectar
   desagües»— se partía en cinco líneas de dos palabras: la tarjeta medía
   doscientos píxeles y los tres últimos días quedaban fuera de la pantalla. */
.semana-casa{display:flex;flex-direction:column}
.dia-fila{display:flex;gap:var(--e-3);align-items:baseline;min-height:32px;
  padding:var(--e-1) 0;border-top:1px solid var(--line)}
.dia-fila:first-child{border-top:0}
.dia-fila .t{flex:0 0 46px;font-size:var(--t-xs);color:var(--muted);text-transform:capitalize}
.dia-fila .t b{color:var(--ink);margin-left:3px}
.dia-fila .qu{flex:1;min-width:0;font-size:var(--t-m);line-height:1.4;color:var(--ink)}
/* «Ya que bajas» se lee como lo que es también aquí: apagado, no en tinta. */
.dia-fila .qu .colgada{color:var(--muted)}
.dia-fila .qu .nada{color:var(--muted)}
.dia-fila.fuera .qu{color:var(--muted);font-style:italic}

.temporada-card{margin-bottom:var(--e-3)}
.temporada-card .sub-sec .ico{vertical-align:-3px;margin-right:2px}
.temporada-card .strip{padding-bottom:2px}
.chip-temp{flex:0 0 auto}
/* El año, dentro del chip y solo cuando cambia: con doce meses en la tira,
   «ene» y «dic» juntos son dos años distintos y no se veía cuál era cuál. */
.chip-temp i{font-style:normal;font-size:var(--t-xs);opacity:.7;margin-left:2px}
/* Un mes sin un solo movimiento se puede abrir igual, pero se dice de antemano:
   entrar para encontrar una pantalla vacía es el viaje que sobra. */
.chip-temp.apagado{opacity:.45}
.chip-temp.nuevo.apagado{opacity:.8}
/* La tira lleva ahora su propia navegación encima, y entre las dos no hace falta
   el hueco de siempre. */
.tira-nav{margin-bottom:var(--e-1)}
.chip-temp.nuevo{background:var(--salvia-soft);color:var(--salvia-ink)}
.pasos{margin:0;padding-left:var(--e-5);font-size:var(--t);color:var(--ink-2)}
.pasos li{margin-bottom:var(--e-2)}
.ingr{display:flex;justify-content:space-between;gap:var(--e-3);padding:var(--e-2) 0;font-size:var(--t-b)}

.ingr b{color:var(--ink-2);font-weight:600;font-variant-numeric:tabular-nums;white-space:nowrap}
.ingr .pill{margin-left:var(--e-1);vertical-align:middle}
.macros{display:flex;gap:var(--e-2);margin:var(--e-3) 0 0}
.macro{flex:1;background:var(--surface-2);border-radius:var(--r-m);padding:var(--e-2) var(--e-1);text-align:center}
.macro b{display:block;font-size:var(--t-xl);font-weight:600;line-height:1.15;font-variant-numeric:tabular-nums;
  font-family:var(--cifra);font-variation-settings:var(--cifra-opsz)}
.macro span{font-size:var(--t-xs);color:var(--muted);font-weight:600}
.barra{height:7px;border-radius:4px;background:var(--surface-2);overflow:hidden;margin-top:var(--e-2);position:relative}
.barra i{display:block;height:100%;background:var(--salvia);border-radius:4px}
/* El exceso sobre el objetivo: rayado desde la derecha, proporcional a cuánto se
   pasa, con la marca del 100 % en su borde. Una barra llena al 100 % y otra al
   123 % eran el mismo dibujo. */
.barra em{position:absolute;right:0;top:0;height:100%;
  background:repeating-linear-gradient(135deg,transparent 0 3px,var(--surface) 3px 5px);
  border-left:1px solid var(--ink);opacity:.75}
.barra.corta i{background:var(--terracota)}
/* Las cuatro macros. Cada una con su color, para reconocerla sin leer la
   etiqueta, y los mismos tokens que ya usa el resto de la app: nada de colores
   nuevos, que los del bloque claro están medidos contra los tres fondos. */
.macrobarras{margin-top:var(--e-2);display:flex;flex-direction:column;gap:var(--e-2)}
.mb .barra{margin-top:3px;height:5px}
.mb-et{display:flex;align-items:baseline;gap:var(--e-1);font-size:var(--t-s);color:var(--muted)}
.mb-et span{flex:1;min-width:0}
.mb-et b{font-size:var(--t-m);color:var(--ink);font-variant-numeric:tabular-nums}
.mb-et i{font-style:normal;font-variant-numeric:tabular-nums}
.mb.kcal .barra i{background:var(--pizarra)}
.mb.prot .barra i{background:var(--salvia)}
.mb.carb .barra i{background:var(--ocre)}
.mb.gras .barra i{background:var(--terracota)}
.mb.corta .barra i{background:var(--danger)}

/* ---------- compra ---------- */
.pasillo{margin-bottom:var(--e-4)}
/* Una tarjeta que solo contiene filas: el relleno vertical lo ponen ellas. Era
   un estilo en línea repetido cuatro veces en app.js. */
.card.densa{padding:var(--e-2) var(--e-4)}
/* Un segmentado o una nota suelta entre tarjetas: el margen que tenían en línea. */
.suelto{margin:0 var(--e-1) var(--e-3)}
/* La leyenda de los puntos del mes. */
.leyenda{display:flex;flex-wrap:wrap;gap:var(--e-2) var(--e-4);font-size:var(--t-s);color:var(--muted);margin:var(--e-2) var(--e-1) 0}
.leyenda i{width:6px;height:6px;border-radius:3px;display:inline-block;margin-right:var(--e-1);vertical-align:middle}
.leyenda .pt-fuera{background:var(--pizarra-soft);box-shadow:inset 0 0 0 1px var(--line)}
/* Una nota en rojo dentro del detalle de una línea: lo que no aguanta. */
.de .urg{color:var(--danger)}
.pasillo-t{display:flex;align-items:center;gap:var(--e-2);font-size:var(--t-m);font-weight:700;
  letter-spacing:.06em;text-transform:uppercase;color:var(--ocre);margin:0 var(--e-1) var(--e-2)}
.linea{display:flex;gap:var(--e-3);align-items:center;padding:var(--e-3) 0}

.linea .cuerpo{flex:1;min-width:0}
.linea .qu{font-size:var(--t);font-weight:600;line-height:1.3}
.linea .de{font-size:var(--t-m);color:var(--muted);margin-top:2px}
.linea.done .qu,.linea.done .de{opacity:.45;text-decoration:line-through}
.enlace-tienda{flex:0 0 auto;width:38px;height:38px;border-radius:50%;display:grid;place-items:center;
  background:var(--ocre-soft);color:var(--ocre);text-decoration:none}
.tienda-et{background:var(--surface-2);color:var(--muted)}

/* ---------- agenda ---------- */
.mes{display:grid;grid-template-columns:repeat(7,1fr);gap:var(--e-1);margin:0 0 var(--e-3)}
.mes-cab{font-size:var(--t-xs);font-weight:700;color:var(--muted);text-align:center;padding:var(--e-1) 0;
  text-transform:uppercase;letter-spacing:.04em}
.mes-d{aspect-ratio:1;border:0;background:var(--surface);border-radius:var(--r-s);cursor:pointer;
  font-family:var(--ui);font-size:var(--t-m);font-weight:600;color:var(--ink);display:flex;
  flex-direction:column;align-items:center;justify-content:center;gap:3px;padding:0}
/* Los días que estás fuera de casa, sombreados. Va antes que `.hoy` y `.sel` a
   propósito: son estados más fuertes y tienen que poder taparlo. Y es un fondo
   y no un punto más porque no dice «pasa algo este día», dice «no estás». */
.mes-d.fuera{background:var(--pizarra-soft)}
.mes-d.hoy{background:var(--salvia);color:var(--sobre-salvia)}
.mes-d.sel{outline:2px solid var(--salvia)}
.mes-d .pts{display:flex;gap:2px;height:4px}
.mes-d .pts i{width:4px;height:4px;border-radius:2px;display:block}
.pt-comida{background:var(--terracota)} .pt-casa{background:var(--salvia)}
.pt-compra{background:var(--ocre)}      .pt-agenda{background:var(--pizarra)}
.pt-deporte{background:var(--salvia-deep)}
.mes-d.hoy .pt-casa{background:var(--sobre-salvia)}
/* El ciclo: registrado va macizo y previsto va hueco. La diferencia entre «esto
   pasó» y «esto creo que pasará» tiene que verse sin leer nada, porque es la
   única honestidad que cabe en un punto de 5 px. */
.pt-ciclo{background:var(--danger)}
/* 1,5 px de trazo sobre un punto de 4 no deja hueco dentro: se veía macizo,
   o sea igual que el registrado. Con 1 px sí se distinguen. */
.pt-ciclo.prev{background:transparent;box-shadow:inset 0 0 0 1px var(--danger)}

.evento{display:flex;gap:var(--e-3);align-items:flex-start;background:var(--surface);
  border-radius:var(--r-l);padding:var(--e-3) var(--e-4);margin-bottom:var(--e-2);box-shadow:var(--sombra-1)}
.evento .hh{flex:0 0 46px;font-size:var(--t-m);font-weight:700;color:var(--pizarra);
  font-variant-numeric:tabular-nums;padding-top:1px}
.evento .cuerpo{flex:1;min-width:0}
.evento .qu{font-size:var(--t);font-weight:600;line-height:1.35}
.evento .de{font-size:var(--t-m);color:var(--muted);margin-top:3px;line-height:1.45}
/* Dentro de la tarjeta del día los eventos van llanos: sin fondo ni sombra,
   separados por el filo de las filas. Iban con un `style` en línea que anulaba
   la tarjeta a medias, y salían como cajas mal cortadas. */
.evento.llano{background:none;box-shadow:none;border-radius:0;padding:var(--e-3) 0;margin:0}
.evento.llano+.evento.llano{border-top:1px solid var(--line)}
/* El mando de la fila de Frecuencias: el desplegable o el «viene de…». */
.frec-mando{flex:0 0 132px}
.frec-mando .hint{margin:0;text-align:right}

/* semana tipo: los siete días con sus bloques */
.tipo-dia{background:var(--surface);border-radius:var(--r-l);padding:var(--e-3) var(--e-4);margin-bottom:var(--e-2);box-shadow:var(--sombra-1)}
.tipo-cab{display:flex;align-items:center;gap:var(--e-2);margin-bottom:var(--e-2)}
.tipo-cab b{flex:1;font-size:var(--t);font-weight:700;text-transform:capitalize}
.tipo-libre{background:var(--salvia-soft);color:var(--salvia-ink)}
.tipo-bloque{display:flex;gap:var(--e-2);align-items:center;padding:var(--e-2) 0;font-size:var(--t-b)}

.tipo-bloque .hh{flex:0 0 92px;font-size:var(--t-m);font-weight:700;color:var(--pizarra);font-variant-numeric:tabular-nums}
.tipo-bloque .qu{flex:1;min-width:0}

/* ---------- navegación inferior ---------- */
nav{position:fixed;left:0;right:0;bottom:0;background:var(--surface);
  display:flex;padding:var(--e-1) var(--e-1) calc(var(--e-2) + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)));z-index:100;
  box-shadow:0 -1px 0 var(--line), 0 -6px 18px rgba(0,0,0,.05)}
nav button{flex:1;background:none;border:0;padding:var(--e-1) 2px;cursor:pointer;font-family:var(--ui);
  font-size:var(--t-xs);color:var(--muted);font-weight:500;display:flex;flex-direction:column;
  align-items:center;gap:3px}
nav button i{font-style:normal;line-height:1;width:56px;height:30px;display:grid;
  place-items:center;border-radius:var(--r-l);transition:background .18s;position:relative}
nav button.on{color:var(--salvia);font-weight:600}
nav button.on i{background:var(--salvia-soft)}

/* El botón central: Hoy va destacado, con el nido de la app dentro de un
   círculo salvia que sobresale de la barra.
   Tres cosas que hay que dejar como están:
     · Los cinco botones siguen en `flex:1` y el círculo sale solo del tamaño
       del <i> y del translate. Con `flex:0 0 auto` los otros cuatro se
       redistribuyen y la barra baila al cambiar de pestaña.
     · El fondo salvia va **siempre**, no solo en `.on`, y hay que anular la
       píldora `--salvia-soft` del activo o se pinta encima del círculo.
     · Dentro va el **logo de la app tal cual** (iconos/nido-boton.png, que sale
       del mismo generador con `componer()`), no una versión de línea. Por eso es
       lo único de la interfaz que no va en `currentColor` ni cambia con el tema:
       el logo es el logo, con su verde hondo y sus huevos terracota, y en oscuro
       tiene que seguir siendo reconocible como la marca.
   `nav` no recorta (no tiene overflow) y va en z-index 100, así que el círculo
   sobresale por encima del contenido sin nada más. */
/* El botón central **no lleva rótulo**: el nido ya dice lo que es. Los otros
   cuatro miden icono + texto; este solo el círculo, así que su altura se iguala
   a mano con `min-height` para que la barra no cambie de alto ni se descuelgue
   ninguno. El `margin-bottom` negativo sigue descontando lo que el círculo mide
   de más (54 contra 30), que es lo que lo mantiene en su sitio. */
nav button[data-p="hoy"]{justify-content:center;min-height:47px}
nav button[data-p="hoy"] i,
nav button[data-p="hoy"].on i{width:54px;height:54px;border-radius:50%;
  background:var(--salvia-deep) url("iconos/nido-boton.png") center/cover no-repeat;
  margin-bottom:calc(-1 * var(--e-6));
  transition:transform .18s,box-shadow .18s,outline-color .18s}

/* Marcado y sin marcar tienen que distinguirse, y las cuatro pestañas normales
   lo hacen con la píldora de fondo, que aquí no cabe: el círculo ya está lleno.
   Así que va por el tamaño y el aro — más pequeño y sin aro cuando no toca,
   entero y con su aro cuando sí —. El aro es `outline` y no `border`: un borde
   cambiaría la caja y movería el círculo dos píxeles al cambiar de pestaña.

   **Apagado no se atenúa** (v2.39). Iba con `grayscale`, `brightness` y
   `opacity:.72`, y eso son cuatro de las cinco pestañas: la marca de la app
   salía gris y, como el círculo sobresale de la barra, **se veía el contenido a
   través** —el texto de la tarjeta de debajo cruzando el logo—. Parecía sucio,
   no apagado. El logo va siempre a color y opaco; lo que cambia es la escala,
   que se hace en el `transform` y no mueve la caja. */
nav button[data-p="hoy"] i{transform:translateY(-26px) scale(.9);
  box-shadow:0 1px 3px rgba(0,0,0,.14);
  outline:3px solid transparent;outline-offset:2px}
nav button[data-p="hoy"].on i{transform:translateY(-26px);
  box-shadow:0 4px 12px rgba(0,0,0,.22);
  outline-color:var(--salvia)}
nav button[data-p="hoy"]:active i{transform:translateY(-26px) scale(.86)}
@media (prefers-reduced-motion:reduce){ nav button[data-p="hoy"] i{transition:none} }
/* Con dos caracteres («9+») crecía a lo ancho y dejaba de ser un círculo, y el
   `right` fijo no lo recentraba: se descolgaba hacia la izquierda del icono. Va
   como píldora honesta —radio grande en vez de la mitad de la altura— y anclada
   por el centro, así que crecer no la mueve de sitio. */
nav .badge{position:absolute;top:1px;left:50%;transform:translateX(3px);
  min-width:16px;height:16px;border-radius:999px;
  background:var(--terracota);color:#fff;font-size:var(--t-xs);font-weight:700;display:grid;
  place-items:center;padding:0 var(--e-1);line-height:1;font-variant-numeric:tabular-nums}

.toast{position:fixed;left:50%;transform:translateX(-50%);bottom:calc(110px + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)));
  background:var(--ink);color:var(--bg);padding:var(--e-3) var(--e-5);border-radius:var(--r-l);font-size:var(--t-b);
  font-weight:500;opacity:0;transition:opacity .22s;pointer-events:none;z-index:950;max-width:86%;text-align:center}
.toast.on{opacity:1}

/* ---------- la tira de los temporizadores ----------
   Encima de la barra de abajo, en toda la app mientras corra alguno. Un solo
   temporizador —el que antes acaba—, «+1 min» y «Parar»; tocar el cuerpo lleva
   a la sesión o a la receta. La altura la descuenta el `body` y el toast con
   `html.con-tira`, o quedarían justo detrás. Nivel 110 en la escalera. */
:root{--tira-alto:48px;--nav-alto:68px}
.tira-temp{position:fixed;left:0;right:0;z-index:110;display:flex;align-items:center;gap:var(--e-2);
  bottom:calc(var(--nav-alto) + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)));
  height:var(--tira-alto);padding:0 var(--e-3);background:var(--ink);color:var(--bg);
  box-shadow:0 -4px 14px rgba(0,0,0,.12)}
/* La cifra del ajuste (v2.52): lo que queda, en grande y centrado, con la
   misma letra de cifras que la tira. */
.temp-grande{font-family:var(--cifra);font-variation-settings:var(--cifra-opsz);font-size:var(--d-l);
  font-variant-numeric:tabular-nums;text-align:center;margin:var(--e-2) 0 var(--e-4)}
.temp-grande.acabado{color:var(--terracota)}
.tira-temp-ir{flex:1;min-width:0;display:flex;align-items:center;gap:var(--e-2);background:none;border:0;
  color:inherit;font-family:var(--ui);text-align:left;min-height:44px;padding:0;cursor:pointer}
.tira-temp-que{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;
  font-size:var(--t-m);font-weight:600}
.tira-temp-que small{font-weight:500;opacity:.7}
.tira-temp-cifra{font-family:var(--cifra);font-variation-settings:var(--cifra-opsz);font-size:var(--t-l);
  font-variant-numeric:tabular-nums;flex:0 0 auto}
/* Los chips van con los tokens de superficie, que en oscuro la tira es clara
   (`--ink`) y un blanco translúcido desaparecía. */
.tira-temp .chip-reloj{background:var(--surface-2);color:var(--ink)}
.tira-temp-cifra.acabado,.chip-reloj .acabado{color:var(--terracota)}
html.con-tira body{padding-bottom:calc(96px + var(--tira-alto) + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)))}
html.con-tira .toast{bottom:calc(110px + var(--tira-alto) + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)))}

/* El chip de un paso: lanza su cuenta, o enseña la cifra viva si ya corre.
   Píldora tonal como los demás chips que se tocan; `.on` es «en marcha». */
.chip-reloj{flex:0 0 auto;display:inline-flex;align-items:center;gap:var(--e-1);min-height:32px;
  padding:var(--e-1) var(--e-3);border:0;border-radius:999px;background:var(--salvia-soft);color:var(--salvia-ink);
  font-family:var(--ui);font-size:var(--t-s);font-weight:600;cursor:pointer;white-space:nowrap}
.chip-reloj.on{background:var(--salvia);color:var(--sobre-salvia)}
.chip-reloj.on span{font-family:var(--cifra);font-variation-settings:var(--cifra-opsz);font-size:var(--t-b);
  font-variant-numeric:tabular-nums}
.chip-reloj.on.acabado{background:var(--terracota);color:#fff}
.chip-reloj.on.acabado .acabado{color:inherit}
.pasos li .chip-reloj{margin-left:var(--e-2);vertical-align:middle}
.item .b .chip-reloj{margin-top:var(--e-1)}
/* El paso que toca en la sesión en marcha, y la tarjeta «Ahora». */
.item.ahora{box-shadow:inset 3px 0 0 var(--salvia);padding-left:var(--e-2)}
.ahora-paso+.ahora-paso{margin-top:var(--e-3);padding-top:var(--e-3);border-top:1px solid var(--line)}
.tramo-grande .ahora-paso .acts{justify-content:center}

/* ---------- aviso de la pantalla de hoy ---------- */
.aviso{margin:0 var(--e-1) var(--e-3)}
.aviso-btn{display:flex;gap:var(--e-3);align-items:center;width:100%;text-align:left;border:0;cursor:pointer;
  font-family:var(--ui);background:var(--terracota-soft);color:var(--ink);
  border-radius:var(--r-l);padding:var(--e-3) var(--e-4)}
.aviso-i{display:grid;place-items:center;color:var(--terracota);flex:0 0 auto}
.aviso-btn .cuerpo{flex:1;min-width:0}
.aviso-btn strong{display:block;font-size:var(--t);font-weight:700}
.aviso-btn small{display:block;font-size:var(--t-m);color:var(--ink-2);margin-top:2px}

/* ---------- buscador ----------
   Un solo bloque, más abajo, junto al del cajón. Hubo dos: este ponía la lupa
   en absoluto y reservaba 44 px a la izquierda del input, y el del cajón,
   escrito después, quitaba ese padding sin quitar la lupa: el texto pasaba por
   debajo de ella en Recetario y en la despensa. */

/* ---------- hoja inferior ---------- */
/* La escalera de capas, entera y en un sitio, porque tenerla repartida ya costó
   un fallo: la barra de abajo (100), **la tira de los temporizadores (110)**,
   el cajón (350), las pantallas de ajustes (360 y subiendo una por cada una
   apilada), **la hoja (500)** y el toast (950).

   La tira va sobre la barra y bajo las pantallas y la hoja: con una receta
   abierta se tocan los chips de sus pasos, no la tira, y en Ajustes no se
   cocina. Se oculta con `hidden`, que la saca del árbol de toques.

   La hoja estaba en 300, o sea **por debajo** del cajón y de las pantallas. Una
   hoja abierta desde Ajustes —Diagnóstico, el registro, deshacer, restaurar una
   copia, apuntar el peso— se abría detrás y no se veía: parecía que el botón no
   hacía nada, y luego la hoja aparecía sola al cerrar los ajustes, encima de la
   pantalla principal. La hoja es lo más de encima que hay salvo el toast, que
   tiene que verse siempre porque es lo que cuenta si algo ha salido bien. */
.hoja{position:fixed;inset:0;z-index:500;display:grid;align-items:end}
.hoja-fondo{position:absolute;inset:0;background:rgba(0,0,0,.45)}
/* El asa: una hoja que sube desde abajo se coge por arriba, y sin nada que lo
   diga parece una pantalla que ha aparecido sola. Es una fibra corta —el mismo
   gesto que la costura de Hoy—, no una barra gris de sistema. */
.hoja-caja::before{content:"";position:absolute;top:8px;left:50%;transform:translateX(-50%);
  width:44px;height:4px;border-radius:2px;background:var(--line)}
.hoja-caja{position:relative;background:var(--surface);border-radius:var(--r-xl) var(--r-xl) 0 0;
  padding:20px 18px calc(20px + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)));animation:sube .2s cubic-bezier(.2,.9,.3,1);
  max-height:86vh;overflow-y:auto}
@keyframes sube{from{transform:translateY(30px);opacity:.6}to{transform:none;opacity:1}}
.hoja-titulo{font-family:var(--display);font-variation-settings:"opsz" 40;font-size:var(--d-s);
  font-weight:600;margin:0 0 var(--e-1);padding-right:44px}
.hoja-sub{font-size:var(--t-m);color:var(--muted);margin:0 0 var(--e-4)}
.hoja-x{position:absolute;top:16px;right:16px;width:36px;height:36px;border:0;border-radius:50%;
  background:var(--surface-2);color:var(--ink-2);display:grid;place-items:center;cursor:pointer}
.hoja .btn.wide small{display:block;font-weight:400;font-size:var(--t-m);opacity:.85;margin-top:3px}
/* En columna **solo el que lleva segunda línea**. Iba para todos, y el que
   lleva icono —«Ponerla un día»— lo apilaba encima del texto. */
.hoja .btn.wide:has(small){flex-direction:column;gap:0;padding:var(--e-3) var(--e-4)}

/* ---------- juego de iconos propio (app/iconos.js) ---------- */
.ico{display:block;flex:0 0 auto}
/* **Cuarenta y cuatro píxeles de dedo, aunque el dibujo mida veinte.** Los
   chips y los iconos sueltos se pintan pequeños a propósito —un chip grande
   dentro de una fila la parte—, y eso deja objetivos de toque de 20 px en los
   que hay que apuntar. El área se agranda con un `::before` transparente
   centrado, que no ocupa sitio en el flujo y no mueve nada de lo que hay al
   lado. Es la medida de la guía de Android y la de `docs/diseno.md`. */
/* El acuse de un solo uso: medio segundo de fondo que se va. Lo pone el
   pintado (`destelloDe` en app.js), así que sobrevive al `innerHTML` que
   repinta la fila entera. Con «menos movimiento» activado no se anima nada:
   el cambio de estado ya está en la propia fila. */
@keyframes nido-destello{ from{ background:var(--salvia-soft) } to{ background:transparent } }
.destello{animation:nido-destello .7s ease-out}
@media (prefers-reduced-motion:reduce){ .destello{animation:none} }

/* «−0,40 € en Alcampo»: el ahorro se dice en verde, que es la única cifra de la
   lista de la compra que es una buena noticia. */
.ahorro{color:var(--salvia);font-weight:600}
/* Cuántos coméis ese día, en la cabecera de la columna. Solo se pinta cuando no
   es el número de siempre. */
.dia-cab .cuantos{flex:0 0 auto;font-size:var(--t-xs);font-weight:700;
  background:var(--salvia-soft);color:var(--salvia-ink);
  border-radius:var(--r-s);padding:1px var(--e-1)}

.dedo{position:relative}
.dedo::before{content:"";position:absolute;top:50%;left:50%;
  width:44px;height:44px;transform:translate(-50%,-50%)}
.mini{background:none;border:0;color:var(--muted);padding:2px;cursor:pointer;
  display:grid;place-items:center;align-self:flex-start;position:relative}
.mini::before{content:"";position:absolute;top:50%;left:50%;
  width:44px;height:44px;transform:translate(-50%,-50%)}
.mini.borrar:active{color:var(--danger)}
.pill .ico,.due .ico{stroke-width:2}

/* Las acciones de cada comida son cuatro por tarjeta: en versión larga la
   pantalla de hoy se convertía en una pared de botones. Aquí van solo el icono. */
.acts.compacto button{padding:var(--e-1);width:44px;height:44px;justify-content:center}

/* ---------- la marca de agua ----------
   El nido del icono con sus tres huevos, en un SVG **en línea** dentro de
   index.html que escribe herramientas/generar_marca_agua.py. En línea y no como
   fichero suelto porque cada grupo coge su color de las variables del tema
   (`var(--salvia)`, `var(--terracota)`, `var(--bg)`), y una imagen externa vive
   en su propio documento y no las ve.
   Fue una **máscara** monocroma hasta que entraron los huevos: una máscara solo
   admite una tinta, así que los huevos salían como manchas de salvia macizo, sin
   contorno y sin las fibras de delante pasándoles por encima —que es lo único
   que dice que están dentro del nido y no delante de él—.

   Tres cosas que costaron un intento fallido:
     · Va `fixed` y colgando de <body>, no dentro de la cabecera. Dentro era
       `absolute` con z-index 0, y eso la pintaba **por encima** de las tarjetas,
       que son contenido en flujo sin posicionar.
     · Por eso mismo `z-index:-1`: la deja por debajo de todo el contenido y por
       encima del fondo de la página, que es justo donde tiene que estar.
     · Y `fixed` en vez de `absolute` porque, siendo más ancha que la pantalla,
       en absoluto generaba desbordamiento horizontal y aparecía una barra de
       desplazamiento lateral en toda la app.
   Grande y muy tenue: pequeña y opaca las fibras se apelmazan y se lee como una
   mancha de suciedad detrás del texto. */
/* `top:-4%` y no `-14%`: con el nido tan alto, los tres huevos caían justo
   detrás de los dos botones de la cabecera y del saludo, que es donde peor se
   leen —y donde el dibujo estorba en vez de acompañar—. Bajándolo diez puntos
   los huevos quedan a la altura de la primera tarjeta, sobre fondo limpio. */
.marca-agua{position:fixed;pointer-events:none;z-index:-1;display:block;
  right:-26%;top:-4%;width:96%;height:auto;aspect-ratio:1;opacity:.06}

/* La de las pantallas apiladas: `.pantalla-caja` lleva fondo `--bg` opaco e
   `inset:0`, así que las dieciséis tapaban la marca de la página entera y el
   nido solo se veía en Hoy. Va **abajo a la izquierda** para no pelear con el
   filo del acento que la cabecera de cada módulo pinta arriba. */
.pantalla-caja .marca-agua{position:absolute;z-index:0;
  right:auto;left:-32%;top:auto;bottom:-24%;width:112%;opacity:.05}
@media (prefers-color-scheme:dark){
  :root:not([data-tema="claro"]) .marca-agua{opacity:.09}
}
:root[data-tema="oscuro"] .marca-agua{opacity:.09}
/* Los días fuera de casa el nido se queda vacío. Son los grupos 2 y 3 del SVG
   —los contornos y las yemas—; las fibras no se tocan. No se anuncia con un
   toast ni con un texto: es lo mismo que la app ya hace en silencio en otras
   tres partes (no propone tareas, vacía el menú y para el reloj de los
   plazos), dicho en el único registro que no es de palabras. */
:root[data-fuera] .marca-agua > g:nth-child(2),
:root[data-fuera] .marca-agua > g:nth-child(3){display:none}
/* la cabecera se queda sin fondo propio: es del mismo color que la página y, si
   lo pinta, tapa la marca de agua justo en la zona donde mejor se ve */
header{background:none}

/* El buscador del cajón: la respuesta directa al «me pierdo». La lupa va dentro
   de la caja y no como botón: no hay nada que pulsar, se filtra al teclear. */
/* Y es el mismo bloque para los tres buscadores —cajón, Recetario y despensa—:
   la lupa va en el flujo flex, no en absoluto, así el input nunca la pisa. */
.buscador{display:flex;align-items:center;gap:var(--e-2);background:var(--surface);
  border-radius:999px;padding:0 var(--e-4);margin:0 0 var(--e-3);box-shadow:var(--sombra-1)}
.buscador i,.buscador .buscador-lupa{color:var(--muted);line-height:0;flex:0 0 auto;
  pointer-events:none;display:grid;place-items:center}
.buscador input{flex:1;min-width:0;border:0;background:none;outline:none;
  font-family:var(--ui);font-size:var(--t);color:var(--ink);padding:var(--e-3) 0}
.buscador input::placeholder{color:var(--muted)}
/* El aspa que Chrome pone en un `type="search"`: se quita, que aquí borrar es
   vaciar el campo y ya hay teclado. */
.buscador input::-webkit-search-cancel-button{display:none}
#busca-res{margin-bottom:var(--e-4)}
/* «Abrirlo todo» y «Recoger todo». El botón lleva `.a-la-derecha`, pero un
   margen automático solo empuja dentro de una fila flex: en un bloque a secas
   se quedaba a la izquierda, como un texto suelto bajo las subpestañas. */
#fin-recoger{display:flex;margin:0 var(--e-1) var(--e-2)}
#fin-recoger:empty{display:none}
#fin-recoger .btn{background:var(--pista);color:var(--ink-2);border-radius:999px;
  font-size:var(--t-m);padding:var(--e-1) var(--e-3)}

/* ---------- cajón lateral de ajustes ---------- */
.ajustes-abrir{position:absolute;top:calc(20px + var(--safe-area-inset-top, env(safe-area-inset-top, 0px)));
  right:70px;width:44px;height:44px;border:0;border-radius:50%;background:var(--surface);
  color:var(--ink);cursor:pointer;display:grid;place-items:center;line-height:1;z-index:2}
.ajustes-abrir:active{transform:scale(.94)}
/* El del asistente, a la izquierda del cajón y solo cuando hay clave. Parado
   se apaga, no se esconde: que se sepa que está y por qué. */
.asistente-abrir{position:absolute;top:calc(20px + var(--safe-area-inset-top, env(safe-area-inset-top, 0px)));
  right:122px;width:44px;height:44px;border:0;border-radius:50%;background:var(--salvia-soft);
  color:var(--salvia-ink);cursor:pointer;display:grid;place-items:center;line-height:1;z-index:2}
.asistente-abrir:active{transform:scale(.94)}
.asistente-abrir.parado{background:var(--surface);color:var(--muted)}
/* El chat: burbujas, las mías a la derecha en salvia y las de la IA a la
   izquierda en superficie; la caja de escribir pegada abajo. */
.charla{display:flex;flex-direction:column;gap:var(--e-2);padding:var(--e-2) 0 var(--e-3)}
.burbuja{max-width:86%;padding:var(--e-3) var(--e-4);border-radius:var(--r-l);font-size:var(--t);
  line-height:1.45;white-space:pre-wrap;word-break:break-word}
.burbuja.yo{align-self:flex-end;background:var(--salvia);color:var(--sobre-salvia);border-bottom-right-radius:var(--r-s)}
.burbuja.ia{align-self:flex-start;background:var(--surface);color:var(--ink);border-bottom-left-radius:var(--r-s);box-shadow:var(--sombra-1);white-space:normal}
/* El Markdown mínimo del modelo: párrafos y listas con aire, sin sangrías de más. */
.burbuja.ia p{margin:0 0 var(--e-2)}
.burbuja.ia p:last-child,.burbuja.ia ul:last-child,.burbuja.ia ol:last-child{margin-bottom:0}
.burbuja.ia ul,.burbuja.ia ol{margin:0 0 var(--e-2);padding-left:var(--e-5)}
.burbuja.ia li{margin:0 0 var(--e-1)}
.burbuja.ia code{font-family:ui-monospace,monospace;font-size:var(--t-b);background:var(--surface-2);padding:0 var(--e-1);border-radius:var(--r-s)}
.burbuja.ia.mal{background:var(--danger-soft);color:var(--danger)}
.burbuja.pensando{color:var(--muted);letter-spacing:.2em}
/* El pie **no va dentro del cuerpo que scrollea**. Era `position:sticky` ahí
   dentro, y eso deja el `padding-bottom` de safe-area del cuerpo por debajo del
   pie: en un móvil con gestos, la barra del sistema se comía la caja de
   escribir. Ahora es hermano de `.pantalla-cuerpo` dentro de `.pantalla-caja`,
   que es flex en columna, así que el cuerpo crece y esto se queda quieto abajo
   — que es justo lo que se pedía: los mensajes suben y donde se escribe no se
   mueve. */
.charla-pie{flex:0 0 auto;background:var(--bg);box-shadow:0 -1px 0 var(--line);
  padding:var(--e-2) 14px calc(var(--e-2) + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)))}
.charla-pie-caja{display:flex;gap:var(--e-2);align-items:flex-end;max-width:620px;margin:0 auto;width:100%}
/* `.area` nació en el diario y trae `min-height:150px`: aquí eso son ciento
   cincuenta píxeles de caja vacía comiéndose la conversación. Empieza en una
   línea y crece con lo escrito (`ajustarAlto`) hasta el tope. */
.charla-pie .area{flex:1;margin:0;min-height:0;max-height:40vh;resize:none;
  font-size:var(--t);overflow-y:auto}
.charla-pie .btn{flex:0 0 auto;width:48px;height:48px;padding:0;border-radius:50%;display:grid;place-items:center}
/* El micrófono del compositor, del tamaño del botón de enviar. Encendido se
   tiñe, que es lo que dice que está escuchando. */
.charla-pie .btn.ghost.redondo{width:48px;height:48px;padding:0;border-radius:50%;
  display:grid;place-items:center;flex:0 0 auto}
.charla-pie .btn.redondo.on{background:var(--salvia);color:var(--sobre-salvia)}
.charla-pie .btn.redondo:disabled{opacity:.45}
/* Apagado, pero se puede tocar: al tocarlo dice por qué no va. */
.charla-pie .btn.redondo.apagado{opacity:.45}
/* El altavoz de cada respuesta: pequeño y a la derecha, que no compite con el
   texto — leer en voz alta es lo raro, no lo normal. */
.burbuja .chip-voz{margin-top:var(--e-2);padding:2px var(--e-2);opacity:.75}

/* Un gráfico dentro de una burbuja. La burbuja va al 86 % y un gráfico
   necesita el ancho entero, así que la que lleva dibujo se estira. */
.burbuja.ia:has(.graf-ia){max-width:100%;width:100%}
.graf-ia{margin:var(--e-3) 0 var(--e-2)}
.graf-ia:first-child{margin-top:0}
.graf-ia:last-child{margin-bottom:0}
.graf-ia .graf-t{margin:0 0 var(--e-2);font-size:var(--t-m);color:var(--muted)}

/* Una imagen pedida al proveedor. No se guarda en la charla: vive en memoria
   mientras dura la pantalla, y por eso lleva su botón de guardar. */
.burbuja.ia:has(.img-ia){max-width:100%;width:100%}
.img-ia{margin:var(--e-2) 0;padding:0}
.img-ia img{width:100%;border-radius:var(--r-m);display:block}
.img-ia figcaption{display:flex;gap:var(--e-2);align-items:center;justify-content:space-between;
  margin-top:var(--e-2);flex-wrap:wrap}
.pensando-img{color:var(--muted);font-style:italic}

/* Los chips de arranque: no son una respuesta, son por dónde empezar. */
.charla-sugerencias{display:flex;flex-wrap:wrap;gap:var(--e-2);justify-content:center;margin-top:var(--e-3)}
.area.contexto{white-space:pre-wrap;font-size:var(--t-s)}
/* El subtítulo no entra: queda por debajo de los botones, así que reservarles
   sitio ahí solo servía para partir la línea («ahorras el / 34 %»). */
.eyebrow,header h1{padding-right:126px}

/* El cajón lateral se fue en la v2.4: era un segundo sistema de navegación en
   paralelo al de las pestañas, y su contenido es ahora la pestaña «Todo». Con él
   se fue el nivel 350 de la escalera de capas, que queda: barra abajo 100,
   pantallas apiladas 360+, hoja 500, fallo 900, toast 950, marca de agua −1. */

/* ---------- la cuenta y el estado de la salud ---------- */
.cuenta-fila{display:flex;align-items:center;gap:var(--e-3)}
.avatar{width:44px;height:44px;border-radius:50%;flex:0 0 auto;display:grid;place-items:center;
  background:var(--salvia);color:var(--sobre-salvia);font-size:var(--t-xxl);font-weight:700;line-height:1}
.avatar.sin{background:var(--surface-2);color:var(--muted)}
.cuenta-quien{flex:1;min-width:0}
.cuenta-quien b{display:block;font-size:var(--t-l);line-height:1.3}
.cuenta-quien small{display:block;font-size:var(--t-m);color:var(--muted);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
/* La franja de la demo de la web: arriba del todo, en el verde del icono, y
   pegada al techo mientras se desplaza, que la demo tiene que decir que lo es
   en todas las pantallas. Va por debajo de la barra de abajo (100). */
.aviso-demo{position:sticky;top:0;z-index:90;margin:0;padding:var(--e-2) var(--e-4);
  background:var(--salvia);color:var(--sobre-salvia);font-size:var(--t-m);text-align:center;line-height:1.4}
.aviso-demo a{color:inherit;font-weight:700;margin-left:var(--e-2)}
/* La sincronización completa, dentro de la tarjeta de la cuenta, y el código de
   rescate: grande, en cifras de ancho fijo y partible por los guiones, que se
   copia a mano a un papel y no puede saltar de línea a mitad de un grupo. */
.cuenta .sincro{margin-top:var(--e-3);padding-top:var(--e-3);border-top:1px solid var(--line)}
.codigo-rescate{font-size:var(--t-xl);font-weight:700;letter-spacing:.06em;text-align:center;
  font-variant-numeric:tabular-nums;word-spacing:.2em;margin:var(--e-3) 0;padding:var(--e-3);
  background:var(--surface-2);border-radius:var(--r-m);user-select:all;overflow-wrap:anywhere}
/* El punto de color es lo que hace que el estado se lea sin leerlo. Verde, ámbar
   y gris, y no rojo: que la salud no esté conectada no es un error. */
.punto{display:inline-block;width:8px;height:8px;border-radius:50%;margin-right:var(--e-1);
  vertical-align:baseline;flex:0 0 auto}
.punto.verde{background:var(--ok)}
.punto.ambar{background:var(--ocre)}
.punto.gris{background:var(--muted);opacity:.5}
.punto.rojo{background:var(--danger)}
/* El aro de la Energía: un número del 0 al 100 se lee mejor con la porción
   pintada al lado. `conic-gradient` y una máscara: nada de SVG para esto. */
.aro{width:34px;height:34px;border-radius:50%;flex:0 0 auto;
  background:conic-gradient(currentColor calc(var(--p) * 1%), var(--surface-2) 0);
  -webkit-mask:radial-gradient(circle, transparent 58%, #000 59%);
          mask:radial-gradient(circle, transparent 58%, #000 59%)}
/* Dos juegos de nombres para el mismo aro: los de la escala de la app
   (alta/media/baja) y los de las cuatro bandas de Samsung, que es la que manda
   cuando su puntuación llega. Sin los segundos, el aro se quedaba sin color y
   parecía roto justo cuando el dato era bueno. */
.aro.alta,      .aro.excelente{color:var(--ok)}
.aro.buena{color:var(--ok)}
.aro.media,     .aro.regular{color:var(--ocre)}
.aro.baja,      .aro.atencion{color:var(--terracota)}
.salud-cab .item .b strong{font-family:var(--cifra);font-variation-settings:var(--cifra-opsz);
  font-size:var(--t-xxl);font-variant-numeric:tabular-nums;line-height:1.15}
.de100{font-size:var(--t-s);font-weight:500;color:var(--muted)}
/* La lista de qué llega y qué no, dato a dato. En dos columnas: son once y en
   una sola la tarjeta se convierte en una pared. */
.datos{display:grid;grid-template-columns:1fr;gap:2px}
@media (min-width:380px){ .datos{grid-template-columns:1fr 1fr;gap:2px var(--e-3)} }
.dato{display:flex;align-items:center;gap:var(--e-1);padding:var(--e-1) 0;font-size:var(--t-m);min-width:0}
.dato span{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.dato b{font-weight:500;color:var(--muted);font-size:var(--t-s);flex:0 0 auto}
/* Un error de Android, entero. Va aparte de la fila porque ahí el
   `text-overflow` corta por el final, y en un `NoClassDefFoundError` el nombre
   de la clase que falta está justo al final: se perdía lo único que servía. */
.fallo-largo{margin:0 0 var(--e-1);font-family:ui-monospace,Menlo,Consolas,monospace;
  font-size:var(--t-xs);line-height:1.5;color:var(--ink-2);background:var(--surface-2);
  border-radius:var(--r-s);padding:var(--e-2) var(--e-2);word-break:break-all}
/* De quién es cada tarea, cuando hay casa compartida. */
.dequien{flex:0 0 auto;align-self:center;border-radius:var(--r-s);padding:3px var(--e-2);
  font-size:var(--t-xs);white-space:nowrap}
.dequien.libre{background:var(--surface-2);color:var(--muted)}
.dequien.mia{background:var(--salvia-soft);color:var(--salvia-ink)}
.dequien.suya{background:var(--pizarra-soft);color:var(--pizarra)}

/* ---------- pantalla de ajustes ----------
   Va por encima del cajón (z-index 360 contra 350) porque se abre desde él y
   tiene que taparlo, y entra desde la derecha igual, para que volver atrás sea
   el mismo gesto. Ocupa el ancho entero: son formularios, y una columna de 88vw
   con campos numéricos se lee peor que la pantalla completa. */
/* Las filas del índice de Ajustes: una por grupo, con lo que hay dentro
   resumido debajo. Van agrupadas en una sola tarjeta, como en One UI, y no
   sueltas: seis tarjetas de una fila cada una es la misma pared con más aire. */
.filas{background:var(--surface);border-radius:var(--r-l);overflow:hidden;
  margin:0 0 var(--e-4);box-shadow:var(--sombra-1)}
.fila-aj{display:flex;align-items:center;gap:var(--e-3);width:100%;background:none;border:0;
  border-top:1px solid var(--line);padding:var(--e-3) var(--e-4);cursor:pointer;text-align:left;
  font-family:var(--ui);color:var(--ink)}
.fila-aj:first-child{border-top:0}
.fila-aj:active{background:var(--surface-2)}
.fila-aj .cuerpo{flex:1;min-width:0}
.fila-aj .qu{display:block;font-size:var(--t-l);font-weight:600;line-height:1.3}
.fila-aj .de{display:block;font-size:var(--t-m);color:var(--muted);margin-top:2px;
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.fila-aj .ico-der{color:var(--muted);flex:0 0 auto}
/* Las filas del índice que no tienen nada que contar, al final y en gris. No se
   esconden —salir en el índice es lo que dice que el interruptor hizo algo—,
   pero dejan de pesar lo mismo que la que avisa de dos plantas sin regar. Sin
   flecha a propósito: la flecha promete que dentro hay algo. */
.fila-aj.vacia .qu{color:var(--muted);font-weight:500}
.fila-aj.vacia .ico-tarea{opacity:.55}

/* Los cuatro objetivos en dos columnas: en una sola son cuatro campos altos
   seguidos y la tarjeta se va de pantalla. */
.rejilla-obj{display:grid;grid-template-columns:1fr 1fr;gap:var(--e-3);margin-bottom:var(--e-3)}
/* En dos columnas la etiqueta va encima y no al lado: al lado, «Calorías» se
   come la mitad del ancho y el número no cabe. La unidad va en la etiqueta,
   como en el resto de la app. */
.rejilla-obj .campo{display:block;margin:0}
.rejilla-obj .campo span{display:block;margin-bottom:var(--e-1);font-size:var(--t-m);color:var(--muted)}
.rejilla-obj .campo input{width:100%;padding:var(--e-3) var(--e-3)}

.pantalla{position:fixed;inset:0;z-index:360}
.pantalla-caja{background:var(--bg);width:100%;height:100%;
  display:flex;flex-direction:column;overflow:hidden;
  transform:translateX(100%);transition:transform .22s cubic-bezier(.2,.9,.3,1)}
.pantalla.abierto .pantalla-caja{transform:none}
@media (prefers-reduced-motion:reduce){ .pantalla-caja{transition:none} }
/* El contenido va por encima de la marca clonada. Se le pone a los dos hijos
   directos y no con `.pantalla-caja>*:not(.marca-agua)`, que es exactamente la
   forma en que `header>*:not(.marca-agua)` rompió los dos botones de la
   cabecera: una regla así pisa el `position` de lo que toque. */
.pantalla-cab,.pantalla-cuerpo{position:relative;z-index:1}
.pantalla-cab{display:flex;align-items:center;gap:var(--e-2);background:var(--surface);
  box-shadow:0 1px 0 var(--line);
  padding:calc(14px + var(--safe-area-inset-top, env(safe-area-inset-top, 0px))) 14px 14px}
.pantalla-cab h2{flex:1;margin:0;font-family:var(--display);font-variation-settings:"opsz" 40;
  font-size:var(--d-s);font-weight:600}
.pantalla-cab .hoja-x{position:static;background:none}
.pantalla-cuerpo{flex:1;min-height:0;overflow-y:auto;
  padding:14px 14px calc(24px + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)));
  max-width:620px;margin:0 auto;width:100%}

/* ---------- despensa: agrupada y con unidades ---------- */
.contador{display:flex;align-items:center;gap:2px;flex:0 0 auto}
.contador button{width:34px;height:34px;border:0;border-radius:50%;background:var(--surface-2);
  color:var(--ink-2);cursor:pointer;display:grid;place-items:center;font-family:var(--ui)}
.contador button:active{background:var(--salvia);color:var(--sobre-salvia)}
.contador b{min-width:26px;text-align:center;font-size:var(--t-l);font-weight:700;
  font-variant-numeric:tabular-nums}
/* Nada de teñir «queda uno»: recién sembrada la despensa está entera a uno y
   salía todo en rojo, como si pasara algo. El número ya lo dice. */

/* ---------- tiendas en ajustes ---------- */
/* La fila con interruptor: icono a la izquierda, texto que crece, interruptor a
   la derecha. Solo el cuerpo lleva `flex:1`; los otros dos van a su tamaño. Es
   la forma de todas las filas de Ajustes, y `.tienda-fila` es el mismo componente
   con otro nombre por razones históricas. */
.fila-sw,
.tienda-fila{display:flex;align-items:center;gap:var(--e-3);padding:var(--e-3) 0}

.fila-sw>.ico-tarea{flex:0 0 auto}
.fila-sw .cuerpo,
.tienda-fila .cuerpo{flex:1;min-width:0}
.fila-sw .qu,
.tienda-fila .qu{font-size:var(--t);font-weight:600}
.fila-sw .de,
.tienda-fila .de{font-size:var(--t-m);color:var(--muted);margin-top:2px;line-height:1.4}
/* Una casilla dentro de una fila. La regla de los campos de formulario
   (`input{width:100%}`) también le llega a un `<input type="checkbox">`, y en
   una fila flex eso lo estira hasta 333 px y aplasta al hermano hasta dejarlo
   en cero: el texto sale una palabra por línea. Es exactamente la trampa de
   `.todo` en la lista de la compra, que se resolvió con `.casilla`. */
.check-fila{flex:0 0 auto;width:auto;min-width:22px;min-height:22px;
  accent-color:var(--salvia)}

.interruptor{flex:0 0 auto;width:50px;height:30px;border:0;border-radius:var(--r-m);cursor:pointer;
  background:var(--surface-2);position:relative;transition:background .18s}
.interruptor::after{content:"";position:absolute;top:3px;left:3px;width:24px;height:24px;
  border-radius:50%;background:var(--sw-bola);transition:transform .18s;
  box-shadow:0 1px 3px rgba(0,0,0,.28)}
.interruptor.on{background:var(--salvia)}
.interruptor.on::after{transform:translateX(20px)}

/* ---------- la pantalla de fallo ----------
   Tapa la app entera a propósito: si el arranque no ha terminado, lo que hay
   debajo está a medio pintar y no se puede usar. Va por encima de todo, incluso
   de las hojas y del cajón. */
.fallo{position:fixed;inset:0;z-index:900;background:var(--bg);
  display:grid;place-items:center;padding:var(--e-6);
  padding-bottom:calc(24px + var(--safe-area-inset-bottom, env(safe-area-inset-bottom, 0px)));
  padding-top:calc(24px + var(--safe-area-inset-top, env(safe-area-inset-top, 0px)))}
.fallo-caja{background:var(--surface);border-radius:var(--r-xl);padding:var(--e-6) var(--e-5);
  max-width:420px;width:100%;text-align:center}
.fallo-ico{color:var(--terracota);display:block;margin:0 auto var(--e-2)}
.fallo-caja h2{font-family:var(--display);font-size:var(--d-s);margin:0 0 var(--e-2);letter-spacing:-.01em}
.fallo-caja p{font-size:var(--t);color:var(--ink-2);line-height:1.55;margin:0 0 var(--e-5)}
.fallo-caja .btn{margin-top:var(--e-2)}

/* El registro, en la hoja: texto corrido y monoespaciado, que se lee mal pero se
   pega bien en un correo, que es para lo que está. */
pre.registro{background:var(--surface-2);border-radius:var(--r-m);padding:var(--e-3);
  font-size:var(--t-s);line-height:1.5;white-space:pre-wrap;word-break:break-word;
  max-height:46vh;overflow:auto;margin:0;color:var(--ink-2)}

/* La caducidad, en la despensa. Tres estados y ni uno más: lo que ya se pasó,
   lo de esta semana y lo que aún aguanta —que no se pinta—. */
.cad{font-weight:600}
.cad.pasado,.cad.hoy{color:var(--danger)}
.cad.pronto{color:var(--ocre)}
/* El chip de fecha de cada línea de la despensa. Se enseña siempre, también
   cuando no hay fecha apuntada: un botón que solo aparece cuando ya sabes que
   existe no lo encuentra nadie. */
.cad-chip{margin-top:var(--e-1);display:inline-flex;align-items:center;gap:var(--e-1);
  border:0;border-radius:var(--r-s);padding:3px var(--e-2);cursor:pointer;font-family:var(--ui);
  font-size:var(--t-s);font-weight:600;background:var(--surface-2);color:var(--muted)}
.cad-chip.sin{font-weight:500}
.cad-chip.pronto{background:var(--ocre-soft);color:var(--ocre)}
.cad-chip.hoy,.cad-chip.pasado{background:var(--danger-soft);color:var(--danger)}

/* La cantidad de una fila de la despensa es un **chip que se toca**: abre
   «¿cuánto queda?». Va sin fondo para no competir con el de la caducidad, que
   está justo debajo y sí tiene color cuando urge; lo que dice que se puede
   tocar es el subrayado punteado, que es lo que llevan los demás textos
   accionables de la casa. */
.cant-chip{border:0;background:none;padding:0;cursor:pointer;font:inherit;color:inherit;
  text-decoration:underline dotted;text-underline-offset:3px}
.cant-chip:active{color:var(--salvia)}

/* Comer fuera: la rejilla de tipos rellena los campos y los campos se pueden
   retocar. Los dos caminos a la vez, en la misma hoja. */
.tipos-fuera{display:flex;flex-wrap:wrap;gap:var(--e-2);margin-bottom:var(--e-3)}
.campos-fuera{display:grid;grid-template-columns:1fr 1fr;gap:var(--e-2);margin-bottom:var(--e-3)}

/* El aviso con «Deshacer» necesita recibir el toque: el aviso a secas lleva
   pointer-events:none para no comerse los clics de lo que hay debajo.

   **Y solo mientras se ve** (`.on`). Sin esa condición, el toast se quedaba
   capturando los toques después de desvanecerse: `.con-boton` no se quitaba al
   ocultarlo, así que quedaba un rectángulo invisible con un botón «Deshacer»
   dentro, justo encima de la barra de abajo —donde acaban casi todos los
   botones de una tarjeta—. Tocabas ahí y **se deshacía lo último que habías
   hecho**, sin haber pedido nada. Atar el poder recibir toques a estar visible
   es lo que hace que no se pueda volver a olvidar. */
.toast.con-boton.on{pointer-events:auto}
.toast.con-boton{padding-right:var(--e-2)}
.toast-btn{background:none;border:0;color:var(--salvia);font:inherit;font-weight:700;
  padding:var(--e-2) var(--e-3);margin-left:var(--e-1);border-radius:var(--r-m);cursor:pointer;min-height:44px}
.toast-btn:active{background:rgba(255,255,255,.14)}

/* ---------- accesibilidad ----------
   Medido en la última revisión: cero aria-live, cero focus(), cero tabindex.
   Esto es la parte que se ve; el resto está en nucleo/foco.js. */

/* Un foco que no se ve deja el teclado inservible, y no había ninguno. Va con
   :focus-visible para que no salte al tocar con el dedo. */
:focus-visible{outline:3px solid var(--salvia);outline-offset:2px;border-radius:6px}
.mes-d:focus-visible,.casilla:focus-visible{outline-offset:1px}
/* El foco de una fila de índice va **hacia dentro**. `.filas` lleva
   `overflow:hidden` para redondear las esquinas del grupo, y eso recorta el aro
   de la primera fila por arriba y por los lados: lo único que sobrevive es su
   borde de abajo, o sea una raya verde suelta bajo la primera fila. Y como el
   cajón atrapa el foco al abrirse, esa raya salía **siempre**, sin que nadie
   hubiera tocado nada. Con el desplazamiento hacia dentro el aro cabe entero. */
.filas .fila-aj:focus-visible{outline-offset:-3px;border-radius:var(--r-l)}

/* Objetivo táctil de 44 px sin cambiar el dibujo: se agranda el área sensible
   con un pseudoelemento en vez de engordar el botón, que descuadraría la fila. */
.casilla{min-width:44px;min-height:44px}
.contador button{position:relative}
.contador button::before,.hoja-x::before{content:"";position:absolute;
  top:50%;left:50%;transform:translate(-50%,-50%);width:44px;height:44px}

/* ---------- la bienvenida ---------- */
.bienvenida .fallo-caja{text-align:left;max-height:88vh;overflow:auto}
.bien-pasos{font-size:var(--t-s);font-weight:700;letter-spacing:.06em;text-transform:uppercase;
  color:var(--salvia);margin:0 0 var(--e-1)}
.bienvenida h2{font-family:var(--display);font-size:var(--d-m);margin:0 0 var(--e-2);letter-spacing:-.01em}
.bienvenida p{font-size:var(--t);color:var(--ink-2);line-height:1.55;margin:0 0 var(--e-4)}
.campo{display:flex;align-items:center;gap:var(--e-2);font-size:var(--t);color:var(--ink-2);
  margin:0 0 var(--e-4)}
.campo span{flex:0 0 auto;font-weight:600;color:var(--ink)}
.campo .unidad{flex:0 0 auto;font-size:var(--t);font-weight:700;color:var(--muted)}
.campo input{flex:1;min-width:0;background:var(--surface-2);border:0;border-radius:var(--r-m);
  padding:var(--e-3) var(--e-4);font:inherit;font-size:var(--t-xl);font-weight:700;color:var(--ink)}
/* La hora de una tarea, debajo de su frecuencia en la lista de Casa. Va en la
   misma columna estrecha, así que no puede heredar el `padding` de `.campo
   input` ni su 17px o rompe la fila en dos líneas. */
.hora-tarea{width:100%;margin-top:var(--e-1);background:var(--surface-2);border:0;
  border-radius:var(--r-s);padding:var(--e-2) var(--e-2);font:inherit;font-size:var(--t-b);
  font-weight:600;color:var(--ink)}
.hora-tarea:invalid{color:var(--muted)}

.bien-rejilla{display:flex;flex-wrap:wrap;gap:var(--e-2);margin:0 0 var(--e-5);max-height:44vh;overflow:auto}
.bien-chip{background:var(--surface-2);color:var(--ink-2);border:2px solid transparent;
  border-radius:var(--r-l);padding:var(--e-2) var(--e-3);min-height:44px;font:inherit;font-size:var(--t-b);
  font-weight:600;cursor:pointer;display:flex;align-items:center;gap:var(--e-2)}
.bien-chip.ancho{flex:1 1 44%}
.bien-chip.on{background:var(--salvia-soft);border-color:var(--salvia);color:var(--salvia-ink)}

/* ---------- fotos de las recetas ----------
   Una receta sin foto no puede quedar como un hueco gris: el marcador lleva el
   icono de su momento del día y a tamaño de tarjeta se lee como ilustración. */
.foto-receta{width:100%;border-radius:var(--r-m);overflow:hidden;margin:0 0 var(--e-3);
  background:var(--surface-2);display:grid;place-items:center}
.foto-receta img{width:100%;height:100%;object-fit:cover;display:block}
.foto-receta.sin{background:var(--terracota-soft);color:var(--terracota)}
.receta .foto-receta{margin:0 0 var(--e-2)}

/* El selector de raciones de la ficha */
.raciones{display:flex;align-items:center;gap:var(--e-3);margin:0 0 var(--e-3)}
.raciones>span{font-size:var(--t);font-weight:600;color:var(--ink)}

/* ---------- precios ----------
   El precio es un botón: tocarlo es corregirlo. El tuyo se distingue del
   orientativo, porque no es lo mismo un dato tuyo que una estimación. */
.precio-et{flex:0 0 auto;border-radius:var(--r-s);padding:var(--e-2) var(--e-2);min-height:44px;
  font-size:var(--t-b);font-weight:700;color:var(--ink-2);font-variant-numeric:tabular-nums}
.precio-et.mio{background:var(--salvia-soft);color:var(--salvia-ink)}
.pie-lista{text-align:center;margin:var(--e-3) 0 var(--e-1)}
.pie-lista p{margin:0 0 var(--e-1);font-size:var(--t)}
.pie-lista b{font-size:var(--t-xxl);font-family:var(--cifra);
  font-variation-settings:var(--cifra-opsz);font-variant-numeric:tabular-nums}

/* La línea de la evolución del peso. Va con `non-scaling-stroke` porque el SVG
   se estira a lo ancho con `preserveAspectRatio="none"`: sin eso el trazo se
   deforma con él y sale una línea gruesa en un lado y fina en el otro. */
.linea-caja{flex:0 0 92px;color:var(--salvia);line-height:0}
/* La línea de Salud la pinta ahora `Graf.lineaSVG`, que emite `.graf.graf-linea`
   (ancho 100 %, alto 56). Hace falta esta especificidad para acotarla a la caja. */
.linea-caja .graf.graf-linea{width:92px;height:44px}
/* ---------- la pantalla de Salud ----------
   Las barras por día: pasos y sueño. Un hueco se pinta como hueco —la columna
   vacía y un guion debajo— y no como cero: el día que el móvil se quedó en casa
   no es un día sentado, y una barra a cero diría que sí.

   Van con `overflow-x:auto` porque con treinta días no caben, y el cuerpo de la
   página nunca puede desplazarse a lo ancho. */
.barras{display:flex;gap:var(--e-1);align-items:flex-end;margin:var(--e-3) 0 var(--e-1);
  overflow-x:auto;scrollbar-width:none;padding-bottom:2px}
.barras::-webkit-scrollbar{display:none}
.bd{flex:1 0 26px;min-width:26px;text-align:center}
.bd-t{height:74px;display:flex;align-items:flex-end;justify-content:center;
  background:var(--surface-2);border-radius:var(--r-s);overflow:hidden}
.bd-t i{display:block;width:100%;background:var(--salvia);border-radius:var(--r-s)}
.barras.sueno .bd-t i{background:var(--pizarra)}
.barras.pasos .bd-t i{background:var(--salvia)}
.bd.vacia .bd-t{opacity:.55}
.bd span{display:block;font-size:var(--t-xs);color:var(--muted);margin-top:var(--e-1)}
.bd b{display:block;font-size:var(--t-xs);font-weight:600;font-variant-numeric:tabular-nums}
.bd.vacia b{color:var(--muted);font-weight:400}
/* La cabecera de la pantalla: la Energía, encima de las subtabs y siempre a la
   vista. Sin margen abajo porque las subtabs ya traen el suyo. */
.salud-cab{margin-bottom:var(--e-3)}
/* Las subtabs dentro de una pantalla apilada se estrenan aquí. El `#salud-rango`
   va debajo y con menos aire que un `.seg` suelto: son dos filas de controles
   seguidas y con el margen normal la primera tarjeta se iba al fondo. */
#salud-rango{margin:0 var(--e-1) var(--e-4)}

/* La lista de redes de casa, para que las filas no se peguen al botón de abajo. */
.lista-redes{margin:var(--e-1) 0 var(--e-2)}

/* El chip de posponer. Vive **dentro** del botón de la tarea, así que su rama
   del listener va antes que la de `hacer-tarea` (ver app.js): si no, tocarlo la
   marcaría como hecha. Es la misma trampa que el chip de «de quién es». */
.posponer{flex:0 0 auto;align-self:center;border-radius:var(--r-s);padding:var(--e-1) var(--e-2);
  background:var(--surface-2);color:var(--muted);line-height:0;cursor:pointer;position:relative}
.posponer::before{content:"";position:absolute;top:50%;left:50%;
  width:44px;height:44px;transform:translate(-50%,-50%)}
.posponer:active{background:var(--ocre-soft)}
/* Lo que va colgado de otra tarea —el buzón de la basura— entra un poco y con
   una guía, para que se lea como «de paso» y no como una tarea más de la lista. */
.todo.colgada{padding-left:var(--e-5);position:relative}
.todo.colgada::before{content:"";position:absolute;left:10px;top:12px;bottom:12px;
  width:2px;border-radius:2px;background:var(--surface-2)}

/* El «ver receta» de la rejilla de la semana. Va dentro del botón de la ranura,
   como el chip de posponer en las tareas: `closest()` coge el de más adentro, así
   que se queda el toque sin robárselo al de cambiar de plato. */
.ranura .ver-r{flex:0 0 auto;color:var(--muted);line-height:0;padding:var(--e-1) 2px var(--e-1) var(--e-1);cursor:pointer;position:relative}
.ranura .ver-r::before{content:"";position:absolute;top:50%;left:50%;
  width:44px;height:44px;transform:translate(-50%,-50%)}
.ranura .ver-r:active{color:var(--terracota)}
/* El chip de tupper de la ranura: apagado va como el de ver la receta, en
   `--muted`; encendido, salvia, que es «esta comida te la llevas». */
.ranura .tup.on{color:var(--salvia)}

/* Un paso de la coreografía del domingo que esta semana no hace falta. Se apaga
   en vez de quitarse: la coreografía es un reloj y borrar un paso dejaría los
   minutos de los demás mintiendo. */
.item.apagado{opacity:.42}
.item.apagado strong{font-weight:500;text-decoration:line-through}

/* ---------- la pantalla de Hoy (v2.1) ----------
   Eran once tarjetas seguidas, todas del mismo tamaño y con la misma cabecera,
   y por tanto ninguna mandaba. Ahora hay dos bandas:

     · Arriba, a lo que uno abre la app: qué come, qué tiene que hacer, qué se
       le va a echar a perder y qué se le pasa.
     · Debajo de «También hoy», lo que está bien tener a mano y no es la razón
       de entrar: la salud, el armario, el ciclo, los suplementos y el diario.

   La segunda banda no esconde nada —sigue entera y con sus acciones—, va más
   compacta y con menos peso. Bajar el tamaño del titular es lo que de verdad
   hace la jerarquía; el resto son ajustes de aire. */
/* La costura entre las dos bandas de Hoy. Era un rótulo suelto con margen: la
   decisión de forma más importante de la v2.1 la sostenía un `<p>` y nada más.
   La línea es **una fibra del propio nido** —sacada de la misma siembra que
   dibuja la marca de agua, con su curvatura y su desnivel—, no un `border-top`,
   que es lo que pondría cualquiera. Va en `currentColor`, así que cambia sola
   con el tema, y `preserveAspectRatio:none` la deja estirarse al ancho que
   sobre, que es lo que hace una fibra de verdad. */
.hoy-costura{margin:var(--e-6) var(--e-1) var(--e-3);width:calc(100% - var(--e-2));
  display:grid;grid-template-columns:auto 1fr auto;align-items:center;gap:var(--e-3);
  background:none;border:0;padding:0;cursor:pointer;text-align:left;font-family:var(--ui)}
.hoy-costura .et{font-size:var(--t-m);font-weight:700;letter-spacing:.06em;
  text-transform:uppercase;color:var(--muted);
  /* La etiqueta puede llevar icono delante —las zonas de Frecuencias lo llevan—,
     así que alinea lo que le metan en vez de suponer que es solo texto. */
  display:inline-flex;align-items:center;gap:var(--e-2)}
/* Lo que hay dentro, dicho en la propia costura: plegar sin decir qué se ha
   plegado sí sería esconderlo. Ocupa toda la segunda línea de la rejilla. */
.hoy-costura .que{grid-column:1 / 3;font-size:var(--t-m);color:var(--muted);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.hoy-costura .ch{grid-row:1 / 3;grid-column:3;color:var(--muted);line-height:0;
  transform:rotate(90deg);transition:transform .18s ease}
.hoy-costura .ch.abierta{transform:rotate(-90deg)}
@media (prefers-reduced-motion:reduce){ .hoy-costura .ch{transition:none} }
.costura-fibra{color:var(--line);line-height:0;min-width:0}
/* Varios plegables en una sola tarjeta (`pliegues()` en app.js). La costura
   trae el aire de quien separa dos bandas de una página; dentro de una lista
   sobra, y es lo que hacía que cada zona de Frecuencias midiera 110 px. */
.card.pliegues{padding-top:var(--e-1);padding-bottom:var(--e-1)}
.pliegue{border-top:1px solid var(--line);padding:var(--e-1) 0}
.pliegue:first-child{border-top:0}
.pliegue>.hoy-costura{margin:var(--e-2) 0;width:100%}
.hoy-secundario .card{padding:var(--e-3) var(--e-4);border-radius:var(--r-l)}
.hoy-secundario .card-t{margin-bottom:var(--e-2)}
.hoy-secundario .card-t h3{font-size:var(--t)}
.hoy-secundario .card-t .ico{color:var(--muted)}

/* El subtítulo de cada dominio dentro de «No se te olvide». Seis listas
   seguidas sin nada que las separe se leen como un revoltijo; con esto se ve de
   un vistazo que lo de arriba es el coche y lo de abajo, las plantas.
   Va en el hueco del icono de las filas (`.item .ico-izq`) para que el título y
   los elementos que cuelgan de él queden en la misma columna. */
.grupo-t{display:flex;align-items:center;gap:var(--e-2);margin:var(--e-3) 0 var(--e-1);
  font-size:var(--t-xs);font-weight:700;letter-spacing:.06em;text-transform:uppercase;
  color:var(--muted)}
.grupo-t:first-child{margin-top:0}
/* La fila que va justo detrás de un título de grupo no lleva filo: el título ya
   separa, y con los dos se ve una raya doble. */
.grupo-t + .item{border-top:0}

/* ---------- el índice de módulos, por familias (v2.1) ----------
   El cajón era una lista plana de hasta ocho filas idénticas, que es el mismo
   reproche que `index.html` le hacía a la versión anterior. Ahora va por
   familias, y cada una tiñe el icono de sus filas: una fila se reconoce por el
   color antes de leerla.

   El acento va **solo en el icono**, no en el texto ni en el fondo. Con la fila
   entera teñida, tres familias seguidas convierten el cajón en un semáforo y se
   pierde justo lo que se quería: poder recorrerlo de un vistazo. */
.indice-t{margin:var(--e-5) var(--e-1) var(--e-2)}
.indice-t:first-child{margin-top:var(--e-1)}
.fila-aj .ico-tarea{color:var(--muted)}
.fila-aj.ac-cuerpo .ico-tarea{color:var(--ac-cuerpo)}
.fila-aj.ac-casa   .ico-tarea{color:var(--ac-casa)}
.fila-aj.ac-vida   .ico-tarea{color:var(--ac-vida)}

/* ---------- las pantallas de módulo (v2.1) ----------
   Las ocho `mod-*` se veían exactamente iguales: la misma cabecera blanca con
   el mismo título negro. El acento de familia va en un filo bajo la cabecera y
   en el icono de vuelta, que es suficiente para saber dónde estás sin leer y no
   convierte la pantalla en un tema de color. */
.pantalla-cab{border-bottom:3px solid transparent}
.pantalla.ac-cuerpo .pantalla-cab{border-bottom-color:var(--ac-cuerpo)}
.pantalla.ac-casa   .pantalla-cab{border-bottom-color:var(--ac-casa)}
.pantalla.ac-vida   .pantalla-cab{border-bottom-color:var(--ac-vida)}

/* ---------- el estado vacío de un módulo (v2.1) ----------
   Una planta o un animal recién dados de alta tardan en tener nada que contar,
   y hasta entonces la pantalla era una tarjeta pequeña arriba del todo con
   ochocientos píxeles de vacío debajo: se lee como que algo ha fallado.

   Decir «aquí todavía no hay nada» está permitido en esta casa —lo hacen
   `ritmoDe`, `kmMes` y `edadEn` cuando no saben—, pero hay que **decirlo bien**.
   Así que la tarjeta se centra, respira y el título es de titular: es la única
   cosa de la pantalla, y tiene que parecer que está ahí a propósito. */
.vacio-mod{margin-top:var(--e-6);padding:var(--e-6) var(--e-5) var(--e-5);
  text-align:center;box-shadow:var(--sombra-2)}
.vacio-mod .card-t{flex-direction:column;gap:var(--e-2);margin-bottom:var(--e-3)}
/* Un punto por debajo del titular de la pantalla (`--d-s`): los dos en
   Fraunces al mismo tamaño competían, y el que manda es el de la cabecera. */
.vacio-mod .card-t h3{font-family:var(--display);font-variation-settings:"opsz" 40;
  font-size:var(--t-xxl);font-weight:600;flex:none}
/* El icono grande y en su acento: es lo que dice de qué módulo está vacío. */
.vacio-mod .card-t .ico{width:34px;height:34px}
.ac-cuerpo .vacio-mod .card-t .ico{color:var(--ac-cuerpo)}
.ac-casa   .vacio-mod .card-t .ico{color:var(--ac-casa)}
.ac-vida   .vacio-mod .card-t .ico{color:var(--ac-vida)}
.vacio-mod .hint{margin-left:0;margin-right:0;text-align:center}

/* ---------- los descansos de los suplementos ----------

   La barra de ciclo: cuánto llevas de la fase en la que estás. Va en salvia
   mientras queda camino y en terracota cuando se ha cumplido, que es cuando hay
   algo que decidir. Los dos colores son los tokens de tema, así que el modo
   oscuro sale solo.

   `.mito` es la única tarjeta de la app que existe para **contradecir a una
   etiqueta**: es donde se dice que lo que pide el bote de creatina no lo
   sostiene ningún ensayo. Va en ocre —el acento de «esto es información, no una
   alarma»— y no en terracota, que aquí leería como un peligro y no lo es. */
.barra-ciclo{height:6px;border-radius:999px;background:var(--surface-2);
  overflow:hidden;margin:var(--e-2) 0 0}
.barra-ciclo>span{display:block;height:100%;border-radius:999px;
  background:var(--salvia);transition:width .3s ease}
.barra-ciclo.urg>span{background:var(--terracota)}
.item.mito{background:var(--ocre-soft);border-radius:var(--r-m);
  margin:var(--e-2) 0 0;padding:var(--e-2) var(--e-3)}
.item.mito .b strong{color:var(--ocre)}

/* La rejilla del gasto rápido. Reutiliza `.supl-card`, que ya es un botón grande
   con icono y nombre: hacer otra clase igual para dos toques sería la clase de
   duplicado del que avisa `docs/diseno.md`. Aquí van sin dosis ni evidencia, así
   que se le quita el alto mínimo que allí necesita. */
.rejilla-rapido{display:grid;grid-template-columns:1fr 1fr;gap:var(--e-3);
  margin:0 0 var(--e-4)}
.rejilla-rapido .supl-card{min-height:0;gap:var(--e-2);padding:var(--e-4)}

/* La tarta de categorías, en SVG a mano y sin librería —regla 3—. El donut es un
   círculo con `stroke-dasharray`, así que el CSS solo tiene que darle tamaño y
   colocar la leyenda al lado. Los colores salen de los tokens de tema, así que el
   modo oscuro no necesita ni una línea aparte. */
.tarta-fila{display:flex;gap:var(--e-4);align-items:center;flex-wrap:wrap}
.tarta{width:132px;height:132px;flex:0 0 auto}
.tarta-ley{flex:1;min-width:140px;display:flex;flex-direction:column;gap:var(--e-2)}
.tarta-ley .ley{display:flex;align-items:center;gap:var(--e-2);font-size:var(--t-m)}
.tarta-ley .punto{width:10px;height:10px;border-radius:50%;flex:0 0 auto}
.tarta-ley .ley-n{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;
  white-space:nowrap;color:var(--muted)}
.tarta-ley b{font-variant-numeric:tabular-nums}

/* El chip que abre la ficha desde el suplemento que ya tomas. Mismo patrón que
   `.posponer`: un chip dentro del botón, no un botón dentro de otro —eso no es
   HTML válido—. `closest()` coge el de más adentro y se lleva el toque. */
.ver-supl{display:inline-flex;align-items:center;justify-content:center;
  margin-left:var(--e-1);padding:2px;border-radius:50%;line-height:0;
  color:var(--muted);cursor:pointer;flex:0 0 auto;position:relative}
.ver-supl::before{content:"";position:absolute;top:50%;left:50%;
  width:44px;height:44px;transform:translate(-50%,-50%)}
.ver-supl:active{background:var(--surface-2)}
.chip-supl.on .ver-supl{color:inherit;opacity:.8}

/* El selector de icono de una tarea propia. Rejilla que se llena sola con los
   iconos que haya en `iconos.js`, así que dibujar uno nuevo lo mete aquí sin
   tocar nada. Se pinta en `currentColor`, como todos. */
.rejilla-iconos{display:grid;grid-template-columns:repeat(auto-fill,minmax(46px,1fr));
  gap:var(--e-2);max-height:216px;overflow-y:auto}
.pico{display:grid;place-items:center;aspect-ratio:1;border:0;border-radius:var(--r-s);
  background:var(--surface-2);color:var(--muted);cursor:pointer;padding:0}
.pico.on{background:var(--salvia);color:var(--sobre-salvia)}

/* ---------- la cuenta de valores ----------

   La tabla de un bróker son doce columnas. En 460 px una tabla se convierte en
   un carrusel horizontal donde no se puede comparar nada, y **no hay componente
   de tabla en esta casa**: no se inventa uno para esto. Cada posición es una
   ficha que se abre, y por eso la definición es de fila, no de rejilla.

   Cerrada dice lo único que se mira de pasada —cuánto vale y si gana—, con la
   cifra en `--t-xxl` y `tabular-nums`, que es lo que permite leer una columna de
   importes de arriba abajo sin que bailen las comas. Abierta, las doce en una
   rejilla de dos, cada una con su etiqueta: lo que había era hasta siete
   `<small>` apilados y se leía como un párrafo.

   El filo de arriba va como en `.item` y por la misma razón, y la primera no lo
   lleva. */
.valores{display:flex;flex-direction:column}
.valor{border-top:1px solid var(--line)}
.valor:first-child{border-top:0}
.valor-cab{display:flex;align-items:center;gap:var(--e-3);width:100%;
  padding:var(--e-3) 0;background:none;border:0;text-align:left;color:inherit;
  font:inherit;cursor:pointer}
.valor-n{flex:1;min-width:0;display:flex;flex-direction:column;gap:2px}
.valor-n strong{font-size:var(--t-b);overflow:hidden;text-overflow:ellipsis;
  white-space:nowrap}
.valor-n small{font-size:var(--t-s);color:var(--muted)}
.valor-v{flex:0 0 auto;display:flex;flex-direction:column;align-items:flex-end;gap:2px}
.valor-cifra{font-size:var(--t-xxl);font-weight:600;font-variant-numeric:tabular-nums;
  line-height:1.1;font-family:var(--cifra);font-variation-settings:var(--cifra-opsz)}
.valor-pc{font-size:var(--t-s);font-variant-numeric:tabular-nums;color:var(--muted)}
/* El color del signo. Son los tokens de estado y **solo se usan aquí para eso**:
   una plusvalía negativa es un estado del dinero, no una decoración. */
.valor-pc.sube,.valor-det .sube{color:var(--ok)}
.valor-pc.baja,.valor-det .baja{color:var(--danger)}
.valor.abierta .valor-cab{padding-bottom:var(--e-2)}
.valor-det{display:grid;grid-template-columns:1fr 1fr;gap:var(--e-2) var(--e-3);
  margin:0 0 var(--e-3);padding:var(--e-3);border-radius:var(--r-m);
  background:var(--surface-2)}
.valor-d{min-width:0}
.valor-d.ancho{grid-column:1 / -1}
.valor-d dt{font-size:var(--t-xs);letter-spacing:.04em;text-transform:uppercase;
  color:var(--muted)}
.valor-d dd{margin:0;font-size:var(--t-b);font-variant-numeric:tabular-nums;
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.valor>.due{margin-bottom:var(--e-2)}

/* ---------- el cuerpo: deporte (v31) ----------
   Los dibujos de los ejercicios heredan `currentColor`, como los iconos: en
   oscuro salen claros sin declarar nada. Los ritmos y los tramos llevan el
   color de su zona con los tokens del tema; ni un color literal. */
.dibujo-ej{display:block;color:var(--ink-2);flex:0 0 auto}
.dibujo-ej.chico{width:72px;height:36px;margin-top:2px}
.dibujo-ej.grande{width:100%;height:auto;max-height:160px;margin:0 0 var(--e-3);color:var(--ink)}
.item .dibujo-ej.chico+.b{min-width:0}
.pasos,.errores{margin:0;padding:0 0 0 var(--e-5);font-size:var(--t);line-height:1.5;color:var(--ink-2)}
.pasos li,.errores li{margin:0 0 var(--e-2)}
.pasos li::marker{font-weight:700;color:var(--salvia)}
.errores li::marker{color:var(--terracota)}
.ej-hoy .sug{display:block;margin-top:3px;color:var(--ink-2)}
.ej-hoy .sug.subir{color:var(--salvia-ink)}
.ej-hoy .sug.bajar{color:var(--terracota)}
.series{display:flex;flex-wrap:wrap;gap:var(--e-2);margin-top:var(--e-2)}
.chip-serie{border:0;background:var(--salvia-soft);color:var(--salvia-ink);border-radius:var(--r-l);
  padding:var(--e-2) var(--e-3);font-size:var(--t-m);font-weight:600;min-height:34px;display:inline-flex;align-items:center;gap:var(--e-1);
  font-variant-numeric:tabular-nums;cursor:pointer}
.chip-serie:active{transform:scale(.96)}
.serie-form{display:flex;gap:var(--e-2);align-items:flex-end;margin-top:var(--e-2)}
.serie-form .campo{flex:1;margin:0}
.serie-form .campo input{width:100%}
.serie-form .btn{flex:0 0 auto}
.tramos{display:flex;flex-direction:column;gap:var(--e-1);margin:0 0 var(--e-3)}
.tramo{display:flex;gap:var(--e-3);align-items:baseline;font-size:var(--t-m);color:var(--ink-2);
  padding:var(--e-1) var(--e-2);border-radius:var(--r-s);background:var(--surface-2)}
.tramo b{flex:0 0 40px;font-variant-numeric:tabular-nums;color:var(--ink)}
.tramo i{font-style:normal;font-weight:700;font-variant-numeric:tabular-nums}
.tramo.tempo,.tramo.maraton{box-shadow:inset 3px 0 0 var(--ocre)}
.tramo.fuerte,.tramo.cuesta{box-shadow:inset 3px 0 0 var(--terracota)}
.tramo.suave,.tramo.trote{box-shadow:inset 3px 0 0 var(--salvia)}
.ritmos{display:grid;grid-template-columns:repeat(4,1fr);gap:var(--e-2)}
.ritmo{background:var(--surface-2);border-radius:var(--r-m);padding:var(--e-2);text-align:center}
.ritmo b{display:block;font-weight:600;font-family:var(--cifra);font-variation-settings:var(--cifra-opsz);font-size:var(--t-l);
  font-variant-numeric:tabular-nums;color:var(--ink)}
.ritmo small{display:block;font-size:var(--t-xs);color:var(--muted);margin-top:2px}
.ico-izq.ver-como_tocaba{color:var(--salvia)}
.ico-izq.ver-mas_lenta,.ico-izq.ver-corta{color:var(--terracota)}
.ico-izq.ver-mas_rapida{color:var(--ocre)}
.acts button.on{background:var(--salvia-soft);color:var(--salvia-ink)}

.tramo.hecho{opacity:.45}
.tramo.ahora{background:var(--surface-2);border-radius:var(--r-s)}
.tramo-grande{text-align:center}
.tramo-grande .qu{font-size:var(--t-l);font-weight:700;margin-top:var(--e-1)}
.tramo-grande .cifra-grande{font-family:var(--cifra);font-variation-settings:var(--cifra-opsz);font-size:var(--t-xxl);font-variant-numeric:tabular-nums;line-height:1.1;margin:var(--e-2) 0}
.tramo-grande .de b{font-variant-numeric:tabular-nums}
.graf-parciales .graf-g.fuerte .graf-b{background:var(--terracota)}
.chips{display:flex;flex-wrap:wrap;gap:var(--e-2)}
.chips .chip{cursor:pointer}
.chips .chip.on{background:var(--salvia-soft);color:var(--salvia);font-weight:700}
.parciales{display:flex;flex-wrap:wrap;gap:var(--e-1);margin-top:var(--e-1)}
.parciales span{font-size:var(--t-xs);font-variant-numeric:tabular-nums;background:var(--surface-2);border-radius:var(--r-s);padding:2px var(--e-1);color:var(--ink-2)}
.parciales span.fuerte{background:var(--terracota-soft);color:var(--terracota);font-weight:700}
/* ---------- los gráficos (nucleo/graficos.js) ----------
   Un solo dibujo para Salud, Deporte y Dinero. Las series van por clase
   (`graf-s0`, `graf-s1`…) y el color lo pone el tema. */
.graf-caja{margin:0 0 var(--e-3);line-height:0;color:var(--salvia)}
/* Los gráficos salían achatados: 56 px de alto para doce meses de datos dejan
   las variaciones aplastadas contra el eje, y una línea que no sube ni baja no
   dice nada. Con 78 se lee la forma sin que la tarjeta crezca de más. La de la
   pantalla de Salud va aparte y se queda pequeña, que ahí es un apunte. */
.graf.graf-linea{width:100%;height:78px;display:block;overflow:visible}
.graf-spark{width:80px;height:24px;display:inline-block;vertical-align:middle}
.graf-linea .graf-s1{color:var(--terracota)}
.graf-linea .graf-s2{color:var(--pizarra)}
/* La cuarta línea. Hacía falta al pintar el IRPF en «Tu sueldo»: con tres
   colores y cuatro series, la cuarta heredaba el `currentColor` de la caja —el
   salvia de la primera— y dos líneas distintas salían del mismo color. El ocre
   es el que ya le toca a la serie 3 en la leyenda y en las barras, así que las
   tres formas de dibujar dicen lo mismo. */
.graf-linea .graf-s3{color:var(--ocre)}
.graf-linea .graf-prev{stroke-dasharray:3 3;opacity:.7}
.graf-linea .graf-area{fill:currentColor;opacity:.12}
.graf-linea .graf-ic{fill:currentColor;opacity:.14;stroke:none}
:root[data-tema="oscuro"] .graf-linea .graf-ic{opacity:.22}
/* Las áreas apiladas llevan hasta diez franjas, así que necesitan más sitio que
   una línea suelta para que la de abajo no quede en un hilo. */
.graf.graf-areas{height:112px}
/* Entre franja y franja, **un hilo del color de la tarjeta** (v2.39). Iban a
   tope una contra otra y dos franjas vecinas se leían como un solo bloque de
   color; el hilo las separa sin añadir una tinta más. `non-scaling-stroke`
   porque el SVG se estira a lo ancho y sin eso el hilo se deforma con él. */
.graf-areas .graf-apilada{stroke:var(--surface);stroke-width:1.5;stroke-linejoin:round;
  vector-effect:non-scaling-stroke}
/* El cero de las áreas a dos lados: más marcado que la rejilla, porque es la
   referencia que separa lo que entra de lo que se va. */
.graf-areas .graf-cero{stroke:var(--ink-2);stroke-width:.6;opacity:.55;vector-effect:non-scaling-stroke}
/* La línea del total va por encima de las franjas y en la tinta del texto: no es
   una parte más de la pila, es el resultado. */
.graf-areas .graf-neto{color:var(--ink)}
.graf-areas .graf-zona{cursor:pointer}
/* La banda del tramo al que uno se ha acercado arrastrando. Va por debajo de
   todo —es el primer hijo del SVG— y muy tenue: señala una zona, no la tiñe.
   `touch-action:pan-y` en el gráfico deja que el dedo siga desplazando la
   página verticalmente y se queda solo con el gesto horizontal, que es el que
   acota: sin eso, arrastrar en diagonal bloquea el scroll de la pantalla, que
   fue justo lo que costó afinar el cajón antes de quitarlo. */
.graf-areas[data-rango]{touch-action:pan-y}
.graf-areas .graf-banda{fill:var(--salvia);opacity:.14}
:root[data-tema="oscuro"] .graf-areas .graf-banda{opacity:.22}
@media (prefers-color-scheme:dark){
  :root:not([data-tema="claro"]) .graf-areas .graf-banda{opacity:.22}
}
/* El mes que se ha tocado, señalado en el propio dibujo. Es el hermano quieto
   de `.graf-banda`: aquella marca un tramo mientras se arrastra y esta marca la
   columna cuyo desglose se está leyendo más abajo. Va con `--surface-2` y no con
   el acento porque no es un dato, es dónde estoy mirando. */
.graf-areas .graf-marca{fill:var(--ink-2);opacity:.1}
:root[data-tema="oscuro"] .graf-areas .graf-marca{opacity:.18}
@media (prefers-color-scheme:dark){
  :root:not([data-tema="claro"]) .graf-areas .graf-marca{opacity:.18}
}

/* La cifra de la cabecera de un gráfico: el último dato en grande y la media
   debajo en pequeño. Alineada a la derecha porque va al final del `.card-t`, y
   en dos líneas porque una sola con las dos cifras seguidas se lee como un
   rango. */
.dato-cab{display:flex;flex-direction:column;align-items:flex-end;line-height:1.15;text-align:right}
.dato-cab b{font-weight:600;font-family:var(--cifra);font-variation-settings:var(--cifra-opsz);
  font-size:var(--t-l);font-variant-numeric:tabular-nums;color:var(--ink)}
.dato-cab b.urg{color:var(--danger)}
.dato-cab small{font-size:var(--t-xs);color:var(--muted)}

/* Las migas del súper gráfico: dónde estoy y por dónde se vuelve. La última no
   es un botón —es dónde estás— y por eso va en `--muted` y sin caja. */
.sg-migas{display:flex;flex-wrap:wrap;align-items:center;gap:var(--e-1);margin-bottom:var(--e-2);
  font-size:var(--t-m)}
.sg-migas>span{color:var(--muted);font-weight:600}
.sg-migas>button::after{content:"›";margin-left:var(--e-1);color:var(--muted)}

/* El desglose por serie del panel de agregados: filas finas, que aquí lo que se
   compara son cifras y no hace falta el peso de un `.item` entero. */
.sg-partes .item{padding-top:var(--e-1);padding-bottom:var(--e-1)}
/* Los dos porcentajes de una fila —qué parte de lo que entra y de lo que sale—.
   Van debajo del nombre y en pequeño: la cifra sigue siendo el titular, y esto
   es lo que la pone en contexto. */
.sg-peso{display:block;font-size:var(--t-xs);color:var(--muted)}

.graf-linea .graf-eje{stroke:var(--muted);stroke-width:.4;opacity:.5;vector-effect:non-scaling-stroke}
.graf-linea .graf-tick{fill:var(--muted);font-size:5px;font-family:system-ui,sans-serif}
.graf-linea circle{fill:currentColor}
.graf-barras{display:flex;gap:var(--e-2);align-items:flex-end;height:128px;margin-top:var(--e-1)}
.graf-g{flex:1;display:flex;flex-direction:column;align-items:center;min-width:0;height:100%}
.graf-c{flex:1;width:100%;display:flex;gap:2px;align-items:flex-end;justify-content:center;position:relative}
.graf-b{display:block;flex:1;max-width:22px;border-radius:4px 4px 0 0;background:var(--salvia);min-height:2px}
.graf-b.graf-s1{background:var(--terracota)}
.graf-b.graf-s2{background:var(--pizarra)}
.graf-b.graf-s3{background:var(--ocre)}
.graf-b.neg{background:var(--terracota)}
.graf-pila{display:flex;flex-direction:column-reverse;width:22px;height:100%;justify-content:flex-start}
.graf-pila .graf-b{width:100%;max-width:none;border-radius:0}
.graf-pila .graf-b:last-child{border-radius:4px 4px 0 0}
.graf-vacia{color:var(--muted);font-weight:700;align-self:flex-end;line-height:1}
.graf-g small{font-size:var(--t-xs);color:var(--muted);margin-top:var(--e-1);white-space:nowrap;overflow:hidden;text-overflow:ellipsis;max-width:100%}
.graf-g b{font-size:var(--t-xs);font-variant-numeric:tabular-nums;color:var(--ink-2)}
.graf-g.vacia small{opacity:.6}

/* ---------- Vehículos ---------- */

/* Tres cifras en fila, grandes y con su unidad debajo: es la forma de leer de un
   vistazo lo que consume, a cómo sale el litro y lo que cuesta el kilómetro.
   Con dos también funciona, que es lo que hay hasta el segundo lleno. */
.tres-cifras{display:flex;gap:var(--e-2);margin:0 0 var(--e-3);text-align:center}
.tres-cifras>div{flex:1;min-width:0;background:var(--surface-2);border-radius:var(--r-m);
  padding:var(--e-3) var(--e-2)}
.tres-cifras b{display:block;font-size:var(--t-xl);font-weight:600;font-variant-numeric:tabular-nums;
  font-family:var(--cifra);font-variation-settings:var(--cifra-opsz);
  line-height:1.1;color:var(--ink)}
.tres-cifras small{display:block;margin-top:var(--e-1);font-size:var(--t-xs);color:var(--muted)}

/* ---------- Dinero y finanzas (v32) ---------- */
.cats-chip{display:flex;flex-wrap:wrap;gap:var(--e-2);margin-top:var(--e-2)}
.chip-cat{border:0;background:var(--surface-2);color:var(--ink);border-radius:var(--r-l);padding:var(--e-2) var(--e-3);
  font-size:var(--t-m);font-weight:600;min-height:36px;display:inline-flex;align-items:center;gap:var(--e-1);cursor:pointer}
.chip-cat .ico{color:var(--salvia)}
.chip-cat.otra{color:var(--muted)}
.chip-cat:active{transform:scale(.96)}
/* El chip que además dice **por qué** se propone esa categoría: dos líneas, el
   nombre y el motivo. En una sola línea el motivo empujaba el nombre fuera de
   la pantalla a 460 px, que es donde se lee esto. */
.chip-cat.con-porque{flex-direction:column;align-items:flex-start;gap:0;
  padding-top:var(--e-1);padding-bottom:var(--e-1);text-align:left}
.chip-cat.con-porque .porque{font-size:var(--t-xs);font-weight:400;color:var(--muted)}
/* La leyenda está declarada **una sola vez**, arriba: la copia que había aquí
   la pisaba entera y le quitaba el tamaño y el color. */
.ley-chip{border:0;background:none;padding:var(--e-1) var(--e-2);font-size:var(--t-s);color:var(--ink-2);display:inline-flex;align-items:center;gap:var(--e-1);border-radius:var(--r-s)}
button.ley-chip{cursor:pointer;background:var(--surface-2)}
button.ley-chip.on{background:var(--salvia-soft);color:var(--salvia-ink)}
.ley-chip i{width:10px;height:10px;border-radius:3px;background:var(--salvia);display:inline-block}
.ley-chip i.graf-s1{background:var(--terracota)}
.ley-chip i.graf-s2{background:var(--pizarra)}
.ley-chip i.graf-s3{background:var(--ocre)}
/* La leyenda de las áreas apiladas **es el mando**: cada entrada enciende y
   apaga su franja. Lo apagado no desaparece —si desapareciera no habría forma de
   volver a encenderlo—: se queda en gris y tachado, que es lo que distingue «lo
   he quitado yo» de «no hay dato». El área de dedo la da el `min-height`, que
   una leyenda de 6 px de tinta no se toca. */
.leyenda-toca{gap:var(--e-2)}
.leyenda-toca .ley-chip{min-height:34px}
button.ley-chip.off{color:var(--muted);text-decoration:line-through;background:none}
.ley-chip i.graf-s4{background:var(--salvia-deep)}
.ley-chip i.graf-s5{background:var(--muted)}
.graf-b.graf-s4{background:var(--salvia-deep)}
.graf-b.graf-s5{background:var(--muted)}
.graf-barras.alto{height:150px}

/* La cascada: cada columna cuelga de donde acabó la anterior, y eso es todo lo
   que la distingue de una barra.

   La columna va **posicionada** dentro de su caja, con `bottom` y `height` en
   porcentaje. No con un margen: un porcentaje en un margen vertical se mide
   contra el **ancho** del padre, no contra su alto, así que la cascada salía
   levantada a una altura que no tenía nada que ver con el importe — y en una
   pantalla estrecha, casi a ras de suelo. */
.graf-cascada{display:flex;gap:var(--e-2);align-items:flex-end;height:150px;margin-top:var(--e-1)}
.graf-cascada .graf-g{flex:1;display:flex;flex-direction:column;align-items:center;min-width:0;height:100%}
.graf-cascada .graf-c{flex:1;width:100%;position:relative}
.graf-cascada .graf-b{position:absolute;left:50%;transform:translateX(-50%);width:100%;max-width:34px;border-radius:var(--r-s);background:var(--muted);min-height:2px}
.graf-cascada .casc-base .graf-b{background:var(--salvia)}
.graf-cascada .casc-total .graf-b{background:var(--salvia-deep)}
.graf-cascada .casc-resta .graf-b{background:var(--terracota)}
.graf-cascada .casc-suma .graf-b{background:var(--ocre)}
.graf-cascada small{font-size:var(--t-xs);color:var(--muted);margin-top:var(--e-1);
  text-align:center;overflow:hidden;text-overflow:ellipsis;max-width:100%}
.graf-cascada b{font-size:var(--t-xs);font-variant-numeric:tabular-nums;color:var(--ink-2)}

/* Barras horizontales: el nombre en su línea y la barra debajo, que es lo que
   cabe en 460 px con nombres de verdad. */
.graf-barrasH{display:flex;flex-direction:column;gap:var(--e-3);margin-top:var(--e-2)}
.graf-h-t{display:flex;justify-content:space-between;gap:var(--e-2);font-size:var(--t-m);align-items:baseline}
.graf-h-t span{min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.graf-h-t b{font-variant-numeric:tabular-nums;flex:0 0 auto;color:var(--ink-2)}
.graf-h-p{height:10px;background:var(--surface-2);border-radius:var(--r-s);overflow:hidden;margin-top:var(--e-1)}
.graf-h-p .graf-b{display:block;height:100%;border-radius:var(--r-s);min-width:2px}

/* Los dos ejes de una línea van **fuera del SVG**: dentro, el
   `preserveAspectRatio="none"` que hace que la línea llene el ancho estira
   también las letras, y las marcas salían deformadas y encimadas. Fuera son
   texto de verdad, con la tipografía del sistema.

   El eje vertical se superpone al gráfico —de ahí el contenedor relativo— y el
   horizontal va debajo, en flujo. */
.graf-conejes{position:relative}
.graf-ejey{position:absolute;inset:0;pointer-events:none;font-size:var(--t-xs);
  color:var(--muted);line-height:1}
/* Las cifras van **a la derecha**: es donde acaba la serie y donde uno mira para
   saber en cuánto está ahora, y a la izquierda obligaban a cruzar el gráfico
   entero para leer el último valor. El hueco lo reserva `lineaSVG` por ese lado.
   El fondo es el de la tarjeta, para que la rejilla no se lea por debajo. */
.graf-ejey span{position:absolute;right:0;transform:translateY(-50%);
  background:var(--surface);padding-left:2px;text-align:right}

/* El eje horizontal de una línea: cada etiqueta en la x de su punto, centrada
   sobre ella. Va fuera del SVG para que sea texto de verdad. */
.graf-ejex{position:relative;height:1.2em;margin:0 0 var(--e-2);font-size:var(--t-xs);color:var(--muted)}
.graf-ejex span{position:absolute;transform:translateX(-50%);white-space:nowrap}
.graf-g.peor .graf-b.graf-s0{background:var(--terracota)}
.graf-g.mejor .graf-b.graf-s0{background:var(--salvia)}
.graf-g.peor .graf-b.graf-s1,.graf-g.mejor .graf-b.graf-s1{background:var(--muted);opacity:.6}
/* `.graf-meses` se ha ido: repartía las etiquetas a partes iguales sin
   alinearlas con los puntos. Lo hace `Graf.ejeX`, que las coloca en su x. */
.graf-caja.spark{flex:0 0 80px;line-height:0;color:var(--salvia)}

/* ---------- el ordenador (v2.51) ----------
   Desde 1024 px —la web en nido-casa.pages.dev/app/ y la app instalada en un
   portátil— la columna del móvil se quedaba sola en medio de la pantalla y la
   barra de abajo se estiraba de lado a lado con las cinco pestañas a un palmo
   unas de otras. La decisión del usuario (2 de octubre de 2026): **barra lateral
   y dos columnas**. Docs: `docs/escritorio.md`.

   Todo es CSS sobre el mismo DOM: ni un `render*` ni un id cambian, y en el
   móvil nada de esto existe. Tres piezas:

   - **La barra pasa a la izquierda, en vertical y con el mismo orden** (Hoy en
     el centro, que es lo que se defiende de la barra). El círculo del nido deja
     de sobresalir: en vertical no hay hacia dónde.
   - **Las tarjetas van a dos columnas** donde hay dos o más en un mismo
     contenedor (`:has(> .card ~ .card)`), en columnas de periódico y no en rejilla, para que
     una tarjeta alta no deje un hueco al lado. Leen de arriba abajo, así que lo
     primero de Hoy sigue arriba a la izquierda.
   - **Lo que se apila deja de tapar la pantalla entera**: las hojas salen
     centradas y las pantallas de Ajustes como un panel a la derecha. */
@media (min-width:1024px){
  :root{--carril:112px}
  body{padding-bottom:var(--e-6);padding-left:var(--carril)}
  .wrap{max-width:1180px;padding:0 var(--e-5)}

  nav{top:0;bottom:0;right:auto;width:var(--carril);flex-direction:column;justify-content:center;
    gap:var(--e-3);padding:var(--e-5) var(--e-2);
    box-shadow:1px 0 0 var(--line), 6px 0 18px rgba(0,0,0,.04)}
  nav button{flex:0 0 auto;font-size:var(--t-s);padding:var(--e-2) 0}
  nav button[data-p="hoy"]{min-height:0;margin:var(--e-2) 0}
  nav button[data-p="hoy"] i,
  nav button[data-p="hoy"]:active i{margin-bottom:0;transform:scale(.9)}
  nav button[data-p="hoy"].on i{transform:none}

  main{padding-left:0;padding-right:0}
  main .panel div:has(> .card ~ .card){columns:2;column-gap:var(--e-4)}
  main .panel div:has(> .card ~ .card) > *{break-inside:avoid}
  /* **Todo lo que no es tarjeta cruza las dos columnas** —un título de grupo,
     una pista, la barra de la semana, un botón ancho— y parte el flujo en
     tramos, cada uno con sus columnas. Sin eso un «Fruta y verdura» se quedaba
     colgando al pie de una columna con su grupo empezando en la otra. */
  main .panel div:has(> .card ~ .card) > :not(.card){column-span:all}
  .subtabs{max-width:560px}
  /* El mes: el calendario a la izquierda y el día elegido a la derecha. A todo
     lo ancho cada casilla medía cien píxeles y el detalle del día quedaba debajo,
     fuera de la pantalla: tocabas un día y no veías qué pasaba. */
  /* La última fila es elástica (`1fr`) y es la que absorbe la altura del día:
     si no, el detalle —que es alto— estiraba las filas del calendario y abría un
     hueco entre el mes y los días de la semana. */
  #y-mes.on{display:grid;grid-template-columns:minmax(0,1.15fr) minmax(0,1fr);
    grid-template-rows:auto auto auto auto 1fr;column-gap:var(--e-5);align-items:start}
  #y-mes > .nav-periodo{grid-column:1;grid-row:1}
  #y-mes > .mes{grid-column:1;grid-row:2}
  #y-mes > #mes-leyenda{grid-column:1;grid-row:3}
  #y-mes > .btn.wide{grid-column:1;grid-row:4}
  #y-mes > #recordatorios-caja{grid-column:1;grid-row:5}
  #y-mes > #dia-detalle{grid-column:2;grid-row:1 / 6}

  .hoja{align-items:center;justify-items:center;padding:var(--e-6)}
  .hoja-caja{width:min(600px, 100%);border-radius:var(--r-xl);max-height:84vh;
    padding-bottom:var(--e-5);animation-name:aparece}
  .hoja-caja::before{display:none}
  @keyframes aparece{from{transform:translateY(12px) scale(.98);opacity:.6}to{transform:none;opacity:1}}

  .pantalla{left:auto;width:min(620px, 100%);box-shadow:-12px 0 32px rgba(0,0,0,.16)}

  .toast{bottom:var(--e-6);margin-left:calc(var(--carril) / 2)}
  html.con-tira .toast{bottom:calc(var(--e-6) + var(--tira-alto))}
  .tira-temp{left:var(--carril);bottom:0}

  .marca-agua{right:-12%;top:-10%;width:60%}
}

/* ---------- utilidades (v2.1) ----------
   Existen para vaciar los `style="…"` en línea, que eran casi doscientos y casi
   todos márgenes. `docs/critica.md` ya los señalaba: «es el síntoma de que no
   hay inventario de componentes».

   **Van al final del fichero a propósito.** Una utilidad y el componente al que
   corrige tienen la misma especificidad —una clase cada uno—, así que lo único
   que decide es el orden de aparición. Si este bloque sube, `.hint.m0` deja de
   quitar el margen y no se entiende por qué.

   Y son solo espaciado y alineación: una utilidad de color o de tamaño sería
   volver a elegir a ojo, que es justo lo que se ha quitado. */
.m0{margin:0}
.mt0{margin-top:0}
.mb-2{margin:0 0 var(--e-2)}
.mb-3{margin:0 0 var(--e-3)}
.mb-4{margin:0 0 var(--e-4)}
.mt-1{margin-top:var(--e-1)}
.mt-2{margin-top:var(--e-2)}
.mt-3{margin-top:var(--e-3)}
.mt-4{margin-top:var(--e-4)}
.my-3{margin:var(--e-3) 0}
.p-2{padding:var(--e-2)}
.centrado{text-align:center}
.apagado-txt{color:var(--muted)}
/* El pie de versión, que sale igual en el cajón y en Ajustes. */
.pie-version{text-align:center;margin:var(--e-5) 0 var(--e-2)}
/* Empuja lo que venga después al otro extremo de una fila flex. */
.a-la-derecha{margin-left:auto}
