/* Identidad visual NuFlow. Los tokens salen del documento y se envian tal cual:
   son la identidad del producto, no una sugerencia.

   Dos reglas que no se negocian y que estan implementadas aca:
   - EL AQUA ES EL ESTADO NORMAL Y NUNCA SIGNIFICA ALERTA. La escala de estados
     de ejecucion es APARTE de la marca.
   - EL COLOR NO ES EL UNICO PORTADOR: cada estado lleva ademas su porcentaje en
     texto, para daltonismo y para impresion en blanco y negro. */

:root {
  /* Marca */
  --nf-azul-profundo: #0671c6;
  --nf-azul-oscuro:   #033863;
  --nf-azul-xoscuro:  #020C14;
  --nf-aqua:          #03cdd3;
  /* El aqua de marca no cumple contraste 4.5:1 sobre blanco para texto chico:
     se usa como relleno de barra o borde. Este es su equivalente legible. */
  --nf-aqua-texto:    #067b80;
  --nf-blanco:        #ffffff;

  /* Superficies */
  --superficie:     var(--nf-blanco);
  --superficie-alt: #f4f7fa;
  --superficie-pag: #eef2f6;
  --borde:          #dbe3ec;
  --borde-suave:    #e9eef3;
  --texto:          #0f1b26;
  --texto-suave:    #5a6b7b;

  /* Estados de ejecucion: escala APARTE de la marca */
  --exec-normal:    var(--nf-aqua);
  --exec-atencion:  #e8a33d;
  --exec-sobregiro: #d64550;
  --exec-sin-datos: #c3ccd6;
  --exec-normal-bg:    #e6f8f8;
  --exec-atencion-bg:  #fdf3e3;
  --exec-sobregiro-bg: #fbe9eb;

  /* Tipografia */
  --fuente-titulo: 'Kanit', system-ui, -apple-system, 'Segoe UI', sans-serif;
  --fuente-texto:  'Nunito', system-ui, -apple-system, 'Segoe UI', sans-serif;
  --txt-cifra-hero: 2.5rem;
  --txt-titulo:     1.5rem;
  --txt-subtitulo:  1.125rem;
  --txt-cuerpo:     0.9375rem;
  --txt-tabla:      0.875rem;
  --txt-etiqueta:   0.75rem;

  /* Espaciado, escala de 4 */
  --e1: 4px;  --e2: 8px;  --e3: 12px; --e4: 16px;
  --e5: 24px; --e6: 32px; --e7: 48px; --e8: 64px;
  --radio: 10px;
  --sombra: 0 1px 2px rgba(3, 56, 99, .06), 0 4px 16px rgba(3, 56, 99, .06);

  --barra-lateral: 248px;
  /* El encabezado de la tabla del presupuesto tiene alto FIJO: las filas de
     area se pegan justo debajo, y para eso hay que saber donde termina. */
  --alto-encabezado: 36px;
  /* El fondo de la fila de area. Lo usan la fila y la sombra que tapa la
     rendija de subpixel debajo de ella: dos literales iguales se desincronizan. */
  --fondo-area: #e7eff8;
}

:root[data-tema="oscuro"] {
  --superficie:     var(--nf-azul-xoscuro);
  --superficie-alt: #0a1826;
  --superficie-pag: #060f18;
  --borde:          #16293b;
  --borde-suave:    #12212f;
  --texto:          #e8eef4;
  --texto-suave:    #94a6b8;
}

* { box-sizing: border-box; }
html, body { margin: 0; height: 100%; }

/* El atributo `hidden` se apaga con `display:none` de la hoja del navegador, y
   CUALQUIER regla de autor que fije `display` la gana: `aside`, `main` y la
   pantalla de entrada lo hacen. Sin esto, ocultar un panel no lo oculta -queda
   en la maquetacion, tapando lo de al lado-, que es exactamente como se veria
   un usuario sin acceso el tablero que no deberia ver. */
[hidden] { display: none !important; }

body {
  font-family: var(--fuente-texto);
  font-size: var(--txt-cuerpo);
  color: var(--texto);
  background: var(--superficie-pag);
  display: flex;
  /* Alto exacto y sin scroll propio: el que se desplaza es `main`. Si el
     cuerpo tambien se desplazara, la barra lateral se iria con el. */
  height: 100vh;
  overflow: hidden;
}

h1, h2, h3 {
  font-family: var(--fuente-titulo);
  font-weight: 600;
  letter-spacing: -.01em;
  margin: 0;
}

/* Todas las cifras monetarias: tabular y a la derecha. Sin esto una columna de
   doce meses no se puede leer en diagonal. */
.cifra {
  font-variant-numeric: tabular-nums;
  text-align: right;
}

.suave { color: var(--texto-suave); }
.chico { font-size: var(--txt-etiqueta); }

/* --- Barra lateral --- */

/* Alto fijo, al lado del contenido. Ya no hace falta `sticky`: no hay nada que
   pegar, porque el cuerpo de la pagina no se desplaza. */
aside {
  width: var(--barra-lateral);
  background: var(--nf-azul-oscuro);
  color: #dbe8f3;
  display: flex;
  flex-direction: column;
  height: 100vh;
  flex-shrink: 0;
}

.marca {
  padding: 22px 22px 14px;
  border-bottom: 1px solid rgba(255, 255, 255, .08);
}
.marca .nombre {
  font-family: var(--fuente-titulo);
  font-weight: 600;
  font-size: 15px;
  color: #fff;
  line-height: 1.1;
}
.marca .nombre small {
  display: block;
  font-family: var(--fuente-texto);
  font-weight: 400;
  font-size: 11px;
  color: #9db8cf;
  letter-spacing: .06em;
  text-transform: uppercase;
  margin-top: 3px;
}

