/* ==================================================================
   DENTAL CARE FAMILY SRL · Sistema de diseño

   El azul marino de la marca (#1F3A93) es el mismo del sello impreso del
   recetario: la pantalla y el papel que el paciente se lleva a casa hablan
   el mismo idioma. Es el unico color de identidad; verde, ambar y rojo son
   estados, no marca.
   ================================================================== */

:root{
  --brand-50:#EEF1FA;  --brand-100:#DAE1F2; --brand-200:#B5C2E3; --brand-300:#8697CE;
  --brand-400:#4E68B4; --brand-500:#1F3A93; --brand-600:#1A3180; --brand-700:#152868;
  --brand-800:#122152; --brand-900:#0F1B42;

  --ink-900:#0F1B34; --ink-800:#1C2B4A; --ink-700:#2E3F62; --ink-600:#3B4A6B;
  --ink-500:#4A5878; --ink-400:#5C6B90; --ink-300:#93A0B8; --ink-200:#CBD4E3;
  --ink-100:#E7ECF5; --ink-50:#F4F7FC;

  --canvas:#F3F5F8;
  --surface:#FFFFFF;
  --line:#E6EBF4;
  --line-soft:#F0F3F9;

  --ok:#10B981; --warn:#F59E0B; --danger:#D73D3D; --info:#0EA5E9; --violet:#8B5CF6;

  --r-sm:8px; --r-md:10px; --r-lg:14px; --r-xl:18px;
  --sh-xs:0 1px 2px rgba(16,32,64,.05);
  --sh-sm:0 1px 3px rgba(16,32,64,.06),0 1px 2px rgba(16,32,64,.04);
  --sh-md:0 4px 16px rgba(16,32,64,.07),0 1px 3px rgba(16,32,64,.04);
  --sh-lg:0 12px 36px rgba(16,32,64,.10),0 2px 8px rgba(16,32,64,.05);
  --sh-xl:0 24px 64px rgba(16,32,64,.14);
  --sh-brand:0 8px 24px rgba(31,58,147,.28);

  --sidebar-w:264px;
  --sidebar-rail:76px;
  --surface-nav:#F8FAFE;   /* la navegacion es su propia capa, no una tarjeta mas */
  --topbar-h:64px;
}

*,*::before,*::after{box-sizing:border-box}
html{-webkit-text-size-adjust:100%;overflow-x:clip}
body{
  /* Nada de decoracion puede crear scroll lateral: un globo de ayuda junto al
     borde derecho ensanchaba el documento. `clip` recorta sin crear un
     contenedor de scroll, asi que los encabezados pegajosos siguen pegados
     —cosa que `hidden` si habria roto—. El contenido ancho de verdad (tablas,
     cintas) desplaza dentro de su propio contenedor. */
  overflow-x:clip;
  margin:0; background:var(--canvas); color:var(--ink-900);
  font-family:'Schibsted Grotesk',-apple-system,BlinkMacSystemFont,'Segoe UI',Helvetica,Arial,sans-serif;
  font-size:14px; line-height:1.55; -webkit-font-smoothing:antialiased; -moz-osx-font-smoothing:grayscale;
  font-feature-settings:'cv02','cv03','cv04','tnum' 0;
}
h1,h2,h3,h4,h5{margin:0; font-weight:700; letter-spacing:-.015em; color:var(--ink-900); line-height:1.25; text-wrap:balance}
/* La voz de display se reserva a los titulares: da caracter sin tocar la
   legibilidad de etiquetas, tablas y formularios. */
h1{font-family:'Bricolage Grotesque','Schibsted Grotesk',sans-serif;font-weight:800;letter-spacing:-.032em}
h2{letter-spacing:-.022em}
.display{font-family:'Bricolage Grotesque','Schibsted Grotesk',sans-serif;font-weight:800;letter-spacing:-.038em;line-height:1.02}
:is(h1,h2,h3,h4,h5)+p{margin-top:.35em}
p{margin:0}
a{color:inherit; text-decoration:none}
img,svg{display:block; max-width:100%}
button,input,select,textarea{font:inherit; color:inherit}
hr{border:0;border-top:1px solid var(--line);margin:0}
[hidden]{display:none !important}
/* Tailwind se inyecta antes que esta hoja, asi que los componentes que
   fijan display ganaban a .hidden y el estado oculto no se aplicaba.
   Esta regla es mas especifica que ambos y no usa !important, para no
   romper utilidades responsive del tipo "hidden sm:inline". */
.btn.hidden,
.chip.hidden,
.card-head.hidden,
.cal-grid.hidden,
.carga.hidden,
.check.hidden,
.empty.hidden,
.empty-ico.hidden,
.err-msg.hidden,
.field.hidden,
.input-group.hidden,
.kbd.hidden,
.mini-cal.hidden,
.modal-foot.hidden,
.modal-head.hidden,
.odo-svg.hidden,
.seg.hidden,
.stat-ico.hidden,
.stat-trend.hidden,
.switch.hidden,
.tabs.hidden,
.toast-ico.hidden,
.truncate-2.hidden,
.truncate-3.hidden{display:none}

::selection{background:var(--brand-100); color:var(--brand-800)}
input,textarea,[contenteditable]{caret-color:var(--brand-500)}
a{text-underline-offset:.18em;text-decoration-thickness:from-font}
:focus-visible{outline:2px solid var(--brand-500);outline-offset:2px;border-radius:4px}

