/* ---- Fuentes auto-alojadas (OFL; sin terceros / sin Google Fonts) ---- */
@font-face{
  font-family:'Inter';font-style:normal;font-weight:100 900;font-display:swap;
  src:url(/fonts/inter-latin.woff2) format('woff2');
}
@font-face{
  font-family:'Source Serif 4';font-style:normal;font-weight:100 900;font-display:swap;
  src:url(/fonts/source-serif-4-latin.woff2) format('woff2');
}

/* ==========================================================================
   utprpro — sistema visual institucional (referencia Enagás, paleta utprpro)
   Sobrio, blanco, serif institucional para titulares + sans para cuerpo.
   Colores planos, líneas finas, sin degradados ni ornamento decorativo.
   ========================================================================== */
:root{
  --font-serif:"Source Serif 4",Georgia,"Times New Roman",serif;
  --font-sans:"Inter","Inter Variable",system-ui,-apple-system,sans-serif;
  --radius:8px;

  /* Neutros */
  --bg:#ffffff;
  --bg-alt:oklch(0.975 0.006 75);
  --ink:oklch(0.26 0.012 55);
  --body:oklch(0.42 0.012 55);
  --muted-fg:oklch(0.54 0.010 55);
  --line:oklch(0.905 0.006 70);

  /* Marca (naranja sobrio) */
  --brand:oklch(0.62 0.17 45);
  --brand-strong:oklch(0.54 0.16 44);
  --brand-ink:oklch(0.50 0.15 42);       /* naranja para texto sobre blanco (contraste) */
  --brand-soft:oklch(0.95 0.03 60);

  /* Semáforo (colores planos e institucionales) */
  --ok:oklch(0.50 0.11 150);
  --ok-line:oklch(0.62 0.12 150);
  --warn-ink:oklch(0.52 0.11 66);
  --warn-line:oklch(0.76 0.14 78);
  --danger:oklch(0.53 0.17 28);
  --danger-line:oklch(0.60 0.18 28);

  /* Grises del área de trabajo logueada (panel). Serios, por capas, sin blanco plano. */
  --app-canvas:oklch(0.955 0.004 70);    /* fondo del área de trabajo */
  --app-bar:oklch(0.905 0.006 70);       /* barra superior, gris más marcado */
  --app-bar-line:oklch(0.80 0.008 70);   /* línea inferior de la barra */

  /* Compatibilidad con login / panel de aplicación */
  --background:var(--bg);
  --foreground:var(--ink);
  --card:#ffffff;
  --primary:var(--brand);
  --primary-foreground:#ffffff;
  --muted:var(--bg-alt);
  --muted-foreground:var(--muted-fg);
  --border:var(--line);
  --input:var(--line);
  --destructive:var(--danger);
  --ring:var(--brand);
}

*{box-sizing:border-box}
html{scroll-behavior:smooth}
html,body{margin:0;height:100%}
body{font-family:var(--font-sans);background:var(--bg);color:var(--body);line-height:1.5;-webkit-font-smoothing:antialiased;text-rendering:optimizeLegibility}
@media(prefers-reduced-motion:reduce){html{scroll-behavior:auto}}

h1,h2{font-family:var(--font-serif);font-weight:600;letter-spacing:-0.01em;color:var(--ink);margin:0}
h3,h4{font-family:var(--font-sans);color:var(--ink);margin:0}
a{color:var(--brand-ink)}
p{margin:0}
.muted{color:var(--muted-fg)}
.center{text-align:center}

img.logo{width:auto;max-width:100%;display:block}
.logo-lg{height:52px}
.logo-sm{height:28px}
.brand{display:inline-flex;align-items:center;gap:8px;font-weight:700;font-family:var(--font-sans)}
.brand .dot{width:9px;height:9px;border-radius:50%;background:var(--brand)}

