/* Piel gruspa del Sistema: lo que comparten TODAS las pantallas.
 *
 * Se carga última en base.html (después de anthropic-theme y ui-mobile) y
 * sólo toca la cáscara: tipografía, el topbar, el tinte del módulo activo y
 * las animaciones de entrada. No pisa componentes; eso sigue en el tema.
 *
 * El color de cada módulo llega como --c ("r,g,b", nav.MODULE_COLOR) en el
 * <nav class="topbar"> y en .page-tint, la misma fuente que usan los tiles
 * del inicio y las solapas.
 */

/* ── Tipografía: IBM Plex Sans en todo el sistema (era Inter) ────────────
   anthropic-theme.css define --font-sans y body usa la variable: alcanza
   con redefinirla acá. Los alt-glyphs eran de Inter. */
:root { --font-sans: "IBM Plex Sans", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif; }
body { font-feature-settings: normal; }

/* ── Topbar: ícono del módulo activo ─────────────────────────────────────
   El mismo cuadradito teñido del tile del inicio, en 30px: al entrar a un
   módulo el ícono del tile "vuela" hasta acá (view-transition-name vt-<key>)
   y al volver, hace el camino inverso. */
.tb-mod-ico {
    flex: none;
    width: 30px; height: 30px; border-radius: 9px;
    display: grid; place-items: center;
    font-size: .95rem; line-height: 1;
    background: color-mix(in srgb, rgb(var(--c, 200,205,215)) 22%, #212630);
    color: rgb(var(--c, 200,205,215));
    box-shadow: inset 0 0 0 1px color-mix(in srgb, rgb(var(--c, 200,205,215)) 35%, transparent);
}
.topbar-module .module-name { min-width: 0; }
.topbar-module .module-name .mn-txt { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.topbar-brand img { height: 26px; width: auto; display: block; }
@media (max-width: 575.98px) {
    .topbar-brand img { height: 22px; }
    .topbar-module .module-name { font-size: .9rem; }
}

/* ── Sub-solapas (segundo nivel, adentro de una solapa del topbar) ───────
   Una sola barra para todos los módulos: Comercial › Propuestas, RRHH ›
   Liquidación, Producción › Compras… La activa lleva la raya del color del
   módulo (--c llega desde <main>). En el celular scrollea de costado. */
.beo-subtabs {
    display: flex; gap: .15rem; overflow-x: auto; scrollbar-width: none;
    border-bottom: 1px solid var(--card-border, #e5e7eb);
}
.beo-subtabs::-webkit-scrollbar { display: none; }
.beo-subtab {
    flex: none; display: inline-flex; align-items: center; gap: .4rem;
    min-height: 38px; padding: .5rem .85rem;
    font-size: .85rem; font-weight: 500; color: var(--text-secondary);
    text-decoration: none; white-space: nowrap;
    border-bottom: 2px solid transparent; margin-bottom: -1px;
    transition: color .14s, background .14s;
}
.beo-subtab .bi { font-size: .95em; opacity: .85; }
.beo-subtab:hover { color: var(--text-primary); background: var(--surface-2); text-decoration: none; }
.beo-subtab.active {
    color: var(--text-primary); font-weight: 600;
    border-bottom-color: rgb(var(--c, 200,205,215));
}

/* ── Buscador del módulo (la lupa del topbar, atajo "/") ─────────────────
   Un panel oscuro colgado del topbar, como el de la campana. En el celular
   ocupa el ancho. Los resultados van agrupados por tipo (Contactos, BEO…). */
.beo-search {
    position: absolute; top: calc(var(--topbar-h) - 2px); right: .5rem;
    width: min(560px, calc(100vw - 1rem));
    background: #1a1d27; border: 1px solid rgba(255,255,255,.1); border-radius: 12px;
    box-shadow: 0 16px 40px rgba(0,0,0,.5); z-index: 30; overflow: hidden;
    animation: beo-search-in .14s ease-out;
}
@keyframes beo-search-in { from { opacity: 0; transform: translateY(-4px); } }
.beo-search-box { display: flex; align-items: center; gap: .6rem; padding: .55rem .85rem; border-bottom: 1px solid rgba(255,255,255,.08); }
.beo-search-box .bi { color: var(--topbar-text-muted); }
.beo-search-box input {
    flex: 1; min-width: 0; background: none; border: 0; outline: 0;
    color: #fff; font-size: 16px; /* 16px: el celular no hace zoom */
    font-family: inherit;
}
.beo-search-box input::placeholder { color: var(--topbar-text-muted); }
.beo-search-box input::-webkit-search-cancel-button { filter: invert(1); }
.beo-search-box kbd { font-size: .66rem; color: var(--topbar-text-muted); border: 1px solid rgba(255,255,255,.14); border-radius: 5px; padding: .05rem .35rem; background: none; }
.beo-search-res { max-height: min(60vh, 420px); overflow-y: auto; padding: .3rem 0; }
.beo-search-res:empty { display: none; }
.bs-tipo { font-family: "IBM Plex Mono", ui-monospace, monospace; font-size: .64rem; letter-spacing: .14em; text-transform: uppercase; color: var(--topbar-text-muted); padding: .5rem .85rem .2rem; }
.bs-item { display: flex; flex-direction: column; gap: .05rem; padding: .45rem .85rem; color: #e5e7eb; text-decoration: none; min-height: 40px; justify-content: center; }
.bs-item:hover, .bs-item.is-sel { background: rgba(255,255,255,.07); color: #fff; text-decoration: none; }
.bs-item .bs-titulo { font-size: .88rem; font-weight: 500; }
.bs-item .bs-sub { font-size: .74rem; color: var(--topbar-text-muted); }
.bs-empty { padding: 1rem .85rem; font-size: .84rem; color: var(--topbar-text-muted); }
@media (prefers-reduced-motion: reduce) { .beo-search { animation: none; } }

/* ── Tinte del módulo activo ─────────────────────────────────────────────
   Un lavado del pastel del módulo arriba a la izquierda, como el fondo de
   cada área en gruspa. Va con z-index negativo: queda entre el fondo del
   body y el contenido sin crear un stacking context en .page-content (los
   modales de Bootstrap tienen que seguir por encima del topbar). */
.page-tint {
    position: fixed; inset: 0; z-index: -1; pointer-events: none;
    background: radial-gradient(880px 620px at 14% 0%, rgba(var(--c, 200,205,215), .22), transparent 55%);
}
:root[data-bs-theme="dark"] .page-tint {
    background: radial-gradient(880px 620px at 14% 0%, rgba(var(--c, 200,205,215), .16), transparent 55%);
}
@media print { .page-tint { display: none !important; } }

/* ── Abrir un módulo desde su ícono ──────────────────────────────────────
   Zoom tile → pantalla (patrón gruspa): al tocar un tile del inicio, el
   ícono se abre hasta ocupar toda la pantalla del módulo; al volver, la
   pantalla se contrae hasta el ícono. Es la View Transitions API entre
   documentos (Chrome/Edge/Safari 18+); sin soporte, un fundido de CSS.

   Liviano a propósito:
   - la página entera NO se captura (:root sin nombre): el navegador sólo
     guarda dos imágenes, el ícono y la pantalla del módulo;
   - los nombres se ponen desde el <head> de base.html sólo mientras dura la
     transición (data-vt / data-vt-tile), así ningún elemento queda con
     stacking context propio después;
   - entre solapas del mismo módulo no se anima nada;
   - sin el mix-blend-mode plus-lighter que el navegador usa por defecto. */
@view-transition { navigation: auto; }
:root { view-transition-name: none; }
::view-transition-group(*) {
    animation-duration: .3s;
    animation-timing-function: cubic-bezier(.22, 1, .36, 1);
}
::view-transition-image-pair(*) { isolation: auto; }
::view-transition-old(*), ::view-transition-new(*) { mix-blend-mode: normal; object-fit: cover; }
::view-transition-old(*) { animation: beo-vt-out .22s ease both; }
::view-transition-new(*) { animation: beo-vt-in .3s ease both; }
@keyframes beo-vt-out { to { opacity: 0; } }
@keyframes beo-vt-in { from { opacity: 0; } }

/* Sin View Transitions (Firefox, primera carga, recarga, cambio de solapa):
   la pantalla entra con un fundido corto. La clase vt-on la pone el <head>
   cuando el navegador ya animó la entrada, así no se duplica. Sólo opacity:
   un transform en .page-content dejaría a los fixed/sticky de adentro sin
   viewport durante la animación. */
html:not(.vt-on) .page-content { animation: beo-page-in .22s ease both; }
@keyframes beo-page-in { from { opacity: 0; } }

@media (prefers-reduced-motion: reduce) {
    ::view-transition-group(*),
    ::view-transition-old(*),
    ::view-transition-new(*) { animation: none !important; }
    .page-content { animation: none !important; }
}

/* ── Índice lateral de una ficha (BEO, empleado…) ─────────────────────────
   Las solapas de una ficha larga (el BEO tenía 15 en una fila que se
   cortaba en dos) son un índice a la izquierda, agrupado por lo que son y
   fijo mientras se scrollea. En el celular vuelve a ser una fila que
   scrollea de costado, con los grupos como separadores. El punto ámbar
   marca una sección sin cargar. Los links llevan .active (Alpine o
   Bootstrap Tab, da igual). */
.beo-layout { display: grid; grid-template-columns: 196px minmax(0, 1fr); gap: 16px; align-items: start; }
.beo-index { position: sticky; top: calc(var(--topbar-h, 64px) + 12px); display: flex; flex-direction: column; gap: 10px; }
.beo-index-g { display: flex; flex-direction: column; gap: 1px; }
.beo-index-t { display: block; font-family: "IBM Plex Mono", ui-monospace, monospace; font-size: .6rem; font-weight: 500; letter-spacing: .14em; text-transform: uppercase; color: var(--text-secondary); padding: 0 .6rem; margin-bottom: 3px; }
.beo-index a { display: flex; align-items: center; gap: .5rem; padding: .4rem .6rem; border-radius: 9px; font-size: .84rem; color: var(--text-primary); text-decoration: none; min-height: 34px; transition: background .12s; }
.beo-index a .bi { font-size: .9em; opacity: .7; width: 1.1em; text-align: center; }
.beo-index a:hover { background: var(--surface-2); color: var(--text-primary); text-decoration: none; }
.beo-index a.active { background: color-mix(in srgb, rgb(var(--c, 200,205,215)) 18%, var(--surface-2)); box-shadow: inset 0 0 0 1.5px color-mix(in srgb, rgb(var(--c, 200,205,215)) 60%, var(--text-primary)); font-weight: 600; }
.beo-index a.active .bi { opacity: 1; }
.beo-index .beo-dot { margin-left: auto; width: 7px; height: 7px; border-radius: 50%; background: var(--warning); flex: none; }
.beo-content { min-width: 0; }
@media (max-width: 991.98px) {
    .beo-layout { display: block; }
    .beo-index { position: static; flex-direction: row; gap: 2px; overflow-x: auto; scrollbar-width: none; padding-bottom: 6px; margin-bottom: 12px; border-bottom: 1px solid var(--card-border); }
    .beo-index::-webkit-scrollbar { display: none; }
    .beo-index-g { flex-direction: row; gap: 2px; }
    .beo-index-g + .beo-index-g { border-left: 1px solid var(--card-border); padding-left: 6px; margin-left: 4px; }
    .beo-index-t { display: none; }
    .beo-index a { flex: none; white-space: nowrap; min-height: 38px; }
    .beo-index .beo-dot { margin-left: .3rem; }
}