.empresa { padding: 16px 22px 10px; font-size: 12px; color: #9db8cf; }
.empresa b {
  display: block;
  color: #fff;
  font-size: 14px;
  font-family: var(--fuente-titulo);
  font-weight: 500;
  margin-bottom: 2px;
}

nav { padding: 8px 12px; flex: 1; overflow: auto; }
nav .seccion {
  font-size: 10.5px;
  letter-spacing: .1em;
  text-transform: uppercase;
  color: #7f9cb6;
  padding: 14px 10px 6px;
}
nav button {
  display: flex;
  align-items: center;
  gap: 11px;
  width: 100%;
  text-align: left;
  background: none;
  border: 0;
  color: #cfe0ee;
  padding: 9px 10px;
  border-radius: 9px;
  cursor: pointer;
  font-family: inherit;
  font-size: 13.5px;
  font-weight: 600;
}
nav button:hover { background: rgba(255, 255, 255, .06); color: #fff; }
nav button[aria-current="page"] {
  background: rgba(3, 205, 211, .14);
  color: #fff;
  box-shadow: inset 3px 0 0 var(--nf-aqua);
}

.usuario {
  padding: 14px 18px;
  border-top: 1px solid rgba(255, 255, 255, .08);
  display: flex;
  gap: 10px;
  align-items: center;
  font-size: 12.5px;
}
.usuario .inicial {
  width: 34px; height: 34px;
  border-radius: 50%;
  background: var(--nf-aqua);
  color: var(--nf-azul-xoscuro);
  display: grid;
  place-items: center;
  font-family: var(--fuente-titulo);
  font-weight: 700;
}
.usuario b { display: block; color: #fff; }
.usuario span { color: #9db8cf; }

/* --- La capa de arrastrar --- */

/* Cubre la ventana entera a proposito: la factura se suelta donde sea, no
   sobre un recuadro que hay que encontrar primero. `pointer-events: none` en
   la caja de adentro para que no se coma el evento de soltar. */
.capa-soltar {
  position: fixed;
  inset: 0;
  z-index: 60;
  display: grid;
  place-items: center;
  background: rgba(3, 56, 99, .72);
  backdrop-filter: blur(2px);
}
.capa-soltar .caja {
  pointer-events: none;
  background: var(--superficie);
  border: 3px dashed var(--nf-aqua);
  border-radius: var(--radio);
  padding: var(--e7) var(--e8);
  text-align: center;
  display: flex;
  flex-direction: column;
  gap: var(--e2);
  box-shadow: var(--sombra);
}
.capa-soltar b { font-family: var(--fuente-titulo); font-size: var(--txt-titulo); color: var(--nf-azul-oscuro); }
.capa-soltar span { color: var(--texto-suave); font-size: var(--txt-tabla); }

.pie-lateral {
  padding: 12px 18px;
  border-top: 1px solid rgba(255, 255, 255, .08);
  display: flex;
  flex-direction: column;
  gap: 2px;
  font-size: 11.5px;
  color: #9db8cf;
}

/* --- Cuerpo --- */

/* MAIN ES EL UNICO QUE SE DESPLAZA.

   `aside` ya tenia `position: sticky`, pero `html, body { height: 100% }` lo
   encerraba en una caja de una pantalla de alto: `sticky` se pega dentro de SU
   contenedor, y ese contenedor terminaba a la altura del viewport. La pagina
   entera se desplazaba y la barra lateral se iba con ella.

   La solucion no es mas `sticky`: es que el cuerpo de la pagina NO se desplace.
   `main` se lleva el scroll y `aside` queda de alto fijo al lado. */
main {
  flex: 1;
  min-width: 0;
  display: flex;
  flex-direction: column;
  height: 100vh;
  overflow-y: auto;
  overflow-x: hidden;
}

/* --- Barra superior ---

   UNA SOLA FILA, y contrasta. El hallazgo de Joseph era que no se distinguia de
   lo de abajo y no quedaba claro que informaba. Ahora contesta dos preguntas:
   que estas mirando, y hasta cuando cuenta lo ejecutado.

   `flex-wrap: nowrap` es parte de la regla: con `wrap`, a 1280px la barra se
   parte en dos filas en cuanto el titulo de una vista es largo, y deja de ser
   una barra.

   Los colores del texto sobre este fondo cumplen 4.5:1, y hay una prueba de
   navegador que lo CALCULA en vez de confiar en que se ve bien. */
header.superior {
  display: flex;
  align-items: center;
  gap: var(--e4);
  padding: 12px 28px;
  flex-wrap: nowrap;
  background: var(--superficie);
  border-bottom: 1px solid var(--borde);
  position: sticky;
  top: 0;
  z-index: 5;
}
.superior-izq { min-width: 0; display: flex; flex-direction: column; gap: 2px; }
header.superior h1 {
  font-size: 20px;
  color: var(--nf-azul-oscuro);
  line-height: 1.15;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
/* `--texto-suave` sobre blanco da 5.4:1: entra en AA y se lee como secundario. */
header.superior .contexto {
  color: var(--texto-suave);
  font-size: 12.5px;
  font-weight: 600;
  white-space: nowrap;
}

.superior-der {
  display: flex;
  gap: var(--e2);
  align-items: center;
  margin-left: auto;
  flex-wrap: nowrap;
  flex-shrink: 0;
}

.usuario-superior {
  display: flex;
  gap: var(--e2);
  align-items: center;
  font-size: 12px;
  padding-left: var(--e3);
  border-left: 1px solid var(--borde);
  margin-left: var(--e2);
}
.usuario-superior .inicial {
  width: 30px; height: 30px;
  border-radius: 50%;
  background: var(--nf-azul-oscuro);
  color: #fff;
  display: grid;
  place-items: center;
  font-family: var(--fuente-titulo);
  font-weight: 700;
  font-size: 13px;
  flex-shrink: 0;
}
.usuario-superior .quien { display: flex; flex-direction: column; line-height: 1.25; min-width: 0; }
.usuario-superior b { color: var(--texto); font-weight: 700; white-space: nowrap; }
.usuario-superior span { color: var(--texto-suave); white-space: nowrap; }

.fichas { display: flex; gap: 8px; margin-left: auto; flex-wrap: wrap; }
.ficha {
  background: var(--superficie);
  border: 1px solid var(--borde);
  border-radius: 99px;
  padding: 6px 12px;
  font-size: 12.5px;
  font-weight: 600;
  color: var(--texto-suave);
  display: inline-flex;
  gap: 6px;
  align-items: center;
}
.ficha .punto { width: 8px; height: 8px; border-radius: 50%; background: var(--nf-aqua); }

.contenido { padding: 8px 28px 40px; }

/* --- Filtros --- */

/* LINEAL Y CON UNA SOLA FORMA.

   Todos los controles son `.campo` = etiqueta arriba + `.control` abajo, con la
   misma altura, la misma tipografia y la misma separacion. El de fuera de
   presupuesto era un interruptor suelto sin etiqueta, y quedaba desalineado
   contra los dos segmentados de al lado.

   La altura se fija en la variable, no control por control: un `select` y un
   grupo de botones no miden lo mismo solos, y la prueba de navegador compara
   las alturas de verdad. */
.filtros {
  display: flex;
  gap: var(--e3);
  align-items: flex-end;
  flex-wrap: wrap;
  background: var(--superficie);
  border: 1px solid var(--borde);
  border-radius: var(--radio);
  padding: 10px 14px;
  margin: 12px 0 18px;
  box-shadow: var(--sombra);
  --alto-control: 34px;
}
.filtros .campo { display: flex; flex-direction: column; gap: var(--e1); min-width: 0; }
.filtros .etiqueta {
  font-size: 11.5px;
  color: var(--texto-suave);
  font-weight: 700;
  letter-spacing: .04em;
  text-transform: uppercase;
  line-height: 1.2;
  white-space: nowrap;
}
.filtros .control {
  height: var(--alto-control);
  box-sizing: border-box;
  font-family: inherit;
  font-size: 13px;
  font-weight: 600;
  color: var(--texto);
  border: 1px solid var(--borde);
  border-radius: 8px;
  /* `background-color`, NO el atajo `background`: el atajo repone
     `background-image: none` y se lleva por delante el chevron que
     `select.control` dibuja mas abajo. `.filtros .control` (0,2,0) le gana en
     especificidad a `select.control` (0,1,1) sin importar el orden, asi que los
     cuatro filtros del tablero -Año fiscal, Corte, Área y Período- se veian
     como campos de texto. Es la misma trampa de learn.md §6: una regla ancha
     que le gana en silencio a la especifica. */
  background-color: var(--superficie-alt);
}
select.control { padding: 0 10px; }
.filtros .separador { width: 1px; height: var(--alto-control); background: var(--borde); }

.alternador {
  display: inline-flex;
  border: 1px solid var(--borde);
  border-radius: 9px;
  overflow: hidden;
  background: var(--superficie-alt);
}
/* Dentro de la barra de filtros el borde y el radio los pone `.control`, para
   que un segmentado y un `select` midan exactamente lo mismo. */
.filtros .alternador { padding: 0; align-items: stretch; }
.filtros .alternador button { padding: 0 12px; }
.alternador button {
  border: 0;
  background: transparent;
  padding: 7px 12px;
  font-family: inherit;
  font-size: 12.5px;
  font-weight: 700;
  color: var(--texto-suave);
  cursor: pointer;
}
.alternador button[aria-pressed="true"] { background: var(--nf-azul-oscuro); color: #fff; }

.interruptor {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  font-size: 12.5px;
  font-weight: 600;
  color: var(--texto-suave);
  cursor: pointer;
  user-select: none;
  background: none;
  border: 0;
  font-family: inherit;
}
.interruptor i {
  width: 36px; height: 20px;
  border-radius: 99px;
  background: var(--exec-sin-datos);
  position: relative;
  transition: .15s;
}
.interruptor i::after {
  content: "";
  position: absolute;
  top: 2px; left: 2px;
  width: 16px; height: 16px;
  border-radius: 50%;
  background: #fff;
  transition: .15s;
  box-shadow: 0 1px 2px rgba(0, 0, 0, .2);
}
.interruptor[aria-pressed="true"] i { background: var(--nf-azul-profundo); }
.interruptor[aria-pressed="true"] i::after { left: 18px; }

/* --- Tarjetas --- */

.rejilla { display: grid; gap: 16px; }

/* LAS CUATRO TARJETAS COMPARTEN TRES BANDAS: encabezado, valor y pie.

   El problema que resuelve: cada tarjeta se maquetaba sola, asi que el valor de
   una quedaba dos lineas mas arriba que el de la de al lado y el pie de las
   baldosas flotaba en el medio con un hueco debajo. Son las lineas rojas y
   verdes de la revision de uso.

   La alineacion es ESTRUCTURAL, con `subgrid`: las tres filas se definen una
   vez en la rejilla y cada tarjeta las hereda, asi que no depende de que los
   contenidos midan casualmente lo mismo. `1fr` en la banda del valor es lo que
   empuja el pie al fondo de todas por igual.

   Sin `subgrid` -un navegador viejo- las tarjetas siguen teniendo el mismo alto
   por `stretch` y el pie sigue abajo por el `margin-top: auto` de mas abajo:
   se pierde la alineacion entre bandas, no la maquetacion. */
.rejilla.hero {
  grid-template-columns: minmax(300px, 1.2fr) repeat(3, minmax(150px, 1fr));
  grid-template-rows: auto 1fr auto;
  align-items: stretch;
}
.rejilla.hero > .tarjeta {
  display: grid;
  grid-row: span 3;
  grid-template-rows: subgrid;
  gap: var(--e3);
}
/* El valor se apoya en el fondo de su banda: asi las cifras de las cuatro
   quedan sobre la misma linea aunque midan distinto. */
.rejilla.hero [data-banda="valor"] { display: flex; flex-direction: column; justify-content: flex-end; }
.rejilla.hero [data-banda="pie"] { margin-top: 0; }
/* La tarjeta de areas lleva cinco columnas: necesita mas de la mitad. Y las
   tarjetas se alinean arriba en vez de estirarse a la mas alta, que dejaba un
   hueco grande debajo del grafico. */
.rejilla.dos { grid-template-columns: 1.15fr 1fr; align-items: start; }

.tarjeta {
  background: var(--superficie);
  border: 1px solid var(--borde);
  border-radius: var(--radio);
  padding: 18px 20px;
  box-shadow: var(--sombra);
  min-width: 0;
}
.tarjeta h2, .tarjeta h3 {
  font-size: 14.5px;
  color: var(--nf-azul-oscuro);
  margin-bottom: 4px;
}
.tarjeta .desc { font-size: 12px; color: var(--texto-suave); margin-bottom: 12px; }

.tarjeta.principal {
  background: linear-gradient(135deg, var(--nf-azul-oscuro), #0a5299 70%, var(--nf-azul-profundo));
  color: #fff;
  border: 0;
}
.tarjeta.principal h2 { color: #bcd8ef; }
.tarjeta.principal .desc { color: #9dc3e3; }
.tarjeta.principal .cifra-hero {
  font-family: var(--fuente-titulo);
  font-weight: 600;
  font-size: 56px;
  line-height: 1;
  margin: 6px 0 4px;
  letter-spacing: -.02em;
  font-variant-numeric: tabular-nums;
}
.tarjeta.principal .pie {
  display: flex;
  justify-content: space-between;
  gap: 12px;
  font-size: 12px;
  color: #cfe0ee;
}
.tarjeta.principal .pie span { display: flex; flex-direction: column; }
.tarjeta.principal .pie b { font-size: 14px; color: #fff; font-variant-numeric: tabular-nums; }

/* Dentro de la banda del valor, el medidor va pegado a la cifra y no se estira:
   quien empuja el pie al fondo es la banda, no este elemento. */
.rejilla.hero .medidor { margin: var(--e3) 0 0; flex: 0 0 auto; }

.medidor {
  height: 10px;
  border-radius: 99px;
  background: rgba(255, 255, 255, .18);
  overflow: hidden;
  margin: 14px 0 8px;
  position: relative;
}
.medidor i { display: block; height: 100%; background: var(--nf-aqua); border-radius: 99px; }

.baldosa .etiqueta {
  font-size: 12px;
  color: var(--texto-suave);
  font-weight: 700;
  letter-spacing: .03em;
}
.baldosa .valor {
  font-family: var(--fuente-titulo);
  font-weight: 600;
  font-size: 26px;
  color: var(--nf-azul-oscuro);
  margin: 6px 0 2px;
  line-height: 1.1;
  font-variant-numeric: tabular-nums;
}
.baldosa .valor.aqua { color: var(--nf-aqua-texto); }

/* EL PIE DE UNA BALDOSA ES TEXTO, NO UNA CAJA.

   Se llamaba `.nota`, y mas abajo en esta misma hoja `.nota` es un aviso con
   fondo y borde. La clase mas especifica ganaba el color y el tamaño, pero el
   fondo, el borde y el relleno se los quedaba la general: el pie terminaba
   dentro de una caja gris que parece un campo deshabilitado. Es el hallazgo de
   Joseph -notas dentro de campos que no se editan- y su causa era una colision
   de nombres, no una decision. Ahora tiene nombre propio. */
.pie-baldosa {
  font-size: 12px;
  color: var(--texto-suave);
  line-height: 1.35;
}

/* --- Estados de ejecucion --- */

.estado {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  font-size: 11.5px;
  font-weight: 700;
  padding: 3px 9px;
  border-radius: 99px;
}
.estado::before { content: ""; width: 7px; height: 7px; border-radius: 50%; background: currentColor; }
.estado.normal    { background: var(--exec-normal-bg);    color: var(--nf-aqua-texto); }
.estado.atencion  { background: var(--exec-atencion-bg);  color: #9a5f0a; }
.estado.sobregiro { background: var(--exec-sobregiro-bg); color: #a2222c; }
.estado.sin-datos { background: #f1f4f7; color: var(--texto-suave); }

.barra { height: 8px; border-radius: 99px; background: var(--exec-normal-bg); overflow: hidden; }
.barra i { display: block; height: 100%; border-radius: 99px; background: var(--exec-normal); }
.barra.atencion  { background: var(--exec-atencion-bg); }
.barra.atencion i  { background: var(--exec-atencion); }
.barra.sobregiro { background: var(--exec-sobregiro-bg); }
.barra.sobregiro i { background: var(--exec-sobregiro); }
.barra.sin-datos { background: #f1f4f7; }
.barra.sin-datos i { background: var(--exec-sin-datos); }

/* --- Filas por area --- */

/* Cinco columnas dentro de una tarjeta angosta.

   LAS DOS COLUMNAS DE DINERO TIENEN ANCHO FIJO Y LO QUE CEDE ES EL NOMBRE. Con
   `minmax(0, 1fr)` en el dinero, a 1280 px -el ancho de uso real- las cifras
   quedaban en 63 px y `L 15,463,302` pide 77: salian con puntos suspensivos
   en la primera pantalla que se ve. Un nombre de area cortado se entiende
   igual; una cifra cortada es otra cifra.

   Fijo y no `max-content` porque cada fila es su propia rejilla: si el ancho
   dependiera del contenido, dos filas con cifras de distinto largo dejarian
   la columna Ejecutado en distinta x. 96 px alcanzan para doce caracteres en
   negrita, que son mil millones de lempiras. */
.encabezado-areas, .fila-area {
  display: grid;
  grid-template-columns: minmax(0, 1fr) 56px minmax(36px, 0.8fr) 96px 96px;
  gap: 8px;
  align-items: center;
}
.encabezado-areas span, .fila-area > span { min-width: 0; overflow: hidden; text-overflow: ellipsis; }
.encabezado-areas {
  font-size: 10.5px;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--texto-suave);
  font-weight: 700;
  padding: 0 0 8px;
}
.encabezado-areas span:nth-child(n+2) { text-align: right; }
.fila-area {
  padding: 11px 0;
  border-top: 1px solid var(--borde-suave);
  width: 100%;
  background: none;
  border-left: 0; border-right: 0; border-bottom: 0;
  font-family: inherit;
  font-size: inherit;
  color: inherit;
  cursor: pointer;
  text-align: left;
}
.fila-area:first-of-type { border-top: 0; }
.fila-area:hover { background: var(--superficie-alt); }
.fila-area[aria-pressed="true"] { background: #eef5fc; }
.fila-area .nombre { font-weight: 700; }
.fila-area .nombre small { display: block; font-weight: 400; color: var(--texto-suave); font-size: 11.5px; }
.fila-area .pct {
  font-family: var(--fuente-titulo);
  font-weight: 600;
  font-size: 17px;
  color: var(--nf-azul-oscuro);
  text-align: right;
  line-height: 1.05;
  font-variant-numeric: tabular-nums;
}
.fila-area .pct small {
  display: block;
  font-family: var(--fuente-texto);
  font-weight: 400;
  font-size: 10.5px;
  color: var(--texto-suave);
}
.fila-area .monto { text-align: right; font-size: 12.5px; font-weight: 700; font-variant-numeric: tabular-nums; white-space: nowrap; }

/* --- Grafico mensual --- */

.grafico { width: 100%; height: auto; display: block; overflow: visible; }
.leyenda {
  display: flex;
  gap: 16px;
  font-size: 12px;
  color: var(--texto-suave);
  margin: 8px 0 2px;
  flex-wrap: wrap;
}
.leyenda span { display: inline-flex; align-items: center; gap: 6px; }
.leyenda i { width: 12px; height: 12px; border-radius: 3px; display: inline-block; }

/* --- Listas --- */

.lista { display: flex; flex-direction: column; }
.item {
  display: flex;
  gap: 12px;
  align-items: center;
  padding: 10px 0;
  border-top: 1px solid var(--borde-suave);
  font-size: 13px;
}
.item:first-child { border-top: 0; }
.item .texto { flex: 1; min-width: 0; }
.item .texto b { display: block; line-height: 1.3; }
.item .texto span { color: var(--texto-suave); font-size: 12px; display: block; margin-top: 2px; }
.item .derecha { text-align: right; white-space: nowrap; }
.item .derecha b { display: block; font-family: var(--fuente-titulo); font-weight: 600; font-size: 15px; font-variant-numeric: tabular-nums; }

/* --- Tabla del presupuesto ---
   Encabezado fijo, primera columna fija y desplazamiento horizontal PROPIO. El
   cuerpo de la pagina nunca se desplaza en horizontal. */

.envoltorio-tabla {
  overflow: auto;
  border: 1px solid var(--borde);
  border-radius: var(--radio);
  background: var(--superficie);
  max-height: 72vh;
}
table {
  border-collapse: separate;
  border-spacing: 0;
  width: max-content;
  min-width: 100%;
  font-size: var(--txt-tabla);
}
thead th {
  position: sticky;
  top: 0;
  background: var(--nf-azul-oscuro);
  color: #dbe8f3;
  font-weight: 700;
  font-size: 11px;
  letter-spacing: .06em;
  text-transform: uppercase;
  padding: 10px;
  text-align: right;
  white-space: nowrap;
  z-index: 3;
  /* Alto fijo, con el borde adentro: es la referencia de las filas de area. */
  height: var(--alto-encabezado);
  box-sizing: border-box;
}
thead th:first-child { text-align: left; left: 0; z-index: 4; }
tbody td {
  padding: 8px 10px;
  border-top: 1px solid var(--borde-suave);
  text-align: right;
  white-space: nowrap;
  background: var(--superficie);
  font-variant-numeric: tabular-nums;
}
tbody td:first-child {
  text-align: left;
  position: sticky;
  left: 0;
  background: var(--superficie);
  z-index: 2;
  box-shadow: 1px 0 0 var(--borde);
  font-variant-numeric: normal;
  min-width: 300px;
  max-width: 340px;
  overflow: hidden;
  text-overflow: ellipsis;
}
tr.area > td, tr.area > td:first-child {
  background: var(--fondo-area);
  font-family: var(--fuente-titulo);
  font-weight: 600;
  font-size: 13.5px;
  color: var(--nf-azul-oscuro);
  cursor: pointer;
}

/* EL AREA ACOMPAÑA A SUS LINEAS. Cada area es su propio `<tbody>` y la FILA de
   area es pegajosa, justo debajo del encabezado (por eso el encabezado tiene
   alto fijo). Cuando el area se acaba, la siguiente ocupa su lugar y la que sale
   se va hacia arriba, como el indice de una agenda.

   EL EMPUJE NO LO HACE `sticky`, LO CALCULA `nucleo/areas-pegadas.js`. Esta
   nota decia que la fila se confinaba a su `<tbody>` y que por eso el area
   saliente se iba sola. **El bloque contenedor de una fila es la tabla, no la
   seccion**, asi que nunca ocurrio: medido, con el `<tbody>` de Medios
   terminando 109 px por encima del borde su fila seguia clavada y la de Eventos
   entraba encima, cubriendola a media altura -exactamente lo que la nota decia
   haber evitado-. `position: relative` en el `<tbody>` tampoco lo cambia.

   Los indices de apilamiento van en escalera: linea 2, area 3/4, encabezado
   5/6. Las filas de grupo no se pegan: con 44 grupos, dos niveles pegados
   dejan media pantalla de encabezados. Solo en esta tabla: la de dos columnas
   del año siguiente tiene un encabezado de dos filas y otra altura. */
#tabla-presupuesto tbody tr.area { position: sticky; top: var(--alto-encabezado); z-index: 3; }
#tabla-presupuesto tbody tr.area > td:first-child { z-index: 4; }
#tabla-presupuesto thead th { z-index: 5; }
#tabla-presupuesto thead th:first-child { z-index: 6; }

/* EL ENCABEZADO DE DOS FILAS NO LLEVA BORDES: ES UN BLOQUE.
   Con las dos filas pegadas en escalera, el `border-bottom` del `th` de arriba
   queda en la costura entre dos capas pegajosas distintas. Quieto se ve gris
   (#dbe3ec, el borde); al desplazar se ve BLANCO (#ffffff, el fondo del
   envoltorio): la costura no la decide el diseño sino el compositor, y por eso
   la misma linea cambia de color segun si la tabla se movio o no. Medirla no
   sirve -las cajas dan 0 de hueco-; se ve ampliando la captura.

   Las dos filas son un solo encabezado y no necesitan una linea entre ellas.
   Sin `border-bottom` no hay costura que pintar de dos colores. La separacion
   con el cuerpo la da el cambio de fondo, que es el mismo criterio que usa la
   tabla del presupuesto con su encabezado azul. */
#tabla-siguiente thead th { border-bottom: 0; }

/* LA OTRA LINEA CLARA, la de entre filas: eran DOS bordes.
   Esta tabla es `plana` y `compacta` a la vez, asi que sus celdas heredan los
   separadores de las dos: `table.plana td` pone `border-bottom` gris (#dbe3ec)
   y `tbody td` pone `border-top` con `--borde-suave` (#e9eef3, casi blanco).
   Entre dos filas se pintan los dos, uno encima del otro: 2 px de separador, el
   de abajo casi blanco. Debajo del encabezado pasa lo mismo -el borde gris del
   `th` y, pegado, el casi blanco de la fila que quede debajo-, y como esa fila
   se desplaza, la linea clara se mueve con ella.

   Queda UN separador: el `border-bottom`. Sin `border-top` no hay segundo
   pixel que se mueva ni que aclare la linea. */
#tabla-siguiente tbody td { border-top: 0; }
/* --- El encabezado de DOS filas de la tabla del año que se arma ---

   Tres defectos encadenados, medidos con la tabla desplazada 500 px:

   1. LAS DOS FILAS SE PEGABAN AL MISMO `top: 0`. Presupuesto/Ejecutado/Variación
      tapaban a Concepto y a "FY2026 · en curso", y las celdas con `rowspan="2"`
      -Concepto, Origen, FY2027- medían 74 px pegadas a 0 mientras la banda del
      encabezado medía 37: los 37 px que sobresalían son la franja gris que
      quedaba flotando sobre las filas. Ahora se pegan EN ESCALERA.
   2. EL CUERPO GANABA AL ENCABEZADO. `table.plana th` deja z-index 1 y
      `tbody td:first-child` vale 2, así que la primera columna de las filas
      pasaba POR ENCIMA del encabezado: donde tenía que decir "Concepto" se leía
      "RADIO" o "PAUTA DIGITAL", cortados. Los índices van en escalera, como en
      la tabla del presupuesto.
   3. LAS ÁREAS NO SE PEGABAN. Acá se pegan, debajo de las dos filas, y cada una
      dentro de su propio `<tbody>`: cuando el área se acaba, la siguiente la
      EMPUJA hacia arriba en vez de cubrirla a media altura.

   Los grupos NO se pegan, igual que en la tabla del presupuesto: con 44 grupos,
   dos niveles pegados dejan media pantalla de encabezados. */
#tabla-siguiente { --alto-fila-encabezado: 37px; }
#tabla-siguiente thead tr { height: var(--alto-fila-encabezado); }
#tabla-siguiente thead th { height: var(--alto-fila-encabezado); box-sizing: border-box; z-index: 5; }
#tabla-siguiente thead tr:first-child > th { top: 0; }
#tabla-siguiente thead tr + tr > th { top: var(--alto-fila-encabezado); }
/* `th:first-child` de la SEGUNDA fila es "Presupuesto", no la columna pegajosa:
   la regla general le daba `left: 0` y lo habria pegado a la izquierda al
   desplazar en horizontal. La columna que se pega es el Concepto, y vive en la
   primera fila con `rowspan`. */
#tabla-siguiente thead tr:first-child > th:first-child { left: 0; z-index: 6; }
#tabla-siguiente thead tr + tr > th:first-child { left: auto; }
/* Las que abarcan las dos filas se leen al medio: alineadas arriba dejaban el
   rotulo pegado al borde y media celda en blanco debajo, que es justo lo que
   parecia una franja sobrante. */
#tabla-siguiente thead th[rowspan] { vertical-align: middle; }
#tabla-siguiente tbody tr.area {
  position: sticky;
  top: calc(2 * var(--alto-fila-encabezado));
  z-index: 3;
}
#tabla-siguiente tbody tr.area > td:first-child { z-index: 4; }

tr.grupo > td, tr.grupo > td:first-child { background: var(--superficie-alt); font-weight: 700; cursor: pointer; }
tr.linea > td:first-child { padding-left: 34px; font-weight: 600; }
tr.linea.patrocinio > td, tr.linea.patrocinio > td:first-child { background: var(--exec-normal-bg); }
tr.linea.fuera > td, tr.linea.fuera > td:first-child { background: #fdf7ec; }
tr[hidden] { display: none; }
td.cero { color: var(--exec-sin-datos); }

.flecha {
  display: inline-block;
  width: 0; height: 0;
  border-left: 5px solid currentColor;
  border-top: 4px solid transparent;
  border-bottom: 4px solid transparent;
  margin-right: 8px;
  transition: .15s;
  vertical-align: middle;
}
tr[aria-expanded="true"] .flecha { transform: rotate(90deg); }

.insignia {
  display: inline-block;
  font-size: 10px;
  font-weight: 700;
  letter-spacing: .05em;
  text-transform: uppercase;
  padding: 2px 7px;
  border-radius: 5px;
  margin-left: 8px;
  vertical-align: middle;
}
.insignia.patrocinio { background: var(--nf-aqua); color: var(--nf-azul-xoscuro); }
.insignia.fuera { background: var(--exec-atencion); color: #fff; }

/* Dentro o fuera del presupuesto, en la tabla del año que se arma: una pastilla
   que ademas es el interruptor. La de "fuera" se ve siempre porque cambia lo
   que se reporta; la de "dentro" es lo esperado y solo aparece al pasar el
   cursor por la fila o al llegar con el teclado -291 pastillas repitiendo lo
   normal son ruido-. La opacidad, no `display`, para que no salte la fila. */
button.insignia { border: 0; font-family: inherit; line-height: inherit; cursor: pointer; }
.insignia.dentro { background: var(--superficie-alt); color: var(--texto-suave); opacity: 0; transition: opacity .12s; }
tr:hover .insignia.dentro, .insignia.dentro:focus-visible { opacity: 1; }
.insignia.dentro:hover { background: var(--borde); color: var(--texto); }

/* --- Avisos y estados vacios --- */

.aviso {
  background: #eef5fc;
  border: 1px solid #cfe1f3;
  color: var(--nf-azul-oscuro);
  border-radius: var(--radio);
  padding: 10px 14px;
  font-size: 12.5px;
  margin: 0 0 14px;
}
.aviso.atencion { background: var(--exec-atencion-bg); border-color: #f3d9a8; color: #7a4b06; }

.vacio {
  padding: var(--e7) var(--e5);
  text-align: center;
  color: var(--texto-suave);
}
.vacio h2 { color: var(--nf-azul-oscuro); margin-bottom: var(--e2); }

.pantalla-mensaje {
  display: grid;
  place-items: center;
  min-height: 100vh;
  width: 100%;
  padding: var(--e6);
}
.pantalla-mensaje .tarjeta { max-width: 30rem; text-align: center; }

footer {
  padding: 22px 28px;
  color: var(--texto-suave);
  font-size: 12px;
  display: flex;
  justify-content: space-between;
  align-items: center;
  border-top: 1px solid var(--borde);
  margin-top: auto;
}

/* Contexto real de uso: embebido en el CRM, desde 1280px. Por debajo se apila
   para que siga siendo utilizable, sin prometer que ese es el escenario. */
@media (max-width: 1279px) {
  .rejilla.hero { grid-template-columns: 1fr 1fr; }
  .rejilla.dos { grid-template-columns: 1fr; }
}

/* =========================================================================
   EL TELEFONO (D100). La aplicacion entera, no solo el registro de facturas.

   RNF-U4 dice que se trabaja desde 1280 px: eso es donde se trabaja, no donde
   se puede entrar. La factura se registra en el evento, con el telefono, y la
   barra lateral se quedaba con 248 de los 390 px.

   Lo que cambia por debajo de 900 px, en orden de importancia:
     1. La barra lateral sale del flujo y se abre con un boton. Es lo que
        libera los 248 px.
     2. La barra superior en dos filas: contexto arriba, acciones abajo.
     3. Los filtros y los formularios en una columna (o dos, si entran).
     4. Las tablas se desplazan dentro de su caja; el cuerpo, nunca.
   ========================================================================= */

/* Lo que existe solo en el telefono (`.solo-movil`) se define AL FINAL de la
   hoja, en el bloque de utilidades: aca perdia contra `.btn` por orden. */
.telon { position: fixed; inset: 0; background: rgba(2, 12, 20, .45); z-index: 25; }

/* EN ESCRITORIO EL ☰ PLIEGA LA BARRA (D111). A 1280 px dentro del CRM, 248 px
   son la diferencia entre ver diez meses y ver doce. Sin telon: el telon es
   del cajon del telefono. */
@media (min-width: 900px) {
  aside { transition: width .2s ease; overflow: hidden; }
  body.lateral-plegada aside { width: 0; }
}

@media (max-width: 899px) {
  /* 1. La barra lateral, plegada fuera de la pantalla. */
  aside {
    position: fixed;
    top: 0; left: 0; bottom: 0;
    height: 100dvh;
    width: min(280px, 85vw);
    transform: translateX(-100%);
    transition: transform .2s ease;
    z-index: 30;
    box-shadow: 0 0 40px rgba(2, 12, 20, .35);
  }
  body.lateral-abierta aside { transform: none; }
  main { height: 100dvh; }

  /* 2. La barra superior en dos filas. */
  header.superior { flex-wrap: wrap; padding: 10px 12px; gap: var(--e2); }
  .superior-izq { flex: 1; min-width: 0; }
  header.superior h1 { font-size: 17px; }
  header.superior .contexto { white-space: normal; font-size: 12px; }
  .superior-der { margin-left: 0; width: 100%; flex-wrap: wrap; }
  .usuario-superior { margin-left: auto; padding-left: 0; border-left: 0; }
  .usuario-superior .quien { display: none; }

  /* 3. Filtros, formularios y herramientas en una o dos columnas. */
  .contenido { padding: 8px 12px 40px; }
  .filtros { padding: 10px 12px; gap: var(--e2); }
  .filtros .campo { flex: 1 1 calc(50% - var(--e2)); }
  /* Un segmentado de tres opciones no entra en media pantalla. */
  .filtros .campo:has(.alternador) { flex-basis: 100%; }
  .filtros .separador { display: none; }
  .filtros .control, .filtros select.control { width: 100%; }
  .filtros .alternador { display: flex; }
  .filtros .alternador button { flex: 1; padding: 0 6px; }
  .rejilla.hero { grid-template-columns: 1fr; }
  .rejilla-campos { grid-template-columns: 1fr; }
  .herramientas-tabla { padding: 10px 12px; gap: var(--e2); }
  .herramientas-tabla .campo { flex: 1 1 100%; }
  .herramientas-tabla .campo.crece { min-width: 0; max-width: none; }
  .herramientas-tabla .acciones-plegado { flex-wrap: wrap; }
  .card { padding: var(--e4); }
  .fondo-modal { padding: var(--e2); }
  .fondo-modal .panel { max-height: calc(100dvh - 16px); }
  .fondo-modal .cuerpo { --relleno-modal: var(--e4); }

  /* 4. Las tablas, dentro de su caja. */
  .envoltorio-tabla { max-height: none; }

  /* LAS TABLAS LLANAS PIERDEN LA COLUMNA PEGAJOSA Y SU MINIMO. A 390 px una
     primera columna de 300 px tapa el resto y el td pegajoso intercepta el
     toque: el boton Editar de Proveedores no se podia tocar. La del
     presupuesto la conserva, mas angosta (el ancho lo pone el `<col>`). */
  table.plana tbody td:first-child {
    position: static; min-width: 0; max-width: none; box-shadow: none;
  }
  table.compacta tbody td:first-child { min-width: 160px; max-width: 200px; }

  /* Las filas por area: sin la barra, que no entra, y con el dinero entero. */
  .encabezado-areas, .fila-area { grid-template-columns: minmax(0, 1fr) 48px 88px 88px; gap: 6px; }
  .encabezado-areas span:nth-child(3), .fila-area .barra { display: none; }
  .fila-area .monto { font-size: 12px; }
}

@media print {
  aside, .franja, .filtros { display: none; }
  body { background: #fff; }
}

/* Lo que existe solo para el papel: el logo de la cabecera y la tabla del
   presupuesto por trimestres. En pantalla no ocupan lugar. */
@media screen {
  .solo-impresion { display: none; }
}

/* =========================================================================
   Piezas compartidas por las vistas de la noche 2
   ========================================================================= */

/* --- Botones --- */

.btn {
  display: inline-flex; align-items: center; gap: var(--e2);
  font-family: var(--fuente-texto); font-size: var(--txt-cuerpo); font-weight: 700;
  padding: 9px 16px; border-radius: var(--radio); border: 1px solid transparent;
  background: var(--nf-azul-profundo); color: var(--nf-blanco);
  cursor: pointer; line-height: 1.2; text-decoration: none;
}
.btn:hover { background: #0560a8; }
.btn:disabled { opacity: .55; cursor: default; }
.btn.sec { background: var(--superficie); color: var(--nf-azul-oscuro); border-color: var(--borde); }
.btn.sec:hover { background: var(--superficie-alt); }
.btn.peligro { background: var(--exec-sobregiro); }
.btn.peligro:hover { background: #bd3b45; }
.btn.sm { padding: 7px 12px; font-size: var(--txt-tabla); }
.btn.diminuto { padding: 4px 9px; font-size: var(--txt-etiqueta); font-weight: 700; }

.acciones-fila {
  display: flex; align-items: center; gap: var(--e3);
  flex-wrap: wrap; margin-top: var(--e4);
}
.acciones-fila .espaciador { flex: 1; }

/* --- Tarjetas de contenido --- */

.card {
  background: var(--superficie); border: 1px solid var(--borde);
  border-radius: var(--radio); box-shadow: var(--sombra);
  padding: var(--e5); margin-bottom: var(--e4);
}
.card h3 {
  font-family: var(--fuente-titulo); font-weight: 600;
  font-size: var(--txt-subtitulo); color: var(--nf-azul-oscuro); margin: 0;
}
.card .desc { color: var(--texto-suave); font-size: var(--txt-tabla); margin: var(--e1) 0 var(--e4); }

.nota {
  background: var(--superficie-alt); border: 1px solid var(--borde);
  border-radius: var(--radio); padding: var(--e3) var(--e4);
  font-size: var(--txt-tabla); color: var(--texto-suave); margin-bottom: var(--e4);
}
.nota b { color: var(--texto); }
.nota.atencion { background: var(--exec-atencion-bg); border-color: #f3d9a8; color: #7a4b06; }

/* --- Campos de formulario --- */

.rejilla-campos {
  display: grid; grid-template-columns: repeat(auto-fit, minmax(15rem, 1fr));
  gap: var(--e4);
}
.campo { display: flex; flex-direction: column; gap: var(--e1); font-size: var(--txt-tabla); }
.campo > span { font-weight: 700; color: var(--texto); }
.campo input, .campo select, .campo textarea {
  font-family: var(--fuente-texto); font-size: var(--txt-cuerpo);
  padding: 8px 10px; border: 1px solid var(--borde); border-radius: 9px;
  background: var(--superficie); color: var(--texto); width: 100%;
}
.campo input:focus, .campo select:focus, .campo textarea:focus {
  outline: 2px solid var(--nf-aqua); outline-offset: 1px;
}
.campo small { color: var(--texto-suave); font-size: var(--txt-etiqueta); }

/* UN DATO QUE NO SE EDITA SE VE COMO TEXTO, NO COMO CAMPO.

   Va en un `.campo` para conservar la etiqueta chica arriba y la alineacion con
   los campos de al lado, pero sin caja, sin borde y sin fondo. Un `input`
   deshabilitado con texto adentro le promete a la persona que ahi se escribe, y
   despues no la deja; ademas desperdicia el espacio de un control para mostrar
   una linea de texto (hallazgo de la revision de uso). */
.dato {
  font-size: var(--txt-cuerpo);
  color: var(--texto);
  font-variant-numeric: tabular-nums;
  padding: 8px 0;
  min-height: 1.2em;
}
.dato.vacio { color: var(--texto-suave); }
/* Un campo que la lectura automatica no pudo completar. El borde ambar avisa,
   y el texto de abajo dice que hacer: el color nunca va solo. */
.campo.faltante input { border-color: var(--exec-atencion); background: #fffdf7; }
.campo.faltante small { color: #9a5f0a; }

.etiquetas {
  border: 0; padding: 0; margin: var(--e3) 0 0;
  display: flex; flex-wrap: wrap; gap: var(--e2); align-items: center;
}
.etiquetas legend { font-size: var(--txt-tabla); font-weight: 700; padding: 0; margin-right: var(--e2); }
.pastilla {
  display: inline-flex; align-items: center; gap: 6px;
  border: 1px solid var(--borde); border-radius: 99px; padding: 4px 12px;
  font-size: var(--txt-tabla); cursor: pointer; background: var(--superficie);
}
.pastilla:has(input:checked) { background: #eef5fc; border-color: var(--nf-azul-profundo); font-weight: 700; }

/* --- Renglones de una factura --- */

.renglon { border: 1px solid var(--borde); border-radius: var(--radio); padding: var(--e4); margin-bottom: var(--e3); }
.renglon-cabeza { display: flex; align-items: baseline; gap: var(--e3); margin-bottom: var(--e3); flex-wrap: wrap; }
.renglon-cabeza b { font-size: var(--txt-cuerpo); }
.renglon-cabeza .monto {
  margin-left: auto; font-family: var(--fuente-titulo); font-weight: 600;
  font-variant-numeric: tabular-nums;
}
.insignia.confianza-media { background: var(--exec-atencion); color: #fff; }
.insignia.confianza-baja  { background: var(--exec-sobregiro); color: #fff; }
.coincide { color: var(--nf-aqua-texto); font-weight: 700; }

.leyendo { display: flex; align-items: center; gap: var(--e4); }
.leyendo b { display: block; }
.leyendo .suave { font-size: var(--txt-tabla); }
.girando {
  width: 22px; height: 22px; border-radius: 50%; flex: 0 0 auto;
  border: 3px solid var(--exec-normal-bg); border-top-color: var(--nf-aqua);
  animation: girar .8s linear infinite;
}
@keyframes girar { to { transform: rotate(360deg); } }
@media (prefers-reduced-motion: reduce) { .girando { animation: none; } }

.aviso-error { border-left: 3px solid var(--exec-sobregiro); }

/* --- Tabla llana, para las vistas de lista --- */

table.plana { width: 100%; border-collapse: collapse; font-size: var(--txt-tabla); }
table.plana th, table.plana td {
  padding: 9px var(--e3); text-align: left; border-bottom: 1px solid var(--borde);
  vertical-align: top;
}
table.plana th {
  font-family: var(--fuente-titulo); font-weight: 600; font-size: var(--txt-etiqueta);
  text-transform: uppercase; letter-spacing: .04em; color: var(--texto-suave);
  background: var(--superficie-alt); position: sticky; top: 0; z-index: 1;
}
/* Todo el dinero: alineado a la derecha y con cifras de ancho fijo. Sin esto
   una columna de doce meses no se puede leer hacia abajo. */
table.plana th.num, table.plana td.num {
  text-align: right; font-variant-numeric: tabular-nums; white-space: nowrap;
}
table.plana tbody tr:hover { background: var(--superficie-alt); }
table.plana td.acciones, table.plana th.acciones { text-align: right; white-space: nowrap; }

/* UNA TABLA DE LISTA NO ES LA DEL PRESUPUESTO. La primera columna pegajosa y su
   minimo de 300 px son de la tabla de doce meses; heredados acá empujaban las
   acciones fuera de la caja —medido en Usuarios, "Quitar acceso" cortado detrás
   del desplazamiento horizontal— y una lista no necesita columna pegajosa. Es
   la misma regla que el telefono ya aplicaba; acá vale en las dos anchuras. La
   del año que se arma es `plana compacta` y conserva la suya. */
table.plana:not(.compacta) tbody td:first-child {
  position: static; min-width: 0; max-width: none; box-shadow: none; overflow: visible;
}

/* --- La barra de la tabla del presupuesto --- */

/* Misma forma que la barra de filtros de arriba: `.campo` = etiqueta chica
   arriba, `.control` abajo, todos de la misma altura. Dos barras de controles
   en la misma pantalla que se ven distinto se leen como dos cosas distintas. */
/* La suma viva del modal de ajuste. El ajuste se explica por lo que mueve, y
   ese numero decide si necesita aprobacion de nivel 2: verlo mientras se
   escribe evita el viaje de enviar, leer el nivel y volver a corregir. */
.suma-viva {
  margin: var(--e3) 0;
  padding: var(--e3) var(--e4);
  border-radius: var(--radio);
  background: var(--superficie-alt);
  border: 1px solid var(--borde);
  font-size: var(--txt-tabla);
  font-variant-numeric: tabular-nums;
}
.suma-viva b { color: var(--nf-azul-oscuro); }
/* Con renglones a medias el boton de enviar esta apagado: la caja lo dice en
   texto ademas del color, que es la regla de siempre. */
.suma-viva.incompleta { background: var(--exec-atencion-bg); border-color: #f3d9a8; }
.btn:disabled { opacity: .5; cursor: not-allowed; }

/* --- Configuracion --- */

/* Datos que no se editan: una fila de texto con su etiqueta chica, no cuatro
   tarjetas con cajas de formulario. Un campo se ve como campo solo si se puede
   editar. */
.fila-datos {
  display: flex; flex-wrap: wrap; gap: var(--e6);
  padding: var(--e3) 0 var(--e4);
  border-bottom: 1px solid var(--borde-suave);
  margin-bottom: var(--e4);
}
.dato-chico { display: flex; flex-direction: column; gap: 2px; }
.dato-chico span {
  font-size: var(--txt-etiqueta); color: var(--texto-suave);
  text-transform: uppercase; letter-spacing: .04em; font-weight: 700;
}
.dato-chico b { font-size: var(--txt-cuerpo); color: var(--texto); }

/* El sufijo dentro del campo: sin el, "Margen antes de alertar" con un 10
   adentro no dice si son diez por ciento o diez mil lempiras. */
.con-sufijo { position: relative; display: block; }
.con-sufijo input { padding-right: 2rem !important; }
.con-sufijo i {
  position: absolute; right: 12px; top: 50%; transform: translateY(-50%);
  font-style: normal; color: var(--texto-suave); font-weight: 700; pointer-events: none;
}

/* Roles: la lista a la izquierda, los permisos DEL ROL ELEGIDO a la derecha.

   La matriz anterior era una columna por rol, y eso no escala: con el sexto rol
   la tabla se sale de la pantalla, y el ancho disponible por rol obliga a
   abreviar los permisos hasta hacerlos ilegibles. Un rol a la vez deja lugar
   para que cada permiso diga lo que hace. */
.dos-paneles { display: grid; grid-template-columns: 18rem 1fr; gap: var(--e5); align-items: start; }
.lista-roles { display: flex; flex-direction: column; gap: var(--e2); }
.item-rol {
  display: flex; align-items: center; gap: var(--e2);
  border: 1px solid var(--borde); border-radius: var(--radio);
  background: var(--superficie); padding: var(--e2) var(--e3);
}
.item-rol.activo { border-color: var(--nf-azul-profundo); box-shadow: inset 3px 0 0 var(--nf-azul-profundo); }
.item-rol.arrastrando { opacity: .4; }
.item-rol .agarre { cursor: grab; color: var(--exec-sin-datos); user-select: none; }
.item-rol .nombre {
  flex: 1; text-align: left; border: 0; background: none; cursor: pointer;
  font-family: inherit; font-size: var(--txt-tabla); font-weight: 700; color: var(--texto);
  display: flex; flex-direction: column; gap: 1px; min-width: 0;
}
.item-rol .nombre .suave { font-weight: 400; font-size: var(--txt-etiqueta); }
.item-rol .acciones { display: flex; gap: var(--e1); }

.cabecera-rol { display: flex; gap: var(--e4); align-items: flex-start; margin-bottom: var(--e4); }
.cabecera-rol .campo.crece { flex: 1; }

/* Las cuatro columnas de accion, siempre las mismas y siempre en el mismo
   orden. La casilla vacia se ve vacia: un guion o una casilla apagada se leen
   como "esta en cero", que es otra cosa. */
.matriz-permisos th.centro, .matriz-permisos td.centro { text-align: center; width: 7.5rem; }
.matriz-permisos td.vacia { background: var(--superficie-alt); }
.matriz-permisos td .suave { display: block; font-size: var(--txt-etiqueta); }

/* --- Submenu --- */

/* Un boton que abre dos opciones. Exportar tiene dos formatos y son dos usos
   distintos del mismo reporte -uno se abre en Excel, el otro entra en
   cualquier cosa-, asi que no hay un default correcto: se pregunta. */
.submenu { position: relative; display: inline-block; }
.submenu .opciones {
  position: absolute;
  top: calc(100% + 4px);
  right: 0;
  z-index: 20;
  background: var(--superficie);
  border: 1px solid var(--borde);
  border-radius: 8px;
  box-shadow: var(--sombra);
  min-width: 8rem;
  padding: var(--e1);
  display: flex;
  flex-direction: column;
}
.submenu .opciones button {
  border: 0; background: none; text-align: left;
  font-family: inherit; font-size: var(--txt-tabla); font-weight: 600;
  color: var(--texto); padding: var(--e2) var(--e3); border-radius: 6px; cursor: pointer;
}
.submenu .opciones button:hover { background: var(--superficie-alt); }

/* --- Pestañas de catalogo --- */

/* Un boton que se ve como enlace. Es una accion, no una navegacion -no hay una
   URL a la que llevar-, asi que por dentro es un boton: un `<a href="#">` le
   miente al teclado y al lector de pantalla. */
.enlace {
  border: 0; background: none; padding: 0;
  font: inherit; color: var(--nf-azul-profundo);
  text-decoration: underline; cursor: pointer;
}

.pestanas {
  display: flex;
  gap: var(--e1);
  border-bottom: 1px solid var(--borde);
  margin: var(--e4) 0;
}
.pestanas button {
  border: 0;
  background: none;
  font-family: var(--fuente-texto);
  font-size: var(--txt-tabla);
  font-weight: 700;
  color: var(--texto-suave);
  padding: var(--e3) var(--e4);
  cursor: pointer;
  border-bottom: 2px solid transparent;
  margin-bottom: -1px;
}
.pestanas button[aria-selected="true"] {
  color: var(--nf-azul-oscuro);
  border-bottom-color: var(--nf-azul-profundo);
}

/* Una entrada desactivada sigue en la lista -para poder reactivarla- pero se
   lee como lo que es: algo que ya no se ofrece. */
tr.inactiva > td { color: var(--texto-suave); }
tr.inactiva b { font-weight: 400; text-decoration: line-through; }

/* --- Sugerencias de duplicados --- */

.sugerencias {
  background: #fdf7ec;
  border: 1px solid #f3d9a8;
  border-radius: var(--radio);
  padding: var(--e4);
  margin-bottom: var(--e4);
}
.sugerencias > b { font-family: var(--fuente-titulo); color: #7a4b06; }
.sugerencias p { margin: var(--e1) 0 var(--e3); font-size: var(--txt-tabla); }
.sugerencias ul { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: var(--e2); }
.sugerencias li {
  display: flex; align-items: center; justify-content: space-between; gap: var(--e3);
  font-size: var(--txt-tabla); background: var(--superficie);
  border: 1px solid var(--borde); border-radius: 8px; padding: var(--e2) var(--e3);
}

.herramientas-tabla {
  display: flex;
  gap: var(--e3);
  align-items: flex-end;
  flex-wrap: wrap;
  background: var(--superficie);
  border: 1px solid var(--borde);
  border-radius: var(--radio);
  padding: 10px 14px;
  margin-bottom: var(--e4);
  box-shadow: var(--sombra);
  --alto-control: 34px;
}
.herramientas-tabla .campo { display: flex; flex-direction: column; gap: var(--e1); min-width: 0; }
/* Las acciones sobre la tabla van en su propia linea, debajo de los filtros. */
.herramientas-tabla .campo.linea-nueva { flex: 1 1 100%; }
.herramientas-tabla .campo.crece { flex: 1; min-width: 14rem; max-width: 26rem; }
.herramientas-tabla .etiqueta {
  font-size: 11.5px;
  color: var(--texto-suave);
  font-weight: 700;
  letter-spacing: .04em;
  text-transform: uppercase;
  line-height: 1.2;
  white-space: nowrap;
}
.herramientas-tabla .control {
  height: var(--alto-control);
  box-sizing: border-box;
  font-family: inherit;
  font-size: 13px;
  font-weight: 600;
  color: var(--texto);
  border: 1px solid var(--borde);
  border-radius: 8px;
  /* `background-color`, no el atajo: el atajo borraba el chevron que
     `select.control` dibuja como imagen de fondo (D148). */
  background-color: var(--superficie-alt);
}
.herramientas-tabla input.control, .herramientas-tabla select.control { padding: 0 10px; width: 100%; }
.herramientas-tabla .alternador { padding: 0; align-items: stretch; }
.herramientas-tabla .alternador button { padding: 0 12px; }
.herramientas-tabla .acciones-plegado {
  display: flex; align-items: center; gap: var(--e2);
  background: transparent; border: 0; padding: 0;
}
/* CADA GRUPO DE ACCIONES, SU CAJA. Siete botones seguidos en una fila no dicen
   cuáles aplican a lo que está a la vista y cuáles agregan al año que se arma:
   la etiqueta de arriba lo decía y la fila de botones lo desmentía. La caja
   ata cada grupo a su etiqueta. El botón de aprobar queda fuera a propósito: es
   la acción principal y no pertenece a ninguno de los dos grupos. */
.herramientas-tabla .acciones-plegado.caja {
  border: 1px solid var(--borde); background: var(--superficie-alt);
  border-radius: 8px; padding: 0 var(--e2);
}

/* El pie de la tabla: cuantas lineas se ven de cuantas, y cuanto suman. Sale
   de lo VISIBLE: si fuera del arbol entero, un filtro mostraria una cifra que
   no corresponde a lo que se esta viendo y alguien la copiaria a una
   presentacion. */
.pie-tabla {
  margin: var(--e3) 0 0;
  font-size: var(--txt-tabla);
  color: var(--texto-suave);
  font-variant-numeric: tabular-nums;
}

/* --- Densidad compacta --- */

/* Fila de 32px. Con 304 lineas, cada pixel de alto de fila son 304 pixeles de
   scroll: la diferencia entre ver un area completa de un vistazo y no verla.

   `table-layout: fixed` es lo que hace que los anchos arrastrables funcionen:
   con `auto`, el navegador reparte el ancho por contenido y el `<col>` es una
   sugerencia que ignora. */
table.compacta {
  table-layout: fixed;
  width: max-content;
}
table.compacta tbody td { height: 32px; padding-top: 0; padding-bottom: 0; }
table.compacta tbody td:first-child {
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}

/* Los ceros en gris claro. Se muestran como cifra y no como raya: una columna
   de doce meses con rayas no se puede leer en diagonal, que es justo para lo
   que existe `tabular-nums`. */
table.compacta td.cero { color: var(--exec-sin-datos); }

/* Comparar (D147): dos cifras por celda, la que se juzga arriba y la referencia
   en chico debajo. La fila crece a 44px para las dos lineas; el chip de estado
   va en la columna Total y lleva siempre el porcentaje en texto (D29). */
table.compacta.comparando tbody td { height: 44px; }
td.par { line-height: 1.2; vertical-align: middle; }
td.par b { display: block; }
td.par small { color: var(--texto-suave); font-size: 11px; }
/* El chip va en su propia columna, Diferencia, para que quede en una linea
   recta: dentro de Total se corria con el ancho de cada cifra (D148). */
table.compacta th.diferencia, table.compacta td.diferencia { white-space: nowrap; }
/* Lo juzgado que pasa a la referencia va en rojo; solo esa cifra, y siempre
   con el numero (D29). En Diferencia, el delta y el porcentaje. */
td.par small.excede, td.diferencia.excede b, td.diferencia.excede small { color: var(--exec-sobregiro); }
td.diferencia.excede small { font-weight: 700; }
tr.total-visible td { font-weight: 700; background: var(--superficie-alt); border-top: 2px solid var(--borde); }

/* Registrar un gasto parado sobre la linea: un boton chico pegado al borde
   derecho de la celda del concepto -la celda es pegajosa, asi que es su bloque
   contenedor-, que aparece al pasar por la fila. Donde no hay puntero se ve
   siempre. Al final del texto se perdia detras de la elipsis. */
table.compacta tr.linea > td:first-child { padding-right: 30px; }
table.compacta td .registrar {
  position: absolute; right: 7px; top: 50%; transform: translateY(-50%);
  border: 1px solid var(--nf-azul-profundo); border-radius: 50%; background: var(--superficie);
  color: var(--nf-azul-profundo); width: 18px; height: 18px; padding: 0;
  font-size: 14px; line-height: 1; cursor: pointer;
}
table.compacta td .registrar:hover { background: var(--nf-azul-profundo); color: #fff; }
@media (hover: hover) {
  table.compacta td .registrar { opacity: 0; }
  table.compacta tr:hover td .registrar, table.compacta td .registrar:focus-visible { opacity: 1; }
}

/* Encabezado ordenable, con su tirador de ancho al borde derecho.

   `position: sticky`, NO `relative`: el tirador es `absolute` y un antepasado
   pegajoso le sirve igual de caja de referencia. Con `relative` esta regla
   -de mayor especificidad que `thead th`- le ganaba al encabezado fijo, y la
   tabla perdio el encabezado el dia que entraron los tiradores. */
thead th[data-orden] { cursor: pointer; position: sticky; user-select: none; }
thead th[data-orden]:hover .rotulo { text-decoration: underline; }
thead th .tirador {
  position: absolute;
  top: 0; right: 0; bottom: 0;
  width: 6px;
  cursor: col-resize;
}
thead th .tirador:hover { background: var(--nf-aqua); }

td.sin-datos { padding: var(--e6); text-align: center; color: var(--texto-suave); }

/* En la vista por concepto, lo que se repite se destaca: es lo unico que hay
   para mirar ahi. */
tr.repetido > td { background: #fdf7ec; font-weight: 700; }

.herramientas { display: flex; gap: var(--e3); align-items: center; flex-wrap: wrap; margin-bottom: var(--e4); }
.herramientas input[type="search"], .herramientas select {
  font-family: var(--fuente-texto); font-size: var(--txt-tabla);
  padding: 8px 10px; border: 1px solid var(--borde); border-radius: 9px;
  background: var(--superficie); color: var(--texto);
}
.herramientas input[type="search"] { min-width: 18rem; flex: 1; max-width: 30rem; }
.herramientas .espaciador { flex: 1; }

/* --- Estado vacio: dice que hacer, no que falta --- */

.estado-vacio {
  border: 1px dashed var(--borde); border-radius: var(--radio);
  padding: var(--e7) var(--e5); text-align: center; color: var(--texto-suave);
}
.estado-vacio b { display: block; color: var(--texto); font-size: var(--txt-subtitulo); font-family: var(--fuente-titulo); }
.estado-vacio p { margin: var(--e2) auto var(--e4); max-width: 34rem; }

/* --- Panel modal --- */

.fondo-modal {
  position: fixed; inset: 0; background: rgba(2, 12, 20, .45);
  display: flex; align-items: center; justify-content: center; padding: var(--e5); z-index: 50;
}
.fondo-modal .panel {
  background: var(--superficie); border-radius: var(--radio);
  box-shadow: 0 12px 48px rgba(3, 56, 99, .28);
  width: 100%; max-height: 90vh; display: flex; flex-direction: column;
}
.fondo-modal header {
  display: flex; align-items: center; gap: var(--e3);
  padding: var(--e4) var(--e5); border-bottom: 1px solid var(--borde);
}
.fondo-modal header h2 {
  font-family: var(--fuente-titulo); font-weight: 600; font-size: var(--txt-subtitulo);
  color: var(--nf-azul-oscuro); margin: 0; flex: 1;
}
.fondo-modal .cerrar {
  border: 0; background: transparent; font-size: 24px; line-height: 1;
  color: var(--texto-suave); cursor: pointer; padding: 0 4px;
}
/* `min-height: 0` es lo que hace que el `overflow-y` sirva de algo.

   Un hijo de flex no baja de su alto de contenido salvo que se le diga: sin
   esto, el cuerpo del modal se desborda del panel en vez de desplazarse, y en
   una pantalla corta los botones de accion quedan FUERA de la ventana. El modal
   se abre, se llena, y no hay forma de enviarlo. */
.fondo-modal .cuerpo { --relleno-modal: var(--e5); padding: var(--relleno-modal); overflow-y: auto; min-height: 0; flex: 1; }
.fondo-modal .cuerpo .campo { margin-bottom: var(--e4); }

/* --- Aviso flotante --- */

.aviso-flotante {
  position: fixed; bottom: var(--e5); left: 50%; transform: translateX(-50%);
  background: var(--nf-azul-xoscuro); color: var(--nf-blanco);
  padding: 10px 18px; border-radius: var(--radio);
  font-size: var(--txt-tabla); z-index: 60; max-width: min(90vw, 34rem);
  box-shadow: 0 6px 24px rgba(2, 12, 20, .3);
}

.oculto-visual {
  position: absolute; width: 1px; height: 1px; overflow: hidden;
  clip: rect(0 0 0 0); white-space: nowrap;
}

/* Estados de un movimiento y de un ajuste, en la tabla y en las tarjetas. */
.insignia.estado-confirmado     { background: var(--exec-normal); color: var(--nf-azul-xoscuro); }
.insignia.estado-borrador       { background: #e3e9ef; color: var(--texto-suave); }
.insignia.estado-anulado        { background: var(--exec-sobregiro); color: #fff; }
.insignia.estado-propuesto      { background: #e3e9ef; color: var(--texto-suave); }
.insignia.estado-aprobado_nivel1 { background: var(--exec-atencion); color: #fff; }
.insignia.estado-aprobado_nivel2 { background: var(--exec-normal); color: var(--nf-azul-xoscuro); }
.insignia.estado-rechazado      { background: var(--exec-sobregiro); color: #fff; }

/* Encabezado de grupo dentro de la matriz de permisos. */
table.plana tr.grupo-permisos td {
  background: var(--superficie-alt); text-transform: uppercase;
  font-size: var(--txt-etiqueta); letter-spacing: .04em; color: var(--texto-suave);
}
.herramientas .campo { gap: 2px; }
.herramientas .campo > span { font-size: var(--txt-etiqueta); color: var(--texto-suave); font-weight: 400; }

/* =========================================================================
   UTILIDADES QUE APAGAN `display`. AL FINAL DE LA HOJA Y CON !important.

   Es la trampa de `[hidden]` (learn.md §6) con una clase: `.solo-movil {
   display: none }` vivia a mitad de la hoja y `.btn { display: inline-flex }`
   venia despues con la misma especificidad, asi que ganaba `.btn`. El ☰ y
   Tomar foto se veian en escritorio, y el ☰ oscurecia la pantalla sin mover
   nada. Una utilidad que apaga `display` se escribe aca abajo y con
   !important, para que ninguna regla de componente que se agregue despues
   vuelva a ganarle por orden. Hay una prueba que recorre cada `.solo-movil`
   del documento a 1280 px y exige `display: none`.
   ========================================================================= */
.solo-movil { display: none !important; }
@media (max-width: 899px) {
  .solo-movil { display: inline-flex !important; }
}

/* --- Selector con busqueda (D109) --- */

/* Un campo de texto y una lista debajo, para toda lista de mas de quince
   opciones. Ancho = ancho del campo, nunca mas que el panel; la lista mide
   hasta 40 vh y se desplaza por dentro. En el telefono se abre debajo igual. */
.selector-busqueda { position: relative; min-width: 0; }
.selector-busqueda .sb-campo { position: relative; display: flex; align-items: center; }
.selector-busqueda .sb-entrada { width: 100%; padding-right: 2rem; text-overflow: ellipsis; }
.selector-busqueda .sb-limpiar {
  position: absolute; right: 6px; top: 50%; transform: translateY(-50%);
  border: 0; background: transparent; color: var(--texto-suave);
  font-size: 18px; line-height: 1; cursor: pointer; padding: 0 4px;
}
.selector-busqueda .sb-limpiar:hover { color: var(--texto); }
.selector-busqueda .sb-lista {
  position: absolute; left: 0; right: 0; top: calc(100% + 4px); z-index: 40;
  margin: 0; padding: 4px; list-style: none;
  max-height: 40vh; overflow: auto;
  background: var(--superficie); border: 1px solid var(--borde); border-radius: 8px;
  box-shadow: 0 8px 28px rgba(3, 56, 99, .16);
  text-align: left; font-weight: 400;
}
/* El encabezado del grupo, pegajoso DENTRO de la lista. */
.selector-busqueda .sb-grupo {
  position: sticky; top: -4px; z-index: 1;
  background: var(--superficie-alt); color: var(--texto-suave);
  font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase;
  padding: 6px 10px 4px; margin: 0 -4px;
}
.selector-busqueda [role="option"] {
  display: flex; align-items: center; gap: var(--e3);
  padding: 7px 10px; border-radius: 6px; cursor: pointer;
  font-size: var(--txt-tabla); color: var(--texto);
}
.selector-busqueda .sb-texto { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 1px; }
/* Titulo en una linea con puntos suspensivos; el nombre entero va en `title`
   y en el campo al elegirlo (D110). */
.selector-busqueda .sb-titulo { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; font-weight: 600; }
.selector-busqueda .sb-sub {
  font-size: var(--txt-etiqueta); color: var(--texto-suave);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.selector-busqueda .sb-extra {
  font-variant-numeric: tabular-nums; white-space: nowrap;
  font-size: var(--txt-tabla); color: var(--texto-suave);
}
.selector-busqueda .sb-activa, .selector-busqueda [role="option"]:hover { background: #eef5fc; }
.selector-busqueda [aria-selected="true"] .sb-titulo { color: var(--nf-azul-profundo); }
/* Lo que coincide se subraya con el aqua: es foco y dato vivo, no alerta (D29). */
.selector-busqueda mark {
  background: none; color: inherit; font-weight: 800;
  text-decoration: underline; text-decoration-color: var(--nf-aqua); text-decoration-thickness: 2px;
  text-underline-offset: 2px;
}
.selector-busqueda .sb-vacio { padding: 8px 10px; color: var(--texto-suave); font-size: var(--txt-tabla); }
.selector-busqueda .sb-nota { display: block; color: var(--texto-suave); font-size: var(--txt-etiqueta); margin-top: 4px; }
/* En las barras de filtros el control mide lo que media el `select`. */
.herramientas-tabla .selector-busqueda { width: 14rem; }
.herramientas-tabla .selector-busqueda .control { padding-right: 2rem; }
/* Con algo elegido la × ocupa el lugar del chevron (D148). */
.herramientas-tabla .sb-campo:has(.sb-limpiar:not([hidden])) .sb-entrada { background-image: none; }

/* --- Modales: pie pegado, pregunta al cerrar, lista de casillas (Fase 35) --- */

/* El pie con las acciones queda a la vista aunque el cuerpo se desplace:
   medido en el modal de proveedor, 1.136 px de cuerpo en 750 visibles y
   Guardar fuera de pantalla. `sticky` dentro del cuerpo que se desplaza, con
   margenes negativos para pisar el relleno y llegar al borde.

   EL DESPLAZAMIENTO SE MIDE CONTRA EL RELLENO, NO CONTRA EL BORDE. Con
   `bottom: 0` el pie se pegaba var(--e5) MAS ARRIBA de donde lo deja el flujo,
   y tapaba las ultimas lineas del cuerpo aunque no hubiera nada que desplazar:
   medido en Renombrar categoria, el pie a 494 px con el `<small>` terminando en
   502. El desplazamiento tiene que compensar el margen negativo, y por eso el
   relleno del cuerpo vive en una variable: en el telefono mide var(--e4). */
.fondo-modal .panel { position: relative; }
.fondo-modal .cuerpo > .acciones-fila:last-child {
  position: sticky; bottom: calc(-1 * var(--relleno-modal)); z-index: 2;
  margin: var(--e4) calc(-1 * var(--relleno-modal)) calc(-1 * var(--relleno-modal));
  padding: var(--e3) var(--relleno-modal);
  background: var(--superficie); border-top: 1px solid var(--borde);
}
.pregunta-cierre {
  position: absolute; left: 0; right: 0; bottom: 0; z-index: 3;
  display: flex; align-items: center; justify-content: space-between; gap: var(--e3); flex-wrap: wrap;
  padding: var(--e3) var(--e5);
  background: var(--exec-atencion-bg); border-top: 1px solid #f3d9a8; color: #7a4b06;
  border-radius: 0 0 var(--radio) var(--radio); font-size: var(--txt-tabla);
}
.pregunta-cierre .acciones { display: flex; gap: var(--e2); }

/* La lista de casillas: columnas alfabeticas hacia abajo (columnas CSS, no
   rejilla: la rejilla llena por filas), buscador y las elegidas primero. */
.lista-casillas { border: 0; padding: 0; margin: var(--e3) 0 0; }
.lista-casillas legend { font-size: var(--txt-tabla); font-weight: 700; padding: 0; margin-bottom: var(--e2); }
.lista-casillas .lc-contador { font-weight: 400; color: var(--texto-suave); margin-left: var(--e1); }
.lista-casillas .lc-buscar {
  font-family: var(--fuente-texto); font-size: var(--txt-tabla);
  padding: 7px 10px; border: 1px solid var(--borde); border-radius: 9px;
  background: var(--superficie); color: var(--texto); width: 100%; max-width: 20rem; margin-bottom: var(--e3);
}
.lista-casillas .lc-bloque { margin-bottom: var(--e3); }
.lista-casillas h4 {
  margin: 0 0 var(--e1); font-family: var(--fuente-texto); font-size: var(--txt-etiqueta);
  font-weight: 700; letter-spacing: .04em; text-transform: uppercase; color: var(--texto-suave);
}
.lista-casillas .lc-columnas { column-width: 220px; column-gap: var(--e4); }
.casilla {
  display: flex; align-items: center; gap: var(--e2); break-inside: avoid;
  padding: 4px 2px; font-size: var(--txt-tabla); cursor: pointer;
}
.casilla input { margin: 0; flex-shrink: 0; }
.casilla:has(input:checked) > span:first-of-type { font-weight: 700; }

/* Cada renglon de un ajuste lleva su numero y su ✕ arriba a la derecha. */
.renglon { position: relative; }
.renglon .quitar-renglon {
  position: absolute; top: 6px; right: 8px;
  border: 0; background: transparent; font-size: 22px; line-height: 1;
  color: var(--texto-suave); cursor: pointer; padding: 2px 6px;
}
.renglon .quitar-renglon:hover { color: var(--exec-sobregiro); }
.renglon .numero-cambio { font-size: var(--txt-etiqueta); color: var(--texto-suave); text-transform: uppercase; letter-spacing: .04em; font-weight: 700; }

/* --- La nota de una linea (D113) --- */

/* El expansor abre la fila de debajo con la nota; el PDF no la lleva (D99). */
.expansor {
  border: 0; background: none; cursor: pointer; padding: 0 4px;
  color: var(--nf-azul-profundo); font-size: 12px; line-height: 1; vertical-align: middle;
}
table.compacta tbody tr.nota-linea > td,
table.compacta tbody tr.nota-linea > td:first-child {
  position: static; height: auto; min-width: 0; max-width: none; overflow: visible;
  white-space: normal; text-align: left; box-shadow: none;
  padding: 4px 10px 8px 34px; font-size: 12.5px; color: var(--texto-suave);
  background: var(--superficie-alt); font-weight: 400;
}
.nota-corta { display: inline-block; max-width: 26rem; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; vertical-align: bottom; }

/* --- Auditoria: que cambió, campo por campo --- */

/* La bitacora existe para responderle a alguien, y responder es nombrar el
   campo, lo que decia y lo que dice. El antes va tachado y apagado, el despues
   firme: la diferencia se lee sin depender del color (D29). */
/* La celda de la tabla viene con `nowrap` -es lo que hace legible una columna de
   dinero- y acá adentro no va dinero sino texto: sin esto una fecha larga
   empujaba la tabla a lo ancho y dejaba el botón de detalle fuera de la vista. */
.cambios { display: flex; flex-direction: column; gap: 3px; white-space: normal; }
.cambio { line-height: 1.45; overflow-wrap: anywhere; }
.cambio-campo {
  font-family: var(--fuente-titulo); font-weight: 600; font-size: var(--txt-etiqueta);
  color: var(--texto-suave); margin-right: 6px;
}
.cambio-antes { color: var(--texto-suave); text-decoration: line-through; text-decoration-thickness: 1px; }
.cambio-flecha { color: var(--texto-suave); margin: 0 4px; }
.cambio-despues { color: var(--texto); font-weight: 600; }
.cambio.igual .cambio-campo { font-weight: 400; }

/* --- Configuracion: las pestañas de seccion (37.4) --- */

/* Cuatro secciones largas en una pantalla, y se ve UNA. El control es el mismo
   segmentado que el tablero usa para Vista y Montos: en la aplicacion hay una
   sola forma de elegir entre pocas opciones. Queda pegado arriba al desplazarse.
   El fondo de la pagina detras, para que al pegarse no se le vea el contenido
   pasar por abajo. */
.mini-nav {
  position: sticky; top: 0; z-index: 4;
  background: var(--superficie-pag); padding: var(--e2) 0 var(--e3); margin-bottom: var(--e2);
  border: 0; border-radius: 0;
}
/* `width: auto` porque `nav button` -las reglas de la barra lateral, escritas
   sin clase- alcanzaba a este bloque tambien y le ponia `width: 100%`: las
   cuatro pestañas salian como cuatro barras apiladas de lado a lado. Se deja
   aunque ya no sea un `nav`: la regla vieja sigue ahi para el que la mueva. */
.mini-nav.alternador {
  display: inline-flex; flex-wrap: wrap; gap: var(--e1);
}
.mini-nav.alternador button {
  width: auto;
  border: 1px solid var(--borde); background: var(--superficie); border-radius: 99px;
  padding: 6px 14px; font-family: inherit; font-size: var(--txt-etiqueta); font-weight: 700;
  color: var(--nf-azul-oscuro); cursor: pointer;
}
.mini-nav.alternador button:hover { border-color: var(--nf-azul-profundo); }
.mini-nav.alternador button[aria-selected="true"] {
  background: var(--nf-azul-oscuro); border-color: var(--nf-azul-oscuro); color: var(--nf-blanco);
}

/* Los que ya no entran, plegados: se guardan, no se muestran. */
.plegado-usuarios { margin-top: var(--e4); border-top: 1px solid var(--borde); padding-top: var(--e3); }
.plegado-usuarios > summary {
  cursor: pointer; font-family: var(--fuente-titulo); font-weight: 600;
  font-size: var(--txt-tabla); color: var(--texto-suave); list-style-position: outside;
}
.plegado-usuarios > summary:hover { color: var(--nf-azul-profundo); }
.plegado-usuarios[open] > summary { margin-bottom: var(--e2); }
.plegado-usuarios > summary:focus-visible { outline: 2px solid var(--nf-aqua); outline-offset: 2px; }

/* =========================================================================
   CONTROLES (Fase 38). Un solo control, en dos tamaños.

   Habia cuatro estilos de `select` -`.filtros .control`, `.herramientas-tabla
   .control`, `.campo select` y `.herramientas select`- con tres alturas y dos
   radios. Quedan dos tamaños: `control` (34 px, en las barras de filtros y de
   herramientas) y el grande (40 px, en los formularios: dentro de un `.campo`
   que no esta en una barra). El bloque va al final de la hoja para ganar por
   orden, y esta escrito para mudarse a `packages/ui` cuando activos lo
   necesite: no depende de ningun id de esta aplicacion.

   Lo que no se puede diseñar se dice: el MENU del `<select>` nativo lo pinta el
   sistema. Por eso las listas largas se fueron al selector con busqueda (D109)
   y las cortas se quedan nativas.
   ========================================================================= */

/* --- La forma comun --- */
.control,
.campo input:not([type="checkbox"]):not([type="radio"]):not([type="file"]),
.campo select,
.campo textarea,
.herramientas select,
.herramientas input[type="search"] {
  font-family: var(--fuente-texto);
  color: var(--texto);
  border: 1px solid var(--borde);
  background-color: var(--superficie);
  border-radius: 8px;
  box-sizing: border-box;
}

/* --- Tamaño de barra: 34 px --- */
select.control, input.control, .herramientas select, .herramientas input[type="search"] {
  height: var(--alto-control, 34px);
  padding: 0 10px;
  font-size: 13px;
  font-weight: 600;
  background-color: var(--superficie-alt);
}
.herramientas { --alto-control: 34px; }

/* --- Tamaño de formulario: 40 px. Todo `.campo` que no vive en una barra. --- */
.campo:not(.filtros *, .herramientas-tabla *, .herramientas *) select.control,
.campo:not(.filtros *, .herramientas-tabla *, .herramientas *) input:not([type="checkbox"]):not([type="radio"]):not([type="file"]),
.campo:not(.filtros *, .herramientas-tabla *, .herramientas *) .sb-entrada {
  height: 40px;
  padding: 0 12px;
  font-size: var(--txt-cuerpo);
  font-weight: 400;
  background-color: var(--superficie);
  border-radius: 9px;
  width: 100%;
}
.campo textarea { padding: 8px 12px; border-radius: 9px; min-height: 40px; }
/* El `grande` fuera de un .campo (un select suelto en un formulario) mide lo mismo. */
select.control.grande:not(.filtros *):not(.herramientas-tabla *):not(.herramientas *) {
  height: 40px; padding: 0 12px; font-size: var(--txt-cuerpo); font-weight: 400; background-color: var(--superficie); border-radius: 9px;
}
/* Y dentro de una barra, `grande` no manda: la barra mide 34 px y el control se ajusta a su texto. */
.filtros select.control, .herramientas-tabla select.control, .herramientas select.control { height: var(--alto-control, 34px); width: auto; }

/* --- El chevron propio del select. Tambien en el combobox de la barra de la
   tabla, que se despliega igual aunque se escriba en el (D148). --- */
select.control, .campo select, .herramientas-tabla .sb-entrada {
  appearance: none;
  -webkit-appearance: none;
  background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='12' height='8' viewBox='0 0 12 8'><path d='M1 1.5l5 5 5-5' fill='none' stroke='%230671c6' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/></svg>");
  background-repeat: no-repeat;
  background-position: right 10px center;
  padding-right: 30px !important;
}
select.control.diminuto { height: 28px; padding: 0 26px 0 8px !important; font-size: var(--txt-etiqueta); }
:root[data-tema="oscuro"] select.control, :root[data-tema="oscuro"] .campo select,
:root[data-tema="oscuro"] .herramientas-tabla .sb-entrada {
  background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='12' height='8' viewBox='0 0 12 8'><path d='M1 1.5l5 5 5-5' fill='none' stroke='%23e8eef4' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/></svg>");
}

/* --- Estados: hover, foco, deshabilitado --- */
.control:hover, .campo select:hover, .campo input:hover, .campo textarea:hover { border-color: var(--nf-azul-profundo); }
/* UN SOLO ANILLO DE FOCO, en aqua, y solo cuando el foco viene del teclado.
   El aqua es foco y dato vivo, nunca alerta (D29). */
.control:focus-visible, .campo select:focus-visible, .campo input:focus-visible, .campo textarea:focus-visible,
.lc-buscar:focus-visible, .alternador button:focus-visible, .btn:focus-visible, .mini-nav button:focus-visible {
  outline: 2px solid var(--nf-aqua);
  outline-offset: 1px;
}
.campo input:focus, .campo select:focus, .campo textarea:focus { outline: none; }
.campo input:focus-visible, .campo select:focus-visible, .campo textarea:focus-visible {
  outline: 2px solid var(--nf-aqua); outline-offset: 1px;
}
.control:disabled, .campo select:disabled, .campo input:disabled, .campo textarea:disabled {
  background-color: var(--superficie-alt);
  color: var(--texto-suave);
  border-color: var(--borde);
  cursor: not-allowed;
}

/* --- Casillas y radios, con el color de la marca --- */
input[type="checkbox"], input[type="radio"] { accent-color: var(--nf-azul-profundo); width: 16px; height: 16px; margin: 0; }
.pastilla input[type="checkbox"] { width: 14px; height: 14px; }
/* Las pastillas que quedan ganan la marca de elegida, ademas del color. */
.pastilla:has(input:checked) > span::before { content: "✓ "; color: var(--nf-azul-profundo); font-weight: 800; }

/* --- Busqueda: lupa a la izquierda y ✕ de limpiar propia --- */
input[type="search"] {
  padding-left: 32px !important;
  background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='14' height='14' viewBox='0 0 14 14'><circle cx='6' cy='6' r='4.2' fill='none' stroke='%235a6b7b' stroke-width='1.6'/><path d='M9.2 9.2L13 13' stroke='%235a6b7b' stroke-width='1.6' stroke-linecap='round'/></svg>");
  background-repeat: no-repeat;
  background-position: 10px center;
}
input[type="search"]::-webkit-search-cancel-button {
  -webkit-appearance: none;
  appearance: none;
  width: 14px; height: 14px;
  background: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='14' height='14' viewBox='0 0 14 14'><path d='M3 3l8 8M11 3l-8 8' stroke='%235a6b7b' stroke-width='1.8' stroke-linecap='round'/></svg>") no-repeat center;
  cursor: pointer;
}

/* --- Un solo menu flotante: el submenu de exportar y la lista del selector --- */
.submenu .opciones, .selector-busqueda .sb-lista {
  background: var(--superficie);
  border: 1px solid var(--borde);
  border-radius: 8px;
  box-shadow: 0 8px 28px rgba(3, 56, 99, .16);
  padding: 4px;
}

/* La lista de arranque del tablero (PLAN-7 Fase 50). Una empresa que nunca
   aprobo un año ve esto en lugar del estado vacio de una linea.
   El estado va en el simbolo, en la clase Y en el texto del detalle: color y
   simbolo solos no sirven en blanco y negro ni con daltonismo (D29). */
.lista-arranque h3 { margin: 0 0 var(--e1); }
.pasos-arranque { list-style: none; margin: var(--e4) 0 0; padding: 0; counter-reset: paso; }
.pasos-arranque li {
  display: grid;
  grid-template-columns: 1.25rem minmax(11rem, auto) 1fr auto;
  align-items: center;
  gap: var(--e3);
  padding: var(--e3) var(--e2);
  border-top: 1px solid var(--borde);
}
.pasos-arranque li:first-child { border-top: 0; }
.paso-marca { font-weight: 700; text-align: center; }
.paso-hecho .paso-marca { color: var(--exec-normal); }
.paso-falta .paso-marca { color: var(--texto-suave); }
.paso-rotulo { font-family: var(--fuente-titulo); }
.paso-hecho .paso-rotulo { color: var(--texto-suave); }
.paso-detalle { color: var(--texto-suave); font-size: var(--txt-tabla); }

/* En el telefono la fila se apila: cuatro columnas en 360 px dejan el detalle
   en una palabra por renglon. */
@media (max-width: 720px) {
  .pasos-arranque li { grid-template-columns: 1.25rem 1fr; grid-template-areas: "marca rotulo" ". detalle" ". accion"; }
  .paso-marca { grid-area: marca; }
  .paso-rotulo { grid-area: rotulo; }
  .paso-detalle { grid-area: detalle; }
  .pasos-arranque .btn { grid-area: accion; justify-self: start; margin-top: var(--e1); }
}

/* *No sigue* (PLAN-6 Fase 41, D132). La línea del año anterior que ninguna del
   nuevo hereda, y el grupo entero que se fue: en gris, tachados, en su lugar.
   El gris NO es el único portador: la fila lleva la insignia "no sigue" en
   texto y el nombre va tachado (D29). */
#tabla-siguiente tr.no-sigue > td { color: var(--texto-suave); background: var(--superficie-alt); }
#tabla-siguiente tr.no-sigue s { text-decoration-color: var(--texto-suave); }

/* La lista de "en cero sin decidir" del modal de aprobación, con su Conservar
   por línea. Se desborda con scroll propio: pueden ser docenas. */
.lista-en-cero { list-style: none; margin: var(--e3) 0 0; padding: 0; max-height: 15rem; overflow-y: auto; }
.lista-en-cero li {
  display: flex; align-items: center; justify-content: space-between; gap: var(--e3);
  padding: var(--e2) 0; border-top: 1px solid var(--borde);
}
.lista-en-cero .casilla { flex: none; margin: 0; }