/* --------------------------------------------------------------- Botones */
.btn{display:inline-flex;align-items:center;justify-content:center;border:1px solid var(--line);border-radius:4px;padding:11px 20px;font-size:14px;font-weight:600;font-family:var(--font-sans);cursor:pointer;background:#fff;color:var(--ink);text-decoration:none;transition:background .15s,border-color .15s,color .15s;line-height:1.1}
.btn:hover{border-color:var(--muted-fg)}
.btn.primary{background:var(--brand);color:#fff;border-color:var(--brand)}
.btn.primary:hover{background:var(--brand-strong);border-color:var(--brand-strong)}
.btn.outline{background:transparent;color:var(--ink);border-color:var(--line)}
.btn.outline:hover{border-color:var(--brand);color:var(--brand-ink)}
.btn.ghost{background:transparent}
.btn.block{width:100%}
.btn.big{padding:14px 26px;font-size:15px}
.btn.tiny{padding:5px 10px;font-size:12px}
.btn:disabled{opacity:.6;cursor:default}

/* --------------------------------------------------- Formularios / inputs */
input,select{width:100%;background:#fff;border:1px solid var(--input);color:var(--ink);border-radius:6px;padding:11px 12px;font-size:14px;font-family:inherit;outline:none}
input:focus,select:focus{border-color:var(--brand);box-shadow:0 0 0 3px color-mix(in oklab,var(--brand) 16%,transparent)}
label{display:flex;flex-direction:column;gap:6px;font-size:13px;color:var(--muted-fg)}
.error{color:var(--danger);font-size:13px}

/* ========================================================================
   LANDING utprpro
   ======================================================================== */
.wrap{max-width:1160px;margin:0 auto;padding:0 24px;width:100%}
section[id]{scroll-margin-top:118px}

/* ------------------------------------------------------ Cabecera 2 niveles */
.site-header{position:sticky;top:0;z-index:50;background:#fff}
.util-bar{border-bottom:1px solid var(--line);background:#fff}
.util-inner{max-width:1160px;margin:0 auto;padding:8px 24px;display:flex;justify-content:flex-end;align-items:center;gap:22px}
.util-link{background:none;border:0;padding:0;font-family:inherit;font-size:12.5px;color:var(--muted-fg);text-decoration:none;cursor:pointer}
.util-link:hover{color:var(--brand-ink)}
.lang{display:inline-flex;align-items:center;gap:6px;font-size:12.5px;color:var(--muted-fg)}
.lang b{color:var(--ink);font-weight:600}
.lang .sep{opacity:.45}
.lang .off{color:var(--muted-fg)}
.lang .lang-opt{cursor:pointer;background:none;border:0;padding:0;font-family:inherit;font-size:inherit}
.lang .lang-opt:hover{color:var(--brand-ink)}
/* Evitar seleccion de texto al pulsar en la interfaz; se mantiene en campos de formulario */
body{-webkit-user-select:none;user-select:none}
input,textarea,[contenteditable]{-webkit-user-select:text;user-select:text}

.main-nav{border-bottom:1px solid var(--line);background:#fff}
.nav-inner{max-width:1160px;margin:0 auto;padding:15px 24px;display:flex;align-items:center;gap:24px}
.wordmark{font-family:var(--font-sans);font-weight:700;font-size:22px;letter-spacing:-0.02em;color:var(--ink);text-decoration:none;line-height:1}
.wordmark span{color:var(--brand-ink)}
.nav-links{display:flex;align-items:center;gap:26px;margin-left:22px;flex:1}
.nav-links a{font-size:15px;font-weight:500;color:var(--ink);text-decoration:none}
.nav-links a:hover{color:var(--brand-ink)}
.nav-cta{margin-left:auto;padding:9px 18px}
/* El comportamiento en móvil (botón + desplegable) vive en la sección RESPONSIVE (2), al final:
   una sola regla manda sobre .nav-links en pantalla estrecha. */

/* ---------------------------------------------------------------- Secciones */
.section{padding:74px 0}
.section.alt{background:var(--bg-alt)}
.eyebrow{display:inline-block;font-family:var(--font-sans);font-size:12px;font-weight:700;letter-spacing:0.14em;text-transform:uppercase;color:var(--brand-ink);margin:0 0 16px}
.section-head{max-width:820px;margin-bottom:38px}
.section h2{font-size:clamp(25px,3.2vw,36px);line-height:1.2}
.section-lead{margin-top:16px;font-size:18px;line-height:1.6;color:var(--body);max-width:70ch}
.note{margin-top:20px;font-size:13px;color:var(--muted-fg)}

/* Hero */
.hero{padding:90px 0 74px;background:#fff}
.hero h1{font-size:clamp(38px,5.4vw,58px);line-height:1.06;letter-spacing:-0.015em;margin:18px 0 0;max-width:15ch}
.hero .lead{margin:24px 0 0;font-size:19px;line-height:1.6;color:var(--body);max-width:62ch}
.cta-row{display:flex;flex-wrap:wrap;gap:14px;margin-top:32px}
.cta-row .btn{padding:13px 26px;font-size:15px}

/* Bloques a dos columnas (Problema / Marco normativo) */
.two-col{display:grid;gap:28px;align-items:start}
@media(min-width:860px){.two-col{grid-template-columns:0.92fr 1.08fr;gap:64px}}
.col-head h2{font-size:clamp(24px,3vw,34px);line-height:1.2}
.col-body p{color:var(--body);font-size:17px;line-height:1.65}
.pull{margin-top:26px;font-family:var(--font-serif);font-size:clamp(21px,2.4vw,27px);line-height:1.35;color:var(--ink)}

/* Bloques funcionales (copy + visual) */
.feature{display:grid;gap:34px;align-items:center}
@media(min-width:860px){.feature{grid-template-columns:1fr 1fr;gap:58px}}
.feature-copy h2{font-size:clamp(24px,3vw,34px);line-height:1.2}
.feature-copy p{margin-top:18px;color:var(--body);font-size:17px;line-height:1.65;max-width:52ch}
.value-list{list-style:none;padding:0;margin:24px 0 0;display:grid;gap:9px}
.value-list li{position:relative;padding-left:20px;color:var(--body);font-size:15px;line-height:1.5}
.value-list li:before{content:"";position:absolute;left:0;top:9px;width:7px;height:7px;background:var(--brand);border-radius:0}

/* ------------------------------------------------- Recuadros de vista previa */
.panel{border:1px solid var(--line);border-radius:6px;background:#fff;overflow:hidden}
.panel-head{display:flex;justify-content:space-between;align-items:center;gap:12px;padding:12px 16px;background:var(--bg-alt);border-bottom:1px solid var(--line);font-size:13px;font-weight:500;color:var(--muted-fg)}
.panel-head .delta{color:var(--ok);font-weight:700}
.panel-body{padding:18px 16px}
.panel-title{margin:0 0 12px;font-size:12px;font-weight:600;letter-spacing:0.08em;text-transform:uppercase;color:var(--muted-fg)}
.panel-foot{margin:14px 0 0;font-size:14px;color:var(--muted-fg)}
.panel-foot strong{color:var(--ink);font-weight:600}
.report-desc{margin:0 0 18px;color:var(--body);font-size:15px;line-height:1.6}
.report-desc strong{color:var(--ink);font-weight:600}

/* Gráfico de facturación (un solo color plano) */
.chart{display:flex;align-items:flex-end;gap:5px;height:132px;padding-top:6px}
.chart .bar{flex:1;background:var(--brand);border-radius:2px 2px 0 0;min-height:4px}
.chart-foot{margin:12px 0 0;font-size:12.5px;color:var(--muted-fg)}

/* ------------------------------------------------- Semáforo de vencimientos */
.signal-grid{display:grid;gap:20px;margin-top:6px}
@media(min-width:760px){.signal-grid{grid-template-columns:repeat(3,1fr)}}
.signal{background:#fff;border:1px solid var(--line);border-top-width:3px;padding:22px 20px}
.signal.ok{border-top-color:var(--ok-line)}
.signal.warn{border-top-color:var(--warn-line)}
.signal.danger{border-top-color:var(--danger-line)}
.signal-tag{display:block;font-weight:700;font-size:15px;margin-bottom:10px}
.signal.ok .signal-tag{color:var(--ok)}
.signal.warn .signal-tag{color:var(--warn-ink)}
.signal.danger .signal-tag{color:var(--danger)}
.signal-desc{margin:0 0 10px;color:var(--body);font-size:14.5px;line-height:1.5}
.signal-ex{margin:0;color:var(--muted-fg);font-size:13.5px;line-height:1.5}

/* --------------------------------------------------------- Beneficios (3col) */
.benefits{display:grid;gap:30px}
@media(min-width:760px){.benefits{grid-template-columns:repeat(3,1fr);gap:40px}}
.benefit{border-top:2px solid var(--line);padding-top:20px}
.benefit h3{font-size:18px;font-weight:600;margin:0 0 10px;line-height:1.3}
.benefit p{color:var(--body);font-size:15px;line-height:1.6}

/* ---------------------------------------------------------- Marco normativo */
.norm-list{list-style:none;padding:0;margin:22px 0 0;display:grid;gap:11px}
.norm-list li{position:relative;padding-left:22px;color:var(--body);font-size:15px;line-height:1.5}
.norm-list li:before{content:"";position:absolute;left:0;top:8px;width:8px;height:8px;background:var(--brand)}

/* -------------------------------------------------------------- CTA final */
.cta-final{background:var(--bg-alt);border-top:1px solid var(--line);text-align:center}
.cta-final h2{font-size:clamp(26px,3.4vw,38px);line-height:1.18;max-width:20ch;margin:0 auto}
.cta-final p{margin:18px auto 0;max-width:56ch;font-size:18px;line-height:1.6;color:var(--body)}
.cta-final .btn{margin-top:28px;padding:14px 30px;font-size:15px}
.cta-final .note{margin-top:18px}

/* ------------------------------------------------------------------ Footer */
.site-footer{background:#fff;border-top:1px solid var(--line);padding:56px 0 0}
/* Pie minimo: una linea con el copyright a un lado y el correo + las tres legales al otro.
   En movil se apilan. Sustituye a .foot-grid, que eran cuatro columnas repitiendo el menu. */
.foot-min{display:flex;flex-wrap:wrap;gap:10px 22px;align-items:baseline;
  justify-content:space-between;font-size:13px}
.foot-min-links{display:flex;flex-wrap:wrap;gap:6px 16px}
.foot-min-links a{color:var(--body);text-decoration:none}
.foot-min-links a:hover{color:var(--brand-ink)}
@media(max-width:560px){ .foot-min{flex-direction:column;gap:8px} }

.foot-contact{color:var(--body);font-size:14px;line-height:1.7}
.foot-contact a{color:var(--brand-ink)}
.foot-bottom{border-top:1px solid var(--line);margin-top:44px}
.foot-bottom .wrap{padding-top:20px;padding-bottom:20px;text-align:center;color:var(--muted-fg);font-size:13px}

/* ========================================================================
   LOGIN (sobrio, sin degradados)
   ======================================================================== */
/* PORTADA DE UN PORTAL DE TENANT (renderLandingTenant).
   Sus tamanos iban escritos a mano en atributos style dentro del JS, asi que ni cuadraban con la
   web madre ni habia forma de ajustarlos sin tocar el marcado. Aqui estan todos juntos.
   Es DELIBERADAMENTE mas pequena que la portada comercial: alli el titular vende (hasta 58px),
   aqui el usuario viene a entrar y lo que tiene que destacar es el formulario, no el texto. */
/* El acceso ocupa la ventana: las secciones de texto que vienen debajo quedan bajo la linea
   de scroll a proposito. Quien llega a un portal viene a entrar, no a leer. */
/* LAS SECCIONES DE DEBAJO DEL ACCESO, EN UN PORTAL.
   Son las mismas que en la web comercial, pero aqui NO estan vendiendo: acompanan a quien ya ha
   entrado o esta a punto. Se bajan en bloque para que la pantalla entera respire igual que el
   formulario, que tambien se aprieta. Todo va acotado a .portal-secciones: la landing comercial
   no se toca. */
.portal-secciones .section{padding:44px 0}
.portal-secciones .section h2{font-size:clamp(19px,2.4vw,24px);line-height:1.25}
.portal-secciones .section-head{margin-bottom:24px}
.portal-secciones .section-lead{margin-top:11px;font-size:14px;line-height:1.55}
.portal-secciones .eyebrow{font-size:11px;letter-spacing:.12em;margin-bottom:11px}
.portal-secciones p{font-size:14px;line-height:1.6}
.portal-secciones .feature{gap:26px}
.portal-secciones .value-list{margin-top:16px;gap:7px}
.portal-secciones .value-list li{font-size:13.5px;padding-left:17px}
.portal-secciones .value-list li:before{top:8px;width:6px;height:6px}
.portal-secciones .signal-grid{gap:14px}
.portal-secciones .signal{padding:16px 15px}
.portal-secciones .signal-tag{font-size:13px;margin-bottom:7px}
.portal-secciones .signal-desc{font-size:13px}
.portal-secciones .benefit h3{font-size:14px}
.portal-secciones .benefit p{font-size:13.5px}
.portal-secciones .panel-head{font-size:12px}
.portal-secciones .panel-title{font-size:12.5px}
.portal-secciones .panel-foot{font-size:12px}
.portal-secciones .carpeta{font-size:11.5px;padding:8px 9px}

.hero-portal{min-height:calc(100dvh - 64px);display:flex;align-items:flex-start;justify-content:center;
  padding:clamp(24px,9vh,90px) 0 40px}
.hero-portal>.wrap{width:100%}
.hero-portal .wrap{max-width:400px;text-align:center}
.hero-portal .eyebrow{font-size:11px;letter-spacing:.12em;margin-bottom:8px}
.hero-portal h1{font-size:clamp(19px,2.4vw,23px);line-height:1.2;letter-spacing:-.01em;
  margin:0 auto;max-width:18ch}
.hero-portal .lead{font-size:13.5px;line-height:1.5;margin:8px auto 18px;max-width:42ch}
.hero-portal .auth-card{max-width:370px;margin:0 auto;text-align:left;padding:22px 20px;
  box-shadow:0 14px 44px -16px rgba(0,0,0,.22)}
.hero-portal .auth-card form{gap:11px;margin-top:0}
/* Todo lo de dentro del formulario, un punto por debajo de lo general: en esta pantalla no hay
   nada mas que leer, asi que no necesita el tamano de lectura del resto de la web. */
.hero-portal .auth-card label{font-size:12px;gap:5px}
.hero-portal .auth-card input{font-size:13.5px;padding:9px 11px}
.hero-portal .auth-card .btn{font-size:13.5px;padding:10px 18px}
.hero-portal .auth-card .soporte{font-size:11.5px;margin-top:16px}

.auth-wrap{min-height:100dvh;display:flex;flex-direction:column;align-items:center;justify-content:flex-start;padding:clamp(28px,8vh,88px) 24px 40px;background:var(--bg-alt)}
.auth-card{width:100%;max-width:410px;background:#fff;border:1px solid var(--line);border-radius:10px;padding:34px 32px;box-shadow:0 1px 3px rgba(0,0,0,.05)}
.logo-wrap{display:flex;justify-content:center;margin-bottom:18px}
.wordmark-lg{font-size:30px;letter-spacing:-0.02em}
.auth-card h1{margin:0;font-size:24px;text-align:center}
.auth-card .muted{margin:8px 0 0}
.auth-card form{display:flex;flex-direction:column;gap:14px;margin-top:22px}
.soporte{margin-top:20px;text-align:center;font-size:12px;color:var(--muted-fg)}
.linkback{background:none;border:0;color:var(--muted-fg);cursor:pointer;font-size:13px;padding:0;margin-bottom:8px;font-family:inherit}
.linkback:hover{color:var(--ink)}
.backrow{display:flex;justify-content:center;margin-top:18px}
.backlink{display:inline-flex;align-items:center;gap:8px;text-decoration:none}
.powered{text-align:center;font-size:12px;letter-spacing:.02em;color:var(--muted-fg);opacity:.85;margin-top:10px}
.powered a{color:var(--muted-fg);text-decoration:none;font-weight:600}
.powered a span{color:var(--brand)}
.powered a:hover{color:var(--ink)}
.backlink .arw{display:inline-block;transition:transform .15s;line-height:1}
.backlink:hover .arw{transform:translateX(-3px)}

/* ========================================================================
   PANEL DE APLICACIÓN (tras iniciar sesión)
   ======================================================================== */
.layout{min-height:100vh;display:flex;flex-direction:column}
.topbar{display:flex;align-items:center;justify-content:space-between;padding:12px 22px;border-bottom:1px solid var(--line);background:#fff}
.user{display:flex;align-items:center;gap:14px}
.uinfo{display:flex;flex-direction:column;align-items:flex-end;line-height:1.2}
.uinfo strong{font-size:13px;color:var(--ink)}
.badge{font-size:11px;color:#fff;background:var(--brand);padding:2px 9px;border-radius:999px;font-weight:700}
/* Panel = app de datos (tablas anchas): se le da sitio para que las columnas respiren y no
   queden márgenes muertos a los lados. La landing sigue con su ancho de lectura (.wrap). */
.content{padding:26px 28px;max-width:1400px;width:100%;margin:0 auto}
.page-head h1{margin:0 0 4px;font-size:24px}
.stack{display:flex;flex-direction:column;gap:20px}
.card{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:20px}
.card-head{display:flex;align-items:center;justify-content:space-between;margin-bottom:12px}
.card h2{margin:0;font-size:17px}
.row-form{display:flex;gap:10px;flex-wrap:wrap;margin-bottom:14px}
.row-form input,.row-form select{flex:1;min-width:150px}
.table-wrap{overflow-x:auto}
table{width:100%;border-collapse:collapse;font-size:14px}
th,td{text-align:left;padding:9px 10px;border-bottom:1px solid var(--line)}
/* Columnas numéricas (Instalac./Equipos): número centrado JUSTO debajo de su cabecera. */
.table-wrap th.col-num,.table-wrap td.col-num{text-align:center}
th{color:var(--muted-fg);font-weight:600;font-size:12px;text-transform:uppercase;letter-spacing:.03em}
/* `inline-block` + `line-height` + `max-width` para que un texto largo ("Pendiente de
   aceptación") ENVUELVA como una caja limpia en vez de cortarse o romper el borde a mitad de
   línea. El radio no se toca: en el panel (.layout .tag) ya es cuadrado por diseño. */
.tag{background:var(--bg-alt);border:1px solid var(--line);border-radius:999px;padding:2px 9px;
  font-size:12px;line-height:1.35;display:inline-block;max-width:100%}
/* Lista de subcarpetas en el modal de Documentos del cliente. */
.doc-carpetas{margin:14px 0 0;padding-left:20px;color:var(--body);font-size:13.5px;line-height:1.85}
/* Icono de carpeta (Documentos) al final de cada fila de la lista de clientes. */
.col-docs{width:44px}
.td-docs{text-align:center}
.doc-icon{display:inline-flex;align-items:center;justify-content:center;width:32px;height:32px;padding:0;
  border:1px solid var(--line);border-radius:8px;background:#fff;color:var(--muted-fg);cursor:pointer;
  transition:color .12s,border-color .12s,background .12s}
.doc-icon:hover{color:var(--ink);border-color:var(--muted-fg);background:var(--bg-alt)}
.doc-icon svg{display:block}

/* ========================================================================
   RESPONSIVE
   ======================================================================== */
@media(max-width:640px){
  .wrap{padding:0 16px}
  .util-inner,.nav-inner{padding-left:16px;padding-right:16px}
  .section{padding:52px 0}
  .hero{padding:56px 0 48px}
  .section-head{margin-bottom:28px}
  .cta-row .btn{flex:1 1 100%}
  .content{padding:20px 16px}
  .topbar{padding:10px 16px}
  .auth-wrap{padding:18px}
  .auth-card{padding:26px 20px}
  .card{padding:16px}
}
@media(max-width:380px){
  .wrap,.util-inner,.nav-inner{padding-left:13px;padding-right:13px}
  .auth-card{padding:22px 16px}
}

/* ---- Aviso de cookies (barra sobria, no bloqueante) ---- */
.cookie-bar{
  position:fixed;left:0;right:0;bottom:0;z-index:60;
  background:var(--card);color:var(--body);
  border-top:1px solid var(--line);
  padding:14px 20px;font-size:13.5px;line-height:1.5;
  display:flex;gap:12px 22px;align-items:center;justify-content:center;flex-wrap:wrap;
  box-shadow:0 -4px 22px rgba(20,30,40,.07);
}
.cookie-bar span{max-width:66ch}
.cookie-bar strong{color:var(--ink)}
.cookie-bar a{color:var(--brand-ink);text-decoration:underline}
.cookie-bar .cookie-actions{display:flex;gap:18px;align-items:center;white-space:nowrap}
.cookie-bar .cookie-ok{
  background:var(--brand);color:#fff;border:none;border-radius:var(--radius);
  padding:8px 18px;font:inherit;font-weight:600;cursor:pointer;
}
.cookie-bar .cookie-ok:hover{background:var(--brand-strong)}

/* ---- Páginas informativas / legales ---- */
.info-page .doc h2{margin:26px 0 8px}
.info-page .doc p{margin:0 0 12px}
.info-page .doc a{color:var(--brand-ink)}
.foot-client{font-size:13px;opacity:.8;margin-top:8px}
.foot-client a{color:inherit;text-decoration:underline}

/* ---- Panel de soporte: acciones, estado, modal, toast ---- */
.actions-cell{display:flex;gap:8px;flex-wrap:wrap}
/* Una fila de acciones colgando directamente de una tarjeta necesita aire: si no, el botón se
   pega al párrafo de arriba y parece parte de la frase. Va con `>` a propósito: .actions-cell
   se usa también DENTRO de las celdas de tabla, y ahí este margen sobraría. */
.card > .actions-cell{margin-top:20px}
.btn.danger{color:var(--danger);border-color:color-mix(in oklab,var(--danger) 40%,var(--line))}
.btn.danger:hover{border-color:var(--danger);background:color-mix(in oklab,var(--danger) 8%,#fff)}
/* «Reanudar avisos»: cuando una empresa tiene los avisos pausados, el propio botón es el aviso.
   Relleno rojizo suave (no es destructivo como .danger; es un ESTADO que pide atención). */
.btn.avisos-en-pausa{color:var(--danger);border-color:var(--danger-line);
  background:color-mix(in oklab,var(--danger) 10%,#fff)}
.btn.avisos-en-pausa:hover{border-color:var(--danger);color:var(--danger);
  background:color-mix(in oklab,var(--danger) 16%,#fff)}
.state-dot{display:inline-block;width:8px;height:8px;border-radius:999px;margin-right:6px;vertical-align:middle}
.state-dot.on{background:#16a34a}
.state-dot.off{background:var(--muted-fg)}
/* ========================================================================
   Tabla «Personal de la UTPR» — pase de pulido visual
   Clase propia (.t-personal) para no tocar el resto de tablas. En ≤900 la tabla se vuelve fichas
   (regla general de .table-wrap): estos estilos son para la vista de tabla en escritorio.
   ======================================================================== */
/* 6) Cabecera: más contraste (texto oscuro, no gris claro) y separada de la 1ª fila. */
.t-personal thead th{color:var(--ink);font-weight:700;font-size:11.5px;letter-spacing:.04em;
  text-transform:uppercase;padding:0 12px 12px;vertical-align:bottom;border-bottom:1.5px solid var(--line)}
/* 1) Filas: más aire vertical y TODO centrado (misma altura aunque el Cargo ocupe 2 líneas).
   7) Separador sutil entre filas (gris muy claro), sin zebra. */
.t-personal tbody td{padding:15px 12px;vertical-align:middle;font-size:14px;color:var(--body);
  border-bottom:1px solid color-mix(in oklab,var(--line) 55%,transparent)}
.t-personal tbody tr:last-child td{border-bottom:0}
/* 2) Nombre + badge(s): apilados, con separación uniforme y consistente; el nombre en tinta fuerte. */
.t-personal .p-nombre{display:flex;flex-direction:column;gap:5px;align-items:flex-start}
.t-personal .p-name{color:var(--ink);font-weight:600;line-height:1.25}
.t-personal .p-badges{display:flex;gap:6px;flex-wrap:wrap}
/* JPR y Gerente idénticos en tamaño y padding (solo cambia el color de cada uno). */
.t-personal .p-badges .tag{margin:0;font-size:11px;line-height:1.4;padding:2px 8px;font-weight:600}
/* 3) Estado: punto + palabra en la MISMA línea, centrados verticalmente (flex).
   Reutilizable (Personal y Equipamiento disponible): sin scope a .t-personal. */
.p-estado{display:inline-flex;align-items:center;gap:7px;white-space:nowrap}
.p-estado .state-dot{margin:0;flex-shrink:0}
/* Estado en dos renglones cuando es baja: «De baja» y debajo, discreta, la fecha. */
.est-col{display:inline-flex;flex-direction:column;line-height:1.25}
.est-fecha{font-size:11.5px;color:var(--muted-fg);font-variant-numeric:tabular-nums}
/* Equipamiento disponible: barra con selector de estado (a la derecha) + filas de baja atenuadas. */
.eq-barra{display:flex;align-items:center;gap:12px;flex-wrap:wrap}
.eq-verlbl{display:inline-flex;align-items:center;gap:7px;margin-left:auto;font-size:13px;font-weight:600;color:var(--muted-fg)}
.eq-verlbl select{width:auto;min-width:140px;margin:0}
.eq-baja td{color:var(--muted-fg)}
/* 4) Cuenta «sin cuenta»: discreto (gris claro + itálica) frente a un email real. */
.t-personal .p-sincuenta{color:var(--muted-fg);font-style:italic;font-size:13px;opacity:.9}
/* 5) Botones de acción: fila horizontal, gap uniforme, centrados en la fila, mismo alto. */
.t-personal td.acciones{vertical-align:middle}
.t-personal .p-acts{display:inline-flex;align-items:center;gap:8px}
.t-personal .p-acts .btn{margin:0}
/* En modo tarjeta (≤900) la celda de acciones es una barra a lo ancho (ver regla de td.acciones):
   el contenedor .p-acts se estira y los botones reparten el ancho por igual. */
@media(max-width:900px){
  .layout .table-wrap td.acciones .p-acts{display:flex;width:100%;gap:8px}
  .layout .table-wrap td.acciones .p-acts .btn{flex:1 1 auto}
}
/* --- Encaje de las 8 columnas (Nombre·Cargo·Fecha·Cualificación·TE·Cuenta·Estado·acciones) ---
   Los campos del informe ya no caben "a lo bruto": se reparte el ancho a mano. Los datos cortos
   (fecha, TE, estado) se ciñen a su contenido; los textos largos (cargo, cualificación, email)
   pueden envolver a 2 líneas en vez de estirar la tabla hasta el scroll horizontal. Solo escritorio
   (>900): por debajo la tabla ya se vuelve fichas. */
@media(min-width:901px){
  .t-personal{width:100%}
  .t-personal th:nth-child(3),.t-personal td[data-l="Fecha alta"]{width:1%;white-space:nowrap}
  .t-personal th:nth-child(5),.t-personal td[data-l="TE"]{width:1%;text-align:center}
  .t-personal th:nth-child(7),.t-personal td[data-l="Estado"]{width:1%;white-space:nowrap}
  .t-personal td[data-l="Cargo"],.t-personal td[data-l="Cualificación"]{white-space:normal}
  .t-personal .p-cargo{display:inline-block;max-width:22ch;line-height:1.35}
  .t-personal .p-cual{display:inline-block;max-width:30ch;line-height:1.35}
  .t-personal .p-cuenta{overflow-wrap:anywhere}
}
.t-personal .p-fecha{white-space:nowrap;font-variant-numeric:tabular-nums;color:var(--body)}
.t-personal .p-vacio{color:var(--muted-fg)}
/* TE: pastilla compacta (A/B) en vez de una letra suelta perdida en la columna. */
.t-personal .te-pill{display:inline-flex;align-items:center;justify-content:center;min-width:24px;
  height:22px;padding:0 8px;border:1px solid var(--line);background:var(--bg-alt);
  font-size:12px;font-weight:700;color:var(--ink)}

/* --- Formulario de personal: marcas del informe como tarjetas seleccionables ---
   JPR/Gerente son bits del informe, no un "check" cualquiera: se presentan como dos opciones con
   su explicación, y la elegida se resalta con el acento de marca. Cuadradas, a juego con el panel. */
.marca-block{display:flex;flex-direction:column;gap:9px;border-top:1px solid var(--line);
  padding-top:16px;margin-top:2px}
.grp-title{font-size:13px;color:var(--ink);font-weight:600}
.grp-title small{font-weight:400;color:var(--muted-fg)}
.marca-grid{display:grid;grid-template-columns:1fr 1fr;gap:10px}
.marca{flex-direction:row;align-items:flex-start;gap:10px;border:1px solid var(--line);
  padding:11px 12px;margin:0;cursor:pointer;background:#fff;
  transition:border-color .15s,background .15s}
.marca:hover{border-color:var(--muted-fg)}
.marca:has(input:checked){border-color:var(--brand);background:var(--brand-soft)}
.marca input{width:auto;flex-shrink:0;margin-top:2px}
.marca>span{display:flex;flex-direction:column;gap:2px}
.marca strong{font-size:13px;color:var(--ink);font-weight:600;line-height:1.25}
.marca small{font-size:11.5px;color:var(--muted-fg);line-height:1.35}
@media(max-width:560px){.marca-grid{grid-template-columns:1fr}}
.modal-ov{position:fixed;inset:0;background:rgba(0,0,0,.42);display:flex;align-items:center;justify-content:center;padding:20px;z-index:50}
.modal{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:22px;max-width:460px;width:100%;box-shadow:0 24px 64px -20px rgba(0,0,0,.45);max-height:90vh;overflow-y:auto}
/* Modales con formulario a dos columnas (alta y edición de UTPR). A 460px las dos columnas
   quedaban apretadas: se ensancha para que cada campo respire, sin llegar a lo ancho de la
   página (sigue siendo un diálogo). En móvil el width:100% del modal manda igual. */
.modal.modal-ancho{max-width:640px}
/* El hueco del logo va dentro del propio .form-grid, y el margin-top del .pdf-slot sobraría
   ahí porque el gap de la rejilla ya separa: lo anulamos. */
.form-grid .pdf-slot{margin-top:0}
.modal h3{margin:0 0 16px;font-family:var(--font-serif);font-size:19px;letter-spacing:-.01em}
.modal label{display:block;margin:0 0 12px;font-size:13px;color:var(--muted-fg)}
.modal label input{margin-top:5px}
.modal .modal-actions{display:flex;gap:10px;justify-content:flex-end;margin-top:24px;
  border-top:1px solid var(--line);padding-top:18px}

/* Los modales SOLO salen dentro del panel, que es cuadrado y serio por decisión de diseño.
   Estaban heredando el redondeo de la landing (--radius: 8px) y desentonaban: tarjeta cuadrada
   detrás, diálogo con esquinas redondas delante. Van a juego con lo que hay debajo. */
.modal,.modal .btn,.modal input,.modal select,.modal textarea,.toast{border-radius:0}
.toast{position:fixed;bottom:22px;left:50%;transform:translateX(-50%);background:var(--ink);color:#fff;padding:11px 18px;border-radius:6px;font-size:14px;z-index:60;box-shadow:0 12px 34px -8px rgba(0,0,0,.45);max-width:90vw;text-align:center}
.toast.err{background:var(--danger)}

/* ==========================================================================
   Área logueada (panel soporte/admin): cuadrado, serio y espaciado.
   Lienzo gris tenue, tarjetas blancas con borde fino, esquinas RECTAS (sin
   redondeo) y buena separación. Acotado a .layout (no toca landing ni login).
   ========================================================================== */
.layout{background:var(--app-canvas)}
.layout .topbar{background:#fff;border-bottom:1px solid var(--line);padding:15px 24px}
.layout .content{max-width:1120px;padding-top:32px}
/* Más aire entre tarjetas/recuadros. */
.layout .stack{gap:30px}
/* ---- PIE DE PÁGINA GLOBAL (vistas logueadas) ---- */
/* margin-top:auto en el layout flex-column lo cierra al fondo (o justo tras el contenido si es alto).
   Sin fondo propio: hereda el tono de la página (--app-canvas). Contenido centrado. */
.layout .app-footer{margin-top:auto;border-top:1px solid var(--line);background:transparent}
.app-foot-in{max-width:1120px;margin:0 auto;padding:16px 28px;
  display:flex;flex-wrap:wrap;align-items:center;justify-content:center;gap:6px 16px;
  text-align:center;font-size:12.5px;color:var(--muted-fg)}
.app-foot-in .foot-links{display:flex;flex-wrap:wrap;justify-content:center;gap:6px 16px}
.app-foot-in .foot-links a{color:var(--muted-fg);text-decoration:none}
.app-foot-in .foot-links a:hover{color:var(--ink);text-decoration:underline}
.app-foot-in .foot-powered a{color:inherit;text-decoration:none;font-weight:600}
@media(max-width:640px){
  .app-foot-in{flex-direction:column;align-items:center;gap:8px;padding:14px 16px}
}
/* Esquinas rectas y serias en todo el panel: tarjetas, botones, campos, chips. */
.layout .card{border-radius:0;border-color:var(--line);box-shadow:none}
.layout .btn{border-radius:0}
.layout input,.layout select{border-radius:0}
.layout .tag,.layout .badge{border-radius:0}
.layout .card-head{border-bottom:1px solid var(--line);padding-bottom:12px;margin-bottom:16px}
.layout .card-head h2{font-family:var(--font-serif);font-size:18px}
.layout table{width:100%;border-collapse:collapse}
.layout tbody tr{transition:background .12s}
.layout tbody tr:hover{background:var(--app-canvas)}
/* Los botones de acción se ajustan a su texto. Antes tenían min-width:92px para quedar
   uniformes entre filas, pero eso estiraba los cortos ("Borrar" ~50px) hasta 92px dejando
   hueco muerto dentro del botón. Prima no dejar espacios vacíos sin sentido. */
.layout tbody tr.row-off{opacity:.55}
/* Recuadros por rol (Administradores / Técnicos / Clientes) en la ficha de empresa. */
.layout .role-box{padding:24px}
.layout .role-box .rb-list{min-height:28px}
.layout .role-box .card-head h2{font-size:16px}
/* Celda de acción de las cuentas por rol: un <td> en flex se sale del layout de tabla y su
   borde inferior queda a otra altura (la raya de la fila se ve partida). La dejamos como celda
   normal, alineada a la derecha y ceñida; y quitamos el borde de la última fila para que no
   quede una raya suelta metida dentro de la tarjeta. */
.layout .role-box td.rb-acc{text-align:right;white-space:nowrap;width:1%}
.layout .role-box table tr:last-child td{border-bottom:0}
/* Filtro por empresa-cliente (solo la caja de clientes). */
.layout .role-box .rb-filtro{margin:0 0 14px}
.layout .role-box .rb-filtro label{display:inline-flex;align-items:center;gap:10px;margin:0;
  font-size:13px;font-weight:600;color:var(--muted-fg)}
.layout .role-box .rb-filtro select{width:auto;min-width:220px;font-weight:400;margin:0}
/* Nombre de empresa: enlace sutil para entrar en su ficha. */
.layout .emp-open{background:none;border:0;padding:0;font:inherit;font-weight:600;color:var(--ink);cursor:pointer;text-align:left}
.layout .emp-open:hover{color:var(--brand-ink);text-decoration:underline}
/* Motivo de coincidencia del buscador (por qué salió esta clínica): línea pequeña y atenuada. */
.layout .match-why{display:block;margin-top:2px;font-size:11.5px;font-weight:400;color:var(--muted-fg)}
/* Volver + ficha clave-valor de la ficha de empresa. */
.layout .linkback{background:none;border:0;color:var(--muted-fg);font:inherit;font-size:13px;cursor:pointer;padding:0;margin-bottom:4px}
.layout .linkback:hover{color:var(--brand-ink)}
.layout .kv{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:16px 24px;font-size:14px;color:var(--ink)}
.layout .kv .muted{font-size:12px;display:block;margin-bottom:2px}
/* Enlaces en la ficha (web pública, correo de contacto): estilo enlace de marca. */
.layout .kv a{color:var(--brand-ink);text-decoration:underline;word-break:break-all}
.layout .kv a:hover{color:var(--brand)}

/* ---- Ficha de empresa (soporte): cabecera + configuración de plataforma ----
   Cabecera: nombre a la izquierda con su estado; acciones a la derecha, en la misma línea, y
   envolviendo debajo cuando no caben. La configuración (dominio/web/alta) va DEBAJO, apilada a la
   izquierda en flujo natural: antes era un grid de 2 columnas y «Web pública» quedaba en el centro. */
.layout .emp-head{display:flex;flex-wrap:wrap;gap:16px 20px;align-items:flex-start;justify-content:space-between}
.layout .emp-head-l{display:flex;flex-direction:column;gap:10px;min-width:0}
.layout .emp-name{font-family:var(--font-serif);font-size:24px;letter-spacing:-.01em;margin:0;color:var(--ink);line-height:1.12}
.layout .emp-badges{display:flex;flex-wrap:wrap;gap:8px;align-items:center}
.layout .emp-estado{display:inline-flex;align-items:center;gap:7px;font-size:13px;font-weight:600;
  color:var(--ink);border:1px solid var(--line);padding:4px 11px}
.layout .emp-estado.is-off{color:var(--muted-fg)}
.layout .emp-estado .state-dot{margin:0}
.layout .emp-tag-plat{display:inline-flex;align-items:center;font-size:11px;font-weight:700;
  letter-spacing:.03em;text-transform:uppercase;color:var(--brand-ink);background:var(--brand-soft);
  border:1px solid var(--brand-soft);padding:4px 10px}
.layout .emp-head .actions-cell{margin:0}
.layout .emp-config{display:flex;flex-wrap:wrap;gap:16px 44px;margin-top:20px;padding-top:18px;
  border-top:1px solid var(--line)}
.layout .emp-c{display:flex;flex-direction:column;gap:3px;min-width:0}
.layout .emp-c-k{font-size:12px;color:var(--muted-fg)}
.layout .emp-c-v{font-size:14px;color:var(--ink);word-break:break-word}
.layout .emp-c-v a{color:var(--brand-ink);text-decoration:underline;word-break:break-all}
.layout .emp-c-v a:hover{color:var(--brand)}
@media(max-width:640px){ .layout .emp-head .actions-cell{width:100%} .layout .emp-head .actions-cell .btn{flex:1 1 auto} }
/* Panel del tenant: dos cuadrados grandes lado a lado (Mi UTPR / Clientes), clicables. */
.layout .dash-tiles{display:grid;grid-template-columns:repeat(2,1fr);gap:24px}
.layout .dash-tile{display:flex;flex-direction:column;align-items:flex-start;text-align:left;
  background:#fff;border:1px solid var(--line);border-radius:0;padding:32px 28px;min-height:190px;
  font-family:inherit;color:var(--ink);cursor:pointer;transition:border-color .15s,box-shadow .15s,transform .05s}
.layout .dash-tile:hover{border-color:var(--brand);box-shadow:0 4px 18px -8px rgba(20,18,16,.25)}
.layout .dash-tile:active{transform:translateY(1px)}
.layout .dash-tile h2{font-family:var(--font-serif);font-size:24px;margin:0 0 8px}
.layout .dash-tile p{margin:0}
.layout .dash-tile .dash-enter{margin-top:auto;padding-top:18px;color:var(--brand-ink);font-weight:700;font-size:14px}
@media(max-width:640px){ .layout .dash-tiles{grid-template-columns:1fr} }
/* Chip de rol: tinte de marca, esquinas rectas. */
.badge{background:var(--brand-soft);color:var(--brand-ink);padding:3px 9px;font-weight:700;font-size:11px;letter-spacing:.01em;text-transform:none}
@media(max-width:640px){ .layout .topbar{padding:12px 16px} .layout .kv{grid-template-columns:1fr} }

/* ==========================================================================
   ACCESO DE SOPORTE (consentimiento del tenant) + chuleta de perfiles
   ========================================================================== */

/* El sistema solo vestía input/select; el motivo de una solicitud necesita varias líneas. */
textarea{width:100%;background:#fff;border:1px solid var(--input);color:var(--ink);border-radius:6px;
  padding:11px 12px;font-size:14px;font-family:inherit;line-height:1.5;outline:none;resize:vertical;min-height:78px}
textarea:focus{border-color:var(--brand);box-shadow:0 0 0 3px color-mix(in oklab,var(--brand) 16%,transparent)}

/* El texto que explica el modal, separado de los controles: pegado se lee como si el primer
   botón fuera el final de la frase. */
.modal-lead{font-size:13.5px;color:var(--muted-fg);margin:0 0 22px;line-height:1.6}

/* Selector de duración del permiso: un bloque con su borde, no tres líneas sueltas debajo del
   párrafo. La leyenda monta sobre el borde y lo separa visualmente de lo de arriba. */
.radio-set{border:1px solid var(--line);padding:6px 16px 14px;margin:0}
.radio-set legend{font-size:11px;color:var(--muted-fg);padding:0 8px;text-transform:uppercase;
  letter-spacing:.06em;font-weight:600}
.radio{flex-direction:row;align-items:center;gap:11px;font-size:14px;color:var(--ink);
  padding:9px 0;cursor:pointer}
.radio + .radio{border-top:1px solid color-mix(in oklab,var(--line) 55%,#fff)}
.radio input{width:auto;margin:0;accent-color:var(--brand);flex-shrink:0}
.radio:hover span{color:var(--brand-ink)}

/* Chips de estado del permiso (reusan el semáforo institucional). */
.tag.ok{color:var(--ok);border-color:var(--ok-line);background:color-mix(in oklab,var(--ok) 8%,#fff)}
.tag.warn{color:var(--warn-ink);border-color:var(--warn-line);background:color-mix(in oklab,var(--warn-line) 14%,#fff)}

/* El motivo, citado: es texto de una persona, no de la interfaz. */
.motivo{margin:16px 0 0;padding:11px 16px;border-left:3px solid var(--line);background:var(--bg-alt);
  color:var(--ink);font-size:13.5px;line-height:1.6;font-style:italic;overflow-wrap:anywhere}

.acceso-card p{line-height:1.65;max-width:74ch}

/* Pie de la tarjeta mientras se espera decisión. Separado de los botones por una línea: es
   estado, no una acción más. */
.espera-nota{margin-top:20px;padding-top:14px;border-top:1px solid var(--line);
  font-size:12.5px;color:var(--muted-fg);display:flex;align-items:center;gap:9px;line-height:1.5}
.latido{width:7px;height:7px;border-radius:999px;background:var(--warn-line);flex-shrink:0;
  animation:latido 1.8s ease-in-out infinite}
@keyframes latido{0%,100%{opacity:.28}50%{opacity:1}}
@media(prefers-reduced-motion:reduce){.latido{animation:none;opacity:.75}}
.gate-card{text-align:center;padding:44px 28px}
.gate-card h2{font-size:20px;margin-bottom:10px}
.gate-card p{max-width:56ch;margin:0 auto 20px;line-height:1.6}
.gate-card .actions-cell{justify-content:center}

/* Avisos del panel del admin. El hueco se colapsa cuando no hay nada que decir: el panel es
   para trabajar, no para recordarte lo que no pasa. */
.aviso-slot:empty{display:none}
.aviso{display:flex;gap:28px;align-items:flex-start;justify-content:space-between;
  background:#fff;border:1px solid var(--line);padding:22px 24px}
.aviso-txt{min-width:0}
.aviso-txt strong{display:block;color:var(--ink);font-family:var(--font-serif);font-size:16px;
  font-weight:600;margin-bottom:6px}
.aviso-txt p{font-size:13.5px;color:var(--muted-fg);line-height:1.6;margin:0;max-width:70ch}
/* Los botones se alinean con la primera línea del texto, no flotando a media altura. */
.aviso-acts{display:flex;gap:8px;flex-shrink:0;padding-top:2px}
.aviso-pide{border-left:3px solid var(--warn-line)}
.aviso-abierto{border-left:3px solid var(--ok-line)}
.aviso-cerrado{border-left:3px solid var(--line)}
/* Filas de «Avisos por correo»: nombre a la izquierda, interruptor a la derecha. */
.av-row{display:flex;align-items:center;justify-content:space-between;gap:16px;margin:0;
  padding:9px 0;border-top:1px solid var(--line);font-size:13.5px;color:var(--ink)}
.av-row:first-of-type{border-top:0}
.av-toggle{flex-shrink:0;cursor:pointer;min-width:118px;text-align:center;font-size:12.5px;font-weight:600;
  padding:6px 14px;border-radius:6px;border:1px solid transparent;transition:background .15s,border-color .15s,opacity .15s}
.av-toggle.on{color:var(--ok);background:color-mix(in oklab,var(--ok) 12%,#fff);border-color:color-mix(in oklab,var(--ok) 32%,var(--line))}
.av-toggle.off{color:var(--danger);background:color-mix(in oklab,var(--danger) 12%,#fff);border-color:color-mix(in oklab,var(--danger) 32%,var(--line))}
.av-toggle:disabled{opacity:.5;cursor:default}
.av-row-soon span:last-child{flex-shrink:0}
/* Fila de GRUPO: título + la lista de lo que el interruptor apaga de verdad. El botón se sube
   arriba (align-items:flex-start) en vez de centrarse: con la lista debajo, centrado se queda
   flotando a media altura, lejos del título con el que se lee. */
.av-row-grupo{align-items:flex-start;padding:14px 0}
.av-txt{display:flex;flex-direction:column;gap:3px;min-width:0}
.av-tit{font-weight:600}
.av-intro{font-size:12.5px;color:var(--muted-fg)}
.av-detalle{margin:4px 0 0;padding:0 0 0 17px;font-size:12.5px;color:var(--muted-fg);line-height:1.65}
.av-detalle li{margin:0}
/* En móvil el botón no cabe al lado de la lista: se pasa debajo, alineado a la izquierda para
   que no quede colgando en una esquina sin nada que lo ancle. */
@media (max-width:560px){
  .av-row-grupo{flex-direction:column;gap:10px}
  .av-row-grupo .av-toggle{align-self:flex-start}
}

/* Pie del panel: los desplegables van uno pegado a otro, sin el hueco de .stack, para que se
   lean como una sola lista de consulta. La línea de arriba de cada uno hace de separador. */
.dash-pie{display:flex;flex-direction:column}
.dash-pie>.roles-note{margin-top:0}
/* Cerrados ocupan menos alto: la fila del título es más ajustada dentro del bloque. */
.dash-pie>.roles-note:not([open])>summary{padding:10px 2px}

/* Caja de credenciales de la demo, en la pantalla de acceso de demo.utprpro.com. Atenuada a
   propósito: es una ayuda, no la parte principal de la pantalla — quien llega con su cuenta no
   debe distraerse con ella. El <code> en monoespaciada para que la contraseña se lea sin dudas
   (una l y una I en la tipografía del texto son el mismo palo). */
.demo-box{margin:18px 0 4px;padding:14px 16px;border:1px solid var(--line);
  background:rgba(20,18,16,.03);text-align:left}
.demo-box-tit{margin:0 0 6px;font-size:12px;font-weight:700;letter-spacing:.04em;
  text-transform:uppercase;color:var(--brand-ink)}
.demo-box-txt{margin:0 0 10px;font-size:12.5px;line-height:1.6;color:var(--muted-fg)}
.demo-box-cred{margin:3px 0;font-size:13px;display:flex;gap:8px;align-items:baseline}
.demo-box-cred span{color:var(--muted-fg);min-width:78px}
.demo-box-cred code{font-family:ui-monospace,SFMono-Regular,Menlo,monospace;font-size:12.5px;
  background:#fff;border:1px solid var(--line);padding:2px 6px;word-break:break-all}

/* Miniatura del logo actual en el modal de edición de UTPR. object-fit para que un logo
   apaisado y uno cuadrado se vean los dos enteros sin deformarse. */
.logo-prev{max-height:48px;max-width:190px;object-fit:contain;display:block}

/* Chuleta de perfiles: al pie, plegada y en gris. Se consulta, no se lee. */
.roles-note{border-top:1px solid var(--line);margin-top:4px}
.roles-note summary{cursor:pointer;font-size:13px;color:var(--muted-fg);padding:12px 2px;list-style:none;
  display:inline-flex;align-items:center;gap:9px}
.roles-note summary::-webkit-details-marker{display:none}
.roles-note summary::before{content:'+';font-weight:700;font-size:14px;line-height:1;color:var(--brand-ink)}
.roles-note[open] summary::before{content:'–'}
.roles-note summary:hover{color:var(--brand-ink)}
.roles-body{padding:4px 0 18px}
.roles-grid{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:22px 40px}
.perfil h4{font-size:13px;letter-spacing:.02em;margin:0 0 6px}
.perfil h4 .muted{font-weight:400}
.perfil p{font-size:13px;line-height:1.65;color:var(--muted-fg);margin:0}
.perfil-nos{grid-column:1/-1;border-top:1px solid var(--line);padding-top:18px}
.perfil-nos strong{color:var(--ink)}
.perfil-act{margin-top:12px}
.perfil-act:empty{display:none}
/* «Qué puedo hacer»: ficha del PROPIO rol, destacada con un acento a la izquierda. */
.perfil-yo{background:rgba(20,18,16,.03);border:1px solid var(--line);border-left:3px solid var(--brand);padding:14px 16px}
.perfil-yo h4{color:var(--brand-ink)}
.perfil-yo p{color:var(--ink)}
.roles-otros{margin-top:10px}
.roles-otros summary{cursor:pointer;font-size:12px;color:var(--muted-fg);padding:6px 2px;list-style:none;
  display:inline-flex;align-items:center;gap:8px}
.roles-otros summary::-webkit-details-marker{display:none}
.roles-otros summary::before{content:'+';font-weight:700;color:var(--brand-ink)}
.roles-otros[open] summary::before{content:'–'}
.roles-otros .roles-grid{margin-top:12px}

/* ==========================================================================
   VISOR "DATOS CLIENTES"
   ========================================================================== */

/* Área ya construida dentro de una sección: se entra, no es un cartel. */
.layout .area-card{display:block;width:100%;text-align:left;font:inherit;color:inherit;cursor:pointer;
  background:#fff;border:1px solid var(--line);border-radius:0;padding:20px;
  transition:border-color .15s,box-shadow .15s}
.layout .area-card:hover{border-color:var(--brand);box-shadow:0 4px 18px -8px rgba(20,18,16,.25)}
.layout .area-card .card-head{margin-bottom:12px}
.layout .area-card p{margin:0}
.layout .area-card .dash-enter{color:var(--brand-ink);font-weight:700;font-size:13px}

/* Barra de herramientas: buscador ancho + filtro que se ajusta a su texto. */
.visor-tools{display:flex;gap:10px;margin-bottom:16px}
/* Rango de fechas del generador de informe: fila que envuelve en móvil. */
.informe-rango{display:flex;flex-wrap:wrap;align-items:flex-end;gap:12px}
.informe-rango .fld{margin:0}
.informe-rango input[type=date]{padding:9px 10px;border:1px solid var(--line);border-radius:6px;font:inherit}
/* ---- Gráficos: generador configurable (una sola pantalla) ---- */
.graf-conf{display:flex;flex-wrap:wrap;align-items:flex-end;gap:12px}
.graf-conf .fld{margin:0;min-width:180px}
.graf-conf select{padding:9px 10px;border:1px solid var(--line);border-radius:6px;font:inherit;background:#fff}
.graf-rango{display:flex;flex-wrap:wrap;align-items:flex-end;gap:12px}
.graf-rango .fld{margin:0}
.graf-rango input[type=date]{padding:9px 10px;border:1px solid var(--line);border-radius:6px;font:inherit}
.graf-fuente{margin:12px 0 0;font-size:13px}
.graf-lienzo{margin-top:14px}
.graf-cab{margin:0 0 14px}
.graf-cab h3{margin:0 0 2px;font-size:15px}
.graf-cab p{margin:0;font-size:13px}
.graf{display:flex;flex-direction:column;gap:8px}
.graf-row{display:grid;grid-template-columns:minmax(90px,26%) 1fr auto;align-items:center;gap:10px}
.graf-lbl{font-size:13px;color:var(--muted-fg);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.graf-barra{position:relative;height:18px;background:var(--bg-alt);border-radius:4px;overflow:hidden}
.graf-fill{position:absolute;inset:0 auto 0 0;background:var(--brand);border-radius:4px;min-width:3px;transition:width .25s ease}
.graf-val{font-size:13px;font-variant-numeric:tabular-nums;font-weight:600;min-width:2ch;text-align:right}
.graf-vacio{margin:0;color:var(--muted-fg);font-size:13.5px;line-height:1.5}
@media (max-width:560px){.graf-row{grid-template-columns:minmax(72px,34%) 1fr auto}}
.visor-tools #q{flex:1;min-width:0}
/* El filtro de usuarios del panel usa el MISMO patrón que el de clientes: un <select> que se
   auto-etiqueta con su primera opción («Todas las empresas»). Estas reglas iban por #id, así que
   reutilizar el patrón es nombrarlo aquí; una clase sería más limpio, pero cambiar el selector
   de #f tocaría la pantalla de clientes y eso no toca hoy. */
.visor-tools #f,.visor-tools #fz,.visor-tools #usrFiltro{flex:0 0 auto;width:auto}

/* Cabeceras ordenables: parecen texto hasta que pasas por encima. */
.th-orden{background:none;border:0;padding:0;margin:0;font:inherit;color:inherit;cursor:pointer;
  text-transform:inherit;letter-spacing:inherit;font-weight:inherit}
.th-orden:hover{color:var(--brand-ink)}
.th-orden.on{color:var(--ink)}

.visor-pag{display:flex;align-items:center;justify-content:space-between;gap:16px;
  margin-top:16px;padding-top:14px;border-top:1px solid var(--line);font-size:13px;flex-wrap:wrap}
.pag-btns{display:flex;align-items:center;gap:12px}

/* Vacío: ocupa sitio y explica, en vez de dejar la tarjeta en blanco. */
.vacio{padding:36px 20px;text-align:center}
.vacio p{margin:0 0 6px}
.vacio strong{color:var(--ink)}

/* ==========================================================================
   RESPONSIVE (2): menú de móvil, tablas como fichas, barra del panel
   ========================================================================== */

/* --- Menú de la landing en móvil ---
   Antes .nav-links{display:none} bajo 900px: los seis enlaces se esfumaban y no había ningún
   modo de navegar. Ahora se despliegan desde el botón. */
.nav-toggle{display:none;flex-direction:column;justify-content:center;gap:5px;width:42px;height:38px;
  padding:0 9px;background:none;border:1px solid var(--line);border-radius:4px;cursor:pointer}
.nav-toggle span{display:block;height:2px;width:100%;background:var(--ink);border-radius:2px;
  transition:transform .18s ease,opacity .18s ease}
.nav-toggle.is-open span:nth-child(1){transform:translateY(7px) rotate(45deg)}
.nav-toggle.is-open span:nth-child(2){opacity:0}
.nav-toggle.is-open span:nth-child(3){transform:translateY(-7px) rotate(-45deg)}
@media(prefers-reduced-motion:reduce){.nav-toggle span{transition:none}}

@media(max-width:900px){
  .nav-toggle{display:flex;order:3}
  .nav-inner{flex-wrap:wrap;gap:12px}
  .wordmark{order:1}
  .nav-cta{order:2;margin-left:auto;padding:9px 14px;font-size:13px}
  .nav-links{display:none;order:4;flex-basis:100%;margin:0;flex-direction:column;align-items:stretch;
    gap:0;border-top:1px solid var(--line)}
  .nav-links.open{display:flex}
  .nav-links a{padding:13px 2px;border-bottom:1px solid var(--line)}
  .nav-links a:last-child{border-bottom:0}
}
@media(max-width:380px){
  .wordmark{font-size:19px}
  .nav-cta{padding:8px 11px;font-size:12px}
}

/* --- Tablas del panel: en móvil, una ficha por fila ---
   Con 7 columnas (usuarios) el scroll horizontal obligaba a arrastrar para leer una fila
   entera. Cada celda enseña su etiqueta (data-l) y la fila se lee de arriba abajo. */
@media(max-width:900px){
  .layout .table-wrap table{min-width:0}
  .layout .table-wrap thead{display:none}
  .layout .table-wrap table,
  .layout .table-wrap tbody,
  .layout .table-wrap tr,
  .layout .table-wrap td{display:block;width:auto}
  .layout .table-wrap tr{border:1px solid var(--line);padding:12px 14px;margin-bottom:12px;background:#fff}
  .layout .table-wrap tr:hover{background:#fff}
  .layout .table-wrap tr:last-child{margin-bottom:0}
  .layout .table-wrap td{border:0;padding:5px 0;display:flex;gap:16px;align-items:baseline;
    justify-content:space-between;font-size:13.5px;overflow-wrap:anywhere}
  .layout .table-wrap td::before{content:attr(data-l);color:var(--muted-fg);font-size:11px;font-weight:600;
    text-transform:uppercase;letter-spacing:.03em;flex-shrink:0}
  .layout .table-wrap td[data-l="Email"],
  .layout .table-wrap td[data-l="Empresa"]{flex-direction:column;gap:2px;align-items:flex-start}
  /* La celda de acciones no es un dato: sin etiqueta y a lo ancho. */
  .layout .table-wrap td.td-acts{display:block;padding:12px 0 0;margin-top:8px;border-top:1px solid var(--line)}
  .layout .table-wrap td.td-acts::before{display:none}
  /* Igual para las tablas de «Datos de Empresa» (td.acciones): barra de botones a lo ancho, con una
     raya que la separa del dato de arriba. Sin la etiqueta vacía que la partía entre 640 y 900. */
  .layout .table-wrap td.acciones{display:flex;gap:8px;width:auto;white-space:normal;text-align:left;
    padding:12px 0 0;margin-top:8px;border-top:1px solid var(--line)}
  .layout .table-wrap td.acciones::before{content:none}
  .layout .table-wrap td.acciones .btn{flex:1 1 auto;margin-left:0}
  /* Cuentas por rol en móvil: la acción a lo ancho, sin etiqueta; y si va vacía (admin sin
     botón) que no deje una fila en blanco. */
  .layout .table-wrap td.rb-acc{display:block;padding:10px 0 0}
  .layout .table-wrap td.rb-acc::before{display:none}
  .layout .table-wrap td.rb-acc:empty{display:none}
  .layout .table-wrap .actions-cell .btn{flex:1 1 auto}
}

/* ========================================================================
   BOCETOS — áreas del panel todavía sin construir
   ------------------------------------------------------------------------
   El aviso de cabecera no es decorativo: dice de dónde sale lo que estás
   viendo. Se reutiliza la paleta del SEMÁFORO, que ya existe y ya significa
   algo en este producto, en vez de inventar tres colores nuevos:
     verde  = la tabla ya existe, los campos son reales
     ámbar  = es una deducción nuestra, corrígela
     rojo   = no sabemos qué es esto
   ======================================================================== */
.boceto-aviso{border:1px solid var(--line);border-left-width:3px;background:var(--bg-alt);
  padding:16px 18px;border-radius:var(--radius)}
.boceto-aviso .tag{background:#fff}
.boceto-aviso p{margin:10px 0 0;font-size:14px;line-height:1.65;max-width:74ch;color:var(--body)}
.boceto-aviso .boceto-fuente{font-size:13px;color:var(--muted-fg)}
.boceto-aviso .boceto-fuente:empty{display:none}

.seg-tabla{border-left-color:var(--ok-line);background:color-mix(in oklab,var(--ok) 5%,#fff)}
.seg-tabla .tag{color:var(--ok);border-color:var(--ok-line)}
.seg-derivado{border-left-color:var(--warn-line);background:color-mix(in oklab,var(--warn-line) 9%,#fff)}
.seg-derivado .tag{color:var(--warn-ink);border-color:var(--warn-line)}
.seg-incognita{border-left-color:var(--danger-line);background:color-mix(in oklab,var(--danger) 5%,#fff)}
.seg-incognita .tag{color:var(--danger);border-color:var(--danger-line)}

.boceto-campos{margin:0;padding:0;list-style:none}
.boceto-campos li{padding:9px 0 9px 18px;border-bottom:1px solid var(--line);font-size:14px;
  line-height:1.6;color:var(--body);position:relative;max-width:80ch}
.boceto-campos li:last-child{border-bottom:0;padding-bottom:0}
.boceto-campos li::before{content:"";position:absolute;left:0;top:17px;width:6px;height:1px;
  background:var(--muted-fg)}

.boceto-pregunta{border-left:3px solid var(--brand)}
.boceto-pregunta h2{color:var(--brand-ink)}
.boceto-pregunta p{line-height:1.65;max-width:74ch;color:var(--body);font-size:14px}

.boceto-pie{font-size:13px;text-align:center;margin:4px 0 0;line-height:1.6}

/* El área sin construir ya no es un cartel muerto: se entra en ella. */
.tag-boceto{color:var(--muted-fg);white-space:nowrap}

/* --- Barra superior del panel: el email largo no debe empujar al botón Salir --- */
.uinfo strong{overflow-wrap:anywhere}
@media(max-width:640px){
  .layout .topbar{flex-wrap:wrap;gap:10px}
  .layout .topbar .user{width:100%;justify-content:space-between;gap:10px}
  .uinfo{align-items:flex-start;min-width:0}
  .uinfo strong{font-size:12.5px}
  .aviso{flex-direction:column;gap:14px}
  .aviso-acts{width:100%}
  .aviso-acts .btn{flex:1}
  .roles-grid{grid-template-columns:1fr;gap:20px}
  .visor-tools{flex-direction:column}
  .visor-tools #f,.visor-tools #fz,.visor-tools #usrFiltro{width:100%}
  .visor-pag{flex-direction:column;align-items:stretch;gap:12px}
  .pag-btns{justify-content:space-between}
  .row-form{flex-direction:column}
  .row-form input,.row-form select,.row-form .btn{width:100%}
  .modal{padding:18px}
  .modal .modal-actions .btn{flex:1}
  .gate-card{padding:32px 18px}
  /* En el móvil la etiqueta no cabe al lado del título: se va debajo. */
  .area-card .card-head{flex-direction:column;align-items:flex-start;gap:8px}
  .boceto-aviso{padding:14px 16px}
}

/* ========================================================================
   «DATOS DE EMPRESA» — secciones 1-5 del informe al CSN
   ======================================================================== */

/* Indicador de completitud en las tarjetas de área. Es un AVISO, no un candado: dice qué le
   falta al informe y no impide guardar nada a medias. Por eso «falta» es gris y no rojo —
   rellenar esto es trabajo de semanas, y un panel en rojo durante meses deja de leerse. */
.compl{font-size:13px;margin:0 0 6px;font-weight:600}
.compl-ok{color:var(--ok)}
.compl-falta{color:var(--muted-fg)}

/* ---- Formularios ---- */
.form-grid{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:14px 18px}
.form-actions{grid-column:1/-1;display:flex;justify-content:flex-end;border-top:1px solid var(--line);padding-top:16px;margin-top:2px}
.fld{gap:6px;min-width:0}
.fld>span{display:flex;align-items:center;gap:8px;flex-wrap:wrap}
.oblig{font-style:normal;font-size:10px;text-transform:uppercase;letter-spacing:.04em;
  color:var(--muted-fg);border:1px solid var(--line);border-radius:999px;padding:1px 7px}
.chk{flex-direction:row;align-items:center;gap:9px;font-size:14px;color:var(--ink)}
.chk input{width:auto;flex-shrink:0}

/* El error va pegado a SU campo. El servidor manda una lista ({campo, error}) en vez de un
   mensaje único justamente para esto: si faltan 7 obligatorios se ven los 7 a la vez. */
.field-err{color:var(--danger);font-size:12.5px;margin:5px 0 0}
.err-borde{border-color:var(--danger-line)}
.err-borde:focus{box-shadow:0 0 0 3px color-mix(in oklab,var(--danger) 16%,transparent)}

.row-actions{display:flex;gap:10px;align-items:center;flex-wrap:wrap}
.row-actions .sel-anio{width:auto;min-width:110px}
/* Resumen de escala junto al botón de alta (cuánta gente/instrumentos hay). Empuja a la
   derecha para separarlo de la acción: es un dato, no un botón. */
.row-resumen{margin-left:auto;font-size:13px;color:var(--muted-fg)}
.row-resumen strong{color:var(--ink);font-weight:700}
@media(max-width:640px){.row-resumen{margin-left:0}}
/* Celda de acciones de las tablas de «Datos de Empresa» (Personal, Dosimetría, Vigilancia,
   Equipos de medida). Como en las cuentas por rol, un <td> NORMAL (no flex): en flex la celda se
   sale del layout de tabla y la raya inferior de la fila queda a otra altura (se ve partida). Se
   ciñe a su contenido, a la derecha y en una sola línea, alineada con el resto de la fila. */
td.acciones{width:1%;white-space:nowrap;text-align:right;vertical-align:middle}
td.acciones .btn+.btn{margin-left:6px}
/* Que el dato (texto y etiquetas) quede centrado con los botones: fila pareja de arriba abajo. */
.layout .card .table-wrap td{vertical-align:middle}
.btn.small{padding:5px 11px;font-size:12.5px}

/* Nota al pie de un formulario o modal. Antes iba con `style="font-size:13px…"` repetido a mano
   en cada bloque; una clase la deja idéntica en todos y con un solo sitio donde cambiarla. */
.form-nota{font-size:13px;color:var(--muted-fg);line-height:1.55;margin:8px 0 0;max-width:70ch}

/* ---- Marcador de subida de PDF (fase futura, deshabilitado) ----
   El hueco donde irán los PDFs cuando el almacenamiento (Azure Blob) esté montado. Se pinta
   atenuado, con borde discontinuo y la etiqueta «próximamente», para que se vea que el sitio
   existe y que todavía no funciona —sin prometer que ya se puede usar—. Mismo patrón que la
   ficha del cliente; esta regla estiliza también aquel marcador, que se quedó sin CSS. */
.pdf-slot{margin-top:16px;border:1px dashed var(--line);border-radius:var(--radius);
  background:var(--bg-alt);padding:14px 16px;opacity:.62}
.pdf-slot:hover{opacity:.85}
.pdf-slot-head{display:flex;align-items:center;gap:10px;flex-wrap:wrap}
.pdf-slot-head .btn:disabled{opacity:1;color:var(--muted-fg);border-style:dashed;background:#fff}
.soon{font-size:10px;text-transform:uppercase;letter-spacing:.05em;font-weight:700;
  color:var(--muted-fg);border:1px solid var(--line);border-radius:999px;padding:2px 9px;background:#fff}
.pdf-list{margin:12px 0 0;padding-left:20px;color:var(--body);font-size:13px;line-height:1.75}
.pdf-list li{margin:0}
.pdf-note{margin:10px 0 0;font-size:12.5px;line-height:1.6}

/* Historial de auditoría (quién ha accedido a los datos de salud). Va dentro de un <details>. */
.aud{min-width:0}
.aud .muted{font-size:13.5px}

/* ---- Marcas de la plantilla ---- */
/* JPR y Gerente son bits, no texto libre: el informe los nombra expresamente. */
.tag-jpr{background:var(--brand-soft);color:var(--brand-ink);border-color:var(--brand-soft);font-weight:700}
.tag-ger{background:var(--bg-alt);color:var(--muted-fg)}

/* ---- Dosis por encima del límite legal ---- */
/* Esto SÍ es rojo, y a diferencia del indicador de completitud sí debe gritar: una
   sobreexposición se declara al CSN, y enterarse al generar el informe es enterarse tarde. */
.dosis-excede{color:var(--danger);font-weight:700}
.tag-excede{color:var(--danger);border-color:var(--danger-line);
  background:color-mix(in oklab,var(--danger) 8%,#fff);white-space:nowrap;font-weight:600}

/* ---- Avisos de bloque ---- */
/* `.aviso` ya existe y es flex con dos columnas (texto + botones). Estos no llevan botones,
   así que se pintan como un bloque de texto y punto. */
.aviso-falta,.aviso-salud{display:block;padding:14px 18px;font-size:13.5px;line-height:1.6;
  border:1px solid var(--line);border-left-width:3px;background:var(--bg-alt);color:var(--body)}
.aviso-falta{border-left-color:var(--warn-line);background:color-mix(in oklab,var(--warn-line) 9%,#fff)}
/* El aviso de datos de salud va en rojo a propósito: es la única pantalla del producto donde
   MIRAR ya deja rastro, y quien entra tiene derecho a saberlo antes, no después. */
.aviso-salud{border-left-color:var(--danger-line);background:color-mix(in oklab,var(--danger) 4%,#fff)}

details.card>summary{cursor:pointer;font-size:14px;font-weight:600;color:var(--ink);
  font-family:var(--font-serif)}
details.card[open]>summary{margin-bottom:14px;border-bottom:1px solid var(--line);padding-bottom:12px}

@media(max-width:640px){
  .form-grid{grid-template-columns:1fr}
  /* La celda de acciones en modo tarjeta (barra de botones a lo ancho) ya se resuelve en el bloque
     de ≤900 de más arriba, junto al resto de la tabla-ficha. */
}

/* ---- Ficha de empresa: acceso, identificación, borrado ---- */

/* El acceso vive en la fila de acciones, no en una tarjeta aparte. Empuja a la derecha para
   separarlo de Editar/Desactivar: son cosas distintas —administrar la ficha vs. mirar dentro—
   y la separación lo dice sin escribirlo. */
.acceso-slot{display:inline-flex;align-items:center;gap:9px;margin-left:auto}
.acceso-nota{white-space:nowrap;display:inline-flex;align-items:center;gap:6px}
@media(max-width:640px){
  /* En móvil no hay «a la derecha»: la fila se apila y el margen automático no significa nada. */
  .acceso-slot{margin-left:0;width:100%;flex-wrap:wrap}
}

/* Identificación en modo LECTURA. No es un formulario: en una pantalla de consulta, un campo
   editable no dice si estás mirando o tocando. Se edita por «Editar». */
.datos-lista{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:12px 24px;margin:0}
.datos-lista dt{font-size:12px;color:var(--muted-fg);margin:0 0 2px}
.datos-lista dd{margin:0;font-size:14px;color:var(--ink);word-break:break-word}
/* Un obligatorio en blanco no es un hueco: es el informe que no sale. Se ve. */
.falta-oblig{color:var(--warn-ink);font-size:13px}
@media(max-width:640px){ .datos-lista{grid-template-columns:1fr} }

/* Separador dentro del modal de editar: arriba la config de la plataforma, abajo lo que va al
   informe. Son dos cosas y conviene que se note. */
.modal-sep{margin:20px 0 12px;padding-top:16px;border-top:1px solid var(--line);
  font-size:12px;text-transform:uppercase;letter-spacing:.04em;color:var(--muted-fg);font-weight:600}

/* Lo que se va a destruir al borrar una empresa. En rojo porque aquí el susto es el objetivo:
   es lo único irreversible del producto. */
.dep-list{margin:0 0 14px;padding-left:20px;font-size:14px;line-height:1.7}
.dep-list strong{color:var(--danger)}

/* La cabecera de un bloque (centro lector, servicio de prevención): un dato, no un formulario.
   Se lee de un vistazo y se cambia con «Editar», como la identificación. */
.cab-valor{margin:0;font:400 17px/1.4 Georgia,'Times New Roman',serif;color:var(--tinta)}

/* =====================================================================================
   FICHA DEL CLIENTE — rediseño: pestañas de instalación, secciones aireadas y colapsables,
   tarjetas de equipo, tablas legibles, actividades ordenadas, estados vacíos y responsive.
   Todo con las variables de marca del tenant (--brand…): marca blanca en cada tenant.
   ===================================================================================== */
.ficha .page-head{display:flex;justify-content:space-between;align-items:flex-start;gap:12px;flex-wrap:wrap}
.ficha .page-head h1{font-size:23px}
.ficha .page-head h2{margin:0;font-size:18px}
.ficha-cont{display:flex;flex-direction:column;gap:14px}

/* Indicador de carga (Azure puede tardar en despertar) */
.ficha-loading{display:flex;align-items:center;gap:12px;color:var(--muted-fg)}
.spinner{width:18px;height:18px;border-radius:50%;border:2.5px solid var(--line);
  border-top-color:var(--brand);animation:spin .7s linear infinite;flex:0 0 auto}
@keyframes spin{to{transform:rotate(360deg)}}

/* Cabecera del cliente: común y fija arriba */
.cli-card .kv{margin-top:2px}

/* ---- PESTAÑAS DE INSTALACIÓN ---- */
.insts-head{margin-bottom:-6px}
.inst-tabs{display:flex;gap:6px;overflow-x:auto;-webkit-overflow-scrolling:touch;
  border-bottom:2px solid var(--line);padding-bottom:0;scrollbar-width:thin}
.inst-tab{flex:0 0 auto;display:flex;flex-direction:column;gap:1px;align-items:flex-start;
  background:transparent;border:0;border-bottom:2px solid transparent;margin-bottom:-2px;
  padding:9px 14px;cursor:pointer;font-family:inherit;color:var(--muted-fg);border-radius:6px 6px 0 0;
  transition:background .12s,color .12s,border-color .12s;max-width:260px}
.inst-tab:hover{background:var(--bg-alt);color:var(--ink)}
.inst-tab .nm{font-weight:600;font-size:14px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;max-width:230px}
.inst-tab .reg{font-size:11px;color:var(--muted-fg)}
.inst-tab .baja{font-size:10px;text-transform:uppercase;letter-spacing:.04em;color:var(--muted-fg)}
.inst-tab.active{color:var(--brand-ink);border-bottom-color:var(--brand);background:var(--brand-soft)}
.inst-tab.active .reg{color:var(--brand-ink)}

/* Panel de la instalación activa */
.inst-host{padding:14px 18px}
.inst-title{display:flex;justify-content:space-between;align-items:flex-start;gap:12px;flex-wrap:wrap}
.inst-title h3{margin:0;font-size:19px}
.inst-title .muted{font-size:12.5px}
.inst-title .estado{font-size:13px;color:var(--muted-fg);white-space:nowrap}
.inst-acts{display:flex;gap:6px;flex-wrap:wrap;margin:8px 0 2px}
.inst-datos{margin-top:10px}
/* Datos de la instalación compactos: en una fila cuando caben, poco alto. */
.layout .kv.inst-datos{grid-template-columns:repeat(auto-fit,minmax(140px,1fr));gap:6px 20px}
/* Datos del cliente algo más compactos también (menos scroll para llegar al contenido). */
.layout .cli-card .kv{grid-template-columns:repeat(auto-fit,minmax(170px,1fr));gap:8px 20px}
.ficha .cli-card{padding:16px 18px}
.ficha .cli-card .card-head{margin-bottom:10px}

/* ---- SECCIONES (cada una un BLOQUE delimitado: tarjeta blanca con borde) ---- */
.sec{margin-top:14px;padding:16px 18px;border:1px solid var(--line);border-radius:12px;background:var(--card)}
.sec:first-child{margin-top:16px}
.sec-head{display:flex;align-items:center;justify-content:space-between;gap:10px}
.sec.collapsible .sec-head{cursor:pointer;user-select:none}
.sec-title{display:flex;align-items:center;gap:8px;min-width:0}
.sec-title h4{margin:0;font-size:14px;font-weight:600;letter-spacing:.01em;color:var(--ink)}
.sec-title .count{display:inline-flex;align-items:center;justify-content:center;min-width:20px;height:20px;
  padding:0 6px;border-radius:999px;background:var(--bg-alt);border:1px solid var(--line);
  color:var(--muted-fg);font-size:12px;font-weight:600}
.chev{color:var(--muted-fg);font-size:12px;transition:transform .15s;display:inline-block}
.sec.collapsed .chev{transform:rotate(-90deg)}
.sec.collapsed .sec-body{display:none}
.sec-acts{display:flex;gap:6px;flex-wrap:wrap}
/* El cuerpo se separa del título con una línea divisoria: remate cuadrado y claro. */
.sec-body{margin-top:14px;padding-top:14px;border-top:1px solid var(--line)}

/* Tablas de la ficha (Expedientes/Certificados): cabecera con fondo sutil, filas alineadas. */
.inst-panel .table-wrap{border:1px solid var(--line);border-radius:10px;overflow:auto}
.inst-panel .table-wrap table{font-size:13.5px}
.inst-panel .table-wrap thead th{border-bottom:1px solid var(--line)}
.inst-panel .table-wrap tbody tr:last-child td{border-bottom:0}

/* Pestañas de sección dentro de una instalación (Actividades | Equipos | Expedientes | Certificados).
   Tipografía seria (serif) y grande, como el resto de la web. Solo se muestra la sección activa. */
.sec-tabs{display:flex;gap:2px;flex-wrap:wrap;margin-top:10px;border-bottom:1px solid var(--line)}
.sec-tab{background:none;border:0;border-bottom:2px solid transparent;margin-bottom:-1px;
  padding:9px 15px 11px;cursor:pointer;font-family:var(--font-serif);font-size:17px;font-weight:600;
  color:var(--muted-fg);display:inline-flex;align-items:center;gap:8px;line-height:1.1;
  transition:color .12s,border-color .12s}
.sec-tab:hover{color:var(--ink)}
.sec-tab.active{color:var(--ink);border-bottom-color:var(--brand)}
.sec-tab .tag{font-size:12px;font-family:var(--font-sans);font-weight:600}
.sec-tabhost{margin-top:12px}
/* En modo pestaña la sección NO es tarjeta (el contenedor es el panel) y no repite su título;
   solo se conservan sus botones de acción (+ Equipo, Nuevo expediente…), alineados a la derecha. */
.sec-tabhost .sec{margin:0;padding:0;border:0;border-radius:0;background:transparent}
.sec-tabhost .sec .sec-title{display:none}
.sec-tabhost .sec .sec-head{justify-content:flex-end}
.sec-tabhost .sec .sec-body{margin-top:0;padding-top:0;border-top:0}

/* Título de la instalación con la tipografía seria de la web. */
.inst-title h3{font-family:var(--font-serif);font-size:20px;letter-spacing:-.01em}

/* ---- ESTADOS VACÍOS ---- */
.empty{display:flex;align-items:center;gap:12px;flex-wrap:wrap;padding:12px 14px;
  border:1px dashed var(--line);border-radius:8px;background:var(--bg-alt);color:var(--muted-fg);font-size:13px}
.empty-add{border:1px solid var(--brand);background:#fff;color:var(--brand-ink);border-radius:6px;
  padding:5px 12px;font-size:12.5px;font-weight:600;font-family:inherit;cursor:pointer;transition:background .12s}
.empty-add:hover{background:var(--brand-soft)}

/* ---- ACTIVIDADES ---- */
.act-chips{display:flex;flex-wrap:wrap;gap:6px}
.act-chip{display:inline-block;padding:3px 11px;border-radius:999px;font-size:12.5px;
  border:1px solid var(--line);background:var(--bg-alt);color:var(--body)}
.act-chip.on{border-color:var(--brand-soft);background:var(--brand-soft);color:var(--brand-ink);font-weight:600}
.act-grid{display:grid;grid-template-columns:repeat(auto-fill,minmax(220px,1fr));gap:6px;margin-top:12px;
  padding-top:12px;border-top:1px dashed var(--line)}
.act-opt{display:flex;align-items:center;gap:8px;font-size:13px;padding:6px 10px;border-radius:6px;
  border:1px solid var(--line);cursor:pointer;transition:background .12s,border-color .12s}
.act-opt:hover{background:var(--bg-alt)}
.act-opt.on{border-color:var(--brand-soft);background:var(--brand-soft);color:var(--brand-ink);font-weight:600}
.act-opt input{flex:0 0 auto}

/* ---- EQUIPOS COMO TARJETAS ---- */
.eq-list{display:flex;flex-direction:column;gap:12px}
.eq-card{border:1px solid var(--line);border-radius:8px;padding:14px 16px;background:transparent}
.eq-head{display:flex;justify-content:space-between;align-items:flex-start;gap:10px;flex-wrap:wrap}
.eq-name{display:flex;align-items:baseline;gap:8px;flex-wrap:wrap}
.eq-name strong{font-size:15px}
.eq-name .muted{font-size:12px}
.eq-head .acts{display:flex;gap:6px;flex-wrap:wrap}
.spec-chips{display:flex;flex-wrap:wrap;gap:8px;margin-top:10px}
.spec-chip{display:inline-flex;align-items:baseline;gap:6px;background:#fff;border:1px solid var(--line);
  border-radius:6px;padding:4px 10px;font-size:12.5px}
.spec-chip .k{color:var(--muted-fg)}
.spec-chip .v{font-weight:600;color:var(--ink)}
.nested{margin-top:12px;padding-left:14px;border-left:2px solid var(--line);display:flex;flex-direction:column;gap:4px}
.subrow{display:flex;justify-content:space-between;align-items:center;gap:10px;font-size:13px;padding:3px 0}
.subrow-txt{min-width:0}
.subrow-tag{display:inline-block;font-size:10.5px;text-transform:uppercase;letter-spacing:.03em;
  color:var(--brand-ink);background:var(--brand-soft);border-radius:4px;padding:1px 6px;margin-right:4px;font-weight:700}
.subrow .acts{display:flex;gap:6px;flex:0 0 auto}
.nested .empty{padding:8px 12px}

/* ---- TABLAS (rayado + acciones discretas + tooltip) ---- */
/* Filas uniformes (sin rayado ni fondo al pasar): se separan solo por la línea inferior del td. */
.ficha .tbl tbody tr:hover{background:transparent}
.ficha .tbl th{white-space:nowrap}
.ficha .tbl td.acts{text-align:right;white-space:nowrap;width:1%}
.ficha .tbl td.acts .btn{opacity:.7;transition:opacity .12s}
.ficha .tbl tr:hover td.acts .btn{opacity:1}
.ficha .tbl .hint{color:var(--muted-fg);font-size:11px;cursor:help}
.ficha .tbl .desv{font-variant-numeric:tabular-nums;letter-spacing:.02em}

/* ---- RESPONSIVE (móvil) ---- */
@media (max-width:640px){
  .inst-host{padding:14px}
  .inst-tab{padding:8px 12px}
  /* Tablas de la ficha -> tarjetas apiladas usando la etiqueta data-l */
  .ficha .tbl thead{display:none}
  .ficha .tbl,.ficha .tbl tbody,.ficha .tbl tr,.ficha .tbl td{display:block;width:auto}
  .ficha .tbl tr{border:1px solid var(--line);border-radius:8px;background:#fff;padding:8px 10px;margin-bottom:10px}
  .ficha .tbl tbody tr:nth-child(even){background:#fff}
  .ficha .tbl td{display:flex;justify-content:space-between;gap:16px;align-items:baseline;border:0;padding:5px 0}
  .ficha .tbl td::before{content:attr(data-l);color:var(--muted-fg);font-size:11px;font-weight:600;
    text-transform:uppercase;letter-spacing:.03em;flex:0 0 auto}
  .ficha .tbl td.acts{justify-content:flex-end;width:auto}
  .ficha .tbl td.acts::before{content:none}
  .eq-head .acts{width:100%}
}

/* ---- FASE 1: Nº Industria destacado + su fecha de inscripción al lado, arriba y juntos ---- */
.inst-industria{display:flex;flex-wrap:wrap;align-items:flex-end;gap:6px 24px;margin-top:6px}
.inst-industria .ind-num-wrap,.inst-industria .ind-fecha{display:flex;flex-direction:column;gap:1px}
.inst-industria .ind-label{font-size:10.5px;text-transform:uppercase;letter-spacing:.04em;color:var(--muted-fg)}
.inst-industria .ind-num{font-size:22px;font-weight:800;color:var(--ink);letter-spacing:.01em;line-height:1.05}
.inst-industria .ind-fecha-val{font-size:14px;font-weight:600;color:var(--ink);font-variant-numeric:tabular-nums}

/* ---- FASE 1: desplegables optimizados ---- */
/* Los select con opciones largas ocupan toda la fila de la rejilla: no se corta el texto. */
.fld-ancho{grid-column:1/-1}
/* Estilo uniforme y coherente para TODOS los select del formulario. */
.form-grid select{cursor:pointer;width:100%;text-overflow:ellipsis;padding-right:34px;
  background-image:url("data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='8' viewBox='0 0 12 8'%3E%3Cpath fill='%236b7280' d='M1 1l5 5 5-5'/%3E%3C/svg%3E");
  background-repeat:no-repeat;background-position:right 12px center;-webkit-appearance:none;appearance:none}

/* «En desarrollo», al pie de «Todo lo que gestiona». Separado de la reja de lo disponible por
   una línea y en gris: lo que todavía no existe tiene que LEERSE distinto de lo que sí, o la
   lista de arriba deja de valer. Reutiliza la píldora .soon del panel. */
.gest-soon{display:flex;align-items:baseline;gap:14px;flex-wrap:wrap;
  margin-top:30px;padding-top:22px;border-top:1px solid var(--line)}
.gest-soon ul{display:flex;gap:24px;flex-wrap:wrap;margin:0;padding:0;list-style:none}
.gest-soon li{font-size:13.5px;color:var(--muted-fg)}
@media(max-width:640px){
  .gest-soon{flex-direction:column;gap:10px}
  .gest-soon ul{flex-direction:column;gap:6px}
}

/* ---- FASE 1: marcadores de PDF (estructura preparada, función pendiente) ---- */
.soon{display:inline-block;font-size:10.5px;text-transform:uppercase;letter-spacing:.04em;
  color:var(--muted-fg);background:var(--bg-alt);border:1px dashed var(--line);border-radius:999px;padding:1px 8px}
.pdf-soon{opacity:.62}
.pdf-slot{margin-top:12px;border:1px dashed var(--line);border-radius:8px;padding:10px 12px;background:var(--bg-alt)}
.pdf-slot-head{display:flex;align-items:center;gap:10px}
.pdf-slot-head .btn[disabled]{cursor:not-allowed;opacity:.65}
.pdf-list{margin:8px 0 0;padding-left:20px;font-size:12.5px;color:var(--body);line-height:1.7}
.pdf-note{margin:8px 0 0;font-size:11.5px}
.pdf-mini{display:inline-flex;align-items:center;gap:6px;font-size:12px;color:var(--muted-fg);white-space:nowrap}
.pdf-mini .clip{opacity:.7}

/* ---- FASE 1: carpetas del cliente (estructura, sin función) ---- */
.doc-carpetas--pendiente{list-style:none;padding-left:0}
.doc-carpetas--pendiente li{display:flex;align-items:center;gap:8px;padding:6px 0;opacity:.72}
.doc-carpetas--pendiente .folder-ico{opacity:.8}

/* ===========================================================================
   RESPONSIVE — barrido 17/07 (auditoría). Móvil equilibrado: se ocultan datos
   secundarios de las tablas-ficha; lo esencial (Nombre, Instalac., Equipos,
   Estado) se queda. Las tablas ya pasan a ficha en <=900 (ver el bloque de
   arriba .layout .table-wrap).
   =========================================================================== */

/* Ocultar columnas secundarias en móvil. Actúa en modo ficha (<=900): la cabecera
   está oculta y cada celda lleva su etiqueta data-l, así que basta ocultar el <td>.
   Global por data-l -> mismo criterio en todas las tablas de la app. */
@media(max-width:560px){
  .layout .table-wrap td[data-l="Email"],
  .layout .table-wrap td[data-l="Teléfono"],
  .layout .table-wrap td[data-l="NIF / CIF"],
  .layout .table-wrap td[data-l="Dominio"],
  .layout .table-wrap td[data-l="Auth"],
  .layout .table-wrap td[data-l="Observaciones"]{display:none}
  /* El botón "Exportar base de datos" a lo ancho (el page-head ya lo envuelve). */
  #exportar-bd{width:100%}
  /* Chip "supera X" de dosimetría: que envuelva en vez de desbordar la fila. */
  .tag-excede{white-space:normal}
}

/* Selects rígidos (filtro por rol): sin ancho mínimo forzado en móvil. */
@media(max-width:640px){
  .layout .role-box .rb-filtro select{min-width:0;width:100%}
}

/* ── Documentos del cliente: carpetas en la nube (Azure Blob) ── */
.doc-panel{min-height:120px}
/* Carpetas de la clinica en el panel de la landing. Dos columnas: con una sola, diez nombres
   dejaban el panel tres veces mas alto que el texto de al lado y la seccion quedaba descuadrada.
   El cuadradito de la izquierda es una carpeta insinuada en CSS: ni iconos ni fuentes extra. */
/* Carpetas de la clinica en el panel de la landing.
   PRIMER INTENTO (fallido): texto suelto en dos columnas con un cuadradito de CSS por icono.
   Se veia pobre y descuadrado — los nombres son de largo muy desigual («Contrato» frente a
   «Certificado de aceptacion de equipos»), asi que unas filas ocupaban una linea y otras tres,
   y sin caja que los contuviera la reja parecia rota.
   AHORA: tarjetas, como las que pinta el producto de verdad (.doc-card). Al ser celdas de una
   rejilla, las de una misma fila se estiran solas a la misma altura, asi que un nombre de dos
   lineas ya no descuadra a su vecino. Y la landing pasa a enseñar la UI real, que es lo que
   tiene que hacer la captura de un producto. */
.carpeta-grid{display:grid;grid-template-columns:1fr 1fr;gap:8px;margin:4px 0 2px}
.carpeta{display:flex;align-items:center;gap:9px;padding:10px 11px;
  border:1px solid var(--line);border-radius:var(--radius);background:#fff;
  font-size:12px;line-height:1.3;color:var(--ink)}
.carpeta svg{flex:none;color:var(--muted-fg)}
@media(max-width:560px){ .carpeta-grid{grid-template-columns:1fr} }

.doc-grid{display:grid;grid-template-columns:repeat(auto-fill,minmax(150px,1fr));gap:12px}
.doc-card{display:flex;flex-direction:column;align-items:flex-start;gap:7px;padding:16px 15px;border:1px solid var(--line);border-radius:var(--radius);background:#fff;cursor:pointer;text-align:left;font-family:inherit;color:var(--muted-fg);transition:border-color .15s,box-shadow .15s,transform .05s}
.doc-card:hover{border-color:var(--brand);box-shadow:0 3px 12px color-mix(in oklab,var(--brand) 13%,transparent)}
.doc-card:active{transform:translateY(1px)}
.doc-card-ico{color:var(--muted-fg)}
.doc-card.tiene .doc-card-ico{color:var(--brand)}
.doc-card-nombre{font-weight:600;color:var(--ink);font-size:14px;line-height:1.25}
.doc-card-count{font-size:12px;color:var(--muted-fg)}
.doc-card.tiene .doc-card-count{color:var(--brand-ink);font-weight:600}
.doc-detalle-head{display:flex;align-items:center;gap:12px;margin-bottom:14px;flex-wrap:wrap}
.doc-detalle-head h4{margin:0;flex:1;font-size:16px;color:var(--ink);min-width:120px}
.doc-volver{background:none;border:0;color:var(--brand-ink);font-weight:600;cursor:pointer;font-family:inherit;font-size:14px;padding:4px 2px}
.doc-volver:hover{text-decoration:underline}
.doc-subir-label{cursor:pointer;white-space:nowrap}
.doc-subir-label.cargando{opacity:.6;pointer-events:none}
.doc-files{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:6px}
.doc-file-row{display:flex;align-items:center;gap:11px;padding:10px 12px;border:1px solid var(--line);border-radius:6px;background:#fff}
.doc-file-row:hover{background:var(--bg-alt)}
.doc-file-ico{color:var(--muted-fg);display:flex}
.doc-file-nombre{flex:1;font-size:14px;color:var(--ink);word-break:break-word;line-height:1.3}
.doc-file-meta{font-size:12px;color:var(--muted-fg);white-space:nowrap}
.doc-file-act{display:flex;align-items:center;justify-content:center;background:none;border:0;cursor:pointer;color:var(--muted-fg);padding:5px;border-radius:5px;line-height:0}
.doc-file-act:hover{background:color-mix(in oklab,var(--brand) 12%,transparent);color:var(--brand-ink)}
.doc-file-act.doc-borrar:hover{background:color-mix(in oklab,var(--danger) 12%,transparent);color:var(--danger)}
.doc-vacia{list-style:none;text-align:center;color:var(--muted-fg);padding:28px 12px;font-size:14px;line-height:1.6;border:1px dashed var(--line);border-radius:var(--radius)}

/* --------------------------------------------------------------------------- 
   Autocompletado de código postal (catálogo del INE, migración 25)
   ---------------------------------------------------------------------------
   El panel cuelga del .fld del campo, que pasa a ser el contexto de posición.
   Va al final del fichero a propósito: así no se pisa con lo que otras sesiones
   estén tocando más arriba.
   El z-index tiene que superar al del modal: estos campos viven dentro de uno. */
.ac-host{position:relative}
.ac-panel{
  position:absolute;top:100%;left:0;right:0;z-index:60;
  margin-top:4px;max-height:240px;overflow-y:auto;
  background:var(--card);border:1px solid var(--line);border-radius:var(--radius);
  box-shadow:0 8px 24px rgba(0,0,0,.10);
}
.ac-panel[hidden]{display:none}
.ac-opt{
  display:flex;flex-direction:column;gap:2px;width:100%;
  padding:8px 10px;border:0;background:none;text-align:left;cursor:pointer;
  font:inherit;color:var(--ink);
}
.ac-opt+.ac-opt{border-top:1px solid var(--line)}
.ac-opt:hover,.ac-opt.sel{background:var(--brand-soft)}
.ac-opt-t{font-weight:600}
.ac-opt-s{font-size:12px;color:var(--muted-fg)}
/* «Código postal no encontrado»: informa, no bloquea. Nunca en rojo — no es un
   error, y el usuario puede escribir la localidad a mano igualmente. */
.ac-nota{padding:8px 10px;font-size:13px;color:var(--muted-fg)}

/* ── Documentos: borrar una subcarpeta de año ── */
.doc-card-wrap{position:relative}
.doc-card-wrap .doc-card{width:100%}
.doc-card-del{position:absolute;top:8px;right:8px;display:flex;align-items:center;justify-content:center;width:28px;height:28px;padding:0;line-height:0;background:#fff;border:1px solid var(--line);border-radius:6px;color:var(--muted-fg);cursor:pointer;opacity:.55;transition:opacity .12s,color .12s,border-color .12s}
.doc-card-wrap:hover .doc-card-del{opacity:1}
.doc-card-del:hover{color:var(--danger);border-color:var(--danger)}

/* --------------------------------------------------------------------------- 
   Pantalla de Clínicas: EL BUSCADOR MANDA.
   ---------------------------------------------------------------------------
   Al meter el segundo desplegable (comunidad) en la misma fila, el buscador se
   quedaba encogido a la izquierda pareciendo un detalle, cuando es lo primero
   que se usa. Aquí pasa a ocupar la línea entera y los filtros bajan a una
   segunda fila, en tamaño normal: primero se busca, y solo después se afina.

   Acotado a .visor-busca y NO a .visor-tools: esa la comparten otras pantallas
   (usuarios, etc.) y allí el reparto actual está bien. */
.visor-busca{flex-wrap:wrap;align-items:center;row-gap:10px}
.visor-busca #q{
  flex:1 1 100%;
  font-size:16px;      /* 16px además evita que el móvil haga zoom al enfocar */
  padding:12px 14px;
}
.visor-busca #fv,.visor-busca #fz{flex:0 0 auto;width:auto}
/* El botón de alta se va al extremo, lejos de los filtros: no es un filtro. */
.visor-busca #nuevo{margin-left:auto}
@media(max-width:640px){
  .visor-busca{flex-direction:row}          /* que los filtros compartan fila */
  .visor-busca #fv,.visor-busca #fz{flex:1 1 auto}
  .visor-busca #nuevo{flex:1 1 100%;margin-left:0}
}
/* Desplegables encadenados de ubicación (Provincia -> Localidad -> CP) ------- */
/* El escape a texto libre: discreto, pero visible. Sin él, una dirección que el
   catálogo no contemple no se podría dar de alta. */
.ubi-manual{
  display:block;margin-top:6px;padding:0;border:0;background:none;
  font:inherit;font-size:12px;color:var(--muted-fg);text-decoration:underline;
  cursor:pointer;text-align:left;
}
.ubi-manual:hover{color:var(--brand-ink)}
.fld select[disabled]{opacity:.6}
/* Rejilla de carpetas de documentos: TODAS LA MISMA ALTURA ---------------------
   Al envolver cada tarjeta en .doc-card-wrap (para colgarle la papelera), la
   tarjeta dejó de ser hija directa del grid y perdió el `stretch`: cada una
   pasó a medir según su nombre, y con nombres como «Certificado de aceptación de
   equipos» junto a «Contrato» la rejilla quedaba a saltos. En la rejilla de años
   no se notaba porque todos los nombres miden lo mismo («2026»).
   El wrap estira, y la tarjeta ocupa el wrap entero. */
.doc-grid .doc-card-wrap{display:flex}
.doc-grid .doc-card-wrap > .doc-card{width:100%;height:100%}
/* El nombre empuja el contador abajo: así los contadores quedan alineados entre
   tarjetas aunque el nombre ocupe una o dos líneas. */
.doc-grid .doc-card-nombre{flex:1}
/* Barra superior en MÓVIL: el rol, despegado del correo ----------------------
   .uinfo apila correo y rol SIN separación y se leían como una sola cosa.
   ⚠️ Y NADA MÁS. Se probó a forzar aquí el layout de la barra
   (flex-direction:column + align-self) para «ordenarla», y lo que hizo fue
   empujar el logo a la izquierda y cambiarle la caja. El reparto de la barra ya
   lo resuelve el flex-wrap de más arriba: no tocarlo. */
@media(max-width:640px){
  .uinfo{gap:5px}
  .uinfo .badge{align-self:flex-start}
}

/* Portal del cliente y visor de la UTPR: el NOMBRE del archivo abre el documento
   Se marca al pasar el ratón —color de marca y subrayado— porque un texto que
   hace algo y no lo aparenta no lo pulsa nadie. */
.doc-file-nombre.doc-abrible{cursor:pointer}
.doc-file-nombre.doc-abrible:hover,
.doc-file-nombre.doc-abrible:focus-visible{color:var(--brand-ink);text-decoration:underline}

/* El logo de la barra del panel, en su sitio (móvil) -------------------------
   La regla .wordmark con order:1 de la media query de 900px es del MENÚ DE LA
   WEB PÚBLICA (va con .nav-toggle y .nav-cta para recolocar la cabecera de la
   landing), pero el selector es global y alcanza también al logo del panel.
   Allí los demás elementos van con order:0, así que el logo se iba DETRÁS del
   correo — o sea, debajo, en cuanto la barra se envuelve.
   Se le devuelve su orden SOLO dentro de .topbar: la landing no se toca. */
@media(max-width:900px){
  .layout .topbar .wordmark{order:0}
}

/* ══════════════════════════════════════════════════════════════════════════════════
   DENSIDAD DE LA APLICACION (21/07)
   ══════════════════════════════════════════════════════════════════════════════════
   El panel se veia grande al 100% de zoom. Al medirlo, LA LETRA NO ERA EL PROBLEMA: los tamanos
   dominantes ya eran 13px (45 reglas) y 14px (32), y las celdas de tabla ya tenian 9px de
   relleno. Ademas no hay escala tipografica que bajar: son 215 tamanos en pixeles sueltos y solo
   2 usos de rem, asi que tocar el font-size del html no habria hecho nada.

   Lo que ocupaba era EL AIRE: 30px entre cada tarjeta, 20 de relleno dentro, 32 arriba del
   contenido, y titulos de 24px sobre cuerpo de 13. Esto es, por tanto, una pasada de DENSIDAD.

   VA AL FINAL DEL FICHERO A PROPOSITO. A igual especificidad gana la ultima regla, y las
   originales (.layout .content en la 529, .layout .stack en la 531, .layout .card-head en la
   551, .layout .role-box en la 561) estan mas arriba. Puesto junto a ellas no habria servido
   de nada — y habria pasado igualmente todas las comprobaciones.

   TODO acotado a .layout: .card, th/td, .page-head y .topbar las usa TAMBIEN la web publica.

   NINGUN tamano baja de 11px: el panel se usa muchas horas seguidas, y hacerlo minimalista no
   puede significar hacerlo incomodo de leer. */
.layout .content{padding-top:22px}
.layout .stack{gap:20px}
.layout .card{padding:15px}
.layout .card h2{font-size:15px}
.layout .card-head{padding-bottom:9px;margin-bottom:12px}
.layout .page-head{margin-bottom:2px}
.layout .page-head h1{font-size:20px}
.layout th,.layout td{padding:7px 9px}
.layout th{font-size:11px}
.layout .topbar{padding:11px 20px}
.layout .role-box{padding:18px}

/* LA APP, AL 85%.
   Se pidio «que se vea como si le pusiera el zoom al 85%», y con este CSS es literalmente eso:
   no hay escala tipografica que bajar (215 tamanos en px sueltos, 2 usos de rem), asi que
   reescribir tamanos uno a uno habria sido cientos de reglas y un resultado desigual.

   Va sobre el BODY, no sobre .layout, porque los modales, los avisos y la barra de cookies se
   cuelgan del body: escalando solo .layout apareceria un modal a tamano completo encima de una
   app encogida. La clase la pone shell() al entrar y la quitan home() y renderLogin() al salir,
   asi que la web publica y el login se siguen viendo al 100%.

   ⚠️ EFECTO CONOCIDO: los bordes de 1px pasan a 0.85px. Los navegadores los redondean, asi que
   alguna linea puede verse un pelo mas fina o mas gris. Es el precio de escalar de verdad; la
   alternativa era tocar 215 tamanos a mano.

   Para ajustarlo: este numero, y solo este. */
body.app-compacta{--zoom-app:0.85;zoom:var(--zoom-app)}

/* EL HUECO BLANCO AL PIE.
   `.layout` es `min-height:100vh`. Dentro de un elemento con zoom, ese 100vh se mide en la
   escala reducida: 100vh x 0.85 = 85% de la pantalla, y el 15% restante quedaba en blanco por
   debajo del pie. No es que sobre contenido: es que el armazon se quedaba corto.
   Dividiendo por el mismo factor vuelve a llenar la ventana, y `margin-top:auto` del pie lo
   empuja otra vez al fondo de verdad.
   Se usa la MISMA variable a proposito: si se cambia el zoom y no esto, vuelve el hueco. */
body.app-compacta .layout{min-height:calc(100vh / var(--zoom-app))}