/* Editor de documentos del profesional */
.rx-editor{display:grid;grid-template-columns:minmax(340px,1fr) minmax(380px,1fr);gap:24px;align-items:start}
.rx-settings{display:grid;gap:20px;min-width:0}
.rx-fields{padding:20px;display:grid;gap:18px}
.rx-grid{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:16px}
.rx-style-picker{display:grid;gap:8px}
.rx-style{display:flex;align-items:center;gap:12px;padding:12px 14px;border:1px solid var(--line);border-radius:10px;cursor:pointer}
.rx-style:has(input:checked){background:var(--brand-50);border-color:var(--brand-400)}
.rx-style strong{font-size:13px;display:block}.rx-style small{font-size:12px;color:var(--ink-500);display:block;margin-top:2px}
.rx-editor input[type=radio],.rx-editor input[type=checkbox]{accent-color:var(--brand-600);width:16px;height:16px;flex-shrink:0}
.rx-checks{display:grid;grid-template-columns:1fr 1fr;gap:14px}.rx-checks label{display:flex;align-items:center;gap:8px;font-size:12.5px}
.rx-help{font-size:12px;line-height:1.6;color:var(--ink-500)}
.rx-assets{display:grid;gap:22px}.rx-assets input[type=file]{height:auto;padding:10px;font-size:12px;max-width:100%}
.rx-asset{height:76px;max-width:170px;object-fit:contain;margin:10px 0;background:white;border:1px solid var(--line);padding:8px}
.rx-remove{display:flex;align-items:center;gap:8px;font-size:12px;margin:8px 0;color:var(--danger)}
.rx-preview-panel{position:sticky;top:84px;min-width:0;border:1px solid var(--line);border-radius:14px;overflow:hidden;background:var(--surface)}
.rx-preview-head{padding:20px 20px 12px}.rx-preview-head h2{font-size:17px}.rx-preview-head p{font-size:12px;color:var(--ink-500);margin-top:6px}
.rx-preview-actions{display:flex;gap:8px;flex-wrap:wrap;padding:0 20px 16px}
.rx-preview-frame{display:block;width:100%;height:620px;border:0;background:#E7EBF0}
.rx-preview-panel>.rx-help{padding:14px 20px}
.rx-doctor-bar{display:flex;align-items:center;gap:14px;flex-wrap:wrap;margin-bottom:22px;background:var(--surface);border:1px solid var(--line);padding:16px 20px;border-radius:12px}
.rx-doctor-bar>label{font-size:13px;font-weight:600}.rx-doctor-bar>.select{max-width:330px}.rx-doctor-bar>span{font-size:12px;color:var(--ink-500)}
.rx-error{padding:12px 18px;margin-bottom:18px;border:1px solid #FECACA;background:#FEF2F2;color:#991B1B;border-radius:10px}
@media(max-width:1100px){.rx-editor{grid-template-columns:1fr}.rx-preview-panel{position:static}.rx-preview-frame{height:640px}}
@media(max-width:540px){.rx-grid,.rx-checks{grid-template-columns:1fr}.rx-fields{padding:16px}.rx-preview-actions .btn{flex:1}.rx-doctor-bar>.select{max-width:100%;width:100%}}

/* Salto al contenido: fuera de la vista hasta que el tabulador llega a el.
   Sin esto habia que atravesar 36 paradas —el menu entero— en cada pantalla. */
.salto-contenido{
  position:absolute;left:12px;top:-60px;z-index:100;
  background:var(--brand-600);color:#fff;font-size:13px;font-weight:600;
  padding:9px 16px;border-radius:0 0 10px 10px;box-shadow:var(--sh-md);
  transition:top .16s ease;
}
.salto-contenido:focus{top:0}

/* Buscador desplegado en telefono: ocupa la barra entera mientras dura. */
body.buscando #fBuscarGlobal{display:block;flex:1 1 auto;max-width:none}
body.buscando .app-top-acciones,body.buscando [data-buscar]{display:none}
table{font-variant-numeric:tabular-nums}

/* ---------- Scrollbars ---------- */
/* Firefox no entiende los pseudoelementos de WebKit: sin esto conservaba las
   barras del sistema, que no pertenecen a ningun diseno. */
*{scrollbar-width:thin;scrollbar-color:#CBD5E5 transparent}
*::-webkit-scrollbar{width:10px;height:10px}
*::-webkit-scrollbar-track{background:transparent}
*::-webkit-scrollbar-thumb{background:#CBD5E5;border-radius:99px;border:3px solid transparent;background-clip:content-box}
*::-webkit-scrollbar-thumb:hover{background:#93A0B8;background-clip:content-box;border:3px solid transparent}
.scroll-thin::-webkit-scrollbar{width:6px;height:6px}
.scroll-none::-webkit-scrollbar{display:none}
.scroll-none{scrollbar-width:none;-ms-overflow-style:none}

/* ==================================================================
   Superficies
   ================================================================== */
.card{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-lg)}
.card-flat{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-lg)}
.card-hover{transition:box-shadow .22s cubic-bezier(.4,0,.2,1),transform .22s cubic-bezier(.4,0,.2,1),border-color .22s}
.card-hover:hover{box-shadow:var(--sh-md);transform:translateY(-2px);border-color:var(--ink-200)}
.card-pad{padding:20px}
.card-head{display:flex;align-items:center;justify-content:space-between;flex-wrap:wrap;gap:10px 14px;padding:16px 20px;border-bottom:1px solid var(--line-soft)}
.card-title{font-size:15px;font-weight:700;letter-spacing:-.01em}
.card-sub{font-size:12.5px;color:var(--ink-500);margin-top:2px}

.panel{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-lg);overflow:hidden}
.glass{background:rgba(255,255,255,.82);backdrop-filter:blur(14px);-webkit-backdrop-filter:blur(14px)}

/* ==================================================================
   Botones
   ================================================================== */
.btn{
  display:inline-flex;align-items:center;justify-content:center;gap:8px;
  height:40px;padding:0 16px;border-radius:var(--r-md);border:1px solid transparent;
  font-size:13.5px;font-weight:600;letter-spacing:-.005em;cursor:pointer;white-space:nowrap;
  transition:background .16s,color .16s,border-color .16s,box-shadow .16s,transform .12s;
  user-select:none;
}
.btn:active{transform:translateY(1px)}
.btn:disabled,.btn[disabled]{opacity:.5;cursor:not-allowed;transform:none}
.btn:focus-visible{outline:2px solid var(--brand-400);outline-offset:2px}

.btn-primary{background:var(--brand-500);color:#fff;box-shadow:0 1px 2px rgba(16,32,64,.12)}
.btn-primary:hover:not(:disabled){background:var(--brand-600);box-shadow:var(--sh-brand)}
.btn-dark{background:var(--ink-900);color:#fff}
.btn-dark:hover:not(:disabled){background:var(--ink-800)}
.btn-light{background:var(--surface);color:var(--ink-700);border-color:var(--line)}
.btn-light:hover:not(:disabled){background:var(--ink-50);border-color:var(--ink-200);color:var(--ink-900)}
.btn-soft{background:var(--brand-50);color:var(--brand-700)}
.btn-soft:hover:not(:disabled){background:var(--brand-100)}
.btn-ghost{background:transparent;color:var(--ink-600)}
.btn-ghost:hover:not(:disabled){background:var(--ink-50);color:var(--ink-900)}
.btn-danger{background:var(--danger);color:#fff}
.btn-danger:hover:not(:disabled){background:#DC2626}
.btn-danger-soft{background:#FEF2F2;color:#B91C1C}
.btn-danger-soft:hover:not(:disabled){background:#FEE2E2}
.btn-success{background:var(--ok);color:#fff}
.btn-success:hover:not(:disabled){background:#059669}
.btn-success-soft{background:#ECFDF5;color:#047857}
.btn-success-soft:hover:not(:disabled){background:#D1FAE5}
.btn-warn-soft{background:#FFFBEB;color:#B45309}
.btn-warn-soft:hover:not(:disabled){background:#FEF3C7}

.btn-sm{height:34px;padding:0 12px;font-size:12.5px;border-radius:var(--r-sm);gap:6px}
.btn-xs{height:28px;padding:0 10px;font-size:12px;border-radius:9px;gap:5px}
.btn-lg{height:48px;padding:0 24px;font-size:15px;border-radius:var(--r-md)}
.btn-icon{width:40px;padding:0}
.btn-icon.btn-sm{width:34px}
.btn-icon.btn-xs{width:28px}
.btn-block{width:100%}

/* Icon action button (tabla) */
.ico-btn{
  display:inline-grid;place-items:center;width:32px;height:32px;border-radius:9px;
  color:var(--ink-400);background:transparent;border:1px solid transparent;cursor:pointer;
  transition:.16s;
}
.ico-btn:hover{background:var(--ink-50);color:var(--ink-800);border-color:var(--line)}
.ico-btn:active{transform:scale(.94)}
.ico-btn:focus-visible{outline:2px solid var(--brand-500);outline-offset:2px}
.ico-btn:disabled,.ico-btn[disabled]{opacity:.45;cursor:not-allowed;pointer-events:none}
.ico-btn.danger:hover{background:#FEF2F2;color:#DC2626;border-color:#FECACA}
.ico-btn.ok:hover{background:#ECFDF5;color:#047857;border-color:#A7F3D0}

/* ==================================================================
   Formularios
   ================================================================== */
.field{display:flex;flex-direction:column;gap:6px;min-width:0}
.label{font-size:12.5px;font-weight:600;color:var(--ink-600);letter-spacing:-.005em}
/* El asterisco de obligatorio se estilaba solo dentro de .label, asi que el
   unico que vive fuera salia en gris y descolocado. Ahora vale en cualquier
   contexto. */
.req{color:var(--danger);margin-left:2px}
.hint{font-size:11.5px;color:var(--ink-400)}
.err-msg{font-size:11.5px;color:#DC2626;display:flex;align-items:center;gap:4px}

.input,.select,.textarea{
  width:100%;height:42px;padding:0 13px;background:var(--surface);
  border:1px solid var(--ink-200);border-radius:var(--r-md);
  font-size:13.5px;color:var(--ink-900);
  transition:border-color .16s,box-shadow .16s,background .16s;
}
.textarea{height:auto;min-height:92px;padding:11px 13px;line-height:1.55;resize:vertical}
.input::placeholder,.textarea::placeholder{color:var(--ink-400);opacity:1}
.input:hover,.select:hover,.textarea:hover{border-color:var(--ink-300)}
.input:focus,.select:focus,.textarea:focus{
  outline:none;border-color:var(--brand-500);box-shadow:0 0 0 3.5px rgba(31,58,147,.13);background:#fff;
}
.input:disabled,.select:disabled,.textarea:disabled{background:var(--ink-50);color:var(--ink-400);cursor:not-allowed}
.input.is-error,.select.is-error,.textarea.is-error{border-color:#F87171;box-shadow:0 0 0 3.5px rgba(239,68,68,.10)}
.input-sm{height:36px;font-size:12.5px;border-radius:var(--r-sm)}
/* Boton nativo del selector de archivo: sin esto era gris del sistema y
   destacaba en oscuro. Con tokens combina en ambos temas. */
input[type=file]::file-selector-button{
  margin:-2px 12px -2px -2px;padding:7px 13px;border:1px solid var(--line);border-radius:var(--r-sm);
  background:var(--ink-50);color:var(--ink-700);font:inherit;font-weight:600;font-size:12px;cursor:pointer;
  transition:background .16s,border-color .16s,color .16s;
}
input[type=file]::file-selector-button:hover{background:var(--ink-100);border-color:var(--ink-200);color:var(--ink-900)}

.select{
  appearance:none;-webkit-appearance:none;padding-right:38px;cursor:pointer;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='16' height='16' viewBox='0 0 24 24' fill='none' stroke='%237D8CA8' stroke-width='2.2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpolyline points='6 9 12 15 18 9'/%3E%3C/svg%3E");
  background-repeat:no-repeat;background-position:right 13px center;
}
.select[multiple]{height:auto;padding:8px;background-image:none}

.input-group{position:relative;display:flex;align-items:center}
.input-group .input{padding-left:40px}
.input-group>.ig-icon{position:absolute;left:13px;color:var(--ink-400);pointer-events:none;display:flex}
.input-group.right .input{padding-left:13px;padding-right:40px}
.input-group.right>.ig-icon{left:auto;right:13px}
.input-prefix{
  position:absolute;left:1px;top:1px;bottom:1px;display:grid;place-items:center;
  padding:0 12px;color:var(--ink-400);font-size:12.5px;font-weight:600;
  border-right:1px solid var(--line);background:var(--ink-50);border-radius:var(--r-md) 0 0 var(--r-md);
}
.input-group.prefixed .input{padding-left:58px}

/* Checkbox / Radio */
.check{display:inline-flex;align-items:center;gap:9px;cursor:pointer;user-select:none;font-size:13px}
.check input[type=checkbox],.check input[type=radio]{
  appearance:none;-webkit-appearance:none;width:18px;height:18px;flex:0 0 18px;
  border:1.8px solid var(--ink-300);border-radius:6px;background:#fff;cursor:pointer;
  transition:.16s;position:relative;
}
.check input[type=radio]{border-radius:50%}
.check input:checked{background:var(--brand-500);border-color:var(--brand-500)}
.check input[type=checkbox]:checked::after{
  content:'';position:absolute;left:5px;top:1.5px;width:5px;height:10px;
  border:solid #fff;border-width:0 2.2px 2.2px 0;transform:rotate(43deg);
}
.check input[type=radio]:checked::after{
  content:'';position:absolute;left:50%;top:50%;width:7px;height:7px;border-radius:50%;
  background:#fff;transform:translate(-50%,-50%);
}
.check input:focus-visible{outline:2px solid var(--brand-400);outline-offset:2px}
.check input:disabled{background:var(--ink-100);border-color:var(--ink-200);cursor:not-allowed}

/* Switch */
.switch{position:relative;display:inline-flex;align-items:center;gap:10px;cursor:pointer;user-select:none;font-size:13px}
.switch input{appearance:none;-webkit-appearance:none;width:40px;height:23px;flex:0 0 40px;background:var(--ink-200);border-radius:99px;cursor:pointer;transition:.22s;position:relative}
.switch input::after{content:'';position:absolute;top:2.5px;left:2.5px;width:18px;height:18px;border-radius:50%;background:#fff;box-shadow:0 1px 3px rgba(0,0,0,.2);transition:.22s cubic-bezier(.4,0,.2,1)}
.switch input:checked{background:var(--brand-500)}
.switch input:checked::after{transform:translateX(17px)}
.switch input:focus-visible{outline:2px solid var(--brand-400);outline-offset:2px}

/* Segmented control (tabs pill) */
.seg{display:inline-flex;padding:4px;background:var(--ink-50);border:1px solid var(--line);border-radius:var(--r-md);gap:2px}
.seg-item{
  display:inline-flex;align-items:center;gap:7px;padding:7px 15px;border-radius:10px;
  font-size:13px;font-weight:600;color:var(--ink-500);cursor:pointer;border:none;background:transparent;
  transition:.18s;white-space:nowrap;
}
.seg-item:hover{color:var(--ink-800)}
.seg-item:focus-visible{outline:2px solid var(--brand-500);outline-offset:-2px;border-radius:10px}
.seg-item:disabled,.seg-item[disabled]{opacity:.45;cursor:not-allowed}
.seg-item.active{background:#fff;color:var(--brand-600);box-shadow:var(--sh-sm)}

/* En pantallas estrechas el conmutador no cabe: con tres pestanas la ultima
   quedaba fuera de la ventana y era inalcanzable, porque .seg no desplaza ni
   envuelve. Se desplaza en horizontal en lugar de desbordar, que es la unica
   salida que conserva las etiquetas enteras. */
@media (max-width:640px){
  .seg{display:flex;max-width:100%;overflow-x:auto;scrollbar-width:none;-webkit-overflow-scrolling:touch}
  .seg::-webkit-scrollbar{display:none}
  .seg-item{flex:none}
}

/* Tabs underline */
.tabs{display:flex;gap:26px;border-bottom:1px solid var(--line);overflow-x:auto}
.tab{
  position:relative;padding:13px 1px;font-size:13.5px;font-weight:600;color:var(--ink-400);
  white-space:nowrap;transition:color .18s;cursor:pointer;background:none;border:none;
}
.tab:hover{color:var(--ink-700)}
.tab:focus-visible{outline:2px solid var(--brand-500);outline-offset:3px;border-radius:6px;color:var(--ink-700)}
.tab.active{color:var(--brand-600)}
.tab.active::after{
  content:'';position:absolute;left:0;right:0;bottom:-1px;height:2.5px;border-radius:3px 3px 0 0;
  background:var(--brand-500);animation:tabIn .28s cubic-bezier(.4,0,.2,1);
}
@keyframes tabIn{from{transform:scaleX(.3);opacity:0}to{transform:scaleX(1);opacity:1}}

/* ==================================================================
   Tablas
   ================================================================== */
/* Las tablas no caben ni en escritorio (pacientes se pasa 55 px, inventario
   170), asi que desplazan de lado. Estas sombras aparecen solo del lado que
   esconde columnas: las capas blancas van en `local` y viajan con el
   contenido, las sombras en `scroll` y se quedan pegadas a la caja. Sin una
   linea de JavaScript. */
.tbl-wrap{
  overflow-x:auto;-webkit-overflow-scrolling:touch;
  background:
    linear-gradient(to right, var(--surface) 30%, rgba(255,255,255,0)) left center,
    linear-gradient(to left,  var(--surface) 30%, rgba(255,255,255,0)) right center,
    radial-gradient(farthest-side at 0 50%,   rgba(15,27,52,.14), rgba(15,27,52,0)) left center,
    radial-gradient(farthest-side at 100% 50%,rgba(15,27,52,.14), rgba(15,27,52,0)) right center;
  background-repeat:no-repeat;
  background-size:38px 100%, 38px 100%, 15px 100%, 15px 100%;
  background-attachment:local, local, scroll, scroll;
}
/* Cuando la tabla cabe, la envoltura deja de recortar y la cabecera puede
   anclarse a la pagina. Lo decide tablas.js midiendo; el estado por defecto
   —con desplazamiento lateral— es el seguro si ese guion no llega. */
.tbl-wrap.tbl-cabe{overflow:visible;background:none}
/* El desplazamiento de 64px —la altura de la barra superior, que tambien es
   sticky— solo vale cuando la cabecera se ancla a la pagina. Si la tabla no
   cabe, la envoltura vuelve a ser el contenedor de desplazamiento y el sticky
   se ancla a ella, donde no hay barra: esos 64px empujaban la cabecera por
   debajo de la primera fila. */
.tbl-wrap.tbl-cabe .tbl thead th{top:64px}

/* La tarjeta que envuelve una tabla no puede recortar: el `overflow-hidden`
   del marcado la convertia en el contenedor de referencia del sticky y, como
   no hace scroll vertical, la cabecera nunca se quedaba. Las esquinas
   redondeadas se conservan mas abajo, en las celdas. */
.card:has(> .tbl-wrap){overflow:visible !important}
.card:has(> .tbl-wrap) .tbl tbody tr:last-child td:first-child{border-bottom-left-radius:var(--r-lg)}
.card:has(> .tbl-wrap) .tbl tbody tr:last-child td:last-child{border-bottom-right-radius:var(--r-lg)}
.card > .tbl-wrap:first-child .tbl thead th:first-child{border-top-left-radius:var(--r-lg)}
.card > .tbl-wrap:first-child .tbl thead th:last-child{border-top-right-radius:var(--r-lg)}

.tbl{width:100%;border-collapse:separate;border-spacing:0;font-size:13px}
.tbl thead th{
  position:sticky;top:0;z-index:5;background:var(--ink-50);
  padding:11px 16px;text-align:left;font-size:11px;font-weight:700;letter-spacing:.05em;
  text-transform:uppercase;color:var(--ink-400);white-space:nowrap;border-bottom:1px solid var(--line);
}
.tbl tbody td{padding:13px 16px;border-bottom:1px solid var(--line-soft);color:var(--ink-700);vertical-align:middle}
.tbl tbody tr{transition:background .14s}
.tbl tbody tr:hover{background:#FAFBFE}
.tbl tbody tr:last-child td{border-bottom:none}
.tbl .num{text-align:right;font-variant-numeric:tabular-nums;white-space:nowrap}
.tbl .center{text-align:center}
.tbl-compact tbody td{padding:9px 14px}
.tbl-compact thead th{padding:9px 14px}

/* Rejilla de captura: el reparto lo mandan los porcentajes, no el contenido.
   Con `auto`, un `<select>` de servicios se ensancha hasta su opcion mas larga y
   la tabla de conceptos pedia 853px en una columna de 730: el importe de la
   linea y el boton de quitar quedaban fuera del recorte. Los campos encogen; el
   texto largo se corta con puntos suspensivos. */
.tbl.tbl-rejilla{table-layout:fixed}
.tbl-rejilla .select,.tbl-rejilla .input{max-width:100%}
.tbl-rejilla td>.select+.input{margin-top:5px}
.tbl a.link{color:var(--brand-600);font-weight:600;white-space:nowrap}  /* un codigo no se parte */
.tbl a.link:hover{text-decoration:underline}
.tbl a.link:focus-visible{outline:2px solid var(--brand-500);outline-offset:2px;border-radius:5px;text-decoration:underline}
.row-click{cursor:pointer}

.sortable{cursor:pointer;user-select:none}
.sortable:hover{color:var(--ink-600)}
.sortable .arrow{opacity:.35;display:inline-block;margin-left:3px}
.sortable.asc .arrow,.sortable.desc .arrow{opacity:1;color:var(--brand-500)}

/* ==================================================================
   Chips / Badges
   ================================================================== */
.chip{
  display:inline-flex;align-items:center;gap:6px;padding:5px 11px;border-radius:99px;
  font-size:12px;font-weight:600;background:var(--ink-50);color:var(--ink-600);
  border:1px solid var(--line);white-space:nowrap;
}
.chip-btn{cursor:pointer;transition:.16s}
.chip-btn:hover{background:var(--ink-100);border-color:var(--ink-200)}
/* Reloj de espera del tablero de recepcion.
   Su color lo pone JavaScript, asi que no puede depender de utilidades de
   Tailwind: el CDN solo genera las clases que ve en el HTML inicial. */
.chip-espera{background:#FFFBEB;color:#B45309;border-color:#FDE68A}
.chip-espera.alta{background:#FEF2F2;color:#B91C1C;border-color:#FECACA}
.chip-btn:focus-visible{outline:2px solid var(--brand-500);outline-offset:2px}
.chip-btn:disabled,.chip-btn[disabled]{opacity:.45;cursor:not-allowed}
.chip-btn.active{background:var(--brand-500);color:#fff;border-color:var(--brand-500);box-shadow:0 2px 8px rgba(31,58,147,.25)}

.dot{width:7px;height:7px;border-radius:50%;flex:0 0 7px}
.pulse-dot{position:relative}
.pulse-dot::after{
  content:'';position:absolute;inset:-3px;border-radius:50%;background:inherit;opacity:.4;
  animation:pulseRing 1.8s cubic-bezier(.4,0,.6,1) infinite;
}
@keyframes pulseRing{0%{transform:scale(.8);opacity:.5}70%{transform:scale(2);opacity:0}100%{opacity:0}}

/* ==================================================================
   Estadísticas
   ================================================================== */
.stat{
  background:var(--surface);border:1px solid var(--line);border-radius:var(--r-lg);padding:18px 20px;
  position:relative;overflow:hidden;transition:.24s cubic-bezier(.4,0,.2,1);
}
.stat:hover{box-shadow:var(--sh-md);transform:translateY(-2px)}
.stat-label{font-size:12px;font-weight:600;color:var(--ink-400);letter-spacing:.01em}
.stat-value{font-size:26px;font-weight:800;letter-spacing:-.03em;color:var(--ink-900);margin-top:6px;font-variant-numeric:tabular-nums}
.stat-ico{width:40px;height:40px;border-radius:12px;display:grid;place-items:center;flex:0 0 40px}
.stat-trend{display:inline-flex;align-items:center;gap:3px;font-size:12px;font-weight:700;padding:3px 8px;border-radius:99px}
.stat-trend.up{background:#ECFDF5;color:#047857}
.stat-trend.down{background:#FEF2F2;color:#B91C1C}
.stat-trend.flat{background:var(--ink-50);color:var(--ink-500)}
/* La curva es fondo, no dato: se queda por debajo del texto y no compite con
   el, que antes se leia cruzado por la linea. La tarjeta reserva su altura. */
.stat-spark{position:absolute;right:0;bottom:0;left:0;height:42px;opacity:.42;pointer-events:none;z-index:0}
.stat:has(.stat-spark){padding-bottom:34px}
.stat > *{position:relative;z-index:1}

/* ==================================================================
   Sidebar / Navegación
   ================================================================== */
.nav-item{
  display:flex;align-items:center;gap:11px;padding:9px 12px;border-radius:11px;
  font-size:13.5px;font-weight:550;color:var(--ink-500);transition:.16s;position:relative;
}
.nav-item:hover{background:#fff;color:var(--ink-900)}
.nav-item:focus-visible{outline:2px solid var(--brand-500);outline-offset:-2px}
.nav-item.active{background:var(--brand-50);color:var(--brand-700);font-weight:650}
.nav-item.active::before{
  content:'';position:absolute;left:-12px;top:50%;transform:translateY(-50%);
  width:3px;height:20px;border-radius:0 3px 3px 0;background:var(--brand-500);
}
.nav-item .ni-ico{flex:0 0 18px;opacity:.85}
.nav-item.active .ni-ico{opacity:1}
.nav-group{
  font-size:10.5px;font-weight:700;letter-spacing:.09em;text-transform:uppercase;
  color:var(--ink-400);padding:0 12px;margin:22px 0 6px;
}
.nav-badge{margin-left:auto;font-size:10.5px;font-weight:700;padding:2px 7px;border-radius:99px;background:var(--brand-500);color:#fff;line-height:1.5}
/* Ambar con tinta oscura: blanco sobre ambar daba 2.15:1 */
.nav-badge.warn{background:var(--warn);color:#4A2E05}
.nav-badge.soft{background:var(--ink-100);color:var(--ink-500)}

/* ---------- Riel: la navegacion se reduce a iconos ----------
   El estado vive en <html> para que se aplique antes del primer pintado
   y no haya salto al restaurarlo de localStorage.                      */
/* En movil el cajon conserva su ancho fijo: --sidebar-w vale 0 bajo el
   breakpoint y dejaria la barra sin caja. El riel es solo de escritorio. */
.sidebar{width:264px}
.sb-toggle{display:none}
@media (min-width:1024px){
  /* El colapso cambia el ancho, y animarlo refluye toda la pagina en cada
     fotograma (con graficos dentro). Se resuelve de golpe y son las
     etiquetas las que se atenuan. */
  .sidebar{width:var(--sidebar-w)}
  .sidebar .nav-text,.sidebar .sb-marca,.sidebar .sb-user-tx{transition:opacity .14s ease-out}
  .sb-toggle{display:inline-grid}
  html.nav-rail .sidebar{width:var(--sidebar-rail)}
  html.nav-rail .sidebar .nav-text,
  html.nav-rail .sidebar .sb-marca,
  html.nav-rail .sidebar .sb-user-tx{display:none}
  html.nav-rail .sidebar .nav-item{justify-content:center;padding:10px;gap:0}
  html.nav-rail .sidebar .nav-item.active::before{left:-9px}
  html.nav-rail .sidebar .nav-group{height:1px;padding:0;margin:14px 10px;background:var(--line);overflow:hidden;color:transparent}
  html.nav-rail .sidebar .nav-badge{position:absolute;top:5px;right:5px;min-width:8px;height:8px;padding:0;
    font-size:0;border-radius:99px;line-height:0}
  html.nav-rail .sidebar .sb-cab{justify-content:center;padding:0 10px}
  html.nav-rail .sidebar .sb-user{justify-content:center}
  html.nav-rail .sidebar nav{padding-left:10px;padding-right:10px}
  /* En riel la etiqueta viaja al tooltip */
  html.nav-rail .sidebar .nav-item::after{
    content:attr(data-label);position:absolute;left:calc(100% + 10px);top:50%;transform:translateY(-50%) translateX(-4px);
    padding:6px 10px;background:var(--ink-900);color:#fff;font-size:12px;font-weight:600;border-radius:8px;
    white-space:nowrap;opacity:0;pointer-events:none;transition:opacity .16s,transform .16s;z-index:80;box-shadow:var(--sh-md)}
  html.nav-rail .sidebar .nav-item:hover::after,
  html.nav-rail .sidebar .nav-item:focus-visible::after{opacity:1;transform:translateY(-50%) translateX(0)}
}

/* ==================================================================
   Dropdown / Popover
   ================================================================== */
.dd{position:relative}
.dd-menu{
  position:absolute;z-index:60;min-width:210px;padding:6px;
  background:#fff;border:1px solid var(--line);border-radius:var(--r-md);box-shadow:var(--sh-lg);
  opacity:0;visibility:hidden;transform:translateY(-6px) scale(.98);transform-origin:top right;
  transition:opacity .16s,transform .16s,visibility .16s;
}
.dd.open>.dd-menu{opacity:1;visibility:visible;transform:translateY(0) scale(1)}
/* Dentro de una tabla con scroll el menu absoluto queda recortado:
   al abrirse se fija en coordenadas de viewport (ver app.js). */
.dd-menu.flotante{position:fixed;margin:0}
/* Fuera de su .dd el menu ya no hereda el estado abierto */
.dd-menu.flotante.abierto{opacity:1;visibility:visible;transform:none}
.dd-right{right:0}
.dd-left{left:0;transform-origin:top left}
.dd-item{
  display:flex;align-items:center;gap:10px;width:100%;padding:9px 11px;border-radius:9px;
  font-size:13px;color:var(--ink-700);cursor:pointer;transition:.14s;text-align:left;border:none;background:none;
}
.dd-item:hover{background:var(--ink-50);color:var(--ink-900)}
.dd-item:focus-visible{outline:2px solid var(--brand-500);outline-offset:-2px}
.dd-item.danger{color:#DC2626}
.dd-item.danger:hover{background:#FEF2F2}
.dd-sep{height:1px;background:var(--line);margin:5px 0}
.dd-head{padding:9px 11px 5px;font-size:11px;font-weight:700;letter-spacing:.06em;text-transform:uppercase;color:var(--ink-400)}

/* ==================================================================
   Modal / Drawer
   ================================================================== */
.modal-back{
  position:fixed;inset:0;z-index:90;background:rgba(15,27,52,.42);backdrop-filter:blur(3px);
  display:flex;align-items:center;justify-content:center;padding:20px;
  opacity:0;visibility:hidden;transition:opacity .22s,visibility .22s;overflow-y:auto;
}
.modal-back.open{opacity:1;visibility:visible}
.modal{
  width:100%;max-width:600px;background:#fff;border-radius:var(--r-xl);box-shadow:var(--sh-xl);
  transform:translateY(18px) scale(.97);transition:transform .28s cubic-bezier(.16,1,.3,1);
  max-height:92vh;display:flex;flex-direction:column;margin:auto;
}
.modal-back.open .modal{transform:translateY(0) scale(1)}
/* Casi todos los modales envuelven cabecera, cuerpo y pie en un <form>, y ese
   <form> es el unico hijo flexible de .modal: el `flex:1` del cuerpo colgaba de
   un padre que no era el contenedor flexible, asi que no se aplicaba. En una
   pantalla baja —un telefono pequeno, o cualquiera en horizontal— el contenido
   se salia de la tarjeta blanca y el pie, con el boton de guardar, caia 700px
   por debajo de la vista. Medido en el alta de sucursal: pie a 1296px en una
   ventana de 600. */
.modal>form{display:flex;flex-direction:column;min-height:0;flex:1 1 auto}
.modal-head{display:flex;align-items:flex-start;justify-content:space-between;gap:16px;padding:22px 24px 0}
.modal-body{padding:20px 24px;overflow-y:auto;flex:1}
.modal-foot{display:flex;align-items:center;justify-content:flex-end;gap:10px;padding:16px 24px;border-top:1px solid var(--line);background:var(--ink-50);border-radius:0 0 var(--r-xl) var(--r-xl)}
.modal-sm{max-width:440px}
.modal-lg{max-width:820px}
.modal-xl{max-width:1120px}

.drawer-back{position:fixed;inset:0;z-index:90;background:rgba(15,27,52,.42);backdrop-filter:blur(3px);opacity:0;visibility:hidden;transition:.24s}
.drawer-back.open{opacity:1;visibility:visible}
.drawer{
  position:fixed;top:0;right:0;bottom:0;z-index:95;width:min(520px,100%);background:#fff;
  box-shadow:var(--sh-xl);transform:translateX(100%);transition:transform .3s cubic-bezier(.4,0,.2,1);
  display:flex;flex-direction:column;
}
.drawer.open{transform:translateX(0)}

/* ==================================================================
   Toast
   ================================================================== */
#toasts{position:fixed;top:14px;right:14px;left:14px;z-index:120;display:flex;flex-direction:column;align-items:flex-end;gap:10px;pointer-events:none}
@media (min-width:640px){#toasts{left:auto;max-width:400px}}
.toast{
  display:flex;align-items:flex-start;gap:11px;min-width:0;max-width:min(400px,100%);width:100%;padding:13px 15px;
  background:#fff;border:1px solid var(--line);
  border-radius:var(--r-md);box-shadow:var(--sh-lg);pointer-events:auto;
  animation:toastIn .35s cubic-bezier(.16,1,.3,1);
}
.toast.out{animation:toastOut .25s forwards}
.toast-ico{width:30px;height:30px;flex:0 0 30px;border-radius:10px;display:grid;place-items:center}
.toast.success .toast-ico{background:#ECFDF5}
.toast.error .toast-ico{background:#FEF2F2}
.toast.warning .toast-ico{background:#FFFBEB}
.toast.info .toast-ico{background:#EFF6FF}
@keyframes toastIn{from{opacity:0;transform:translateX(40px) scale(.96)}to{opacity:1;transform:none}}
@keyframes toastOut{to{opacity:0;transform:translateX(40px) scale(.96)}}

/* ==================================================================
   Animaciones
   ================================================================== */
@keyframes fadeUp{from{opacity:0;transform:translateY(8px)}to{opacity:1;transform:none}}
@keyframes fadeIn{from{opacity:0}to{opacity:1}}
@keyframes scaleIn{from{opacity:0;transform:scale(.96)}to{opacity:1;transform:none}}
@keyframes slideRight{from{opacity:0;transform:translateX(-14px)}to{opacity:1;transform:none}}
.anim-up{animation:fadeUp .34s cubic-bezier(.16,1,.3,1) both}
.anim-in{animation:fadeIn .4s ease both}
.anim-scale{animation:scaleIn .35s cubic-bezier(.16,1,.3,1) both}
.anim-right{animation:slideRight .4s cubic-bezier(.16,1,.3,1) both}
.d1{animation-delay:.03s}.d2{animation-delay:.06s}.d3{animation-delay:.085s}.d4{animation-delay:.105s}
.d5{animation-delay:.12s}.d6{animation-delay:.13s}.d7{animation-delay:.14s}.d8{animation-delay:.15s}

/* En las superficies de trabajo la pagina entra como un solo gesto: el
   usuario llega a una tarea, no a ver cargar la interfaz. El escalonado
   por tarjeta se mantiene solo en el sitio publico. */
/* La entrada de la pagina es solo opacidad, nunca desplazamiento.
   `fadeUp` termina en `transform:none`, pero con relleno `both` eso se queda
   aplicado como matriz identidad, y un ancestro con transform pasa a ser el
   bloque contenedor de todo `position:fixed`. El resultado: cada modal del
   sistema se centraba dentro de una pagina de 2.300 px en vez de en la
   ventana, y su cabecera quedaba fuera de la pantalla. */
/* La entrada usa fill-mode «backwards» y no «both».
   Una animacion que persiste (forwards/both) sigue aplicandose para siempre, y
   una que toca la opacidad crea un contexto de apilamiento: el z-index:90 del
   modal quedaba atrapado dentro de .app-main y la barra lateral (z-50) le
   pintaba encima ochenta pixeles a 1200px de ancho. Con «backwards» el efecto
   se cubre antes de arrancar y desaparece al terminar, que es lo unico que hace
   falta para una entrada. Es la segunda vez que este relleno rompe los modales:
   antes fue un transform y el contenedor de position:fixed. */
.app-main{animation:fadeIn .22s ease backwards}
.app-main .anim-up,.app-main .anim-in,.app-main .anim-scale,.app-main .anim-right{animation:none}

.skeleton{background:linear-gradient(90deg,var(--ink-100) 25%,var(--ink-50) 50%,var(--ink-100) 75%);background-size:200% 100%;animation:shimmer 1.4s infinite;border-radius:8px}
/* Los contenedores de grafico reservan su altura y muestran una carga
   sobria hasta que ApexCharts monta; sin esto la tarjeta salta. */
.chart-hold{position:relative}
.chart-hold::after{content:'';position:absolute;inset:14px;border-radius:10px;
  background:linear-gradient(90deg,var(--ink-50) 25%,#fff 50%,var(--ink-50) 75%);background-size:200% 100%;
  animation:shimmer 1.4s infinite;pointer-events:none}
.chart-hold.listo::after{display:none}
@keyframes shimmer{to{background-position:-200% 0}}

.spinner{width:18px;height:18px;border:2.2px solid rgba(255,255,255,.35);border-top-color:#fff;border-radius:50%;animation:spin .7s linear infinite}
.spinner.dark{border-color:rgba(31,58,147,.2);border-top-color:var(--brand-500)}
@keyframes spin{to{transform:rotate(360deg)}}

/* Barra de progreso */
.prog{height:7px;background:var(--ink-100);border-radius:99px;overflow:hidden}
/* Se escala en X en lugar de animar el ancho: el ancho provoca reflujo
   en cada fotograma y aqui hay decenas de barras por pantalla. */
.prog>i{display:block;height:100%;width:100%;border-radius:99px;background:var(--brand-500);
  transform-origin:left center;transform:scaleX(var(--p,0));transition:transform .7s cubic-bezier(.16,1,.3,1)}

/* ---------------- Recorrido de estados ----------------
   Una secuencia se lee mejor como recorrido que como lista de opciones
   iguales: la linea une los pasos y el relleno dice hasta donde se ha
   llegado. */
.paso-lista{list-style:none;margin:0;padding:0;position:relative}
.paso{position:relative;display:flex;align-items:center;gap:10px;padding:5px 0 5px 2px;font-size:12.5px;color:var(--ink-400)}
.paso+.paso::before{content:'';position:absolute;left:6px;top:-7px;width:2px;height:14px;background:var(--ink-100)}
.paso.hecho+.paso::before,.paso.actual+.paso::before{background:var(--ink-200)}
.paso-punto{width:10px;height:10px;border-radius:50%;flex:none;background:var(--ink-200);
  box-shadow:0 0 0 2px #fff}
.paso.actual .paso-punto{box-shadow:0 0 0 3px var(--brand-100,#DAE1F2)}
.paso.hecho .paso-txt{color:var(--ink-600)}
.paso.actual .paso-txt{color:var(--ink-800);font-weight:700}
.paso-aqui{margin-left:auto;font-size:10px;font-weight:700;text-transform:uppercase;
  letter-spacing:.06em;color:var(--brand-600);background:var(--brand-50,#EEF1FA);
  padding:2px 7px;border-radius:99px}

/* ---------------- Desplegable con buscador ----------------
   El <select> nativo se queda en su sitio como control real del formulario
   —para que se envie, conserve `required` y su validacion—, invisible y sin
   recibir el raton. Encima va un boton con el mismo aspecto que un .select. */
.bsc{position:relative}
.bsc-nativo{
  position:absolute;inset:0;width:100%;height:100%;
  opacity:0;pointer-events:none;
}
.bsc-btn{
  position:relative;z-index:1;width:100%;text-align:left;
  display:flex;align-items:center;cursor:pointer;
}
.bsc-btn .bsc-val{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.bsc-btn .bsc-vacio{color:var(--ink-400)}
.bsc-btn[aria-expanded="true"]{border-color:var(--brand-500);box-shadow:0 0 0 3px var(--brand-100,#DAE1F2)}

.bsc-pop{
  position:absolute;z-index:70;left:0;right:0;top:calc(100% + 6px);
  background:#fff;border:1px solid var(--line);border-radius:var(--r-lg,14px);
  box-shadow:var(--sh-lg);overflow:hidden;
}
.bsc-pop.arriba{top:auto;bottom:calc(100% + 6px)}
.bsc-cab{padding:8px;border-bottom:1px solid var(--line-soft)}
.bsc-lista{max-height:264px;overflow-y:auto;margin:0;padding:5px;list-style:none}
.bsc-grupo{
  padding:8px 10px 4px;font-size:10.5px;font-weight:700;text-transform:uppercase;
  letter-spacing:.07em;color:var(--ink-400);
}
.bsc-op{
  padding:8px 10px;border-radius:9px;font-size:13px;color:var(--ink-700);cursor:pointer;
  white-space:normal;line-height:1.35;
}
.bsc-op.act{background:var(--ink-50)}
.bsc-op.sel{color:var(--brand-700);font-weight:600}
.bsc-op.sel.act{background:var(--brand-50,#EEF1FA)}
.bsc-nada{padding:14px 12px;text-align:center;font-size:12.5px;color:var(--ink-400)}
.bsc-btn.bsc-mal{border-color:var(--danger);box-shadow:0 0 0 3px rgba(239,68,68,.14)}
.bsc-error{margin-top:5px;font-size:11.5px;color:var(--danger);font-weight:500}

/* En movil ocupa el ancho de la pantalla: una lista de 65 servicios en 320px
   con el texto cortado no resuelve nada. */
@media (max-width:640px){
  .bsc-lista{max-height:min(50vh,320px)}
}

/* ---------------- Tablero de control: arrastrar y soltar ----------------
   La tarjeta levantada sale del flujo y sigue al puntero, y en su lugar queda
   un hueco de la misma altura para que el tablero no de un salto al empezar el
   gesto. Las columnas se marcan al pasar por encima. */
/* Por defecto el dedo desplaza la pagina: en el movil las columnas se apilan y
   arrastrar entre ellas no es practico, ahi se usa el boton de la tarjeta. A
   partir de 1024px el tablero es de columnas y el gesto es el arrastre, asi que
   la tarjeta se queda con el —sin esto el navegador de una tableta interpreta
   el movimiento como desplazamiento y cancela el arrastre a media accion. */
.tarjeta-cita{touch-action:pan-y;cursor:grab}
.kb-asa{display:grid;place-items:center;width:30px;height:32px;flex-shrink:0;border:0;border-radius:6px;background:transparent;color:var(--ink-400);cursor:grab;touch-action:none}
.kb-asa:hover{background:var(--brand-50);color:var(--brand-600)}
#tablero{display:grid;grid-template-columns:repeat(5,minmax(230px,1fr));overflow-x:auto;align-items:stretch;padding:4px 3px 18px;gap:14px}
#tablero>div{display:flex;flex-direction:column;background:var(--ink-50);border:1px solid var(--line);border-radius:var(--r-lg);padding:12px 10px}
#tablero .col-tablero{flex:1;min-height:280px;padding-bottom:24px}
#tablero .col-vacia{border-width:1px;border-color:var(--ink-200);border-radius:10px;margin-top:8px}
#tablero .tarjeta-cita{box-shadow:var(--sh-xs)}
#tablero .mov-pendiente{pointer-events:none}
#tablero[data-editable="0"] .kb-asa,#tablero[data-editable="0"] [data-avanzar]{display:none}
@media(max-width:640px){#tablero{grid-template-columns:repeat(5,minmax(270px,82vw))} .kb-asa{width:36px;height:36px}}
.tarjeta-cita:focus-visible{outline:2px solid var(--brand-500);outline-offset:2px}
.kb-arrastre{cursor:grabbing;user-select:none}
.kb-arrastre .tarjeta-cita{cursor:grabbing}
.kb-arrastrando{
  position:fixed;z-index:100;pointer-events:none;margin:0;
  box-shadow:var(--sh-xl);transform:rotate(1.4deg) scale(1.02);
  opacity:.97;transition:none;
}
.kb-hueco{
  border:2px dashed var(--brand-300,#A5BDFB);border-radius:var(--r-lg,16px);
  background:var(--brand-50,#EEF1FA);
}
.col-tablero.kb-destino{
  outline:2px dashed var(--brand-400,#7C9BF7);outline-offset:6px;border-radius:var(--r-lg,16px);
}

/* Herramientas del espacio clínico; el mapa se desplaza dentro de su lienzo. */
.odo-tools{display:flex;flex-wrap:wrap;align-items:center;gap:10px;padding:12px 20px;background:var(--ink-50);border-bottom:1px solid var(--line)}
.odo-tools>label{font-size:12px;font-weight:600;color:var(--ink-600)}
.odo-tools>.select{width:auto;flex:1;min-width:150px;max-width:320px}
.odo-zoom{display:flex;align-items:center;gap:4px;margin-left:auto}
.odo-zoom output{min-width:45px;text-align:center;font-size:12px;font-variant-numeric:tabular-nums}
/* El tope de altura del visor solo tiene sentido cuando se ha ampliado: es lo
   que convierte al visor en la caja por la que se recorre un dibujo mas grande
   que ella. A escala 1 el odontograma tiene que caber entero —es el mapa de la
   boca, y con 740px el maxilar inferior quedaba fuera, obligando a desplazar
   dentro de una caja para ver la mitad de la dentadura—. La tarjeta crece lo que
   pida el dibujo y la pagina se desplaza como todo lo demas. */
.odo-viewport{overflow:auto;overscroll-behavior:contain}
.odo-viewport.odo-ampliado{max-height:740px}

/* Historial del odontograma: sus columnas no pueden decidirse por el ancho de
   la ventana. La tarjeta vive en una columna que pierde 376px en cuanto aparece
   el carril de la pieza, asi que a 1440px —ventana «grande» para Tailwind— la
   tabla se quedaba sin el importe ni los botones, fuera del recorte. Se decide
   por el ancho de la propia tarjeta. */
.odo-historial{container-type:inline-size}
@container (max-width:1020px){.odo-historial .col-caras{display:none}}
@container (max-width:900px){.odo-historial .col-doctor{display:none}}
.odo-historial .col-fecha{white-space:nowrap}
.odo-workspace .odo-wrap{transition:width .15s ease}
.odo-workspace #panelDiente{scroll-margin-top:84px}
.odo-workspace .card-title{font-size:16px}
.odo-workspace .odo-svg .tooth.sel{filter:drop-shadow(0 2px 3px rgba(31,58,147,.18))}
@media(max-width:1279px){
  .odo-workspace{display:flex;flex-direction:column}
  .odo-workspace>.space-y-4:first-child{display:contents}
  .odo-workspace>.space-y-4:first-child>.card{order:3;width:100%}
  .odo-workspace>.space-y-4:first-child>.card:first-child{order:1}
  .odo-workspace>.space-y-4:first-child>.card:last-child{order:4}
  .odo-workspace>.space-y-4:last-child{order:2;width:100%}
}
@media(max-width:640px){.odo-tools{padding:12px}.odo-tools>label{width:100%}.odo-viewport.odo-ampliado{max-height:560px}.odo-workspace .odo-wrap{min-width:310px}}

/* Confirmacion del servidor: la tarjeta espera, acierta o vuelve. */
.mov-pendiente{opacity:.6}
.mov-ok{animation:kbOk .9s ease}
.mov-error{animation:kbError .5s ease}
@keyframes kbOk{0%{box-shadow:0 0 0 0 rgba(16,185,129,.45)}100%{box-shadow:0 0 0 12px rgba(16,185,129,0)}}
@keyframes kbError{0%,100%{transform:translateX(0)}20%{transform:translateX(-5px)}60%{transform:translateX(5px)}}

/* Muesca del minimo sobre una barra de nivel.
   Va en un envoltorio y no en .prog porque el riel recorta su contenido para
   redondear el relleno, y la marca tiene que sobresalir por arriba y por abajo
   para poder leerse contra el. */
/* Secciones plegables.
   Sin esto <summary> pinta el triangulo del navegador, la unica pieza sin
   disenar de la interfaz. Se sustituye por el mismo galon que usan los
   desplegables del resto del sistema. */
details > summary{list-style:none;display:flex;align-items:center;gap:9px}
details > summary::-webkit-details-marker{display:none}
details > summary::before{content:'';width:6px;height:6px;flex:none;
  border-right:1.7px solid var(--ink-400);border-bottom:1.7px solid var(--ink-400);
  transform:rotate(-45deg);transition:transform .2s ease;position:relative;left:1px}
details[open] > summary::before{transform:rotate(45deg);left:0;top:-2px}

.nivel{position:relative}
.nivel::after{content:'';position:absolute;top:-3px;height:12px;width:2px;left:var(--min,0%);
  margin-left:-1px;background:var(--ink-400);border-radius:1px;opacity:.55}

/* Anillo de progreso */
.gauge{transform:rotate(-90deg)}
.gauge circle{transition:stroke-dashoffset 1.1s cubic-bezier(.4,0,.2,1)}

/* ==================================================================
   Odontograma clínico
   ================================================================== */
.odo-wrap{user-select:none}
.odo-svg{width:100%;height:auto;display:block;overflow:visible}
.odo-guia{stroke:var(--line);stroke-width:1.25;stroke-dasharray:5 5}
.odo-arcada .odo-guia{stroke:var(--ink-200);stroke-width:1;stroke-dasharray:3 6}

.odo-interactivo .tooth{cursor:pointer}
.tooth .root{fill:#FCFDFF;stroke:#AEBBD1;stroke-width:1.15;stroke-linejoin:round}
.tooth .crown{fill:#FCFDFF;stroke:none}
.tooth .crown-line{fill:none;stroke:#8E9EBA;stroke-width:1.35;stroke-linejoin:round;pointer-events:none}
.tooth .surf{fill:#fff;stroke:#C3CDDD;stroke-width:.9;transition:fill .16s,stroke .16s}
.tooth .fissure{fill:none;stroke:#A9B6CC;stroke-width:1.1;stroke-linecap:round;pointer-events:none}
.tooth .hit{fill:transparent}
.tooth .marks,.tooth .badge,.tooth .halo{pointer-events:none}
.odo-eti{pointer-events:none}
.odo-eti .eti-num{font-size:26px;font-weight:800;fill:var(--ink-900);letter-spacing:-.03em}
.odo-eti .eti-nom{font-size:12px;font-weight:700;fill:var(--brand-600)}
.odo-eti .eti-sub{font-size:9.5px;font-weight:600;fill:var(--ink-400);text-transform:uppercase;letter-spacing:.08em}
.tooth .num{font-size:10.5px;font-weight:700;fill:var(--ink-400);text-anchor:middle;
  font-variant-numeric:tabular-nums;letter-spacing:.01em;pointer-events:none}
.tooth .badge-bg{fill:var(--ink-900)}
.tooth .badge-tx{font-size:8.5px;font-weight:800;fill:#fff;pointer-events:none}

.odo-interactivo .tooth:hover .crown-line{stroke:var(--brand-500);stroke-width:1.7}
.odo-interactivo .tooth:hover .crown{fill:var(--brand-50)}
.odo-interactivo .tooth:hover .num{fill:var(--brand-600)}
.odo-interactivo .tooth:hover .root{stroke:var(--brand-300)}
.odo-interactivo .surf:hover{fill:var(--brand-100)}

.tooth .halo{fill:none;stroke:var(--brand-500);stroke-width:2;opacity:0;transition:opacity .18s}
.tooth.sel .halo{opacity:1}
.tooth.sel .num{fill:var(--brand-700)}
.tooth.sel .crown-line{stroke:var(--brand-600);stroke-width:1.7}
.tooth:focus{outline:none}
.tooth:focus-visible .halo{opacity:1;stroke-dasharray:4 3}
.tooth.ausente .root,.tooth.ausente .crown-line,.tooth.ausente .surf,.tooth.ausente .fissure{opacity:.42}
.tooth.dis{opacity:.38;pointer-events:none}

/* Selector de caras del formulario */
.odo-selector{width:116px;height:116px}
.odo-selector .sel-cara{fill:#fff;stroke:#C3CDDD;stroke-width:1.4;cursor:pointer;transition:fill .14s}
.odo-selector .sel-cara:hover{fill:var(--brand-100)}
.odo-selector .sel-cara.on{fill:var(--brand-500);stroke:var(--brand-600)}
.odo-selector .sel-cara:focus{outline:none}
.odo-selector .sel-cara:focus-visible{stroke:var(--brand-600);stroke-width:2.4}
.odo-selector .sel-lbl{font-size:11px;font-weight:700;fill:var(--ink-400);pointer-events:none;transition:fill .14s}
.odo-selector .sel-lbl.on{fill:#fff}

/* ==================================================================
   Agenda / Calendario

   La rejilla es la herramienta principal de recepcion: se lee de un
   vistazo, se opera con el raton y con el teclado, y nunca esconde
   una cita detras de otra.
   ================================================================== */
.cal{--cal-h:64px;position:relative}      /* alto de una hora; lo fija la densidad */
.cal[data-densidad="compacta"]{--cal-h:46px}
.cal[data-densidad="amplia"]{--cal-h:92px}

.cal-grid{display:grid;grid-template-columns:64px repeat(var(--cols,1),minmax(var(--col-min,142px),1fr));position:relative}
.cal-hour{height:var(--cal-h);border-bottom:1px solid var(--line-soft);position:relative}
.cal-hour::after{content:'';position:absolute;left:0;right:0;top:50%;border-top:1px dashed var(--line-soft)}
.cal-time{
  font-size:10.5px;font-weight:600;color:var(--ink-400);text-align:right;padding-right:10px;
  transform:translateY(-7px);font-variant-numeric:tabular-nums;
}
/* La primera hora no se sube: quedaria debajo de la cabecera de odontologos */
.cal-hour:first-child .cal-time{transform:none;padding-top:3px}
/* Fuera del horario de atencion la rejilla se apaga, no desaparece */
.cal-hour.cerrado{background:repeating-linear-gradient(135deg,var(--ink-50) 0 6px,transparent 6px 12px)}

/* --- Celda vacia: invita a crear en ese hueco --- */
.cal-slot{position:absolute;left:0;right:0;cursor:pointer;z-index:1}
.cal-slot::before{
  content:'';position:absolute;inset:1px 3px;border-radius:8px;
  background:var(--brand-50);border:1px dashed var(--brand-300);
  opacity:0;transition:opacity .12s;
}
.cal-slot:hover::before{opacity:1}
.cal-slot:focus-visible{outline:none}
.cal-slot:focus-visible::before{opacity:1;border-style:solid;box-shadow:0 0 0 2px var(--brand-200)}
.cal-slot .slot-h{
  position:absolute;inset:0;display:grid;place-items:center;gap:4px;grid-auto-flow:column;
  font-size:10.5px;font-weight:700;color:var(--brand-600);opacity:0;transition:opacity .12s;
  pointer-events:none;
}
.cal-slot:hover .slot-h,.cal-slot:focus-visible .slot-h{opacity:1}

/* --- Cita --- */
.appt{
  position:absolute;border-radius:9px;padding:6px 9px 6px 15px;overflow:hidden;
  font-size:11.5px;line-height:1.35;cursor:pointer;border:1px solid;z-index:4;
  transition:box-shadow .18s,transform .18s,opacity .18s;box-shadow:var(--sh-xs);
  /* left/width los fija el reparto de columnas cuando hay solape */
  left:3px;right:3px;min-height:20px;
}
/* El color del odontologo se marca con un punto, no con una pestaña lateral */
.appt::before{content:'';position:absolute;left:6px;top:9px;width:5px;height:5px;border-radius:50%;background:currentColor}
.appt:hover{transform:scale(1.015);box-shadow:var(--sh-md);z-index:20}
.appt:focus-visible{outline:2px solid var(--brand-500);outline-offset:1px;z-index:20}
.appt.pasada{opacity:.62}
.appt.pasada:hover{opacity:1}
/* Solape: la cita se estrecha y se escalona, ninguna queda oculta */
.appt[data-col]{right:auto}
.appt.arrastrando{opacity:.35;pointer-events:none}
.appt-fantasma{
  position:absolute;border-radius:9px;border:2px dashed var(--brand-500);background:var(--brand-50);
  z-index:30;pointer-events:none;padding:5px 9px;font-size:11px;font-weight:700;color:var(--brand-700);
  box-shadow:var(--sh-md);overflow:hidden;
}
.appt-fantasma.choca{border-color:var(--danger);background:#FEF2F2;color:#B91C1C}
.cal-col.recibe{background:var(--brand-50)}

/* --- Linea del ahora: una sola, con su hora en la canal --- */
.now-line{position:absolute;left:0;right:0;height:2px;background:#EF4444;z-index:15;pointer-events:none}
.now-line::before{content:'';position:absolute;left:-4px;top:-3px;width:8px;height:8px;border-radius:50%;background:#EF4444}
.now-pill{
  position:absolute;z-index:16;pointer-events:none;transform:translateY(-50%);
  right:6px;background:#C42121;color:#fff;border-radius:6px;padding:1px 5px;
  font-size:9.5px;font-weight:800;letter-spacing:.02em;font-variant-numeric:tabular-nums;
}

/* --- Mini calendario: el punto crece con la carga del dia --- */
.mini-cal{display:grid;grid-template-columns:repeat(7,1fr);gap:2px}
.mini-day{
  aspect-ratio:1;display:grid;place-items:center;border-radius:9px;font-size:12px;font-weight:600;
  color:var(--ink-600);cursor:pointer;transition:.14s;position:relative;
}
.mini-day:hover{background:var(--ink-50)}
.mini-day:focus-visible{outline:2px solid var(--brand-500);outline-offset:-2px}
.mini-day.out{color:var(--ink-200)}
.mini-day.today{color:var(--brand-600);font-weight:800}
.mini-day.sel{background:var(--brand-500);color:#fff}
.mini-day.has::after{
  content:'';position:absolute;bottom:3px;border-radius:99px;background:var(--brand-400);
  height:3px;width:calc(4px + var(--carga,0) * 8px);
}
.mini-day.sel.has::after{background:#fff}

/* --- Aviso de que la rejilla sigue a la derecha --- */
.cal-fade{
  position:absolute;top:0;right:0;bottom:0;width:56px;pointer-events:none;z-index:22;
  background:linear-gradient(to left,#fff 12%,rgba(255,255,255,0));
  display:flex;align-items:center;justify-content:flex-end;padding-right:6px;
}
.cal-fade.hidden{display:none}
.cal-fade > button{pointer-events:auto}

/* --- Barra de carga del dia --- */
.carga{height:6px;border-radius:99px;background:var(--ink-100);overflow:hidden;display:flex}
.carga > i{display:block;height:100%}

/* ==================================================================
   Timeline
   ================================================================== */
.tl{position:relative;padding-left:26px}
.tl::before{content:'';position:absolute;left:6px;top:6px;bottom:6px;width:2px;background:var(--line);border-radius:2px}
.tl-item{position:relative;padding-bottom:22px}
.tl-item:last-child{padding-bottom:0}
.tl-dot{
  position:absolute;left:-26px;top:3px;width:14px;height:14px;border-radius:50%;
  border:3px solid #fff;box-shadow:0 0 0 1.5px var(--line);background:var(--ink-300);
}
.tl-dot.brand{background:var(--brand-500);box-shadow:0 0 0 1.5px var(--brand-200)}
.tl-dot.ok{background:var(--ok);box-shadow:0 0 0 1.5px #A7F3D0}
.tl-dot.warn{background:var(--warn);box-shadow:0 0 0 1.5px #FDE68A}
.tl-dot.danger{background:var(--danger);box-shadow:0 0 0 1.5px #FECACA}

/* ==================================================================
   Utilidades
   ================================================================== */
.tnum{font-variant-numeric:tabular-nums}
.truncate-2{display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}
.truncate-3{display:-webkit-box;-webkit-line-clamp:3;-webkit-box-orient:vertical;overflow:hidden}
.divide-y-soft>*+*{border-top:1px solid var(--line-soft)}
.no-scrollbar::-webkit-scrollbar{display:none}
.no-scrollbar{-ms-overflow-style:none;scrollbar-width:none}

.empty{display:flex;flex-direction:column;align-items:center;justify-content:center;padding:56px 24px;text-align:center}
.empty-ico{width:66px;height:66px;border-radius:20px;background:var(--ink-50);color:var(--ink-400);display:grid;place-items:center;margin-bottom:16px}
.empty h2{font-size:15px;color:var(--ink-700)}
.empty p{font-size:13px;color:var(--ink-400);margin-top:5px;max-width:340px}

.kbd{display:inline-block;padding:2px 6px;border-radius:6px;border:1px solid var(--ink-200);border-bottom-width:2px;background:var(--ink-50);font-size:10.5px;font-weight:700;color:var(--ink-500);font-family:ui-monospace,SFMono-Regular,Menlo,monospace}

.tip{position:relative}
.tip::after{
  content:attr(data-tip);position:absolute;bottom:calc(100% + 8px);left:50%;transform:translateX(-50%) translateY(4px);
  padding:6px 10px;background:var(--ink-900);color:#fff;font-size:11.5px;font-weight:500;border-radius:8px;
  white-space:nowrap;opacity:0;pointer-events:none;transition:.18s;z-index:70;box-shadow:var(--sh-md);
}
.tip:hover::after{opacity:1;transform:translateX(-50%) translateY(0)}
/* El globo es un absoluto con nowrap: junto al borde derecho ensanchaba el
   documento entero (17 px de scroll lateral en el panel general). En pantalla
   tactil, ademas, un globo que solo aparece al pasar el raton no sirve: bajo
   el punto de ruptura no se dibuja. */
@media (max-width:1023px){
  .tip::after{content:none}
}

.gradient-brand{background:linear-gradient(135deg,#152868 0%,#1F3A93 55%,#2F4FB4 100%)}
.gradient-mesh{
  background:
    radial-gradient(at 12% 18%,rgba(31,58,147,.14) 0px,transparent 52%),
    radial-gradient(at 88% 8%,rgba(139,92,246,.12) 0px,transparent 48%),
    radial-gradient(at 72% 92%,rgba(14,165,233,.12) 0px,transparent 48%),
    radial-gradient(at 22% 88%,rgba(16,185,129,.09) 0px,transparent 46%);
}

/* ==================================================================
   Impresión
   ================================================================== */
@media print{
  @page{margin:14mm}
  body{background:#fff !important;font-size:11.5pt}
  .no-print,.no-print *{display:none !important}
  .card,.panel{box-shadow:none !important;border-color:#D8DEE9 !important;break-inside:avoid}
  .print-block{break-inside:avoid}
  a[href]::after{content:''}
  .tbl thead th{background:#F1F4F9 !important;-webkit-print-color-adjust:exact;print-color-adjust:exact}
  *{-webkit-print-color-adjust:exact !important;print-color-adjust:exact !important}
}

/* ==================================================================
   Responsive
   ================================================================== */
@media (max-width:1024px){
  :root{--sidebar-w:0px}
}
@media (max-width:640px){
  body{font-size:13.5px}
  .card-pad{padding:16px}
  .modal{border-radius:var(--r-lg)}
  .modal-head{padding:18px 18px 0}
  .modal-body{padding:16px 18px}
  .modal-foot{padding:14px 18px;border-radius:0 0 var(--r-lg) var(--r-lg)}
  .modal-foot .btn{flex:1}
  .stat-value{font-size:22px}
  #toasts{left:12px;right:12px;top:12px}
  /* `none` descapaba el aviso y lo sacaba de la pantalla: en telefono ocupa
     el ancho de su contenedor, ni un pixel mas. */
  .toast{min-width:0;max-width:100%}
  .tbl thead th,.tbl tbody td{padding:11px 12px}
}

@media (prefers-reduced-motion:reduce){
  *,*::before,*::after{animation-duration:.001ms !important;animation-iteration-count:1 !important;transition-duration:.001ms !important}
}

/* Titulares grandes: el interletraje se cierra al crecer el cuerpo */
.stat-value,.text-\[28px\],.text-\[30px\],.text-\[32px\],.text-\[34px\],.text-\[36px\],
.text-\[40px\],.text-\[44px\],.text-\[48px\],.text-\[56px\],.text-\[64px\],.text-\[92px\]{letter-spacing:-.04em}

/* ==================================================================
   Cinta de cifras — cabecera de una pagina de indice

   Una sola linea en lugar de cuatro tarjetas. Las cifras que
   corresponden a un filtro son enlaces: pulsar una deja la lista en
   ese subconjunto.
   ================================================================== */
.cinta{
  display:flex;align-items:stretch;overflow-x:auto;scrollbar-width:none;
  background:var(--surface);border:1px solid var(--line);border-radius:var(--r-lg);
  box-shadow:var(--sh-sm);margin-bottom:20px;
}
.cinta::-webkit-scrollbar{display:none}

.cinta-dato{
  flex:0 1 auto;min-width:132px;padding:11px 18px;position:relative;
  display:flex;flex-direction:column;gap:1px;
  border-left:1px solid var(--line-soft);transition:background .14s;
}
.cinta-dato:first-child{border-left:0}
.cinta-dato .v{
  font-size:19px;font-weight:700;letter-spacing:-.03em;color:var(--ink-900);
  font-variant-numeric:tabular-nums;line-height:1.2;
}
.cinta-dato .l{font-size:11.5px;font-weight:500;color:var(--ink-400);white-space:nowrap}
.cinta-dato .n{font-size:11px;font-weight:600;color:var(--ink-500);font-variant-numeric:tabular-nums;margin-top:2px}

/* Solo las que filtran responden al puntero */
a.cinta-dato{cursor:pointer}
a.cinta-dato:hover{background:var(--ink-50)}
a.cinta-dato:focus-visible{outline:2px solid var(--brand-500);outline-offset:-2px;border-radius:var(--r-md)}
a.cinta-dato::after{
  content:'';position:absolute;left:18px;right:18px;bottom:0;height:2px;
  background:var(--brand-500);transform:scaleX(0);transform-origin:left;
  transition:transform .2s cubic-bezier(.4,0,.2,1);
}
a.cinta-dato:hover::after{transform:scaleX(1)}
.cinta-dato.on{background:var(--brand-50)}
.cinta-dato.on::after{transform:scaleX(1)}
.cinta-dato.on .l{color:var(--brand-700)}

@media (max-width:640px){
  .cinta-dato{min-width:118px;padding:10px 14px}
  .cinta-dato .v{font-size:17px}
}

/* ==================================================================
   Orden en telefono: la lista es el contenido

   En una pagina de indice las cifras y los graficos son contexto. En
   escritorio caben arriba; en un telefono empujaban la primera fila de
   datos hasta 1.600 px de scroll. Marcados con .ctx-abajo, bajan por
   debajo de la lista sin mover nada en escritorio.
   ================================================================== */
@media (max-width:1023px){
  .app-main > div{display:flex;flex-direction:column}
  .app-main > div > *{order:2}
  .app-main > div > .ctx-abajo{order:5}
}

/* --- Filtros plegados en telefono ---
   Solo el buscador y el boton «Filtros» quedan a la vista; lo demas se
   despliega. En escritorio la barra se comporta como siempre. */
.filtros-tog{display:none}
@media (max-width:1023px){
  .filtros-mov .filtros-tog{display:inline-flex}
  .filtros-mov .filtros-resto{display:none}
  .filtros-mov.abierta .filtros-resto{display:block}
  .filtros-mov.abierta .filtros-resto.flex{display:flex}
  .filtros-mov > div:first-child{grid-template-columns:1fr auto;display:grid;gap:10px;align-items:center}
  .filtros-mov.abierta > div:first-child{grid-template-columns:1fr;align-items:stretch}
  .filtros-mov.abierta .filtros-tog{grid-column:1}
}

/* ==================================================================
   Encogimiento en pantallas estrechas

   Un hijo de rejilla o de caja flexible no baja por defecto de su
   ancho minimo de contenido: una tabla ancha dentro de una tarjeta
   ensanchaba la tarjeta 108 px y, sin scroll lateral de pagina, ese
   trozo quedaba cortado. Con `min-width:0` la tarjeta se ajusta y el
   contenido ancho desplaza dentro de su propio contenedor.
   ================================================================== */
.app-main .grid > *,
.app-main .flex > *{min-width:0}
/* Los controles que deben conservar su tamano lo piden explicitamente */
.app-main .grid > .shrink-0,
.app-main .flex > .shrink-0{min-width:auto}

/* ==================================================================
   MODO OSCURO  ·  capa aditiva bajo [data-theme=dark] (solo el panel)
   El modo claro no se toca: sin el atributo, todo queda igual. Los
   tokens se invierten (arrastran .card/.btn/.input y demas componentes)
   y se re-apuntan las utilidades Tailwind y superficies con color fijo.
   ================================================================== */
:root[data-theme=dark]{
  color-scheme:dark;
  --canvas:#0B1220; --surface:#141E33; --surface-nav:#0F1829;
  --line:#29384F; --line-soft:#1D2A43;
  --ink-900:#EAF1FC; --ink-800:#D9E1F0; --ink-700:#BDC8DE; --ink-600:#A9B5CF;
  --ink-500:#94A2BD; --ink-400:#848FAF; --ink-300:#63728E; --ink-200:#3B4B67;   /* ink-400 subio de #7F8DAA: sobre --ink-50 se quedaba en 4,41 */
  --ink-100:#283549; --ink-50:#1B2841;
  --brand-50:#161F3B; --brand-100:#1E2E5C; --brand-200:#2A3E78; --brand-300:#3E5498;
  --brand-400:#4C64B8; --brand-500:#5473CE; --brand-600:#7C93E0; --brand-700:#A3B4EC;
  --brand-800:#C6D0F5; --brand-900:#E4E9FB;
  --ok:#34D399; --warn:#FBBF24; --danger:#F87171; --info:#38BDF8; --violet:#A78BFA;
  --sh-xs:0 1px 2px rgba(0,0,0,.45);
  --sh-sm:0 1px 3px rgba(0,0,0,.5),0 1px 2px rgba(0,0,0,.35);
  --sh-md:0 4px 16px rgba(0,0,0,.55),0 1px 3px rgba(0,0,0,.4);
  --sh-lg:0 14px 40px rgba(0,0,0,.6),0 2px 8px rgba(0,0,0,.45);
  --sh-xl:0 28px 70px rgba(0,0,0,.66);
  --sh-brand:0 8px 24px rgba(31,58,147,.45);
}

/* Superficies con color fijo (#fff) que los tokens no alcanzan */
:root[data-theme=dark] .glass{background:rgba(17,26,44,.82)}
:root[data-theme=dark] .dd-menu{background:var(--surface);border-color:var(--line)}
:root[data-theme=dark] .modal{background:var(--surface)}
:root[data-theme=dark] .drawer{background:var(--surface)}
:root[data-theme=dark] .input:focus,
:root[data-theme=dark] .select:focus,
:root[data-theme=dark] .textarea:focus{background:var(--surface)}
:root[data-theme=dark] .check input{background:var(--ink-100)}
:root[data-theme=dark] .seg-item.active{background:var(--ink-100);color:var(--brand-600)}
:root[data-theme=dark] .nav-item:hover{background:var(--ink-100);color:var(--ink-900)}

/* Componentes con hex de estado fijo */
:root[data-theme=dark] .tbl tbody tr:hover{background:rgba(255,255,255,.035)}
:root[data-theme=dark] .btn-dark{background:var(--ink-100);color:var(--ink-900)}
:root[data-theme=dark] .btn-dark:hover:not(:disabled){background:var(--ink-200)}
/* Contraste medido sobre el fondo real en oscuro. Blanco sobre --brand-500
   daba 4,45 y sobre el azul de reposo anterior 3,63: por debajo del minimo
   de 4,5 para texto normal. Con brand-300 en reposo (7,1) y brand-400 al
   pasar por encima (5,5) el realce sigue aclarando y ambos cumplen. */
:root[data-theme=dark] .btn-primary{background:var(--brand-300)}
:root[data-theme=dark] .btn-primary:hover:not(:disabled){background:var(--brand-400)}
/* La cabecera de tabla en --ink-400 sobre --ink-50 daba 4,41. */
:root[data-theme=dark] .tbl thead th{color:var(--ink-500)}
/* El segmento activo en --brand-600 sobre --ink-100 daba 4,19. */
:root[data-theme=dark] .seg-item.active{color:var(--brand-700)}
/* El chip de filtro activo lleva el mismo azul que el boton: 4,45 con letra
   blanca. Se le da el mismo tono profundo. */
:root[data-theme=dark] .chip-btn.active{background:var(--brand-300);border-color:var(--brand-300)}
:root[data-theme=dark] .btn-danger-soft{background:#3A1D22;color:#FDA4AF}
:root[data-theme=dark] .btn-danger-soft:hover:not(:disabled){background:#4A2329}
:root[data-theme=dark] .btn-success-soft{background:#10321F;color:#6EE7B7}
:root[data-theme=dark] .btn-success-soft:hover:not(:disabled){background:#164229}
:root[data-theme=dark] .btn-warn-soft{background:#33280D;color:#FCD34D}
:root[data-theme=dark] .btn-warn-soft:hover:not(:disabled){background:#43340F}
:root[data-theme=dark] .ico-btn:hover{background:var(--ink-100);color:var(--ink-800);border-color:var(--line)}
:root[data-theme=dark] .ico-btn.danger:hover{background:#3A1D22;color:#FDA4AF;border-color:#5A272D}
:root[data-theme=dark] .ico-btn.ok:hover{background:#10321F;color:#6EE7B7;border-color:#22563C}
:root[data-theme=dark] .chip-espera{background:#33280D;color:#FCD34D;border-color:#4A390F}
:root[data-theme=dark] .chip-espera.alta{background:#3A1D22;color:#FDA4AF;border-color:#5A272D}
:root[data-theme=dark] .stat-trend.up{background:#10321F;color:#6EE7B7}
:root[data-theme=dark] .stat-trend.down{background:#3A1D22;color:#FDA4AF}
:root[data-theme=dark] .toast.success .toast-ico{background:#10321F}
:root[data-theme=dark] .toast.error .toast-ico{background:#3A1D22}
:root[data-theme=dark] .toast.warning .toast-ico{background:#33280D}
:root[data-theme=dark] .toast.info .toast-ico{background:#16273F}
:root[data-theme=dark] .err-msg{color:#FDA4AF}
:root[data-theme=dark] .input.is-error,
:root[data-theme=dark] .select.is-error,
:root[data-theme=dark] .textarea.is-error{border-color:#F87171}

/* Utilidades Tailwind (hex fijo en config) re-apuntadas a los tokens */
:root[data-theme=dark] .text-ink-900{color:var(--ink-900)}
:root[data-theme=dark] .text-ink-800{color:var(--ink-800)}
:root[data-theme=dark] .text-ink-700{color:var(--ink-700)}
:root[data-theme=dark] .text-ink-600{color:var(--ink-600)}
:root[data-theme=dark] .text-ink-500{color:var(--ink-500)}
:root[data-theme=dark] .text-ink-400{color:var(--ink-400)}
:root[data-theme=dark] .text-ink-300{color:var(--ink-300)}
:root[data-theme=dark] .text-ink-200{color:var(--ink-200)}
:root[data-theme=dark] .hover\:text-ink-900:hover{color:var(--ink-900)}
:root[data-theme=dark] .hover\:text-ink-800:hover{color:var(--ink-800)}
:root[data-theme=dark] .hover\:text-ink-700:hover{color:var(--ink-700)}
:root[data-theme=dark] .hover\:text-ink-600:hover{color:var(--ink-600)}
:root[data-theme=dark] .hover\:text-ink-500:hover{color:var(--ink-500)}
:root[data-theme=dark] .bg-ink-50{background-color:var(--ink-50)}
:root[data-theme=dark] .bg-ink-100{background-color:var(--ink-100)}
:root[data-theme=dark] .bg-ink-200{background-color:var(--ink-200)}
:root[data-theme=dark] .bg-ink-900{background-color:var(--ink-200)}   /* pildora seleccionada, texto blanco */
:root[data-theme=dark] .hover\:bg-ink-50:hover{background-color:var(--ink-100)}
:root[data-theme=dark] .hover\:bg-white:hover{background-color:var(--ink-100)}
:root[data-theme=dark] .border-ink-50{border-color:var(--ink-100)}
:root[data-theme=dark] .border-ink-100{border-color:var(--line)}
:root[data-theme=dark] .border-ink-200{border-color:var(--ink-200)}
:root[data-theme=dark] .border-ink-300{border-color:var(--ink-300)}
:root[data-theme=dark] .bg-white{background-color:var(--surface)}
/* Variantes translucidas de blanco usadas como fondo (pie de pagina, barras
   pegajosas): en oscuro serian una banda gris. El topbar (/85) lo cubre .glass
   y los sellos decorativos (/20,/30) sobre cabeceras de color se dejan. */
:root[data-theme=dark] .bg-white\/50,
:root[data-theme=dark] .bg-white\/70,
:root[data-theme=dark] .bg-white\/90,
:root[data-theme=dark] .bg-white\/92{background-color:var(--surface)}
:root[data-theme=dark] .bg-canvas{background-color:var(--canvas)}
:root[data-theme=dark] .\!bg-ink-50{background-color:var(--ink-50)!important}
:root[data-theme=dark] .\!bg-white{background-color:var(--surface)!important}
:root[data-theme=dark] .focus\:\!bg-white:focus{background-color:var(--surface)!important}
:root[data-theme=dark] .text-brand-400{color:var(--brand-400)}
:root[data-theme=dark] .text-brand-500{color:var(--brand-600)}
:root[data-theme=dark] .text-brand-600{color:var(--brand-600)}
:root[data-theme=dark] .text-brand-700{color:var(--brand-700)}
:root[data-theme=dark] .hover\:text-brand-700:hover{color:var(--brand-700)}
:root[data-theme=dark] .hover\:text-brand-600:hover{color:var(--brand-600)}
:root[data-theme=dark] .hover\:text-brand-400:hover{color:var(--brand-400)}
:root[data-theme=dark] .bg-brand-50{background-color:var(--brand-50)}
:root[data-theme=dark] .bg-brand-100{background-color:var(--brand-100)}
:root[data-theme=dark] .border-brand-100{border-color:var(--brand-200)}
:root[data-theme=dark] .border-brand-200{border-color:var(--brand-300)}
:root[data-theme=dark] .border-brand-300{border-color:var(--brand-300)}
:root[data-theme=dark] .border-brand-400{border-color:var(--brand-400)}
:root[data-theme=dark] .border-brand-500{border-color:var(--brand-500)}

/* Paleta de acento (Tailwind por defecto) en valores para fondo oscuro */
:root[data-theme=dark] .bg-rose-50{background-color:#331A1E}
:root[data-theme=dark] .bg-rose-100{background-color:#3E1F24}
:root[data-theme=dark] .bg-rose-400{background-color:#FB7185}
:root[data-theme=dark] .bg-rose-500{background-color:#F43F5E}
:root[data-theme=dark] .text-rose-400{color:#FDA4AF}
:root[data-theme=dark] .text-rose-500{color:#FB7185}
:root[data-theme=dark] .text-rose-700{color:#FDA4AF}
:root[data-theme=dark] .text-rose-800{color:#FECDD3}
:root[data-theme=dark] .border-rose-100{border-color:#4A2126}
:root[data-theme=dark] .border-rose-200{border-color:#5A272D}
:root[data-theme=dark] .bg-emerald-50{background-color:#10321F}
:root[data-theme=dark] .bg-emerald-500{background-color:#10B981}
:root[data-theme=dark] .text-emerald-500{color:#34D399}
:root[data-theme=dark] .text-emerald-700{color:#6EE7B7}
:root[data-theme=dark] .text-emerald-800{color:#A7F3D0}
:root[data-theme=dark] .border-emerald-100{border-color:#1B4531}
:root[data-theme=dark] .border-emerald-200{border-color:#22563C}
:root[data-theme=dark] .bg-amber-50{background-color:#33280D}
:root[data-theme=dark] .bg-amber-500{background-color:#F59E0B}
:root[data-theme=dark] .text-amber-500{color:#FBBF24}
:root[data-theme=dark] .text-amber-700{color:#FCD34D}
:root[data-theme=dark] .text-amber-800{color:#FDE68A}
:root[data-theme=dark] .text-amber-900{color:#FEF3C7}
:root[data-theme=dark] .border-amber-100{border-color:#4A390F}
:root[data-theme=dark] .border-amber-200{border-color:#5A4712}
:root[data-theme=dark] .bg-violet-50{background-color:#241A3D}
:root[data-theme=dark] .bg-violet-500{background-color:#8B5CF6}
:root[data-theme=dark] .text-violet-500{color:#A78BFA}
:root[data-theme=dark] .text-violet-600{color:#B39DFB}
:root[data-theme=dark] .text-violet-700{color:#C4B5FD}
:root[data-theme=dark] .text-violet-800{color:#DDD6FE}
:root[data-theme=dark] .border-violet-100{border-color:#33255A}
:root[data-theme=dark] .bg-cyan-50{background-color:#0C2E38}
:root[data-theme=dark] .bg-cyan-500{background-color:#06B6D4}
:root[data-theme=dark] .text-cyan-500{color:#22D3EE}
:root[data-theme=dark] .text-cyan-700{color:#67E8F9}
:root[data-theme=dark] .border-cyan-100{border-color:#124451}
:root[data-theme=dark] .bg-orange-50{background-color:#3A2410}
:root[data-theme=dark] .bg-orange-100{background-color:#46290F}
:root[data-theme=dark] .text-orange-700{color:#FDBA74}
:root[data-theme=dark] .border-orange-100{border-color:#4E3115}
:root[data-theme=dark] .border-orange-200{border-color:#5E3A18}
:root[data-theme=dark] .bg-slate-100{background-color:var(--ink-100)}
:root[data-theme=dark] .bg-slate-400{background-color:#94A3B8}
:root[data-theme=dark] .text-slate-700{color:var(--ink-700)}

/* Huecos del modo oscuro encontrados midiendo el contraste real del texto
   contra su fondo real. Dos familias se habian quedado fuera:

   1. Los colores de texto que ningun otro sitio usa —`text-slate-600` es el
      tono de la insignia neutra— seguian en su valor claro sobre un fondo ya
      oscurecido: «Borrador», «Gerencia» y «Reserva bloqueada» quedaban en 1,63.

   2. Las variantes con opacidad (`bg-brand-50/50`) son otra clase distinta de
      la plana (`bg-brand-50`), asi que no heredaban su reasignacion: el aviso
      de los NCF era un panel claro con letra clara, en 1,88. */
:root[data-theme=dark] .text-slate-600{color:var(--ink-500)}
:root[data-theme=dark] .text-rose-600{color:#FDA4AF}
:root[data-theme=dark] .text-pink-700{color:#F9A8D4}
:root[data-theme=dark] .bg-pink-50{background-color:#3A1A2C}
:root[data-theme=dark] .border-pink-100{border-color:#52243D}
:root[data-theme=dark] .border-slate-200{border-color:var(--ink-200)}
:root[data-theme=dark] .bg-brand-50\/30,
:root[data-theme=dark] .bg-brand-50\/40,
:root[data-theme=dark] .bg-brand-50\/50{background-color:var(--brand-50)}
:root[data-theme=dark] .hover\:bg-brand-50:hover,
:root[data-theme=dark] .hover\:bg-brand-50\/40:hover{background-color:var(--brand-50)}
:root[data-theme=dark] .bg-cyan-50\/40,
:root[data-theme=dark] .bg-cyan-50\/50{background-color:#0C2E38}
:root[data-theme=dark] .bg-emerald-50\/40{background-color:#10321F}
:root[data-theme=dark] .bg-rose-50\/40{background-color:#331A1E}
:root[data-theme=dark] .bg-ink-50\/40,
:root[data-theme=dark] .bg-ink-50\/70{background-color:var(--ink-50)}
:root[data-theme=dark] .hover\:bg-ink-50\/60:hover{background-color:var(--ink-100)}
:root[data-theme=dark] .bg-white\/85{background-color:var(--surface)}
:root[data-theme=dark] .hover\:bg-orange-100:hover{background-color:#46290F}

/* El enlace de salto va sobre --brand-600, que en oscuro es un azul claro:
   con letra blanca daba 2,95. Se le da letra oscura y conserva su fuerza. */
:root[data-theme=dark] .salto-contenido{color:var(--canvas)}

/* Graficos (ApexCharts): texto y rejilla legibles sobre oscuro */
:root[data-theme=dark] .apexcharts-text,
:root[data-theme=dark] .apexcharts-datalabel-label,
:root[data-theme=dark] .apexcharts-datalabel-value{fill:var(--ink-500)!important}
:root[data-theme=dark] .apexcharts-legend-text{color:var(--ink-600)!important}
:root[data-theme=dark] .apexcharts-gridline,
:root[data-theme=dark] .apexcharts-xaxis line,
:root[data-theme=dark] .apexcharts-yaxis line{stroke:var(--line)!important}
:root[data-theme=dark] .apexcharts-tooltip{background:var(--surface)!important;border-color:var(--line)!important;color:var(--ink-800)!important;box-shadow:var(--sh-lg)!important}
:root[data-theme=dark] .apexcharts-tooltip-title{background:var(--ink-50)!important;border-color:var(--line)!important}

/* Barrido completo: superficies y detalles con color fijo que faltaban */
:root[data-theme=dark] .toast{background:var(--surface)}
:root[data-theme=dark] .bsc-pop{background:var(--surface);border-color:var(--line)}
:root[data-theme=dark] .dd-item.danger{color:#F87171}
:root[data-theme=dark] .dd-item.danger:hover{background:#3A1D22}
:root[data-theme=dark] .chart-hold::after{background:linear-gradient(90deg,var(--ink-50) 25%,var(--ink-100) 50%,var(--ink-50) 75%);background-size:200% 100%}
:root[data-theme=dark] *{scrollbar-color:#3A4B66 transparent}
:root[data-theme=dark] *::-webkit-scrollbar-thumb{background:#33425C}
:root[data-theme=dark] *::-webkit-scrollbar-thumb:hover{background:#46597A}
/* Tooltip del riel: usaba ink-900 (que ahora es claro) con texto blanco */
:root[data-theme=dark].nav-rail .sidebar .nav-item::after{background:var(--ink-200);color:var(--ink-900)}
/* Odontograma: piezas y badges legibles sobre oscuro */
:root[data-theme=dark] .tooth .root,
:root[data-theme=dark] .tooth .crown{fill:#DDE4F0;stroke:#8494B0}
:root[data-theme=dark] .tooth .surf{fill:#E7ECF5;stroke:#8E9CB6}
:root[data-theme=dark] .tooth .crown-line{stroke:#6E7E9E}
:root[data-theme=dark] .tooth .fissure{stroke:#8494B0}
:root[data-theme=dark] .tooth .badge-bg{fill:var(--ink-200)}
:root[data-theme=dark] .odo-interactivo .tooth:hover .crown{fill:#C7D3EA}
:root[data-theme=dark] .odo-interactivo .surf:hover{fill:#B9C8E6}
:root[data-theme=dark] .odo-selector .sel-cara{fill:#E7ECF5;stroke:#8E9CB6}
/* Agenda: fantasma en conflicto y etiquetas de cita con color de entidad.
   El fondo de la cita ya es translucido (#RRGGBB18) y se adapta; el texto lo
   calcula el servidor para fondo claro, asi que en oscuro lo forzamos legible. */
:root[data-theme=dark] .appt-fantasma.choca{background:#3A1D22;color:#FDA4AF}
/* Etiquetas con color de entidad (citas, chips de ARS/condicion/diente): el
   texto legible para claro lo calcula el servidor; el de oscuro viaja en --cd
   y aqui se aplica. El fondo/borde ya son translucidos y se adaptan solos. */
:root[data-theme=dark] .tono-chip,
:root[data-theme=dark] .tono-chip *{color:var(--cd) !important}
/* --- fin modo oscuro --- */

/* ==================================================================
   DENSIDAD COMPACTA  ·  [data-density=compact] en <html> (solo panel)
   Aprieta las zonas densas de datos —tablas, tarjetas, formularios—
   para quien gestiona muchas filas. No toca botones ni tipografia base.
   ================================================================== */
:root[data-density=compact] .card-pad{padding:14px}
:root[data-density=compact] .card-head{padding:11px 16px}
:root[data-density=compact] .card-title{font-size:14px}
:root[data-density=compact] .tbl thead th{padding:9px 12px}
:root[data-density=compact] .tbl tbody td{padding:8px 12px}
:root[data-density=compact] .tbl-compact tbody td{padding:6px 10px}
:root[data-density=compact] .tbl-compact thead th{padding:7px 10px}
:root[data-density=compact] .input,
:root[data-density=compact] .select,
:root[data-density=compact] .textarea{height:37px}
:root[data-density=compact] .textarea{height:auto;min-height:70px}
:root[data-density=compact] .input-sm{height:32px}
:root[data-density=compact] .field{gap:5px}
:root[data-density=compact] .stat{padding:15px 16px}
:root[data-density=compact] .stat-value{font-size:22px;margin-top:3px}
:root[data-density=compact] .stat-ico{width:36px;height:36px;flex:0 0 36px}
:root[data-density=compact] .nav-item{padding-top:7px;padding-bottom:7px}
:root[data-density=compact] .cinta-dato{padding:8px 15px}
:root[data-density=compact] .dd-item{padding-top:7px;padding-bottom:7px}

/* ==================================================================
   TABLAS -> TARJETAS EN MOVIL  ·  reflujo por debajo de 640px
   Cada fila se vuelve una tarjeta; las celdas se etiquetan con su
   encabezado (lo hace app.js con data-etq, sin tocar las vistas).
   Una tabla puede quedarse como esta anadiendo la clase .tbl-plain.
   ================================================================== */
@media (max-width:639px){
  .tbl-wrap:not(:has(.tbl-plain)){overflow:visible;background:none;box-shadow:none;border:0}
  .tbl:not(.tbl-plain){display:block;font-size:13px}
  .tbl:not(.tbl-plain) thead{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0 0 0 0);white-space:nowrap;border:0}
  .tbl:not(.tbl-plain) tbody,
  .tbl:not(.tbl-plain) tr{display:block}
  .tbl:not(.tbl-plain) tbody tr{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-md);box-shadow:var(--sh-xs);padding:6px 14px;margin-bottom:10px}
  .tbl:not(.tbl-plain) tbody tr:hover{background:var(--surface)}
  .tbl:not(.tbl-plain) tbody tr:last-child{margin-bottom:0}
  .tbl:not(.tbl-plain) td{display:flex;align-items:center;justify-content:space-between;gap:14px;padding:7px 0;border:0;border-bottom:1px solid var(--line-soft);text-align:right;white-space:normal;min-height:0}
  .tbl:not(.tbl-plain) td:last-child{border-bottom:0}
  .tbl:not(.tbl-plain) td[data-etq]::before{content:attr(data-etq);flex:0 0 auto;margin-right:auto;text-align:left;font-size:10.5px;font-weight:700;color:var(--ink-500);text-transform:uppercase;letter-spacing:.02em}
  /* primera celda = titulo de la tarjeta (identidad de la fila) */
  .tbl:not(.tbl-plain) td:first-child{display:block;text-align:left;padding:2px 0 9px;margin-bottom:5px;border-bottom:1px solid var(--line)}
  .tbl:not(.tbl-plain) td:first-child::before{content:none}
  /* celdas que ocupan toda la fila (estados vacios) */
  .tbl:not(.tbl-plain) td[colspan]{display:block;text-align:center;border-bottom:0;padding:14px 0}
  .tbl:not(.tbl-plain) td[colspan]::before{content:none}
  .tbl:not(.tbl-plain) .num{justify-content:space-between}
}

/* Un numero de telefono no se parte. En la vista de tarjetas del telefono la
   celda pasa a `white-space:normal` y comparte el ancho con el correo: «(809)
   555-9999» se cortaba en dos lineas por la mitad del numero. */
.tel{white-space:nowrap}

/* Inventario: la etiqueta de categoria se corta en vez de ensanchar la columna.
   Sin tope, «Bioseguridad y esterilizacion» pedia 198px y empujaba la tabla a
   858 en una caja de 780: los botones de accion quedaban fuera del recorte. */
.col-cat-chip{display:inline-block;max-width:92px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;vertical-align:middle}
.col-cat-chip>.chip{max-width:100%;overflow:hidden;text-overflow:ellipsis;display:inline-block}

/* El nombre del paciente no manda sobre el ancho de la tabla. `truncate` recorta
   al pintar, pero en una celda el texto sin cortes sigue contando para el ancho
   minimo: la cartera de gerencia pedia 278px solo para esta columna y la tabla
   entera se salia de su caja. Con tope, el nombre se corta y la tabla cabe. */
.tbl .cel-pac{max-width:150px}
@media (min-width:1400px){ .tbl .cel-pac{max-width:186px} }
@media (min-width:1600px){ .tbl .cel-pac{max-width:260px} }
/* Cartera de gerencia: sus columnas se deciden por el ancho de la tarjeta. */
.card-cartera{container-type:inline-size}
@container (max-width:640px){.card-cartera .col-nfac{display:none}}
@container (max-width:560px){.card-cartera .col-antigua{display:none}}

.pp-status{padding:14px;font-size:12.5px;line-height:1.5;color:var(--ink-500);text-align:center}
