@import url('https://fonts.googleapis.com/css2?family=Titillium+Web:wght@400;600;700&display=swap');

  :root{
    --bg:#f7fafe;
    --surface:#ffffff;
    --surface-2:#f5f7fc;
    --border:#e3e7f2;
    --border-strong:#cad0e3;
    --text:#141b3c;
    --text-secondary:#4c5573;
    --text-muted:#8991a8;
    --shadow:0 1px 2px rgba(20,26,58,.05), 0 8px 24px rgba(20,26,58,.06);

    --sidebar-bg:#244c97;
    --sidebar-brand-bg:#0c3a84;
    --sidebar-bg-active:#0c3a84;
    --sidebar-text:rgba(255,255,255,.85);
    --sidebar-text-muted:rgba(255,255,255,.55);
    --sidebar-text-active:#ffffff;
    --sidebar-border:rgba(255,255,255,.09);
    --brand-accent-bg:color-mix(in srgb, var(--sidebar-bg) 11%, white);

    --brand-green:#17a672;
    --brand-green-ink:#0d7a53;
    --brand-blue:#2e6fe0;
    --brand-blue-ink:#1d4fa8;
    --brand-gold:#e0972b;

    --status-good:#17a672;
    --status-warning:#e0972b;
    --status-critical:#e5484d;
    --status-neutral:#8991a8;
    --status-info:#1d4fa8;

    --mod-purple:#3c3489;   --mod-purple-bg:color-mix(in srgb, var(--mod-purple) 11%, white);
    --mod-coral:#993c1d;    --mod-coral-bg:color-mix(in srgb, var(--mod-coral) 11%, white);
    --mod-teal:#085041;     --mod-teal-bg:color-mix(in srgb, var(--mod-teal) 11%, white);
    --mod-pink:#72243e;     --mod-pink-bg:color-mix(in srgb, var(--mod-pink) 11%, white);
    --mod-blue:#0c447c;     --mod-blue-bg:color-mix(in srgb, var(--mod-blue) 11%, white);
    --mod-amber:#854f0b;    --mod-amber-bg:color-mix(in srgb, var(--mod-amber) 13%, white);
    --mod-gray:#444441;     --mod-gray-bg:color-mix(in srgb, var(--mod-gray) 10%, white);
    --mod-green:#3b6d11;    --mod-green-bg:color-mix(in srgb, var(--mod-green) 11%, white);

    --radius:14px;
    --radius-sm:9px;
    --radius-btn:32px;
    --font-display:'Titillium Web', system-ui, sans-serif;
    --font-body:'Titillium Web', system-ui, sans-serif;
  }

  :root[data-theme="dark"]{
    --bg:#0c1226; --surface:#131a34; --surface-2:#0f1530; --border:#232c50; --border-strong:#323c66;
    --text:#eef0fa; --text-secondary:#b6bcda; --text-muted:#7c84ab;
    --shadow:0 1px 2px rgba(0,0,0,.3), 0 8px 24px rgba(0,0,0,.35);
    --sidebar-bg:#244c97; --sidebar-brand-bg:#0c3a84; --sidebar-bg-active:#0c3a84; --sidebar-border:rgba(255,255,255,.07);
    --brand-accent-bg:color-mix(in srgb, var(--sidebar-bg) 38%, #0c1226);
    --mod-purple-bg:color-mix(in srgb, var(--mod-purple) 38%, #0c1226);
    --mod-coral-bg:color-mix(in srgb, var(--mod-coral) 38%, #0c1226);
    --mod-teal-bg:color-mix(in srgb, var(--mod-teal) 38%, #0c1226);
    --mod-pink-bg:color-mix(in srgb, var(--mod-pink) 38%, #0c1226);
    --mod-blue-bg:color-mix(in srgb, var(--mod-blue) 38%, #0c1226);
    --mod-amber-bg:color-mix(in srgb, var(--mod-amber) 38%, #0c1226);
    --mod-gray-bg:color-mix(in srgb, var(--mod-gray) 38%, #0c1226);
    --mod-green-bg:color-mix(in srgb, var(--mod-green) 38%, #0c1226);
    --mod-purple:color-mix(in srgb, var(--mod-purple) 62%, white);
    --mod-coral:color-mix(in srgb, var(--mod-coral) 62%, white);
    --mod-teal:color-mix(in srgb, var(--mod-teal) 62%, white);
    --mod-pink:color-mix(in srgb, var(--mod-pink) 62%, white);
    --mod-blue:color-mix(in srgb, var(--mod-blue) 62%, white);
    --mod-amber:color-mix(in srgb, var(--mod-amber) 62%, white);
    --mod-gray:color-mix(in srgb, var(--mod-gray) 68%, white);
    --mod-green:color-mix(in srgb, var(--mod-green) 62%, white);
  }

  /* ---------- Selector de color del sistema (azul / verde) ----------
     Retinta el sidebar y los acentos que usan --brand-blue / --brand-blue-ink
     (eyebrow, ícono de la fecha, línea del gráfico de consumo que la lee vía
     var() desde dashboard.js). --brand-accent-bg no se redefine
     acá: como es color-mix(...,var(--sidebar-bg),...), toma solo el
     --sidebar-bg ya retintado arriba — por eso los íconos de Asociados y
     servicios (que usan var(--sidebar-bg)/var(--brand-accent-bg), no
     --mod-purple) siguen automáticamente el mismo azul/verde del sidebar. */
  :root[data-brand="green"]{
    --sidebar-bg:#1b6b4c;
    --sidebar-brand-bg:#0d4530;
    --sidebar-bg-active:#0d4530;
    --brand-blue:#17a672;
    --brand-blue-ink:#0d7a53;
  }

  *{box-sizing:border-box;}
  body{margin:0;background:var(--bg);color:var(--text);font-family:var(--font-body);}
  .icon{width:18px;height:18px;stroke:currentColor;fill:none;stroke-width:1.8;stroke-linecap:round;stroke-linejoin:round;flex-shrink:0;}
  .icon-fill{fill:currentColor;stroke:none;}
  h1,h2,h3{font-family:var(--font-display);letter-spacing:-.01em;text-wrap:balance;margin:0;}
  button{font:inherit;}
  a{color:inherit;text-decoration:none;}

  .app{display:flex;min-height:100vh;width:100%;}

  /* ---------- Sidebar ---------- */
  .sidebar{width:252px;flex-shrink:0;background:var(--sidebar-bg);display:flex;flex-direction:column;padding:0;gap:0;position:sticky;top:0;height:100vh;overflow-y:auto;overflow-x:hidden;transition:width .2s ease, transform .25s ease;}
  .brand{display:flex;padding:20px 20px 18px;background:var(--sidebar-brand-bg);flex-shrink:0;}
  .brand-logo{width:100%;max-width:170px;height:auto;display:block;}
  .brand-logo-icon{display:none;width:32px;max-width:32px;margin:0 auto;}

  .sidebar-body{flex:1;min-height:0;display:flex;flex-direction:column;padding:16px 14px;gap:18px;}
  .nav{display:flex;flex-direction:column;gap:2px;margin-top:4px;}
  .nav-item{display:flex;align-items:center;gap:10px;padding:9px 10px;border-radius:var(--radius-sm);color:var(--sidebar-text);background:none;border:none;cursor:pointer;text-align:left;font-size:13.5px;font-family:var(--font-body);position:relative;width:100%;}
  .nav-item .icon{color:var(--sidebar-text-muted);}
  .nav-icon-img{width:19px;height:19px;object-fit:contain;flex-shrink:0;display:block;color:var(--sidebar-text-muted);}
  .nav-item:hover{background:rgba(255,255,255,.05);color:#fff;}
  .nav-item:hover .icon{color:var(--sidebar-text);}
  .nav-item:hover .nav-icon-img{color:var(--sidebar-text);}
  .nav-item.active{background:var(--sidebar-bg-active);color:var(--sidebar-text-active);font-weight:600;}
  .nav-item.active .icon{color:var(--brand-green);}
  .nav-item.active .nav-icon-img{color:var(--brand-green);}
  .nav-item.active::before{content:"";position:absolute;left:-14px;top:8px;bottom:8px;width:3px;border-radius:0 3px 3px 0;background:var(--brand-green);}
  .nav-item:focus-visible{outline:2px solid var(--brand-green);outline-offset:1px;}

  /* ---------- Buscador del sidebar ----------
     Filtra el menú (módulos + opciones de submenú) a medida que se tipea —
     ver initSidebarSearch en dashboard.js. Mientras hay una búsqueda
     activa, #sidebar-nav y #sidebar-foot se ocultan y #sidebar-results
     los reemplaza con solo las coincidencias. */
  .sidebar-search{display:flex;align-items:center;gap:8px;background:rgba(255,255,255,.08);border:1px solid var(--sidebar-border);border-radius:999px;padding:7px 11px;color:var(--sidebar-text-muted);}
  .sidebar-search input{border:none;background:none;outline:none;font-size:13px;color:var(--sidebar-text-active);width:100%;font-family:var(--font-body);}
  .sidebar-search input::placeholder{color:var(--sidebar-text-muted);}
  .sidebar-search-clear{background:none;border:none;padding:2px;margin:0;display:flex;color:var(--sidebar-text-muted);cursor:pointer;flex-shrink:0;}
  .sidebar-search-clear:hover{color:var(--sidebar-text-active);}
  .sidebar-search-clear[hidden]{display:none;}

  .nav[hidden], .sidebar-foot[hidden]{display:none;}
  .sidebar-results{display:flex;flex-direction:column;gap:2px;}
  .sidebar-results[hidden]{display:none;}
  .nav-item-text{display:flex;flex-direction:column;gap:1px;min-width:0;}
  .nav-item-text b{font-weight:600;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
  .nav-item-text small{font-size:11px;font-weight:400;color:var(--sidebar-text-muted);overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
  .nav-item.search-result:hover .nav-item-text small{color:var(--sidebar-text);}
  .sidebar-results-empty{margin:0;padding:9px 10px;font-size:12.5px;color:var(--sidebar-text-muted);}

  .sidebar-foot{margin-top:auto;display:flex;flex-direction:column;gap:12px;}
  .sidebar-divider{height:1px;background:var(--sidebar-border);margin:2px 0;}
  .energy-bar{height:4px;border-radius:2px;background:rgba(255,255,255,.08);overflow:hidden;}
  .energy-bar span{display:block;height:100%;width:62%;border-radius:2px;background:linear-gradient(90deg, var(--brand-green), var(--brand-blue), var(--brand-gold));}
  @media (prefers-reduced-motion: no-preference){ .energy-bar span{animation:pulse 5s ease-in-out infinite;} }
  @keyframes pulse{0%,100%{width:56%;} 50%{width:72%;}}
  .sidebar-meta{display:flex;justify-content:space-between;align-items:baseline;font-size:10.5px;color:var(--sidebar-text-muted);padding:0 6px;}
  .sidebar-meta b{color:var(--sidebar-text);font-weight:600;letter-spacing:.03em;}

  /* ---------- Topbar ---------- */
  .main{flex:1;min-width:0;display:flex;flex-direction:column;}
  .topbar{position:sticky;top:0;z-index:5;display:flex;align-items:center;gap:14px;padding:12px 24px;background:var(--surface);border-bottom:1px solid var(--border);}
  .menu-btn{display:flex;background:none;border:1px solid var(--border);border-radius:var(--radius-sm);width:36px;height:36px;align-items:center;justify-content:center;color:var(--text-secondary);cursor:pointer;}
  .menu-btn[aria-pressed="true"]{background:var(--surface-2);border-color:var(--border-strong);color:var(--text);}
  .topbar-search-wrap{position:relative;flex:1;max-width:460px;}
  .search{display:flex;align-items:center;gap:8px;background:var(--surface-2);border:1px solid var(--border);border-radius:999px;padding:8px 12px;color:var(--text-muted);}
  .search input{border:none;background:none;outline:none;font-size:13.5px;color:var(--text);width:100%;font-family:var(--font-body);}
  .search kbd{font-size:10.5px;color:var(--text-muted);border:1px solid var(--border-strong);border-radius:5px;padding:2px 6px;font-family:var(--font-body);}

  /* ---------- Desplegable de resultados del buscador del topbar ----------
     Ver initTopbarSearch en dashboard.js: busca asociados reales a medida
     que se tipea (2+ caracteres) y arma este desplegable con lo que
     devuelve core:asociados_search en JSON. */
  .topbar-search-results{position:absolute;top:calc(100% + 6px);left:0;right:0;background:var(--surface);border:1px solid var(--border);border-radius:var(--radius-sm);box-shadow:var(--shadow);z-index:30;max-height:320px;overflow-y:auto;padding:6px;}
  .topbar-search-results[hidden]{display:none;}
  .topbar-result{display:flex;align-items:center;gap:10px;width:100%;padding:8px 10px;border-radius:var(--radius-sm);color:var(--text);font-size:13.5px;}
  .topbar-result:hover{background:var(--surface-2);}
  .topbar-result .icon{color:var(--text-muted);flex-shrink:0;}
  .topbar-result-text{display:flex;flex-direction:column;gap:1px;min-width:0;}
  .topbar-result-text b{font-weight:600;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
  .topbar-result-text small{font-size:11.5px;color:var(--text-muted);overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
  .topbar-results-empty{margin:0;padding:9px 10px;font-size:12.5px;color:var(--text-muted);}

  .topbar-spacer{flex:1;}
  .brand-picker{display:flex;align-items:center;gap:6px;padding:5px;border:1px solid var(--border);border-radius:999px;background:var(--surface-2);}
  .brand-swatch{width:18px;height:18px;border-radius:999px;border:2px solid transparent;padding:0;cursor:pointer;display:block;}
  .brand-swatch-blue{background:#244c97;}
  .brand-swatch-green{background:#1b6b4c;}
  .brand-swatch[aria-pressed="true"]{border-color:var(--text-secondary);}
  .brand-swatch:hover{filter:brightness(1.15);}
  .badge-dot{position:absolute;top:5px;right:6px;background:var(--status-critical);color:#fff;font-size:9.5px;font-weight:600;min-width:14px;height:14px;border-radius:999px;display:flex;align-items:center;justify-content:center;padding:0 3px;}
  .user-chip{display:flex;align-items:center;gap:9px;padding:5px 8px 5px 5px;border-radius:999px;border:1px solid var(--border);background:var(--surface);cursor:pointer;}
  .avatar{width:28px;height:28px;border-radius:999px;background:var(--brand-green);color:#fff;font-family:var(--font-display);font-weight:700;font-size:11.5px;display:flex;align-items:center;justify-content:center;}
  .user-chip .who{display:flex;flex-direction:column;line-height:1.2;}
  .user-chip .who b{font-size:12.5px;font-weight:600;}
  .user-chip .who span{font-size:10.5px;color:var(--text-muted);}
  .user-chip .icon{color:var(--text-muted);}

  /* ---------- Content ---------- */
  .content{padding:22px 24px 40px;display:flex;flex-direction:column;gap:18px;max-width:1280px;width:100%;margin:0 auto;}
  .page-head{display:flex;justify-content:space-between;align-items:flex-start;gap:16px;flex-wrap:wrap;}
  .eyebrow{font-size:11.5px;font-weight:600;letter-spacing:.08em;color:var(--brand-blue-ink);text-transform:uppercase;}
  .page-head h1{font-size:26px;font-weight:700;margin-top:4px;}
  .page-head p{margin:6px 0 0;color:var(--text-secondary);font-size:13.5px;max-width:52ch;}
  .date-pill{display:flex;align-items:center;gap:8px;background:var(--surface);border:1px solid var(--border);border-radius:999px;padding:9px 14px;font-size:12.5px;color:var(--text-secondary);white-space:nowrap;box-shadow:var(--shadow);}
  .date-pill .icon{color:var(--brand-blue-ink);}
  .date-pill b{color:var(--text);text-transform:capitalize;}

  .sample-note{font-size:11.5px;color:var(--text-muted);display:flex;align-items:center;gap:6px;}
  .sample-note .icon{width:14px;height:14px;}

  .card{background:var(--surface);border:1px solid var(--border);border-radius:var(--radius);box-shadow:var(--shadow);}
  .card-pad{padding:16px 18px;}
  .card-head{display:flex;justify-content:space-between;align-items:center;gap:10px;margin-bottom:12px;}
  .card-head h3{font-size:18px;font-weight:700;}
  .card-head .count{background:var(--surface-2);border:1px solid var(--border);color:var(--text-secondary);font-size:11px;font-weight:600;border-radius:999px;padding:1px 8px;margin-left:6px;}
  /* stat cards */
  .stat-grid{display:grid;grid-template-columns:repeat(4,1fr);gap:14px;}
  .stat-card{padding:16px 18px;display:flex;flex-direction:column;gap:10px;}
  .stat-top{display:flex;justify-content:space-between;align-items:center;}
  .stat-icon{width:38px;height:38px;border-radius:10px;display:flex;align-items:center;justify-content:center;}
  .stat-icon .icon{width:19px;height:19px;}
  .stat-icon-img{width:38px;height:38px;display:block;}
  .stat-label{font-size:15px;font-weight:600;color:var(--text);}
  .stat-value{font-family:var(--font-display);font-size:28px;font-weight:700;font-variant-numeric:tabular-nums;line-height:1;color:var(--brand-green);}
  .stat-trend{font-size:12px;color:var(--text-muted);display:flex;align-items:center;gap:5px;}
  .stat-trend b{color:var(--status-good);display:flex;align-items:center;gap:2px;font-weight:600;}
  .stat-trend b .icon{width:12px;height:12px;}

  /* two column row */
  .row-2{display:grid;grid-template-columns:1.7fr 1fr;gap:14px;align-items:stretch;}
  .select-fake{font-size:12px;color:var(--text-secondary);border:1px solid var(--border);border-radius:var(--radius-sm);padding:5px 10px;display:flex;align-items:center;gap:5px;background:var(--surface-2);}
  .select-fake .icon{width:13px;height:13px;}

  .chart-wrap{position:relative;}
  .chart-wrap svg{width:100%;height:auto;display:block;overflow:visible;}
  .chart-legend{display:flex;gap:16px;font-size:12px;color:var(--text-secondary);margin-bottom:10px;}
  .chart-legend .dot{width:9px;height:9px;border-radius:3px;display:inline-block;margin-right:6px;}
  .chart-tooltip{position:absolute;pointer-events:none;background:var(--text);color:var(--surface);font-size:11.5px;padding:6px 9px;border-radius:8px;transform:translate(-50%,-115%);white-space:nowrap;opacity:0;transition:opacity .1s;box-shadow:var(--shadow);z-index:3;}
  .chart-tooltip b{font-variant-numeric:tabular-nums;}
  .chart-hint{font-size:10.5px;color:var(--text-muted);margin-top:8px;}

  .donut-wrap{display:flex;flex-direction:column;align-items:center;gap:14px;}
  .donut-center{font-family:var(--font-display);}
  .donut-center tspan.pct{font-size:22px;font-weight:700;fill:var(--text);}
  .donut-center tspan.lbl{font-size:9px;fill:var(--text-muted);font-family:var(--font-body);}
  .donut-legend{width:100%;display:grid;grid-template-columns:1fr 1fr;gap:8px 12px;}
  .donut-legend .row{display:flex;align-items:center;gap:7px;font-size:12px;color:var(--text-secondary);}
  .donut-legend .dot{width:8px;height:8px;border-radius:999px;flex-shrink:0;}
  .donut-legend b{color:var(--text);margin-left:auto;font-variant-numeric:tabular-nums;}
  .status-banner{display:flex;gap:9px;align-items:flex-start;background:var(--surface-2);border:1px solid var(--border);border-radius:var(--radius-sm);padding:10px 12px;margin-top:2px;}
  .status-banner .icon{color:var(--status-good);margin-top:1px;}
  .status-banner p{margin:0;font-size:12px;color:var(--text-secondary);}
  .status-banner span{display:block;font-size:11px;color:var(--text-muted);margin-top:2px;}

  /* three column row */
  .row-3{display:grid;grid-template-columns:repeat(3,1fr);gap:14px;align-items:start;}
  .list{display:flex;flex-direction:column;gap:4px;}
  .list-row{display:flex;align-items:center;gap:10px;padding:8px 8px;border-radius:var(--radius-sm);}
  .list-row:hover{background:var(--surface-2);}
  .list-icon{width:30px;height:30px;border-radius:9px;display:flex;align-items:center;justify-content:center;flex-shrink:0;}
  .list-icon .icon{width:15px;height:15px;}
  .list-icon-img{width:30px;height:30px;flex-shrink:0;display:block;}
  .list-body{flex:1;min-width:0;}
  .list-title{font-size:13px;color:var(--text);white-space:nowrap;overflow:hidden;text-overflow:ellipsis;}
  .list-sub{font-size:11px;color:var(--text-muted);margin-top:1px;}
  .list-due{font-size:11px;font-weight:600;color:var(--text-muted);white-space:nowrap;}
  .list-due.urgent{color:var(--status-critical);}

  .quick-grid{display:grid;grid-template-columns:repeat(2,1fr);gap:8px;}
  .quick-item{display:flex;flex-direction:column;align-items:flex-start;gap:8px;padding:12px 10px;border:1px solid var(--border);border-radius:var(--radius-sm);background:var(--surface);cursor:pointer;text-align:left;}
  .quick-item:hover{border-color:var(--border-strong);background:var(--surface-2);}
  .quick-icon{width:30px;height:30px;border-radius:9px;display:flex;align-items:center;justify-content:center;}
  .quick-icon .icon{width:15px;height:15px;}
  .quick-icon-img{width:30px;height:30px;display:block;}
  .quick-item span{font-size:11.5px;color:var(--text-secondary);line-height:1.25;}

  /* module placeholder view */
  .module-view{display:flex;flex-direction:column;gap:16px;}
  .back-btn{align-self:flex-start;display:flex;align-items:center;gap:6px;background:none;border:1px solid var(--border);border-radius:999px;padding:7px 14px 7px 10px;font-size:12.5px;color:var(--text-secondary);cursor:pointer;}
  .back-btn:hover{background:var(--surface-2);}
  .module-head{display:flex;align-items:center;gap:14px;}
  .module-head .stat-icon{width:46px;height:46px;border-radius:12px;}
  .module-head .stat-icon .icon{width:22px;height:22px;}
  .module-head-icon-img{width:46px;height:46px;display:block;}
  .module-head h2{font-size:20px;font-weight:700;}
  .module-head p{margin:2px 0 0;font-size:12.5px;color:var(--text-muted);}
  .module-items{display:grid;grid-template-columns:repeat(2,1fr);gap:8px;}
  .module-item{display:flex;justify-content:space-between;align-items:center;gap:10px;background:var(--surface);border:1px solid var(--border);border-radius:var(--radius-sm);padding:11px 14px;font-size:13px;box-shadow:var(--shadow);}
  .module-item .icon{color:var(--text-muted);width:15px;height:15px;flex-shrink:0;}
  .module-item-link{cursor:pointer;}
  .module-item-link:hover{border-color:var(--border-strong);background:var(--surface-2);}
  .module-item-link:hover .icon{color:var(--sidebar-bg);}

  .home-view{display:flex;flex-direction:column;gap:18px;}

  /* ---------- Ficha del asociado (y solapas en general) ----------
     Componentes reutilizables: encabezado (avatar + nombre + badges +
     acciones), resumen (tiles chicos), solapas, tarjetas de info
     label/valor (modo consulta, sin inputs), tarjetas de entidad
     (suministros), tabla de estado (reclamos/aportes) y alerta info. */
  .ficha-card{display:flex;flex-direction:column;gap:0;}

  .ficha-header{display:flex;justify-content:space-between;align-items:flex-start;flex-wrap:wrap;gap:16px;margin-bottom:18px;}
  .ficha-id{display:flex;gap:14px;align-items:flex-start;min-width:0;}
  .ficha-avatar{width:52px;height:52px;border-radius:999px;background:var(--brand-accent-bg);color:var(--sidebar-bg);font-family:var(--font-display);font-weight:700;font-size:17px;display:flex;align-items:center;justify-content:center;flex-shrink:0;}
  .ficha-id-text{display:flex;flex-direction:column;min-width:0;}
  .ficha-kicker{font-size:11px;font-weight:600;letter-spacing:.05em;text-transform:uppercase;color:var(--text-muted);margin:0;}
  .ficha-name{font-size:19px;font-weight:700;margin:3px 0 0;}
  .ficha-sub{font-size:12.5px;color:var(--text-secondary);margin:4px 0 0;}
  .ficha-badges{display:flex;flex-wrap:wrap;gap:6px;margin-top:9px;}
  .ficha-actions{display:flex;align-items:center;gap:8px;flex-shrink:0;}

  .role-badge{font-size:11.5px;font-weight:600;padding:4px 11px;border-radius:999px;background:var(--brand-accent-bg);color:var(--sidebar-bg);}
  .role-badge.muted{background:var(--surface-2);border:1px solid var(--border);color:var(--text-muted);font-weight:400;}

  .status-chip{display:inline-flex;align-items:center;gap:6px;font-size:11.5px;font-weight:600;padding:4px 10px 4px 8px;border-radius:999px;background:var(--surface-2);border:1px solid var(--border);color:var(--text-secondary);}
  .status-chip i{width:7px;height:7px;border-radius:999px;background:var(--status-neutral);display:block;flex-shrink:0;}
  .status-chip.good{color:var(--status-good);border-color:color-mix(in srgb, var(--status-good) 30%, var(--border));background:color-mix(in srgb, var(--status-good) 10%, var(--surface-2));}
  .status-chip.good i{background:var(--status-good);}

  /* ---------- Sistema de botones (Button System) ----------
     Componente global y único para toda la interfaz: una clase base .btn
     con todo lo común (altura, tipografía, radio, íconos, foco, estado
     disabled) + variantes de color que solo definen la diferencia. Nunca
     se usa una variante sola: siempre junto a .btn, por ejemplo
     class="btn btn-primary". Funciona igual en <button> y en <a>.

     Color: Primary/Secondary/Tertiary usan var(--sidebar-bg) y
     var(--sidebar-bg-active) — las mismas variables que ya sigue el
     selector de marca azul/verde (ver bloque [data-brand="green"] más
     arriba) — así que automáticamente cambian de color si cambia la
     marca, sin tocar este archivo. Danger/Success/Warning/Info usan los
     --status-*, que son fijos y no siguen la marca. Success/Warning/Info
     reutilizan el mismo criterio de "tinte suave" (color-mix con blanco)
     que ya usan .status-pill y .alert-banner, para mantener un único
     lenguaje visual de color semántico en todo el sistema.

     Tamaños: .btn-sm (28px) / sin modificador (32px, el estándar) /
     .btn-lg (40px). .btn-icon es la variante cuadrada para botones de
     solo ícono (editar, eliminar, "⋯"). .btn-loading deshabilita el
     botón y gira su ícono (pensado para usarse con el ícono #i-spinner
     y el texto cambiado a algo como "Guardando..."). .btn-block lo hace
     100% de ancho (nunca automático en mobile — hay que sumarlo a
     propósito). */
  .btn{
    display:inline-flex;align-items:center;justify-content:center;gap:7px;
    height:32px;padding:0 16px;
    border-radius:var(--radius-btn);border:1px solid transparent;
    font-family:var(--font-body);font-size:13px;font-weight:600;line-height:1;
    cursor:pointer;white-space:nowrap;text-decoration:none;
    transition:background-color .12s ease, border-color .12s ease, color .12s ease, opacity .12s ease;
    vertical-align:middle;
  }
  .btn .icon{width:16px;height:16px;flex-shrink:0;}
  .btn:focus-visible{outline:2px solid var(--sidebar-bg);outline-offset:2px;}
  .btn:disabled, .btn.btn-disabled, .btn[aria-disabled="true"]{
    opacity:.5;cursor:not-allowed;pointer-events:none;
  }

  /* tamaños */
  .btn-sm{height:28px;padding:0 12px;font-size:12px;gap:6px;}
  .btn-sm .icon{width:14px;height:14px;}
  .btn-lg{height:40px;padding:0 20px;font-size:14px;gap:8px;}
  .btn-lg .icon{width:18px;height:18px;}

  /* ancho completo — opcional, nunca automático en mobile */
  .btn-block{width:100%;}

  /* solo ícono — mismo alto que el tamaño activo, ancho = alto */
  .btn-icon{width:32px;padding:0;gap:0;position:relative;}
  .btn-icon.btn-sm{width:28px;}
  .btn-icon.btn-lg{width:40px;}

  /* Primary — acción principal de la pantalla */
  .btn-primary{background:var(--sidebar-bg);border-color:var(--sidebar-bg);color:#fff;}
  .btn-primary:hover{background:var(--sidebar-bg-active);border-color:var(--sidebar-bg-active);}
  .btn-primary:active{background:var(--sidebar-brand-bg);border-color:var(--sidebar-brand-bg);}

  /* Secondary — importante pero no es la acción principal */
  .btn-secondary{background:none;border-color:var(--sidebar-bg);color:var(--sidebar-bg);}
  .btn-secondary:hover{background:var(--brand-accent-bg);}
  .btn-secondary:active{background:var(--brand-accent-bg);border-color:var(--sidebar-bg-active);color:var(--sidebar-bg-active);}

  /* Tertiary — menor jerarquía (Ver más, Cancelar, Volver, Limpiar filtros) */
  .btn-tertiary{background:none;border-color:transparent;color:var(--sidebar-bg);}
  .btn-tertiary:hover{background:var(--brand-accent-bg);}
  .btn-tertiary:active{background:var(--brand-accent-bg);color:var(--sidebar-bg-active);}

  /* Ghost — jerarquía mínima: configuración, "⋯", controles auxiliares */
  .btn-ghost{background:none;border-color:transparent;color:var(--text-secondary);}
  .btn-ghost:hover{background:var(--surface-2);border-color:var(--border);}
  .btn-ghost:active{background:var(--surface);border-color:var(--border-strong);}

  /* Danger — acciones destructivas. Outline es el comportamiento normal;
     .btn-solid es solo para confirmaciones destructivas importantes
     (no usar el color rojo para acciones que no sean estas). */
  .btn-danger{background:none;border-color:var(--status-critical);color:var(--status-critical);}
  .btn-danger:hover{background:color-mix(in srgb, var(--status-critical) 10%, white);}
  .btn-danger:active{background:color-mix(in srgb, var(--status-critical) 18%, white);}
  .btn-danger.btn-solid{background:var(--status-critical);border-color:var(--status-critical);color:#fff;}
  .btn-danger.btn-solid:hover{background:color-mix(in srgb, var(--status-critical) 85%, black);border-color:color-mix(in srgb, var(--status-critical) 85%, black);}
  .btn-danger.btn-solid:active{background:color-mix(in srgb, var(--status-critical) 70%, black);border-color:color-mix(in srgb, var(--status-critical) 70%, black);}

  /* Success / Warning / Info — mismo criterio de tinte suave que ya usan
     .status-pill y .alert-banner. No reemplazan a Primary: se usan solo
     cuando el significado semántico de la acción lo justifica. */
  .btn-success{background:color-mix(in srgb, var(--status-good) 14%, white);border-color:transparent;color:var(--status-good);}
  .btn-success:hover{background:color-mix(in srgb, var(--status-good) 24%, white);}
  .btn-warning{background:color-mix(in srgb, var(--status-warning) 16%, white);border-color:transparent;color:var(--status-warning);}
  .btn-warning:hover{background:color-mix(in srgb, var(--status-warning) 26%, white);}
  .btn-info{background:color-mix(in srgb, var(--status-info) 14%, white);border-color:transparent;color:var(--status-info);}
  .btn-info:hover{background:color-mix(in srgb, var(--status-info) 24%, white);}

  /* Loading — pensado para usarse junto con el ícono #i-spinner */
  .btn-loading{cursor:wait;pointer-events:none;opacity:.85;}
  .btn-loading .icon{animation:btn-spin .7s linear infinite;}
  @keyframes btn-spin{to{transform:rotate(360deg);}}

  /* ---------- Menú desplegable de un botón (Exportar ▾, etc.) ----------
     Mismo lenguaje visual que el resto del sistema: el panel reutiliza
     el fondo/borde/radio/sombra de .card y cada opción tiene un hover
     suave igual a .btn-ghost. Abrir/cerrar: ver initBtnDropdowns en
     dashboard.js (data-dropdown-toggle / data-dropdown-menu). */
  .btn-dropdown{position:relative;display:inline-flex;}
  .btn-dropdown-menu{
    position:absolute;top:calc(100% + 6px);right:0;min-width:180px;
    background:var(--surface);border:1px solid var(--border);border-radius:var(--radius-sm);
    box-shadow:var(--shadow);padding:6px;z-index:30;
    display:flex;flex-direction:column;gap:2px;
  }
  .btn-dropdown-menu[hidden]{display:none;}
  .btn-dropdown-item{
    display:flex;align-items:center;gap:8px;width:100%;
    background:none;border:none;border-radius:var(--radius-sm);
    padding:8px 10px;font-family:var(--font-body);font-size:13px;color:var(--text);
    text-align:left;cursor:pointer;
  }
  .btn-dropdown-item:hover{background:var(--surface-2);}
  .btn-dropdown-item .icon{width:15px;height:15px;color:var(--text-muted);flex-shrink:0;}

  .ficha-summary{display:grid;grid-template-columns:repeat(4,1fr);gap:10px;margin-bottom:18px;}
  .ficha-summary-tile{display:flex;align-items:center;justify-content:space-between;gap:8px;background:var(--surface-2);border:1px solid var(--border);border-radius:var(--radius-sm);padding:10px 13px;}
  .ficha-summary-text{display:flex;flex-direction:column;gap:2px;min-width:0;}
  .ficha-summary-label{font-size:11px;color:var(--text-muted);}
  .ficha-summary-value{font-size:14.5px;font-weight:700;color:var(--text);font-family:var(--font-display);}
  .ficha-summary-value.good{color:var(--status-good);}
  .ficha-summary-chevron{width:14px;height:14px;color:var(--text-muted);flex-shrink:0;}

  .ficha-tabs{display:flex;gap:4px;overflow-x:auto;border-bottom:1px solid var(--border);margin-bottom:16px;}
  .ficha-tab{background:none;border:none;border-bottom:2px solid transparent;color:var(--text-secondary);font-family:var(--font-body);font-size:13px;padding:9px 12px;white-space:nowrap;cursor:pointer;margin-bottom:-1px;}
  .ficha-tab:hover{color:var(--text);}
  .ficha-tab.active{color:var(--brand-green);border-bottom-color:var(--brand-green);border-bottom-width:3px;font-weight:600;}
  .ficha-tab.dashed{border-bottom-style:dashed;color:var(--text-muted);}
  .ficha-tab.dashed.active{color:var(--brand-green);border-bottom-color:var(--brand-green);border-bottom-style:solid;}

  .ficha-note{font-size:12px;color:var(--text-muted);margin:0 0 12px;}

  /* tarjetas label/valor — modo consulta, sin <input> */
  .info-grid{display:grid;grid-template-columns:1fr 1fr;gap:14px;}
  .info-card{border:1px solid var(--border);border-radius:var(--radius-sm);padding:14px 16px;background:var(--surface);}
  .info-card-head{display:flex;align-items:center;gap:8px;margin-bottom:12px;}
  .info-card-head .icon{width:16px;height:16px;color:var(--sidebar-bg);}
  .info-card-head h3{font-size:13.5px;font-weight:700;margin:0;}
  .info-card-fields{display:grid;grid-template-columns:1fr 1fr;gap:12px 16px;}
  .info-card-fields-standalone{margin-bottom:14px;}
  .info-field{display:flex;flex-direction:column;gap:3px;min-width:0;}
  .info-label{font-size:11.5px;color:var(--text-muted);}
  .info-value{font-size:13.5px;color:var(--text);word-break:break-word;}
  .info-field.disabled .info-value{color:var(--text-muted);}

  .ficha-table-wrap{overflow-x:auto;}
  .ficha-table{width:100%;border-collapse:collapse;font-size:13px;}
  .ficha-table th{text-align:left;font-weight:600;color:var(--text-secondary);font-size:12px;padding:0 16px 8px 0;}
  .ficha-table td{padding:9px 16px 9px 0;border-top:1px solid var(--border);}
  .ficha-table td:last-child, .ficha-table th:last-child{text-align:right;}

  /* ---------- Tabla responsive genérica (componente reutilizable) ----------
     Mismo comportamiento que las tablas de argentina.gob.ar en mobile: el
     <thead> se oculta (sigue en el DOM, accesible, pero fuera de pantalla)
     y cada <tr> pasa a ser un bloque vertical de ancho completo — sin
     scroll horizontal — donde cada <td> muestra primero el nombre de su
     columna (vía el atributo data-th, con ::before) y debajo su valor.
     Se activa agregando la clase .table-responsive a una .ficha-table; cada
     <td> necesita su data-th, que sale solo si la celda se escribe con
     {% cell "Etiqueta" %}…{% endcell %} en vez de <td>…</td> (ver
     core/templatetags/core_extras.py) — así cualquier tabla nueva suma el
     comportamiento responsive sin reprogramarlo, solo reutilizando este
     bloque de CSS y ese tag. El diseño (colores, radios, tipografía) es el
     mismo que ya usa GELETRIC en el resto del sistema, no el de
     argentina.gob.ar — de ahí solo se toma el comportamiento. */
  @media (max-width: 860px){
    .table-responsive, .table-responsive thead, .table-responsive tbody,
    .table-responsive th, .table-responsive td, .table-responsive tr{
      display:block;width:100%;
    }
    .table-responsive thead tr{position:absolute;top:-9999px;left:-9999px;}
    .table-responsive tbody tr{
      border:1px solid var(--border);border-radius:var(--radius-sm);
      padding:0 14px;margin-bottom:10px;
      background:var(--surface);
    }
    .table-responsive tbody tr:last-child{margin-bottom:0;}
    .table-responsive tbody tr:nth-child(odd){background:var(--surface);}
    .table-responsive tbody tr:nth-child(even){background:var(--surface-2);}
    .table-responsive td{
      padding:9px 0;border-top:1px solid var(--border);
      text-align:left!important;
    }
    .table-responsive td:first-child{border-top:none;}
    .table-responsive td::before{
      content:attr(data-th);display:block;
      font-weight:600;font-size:12px;color:var(--text-secondary);
      margin-bottom:2px;
    }
  }

  /* ---------- Modo accordion para filas mobile (extensión del componente
     responsive de arriba) ----------
     Son los mismos <td> de siempre (generados con {% cell %}), pero en vez
     de quedar todos visibles en bloque, se ocultan por default y sólo se
     muestran cuando se abre la fila — así en una pantalla chica entran
     muchos registros de un vistazo, y se puede entrar al detalle de a uno.
     Se activa sumando la clase .table-accordion (además de
     .table-responsive) a la tabla, y agregando un {% rowsummary %}…
     {% endrowsummary %} como PRIMERA celda de cada <tr> (ver
     core/templatetags/core_extras.py) con lo que se quiere ver siempre,
     aunque la fila esté cerrada — en Asociados es nombre + N° + estado,
     pero queda a criterio de cada tabla (por ejemplo, en Órdenes de
     Trabajo podría ser N° de OT + cliente + estado). Las columnas que ya
     están repetidas en ese resumen se marcan con
     {% cell "Label" "accordion-hide" %} para que no se dupliquen en el
     detalle. Abrir/cerrar cada fila es dashboard.js (initAccordionRows)
     — con CSS solo no alcanza porque cada fila necesita su propio estado
     independiente.
     En desktop esta celda nueva no debe verse (ahí la tabla sigue mostrando
     sus columnas de siempre, intactas) — por eso .row-summary arranca en
     display:none fuera de la media query, y solo la media query de abajo
     la vuelve a mostrar en mobile. */
  .table-accordion td.row-summary{display:none;}

  @media (max-width: 860px){
    .table-accordion tbody tr{padding:0;}
    .table-accordion td.row-summary{
      display:block;border-top:none!important;padding:0;
    }
    .table-accordion .row-summary-btn{
      display:flex;align-items:center;justify-content:space-between;gap:10px;
      width:100%;background:none;border:none;padding:11px 14px;margin:0;
      font-family:var(--font-body);text-align:left;cursor:pointer;color:inherit;
    }
    .table-accordion .row-summary-content{display:flex;flex-direction:column;gap:3px;min-width:0;}
    .table-accordion .row-summary-title{font-size:13.5px;font-weight:600;color:var(--text);}
    .table-accordion .row-summary-meta{display:flex;align-items:center;gap:6px;font-size:12px;color:var(--text-muted);}
    .table-accordion .row-summary-dot{opacity:.6;}
    .table-accordion .row-chevron{color:var(--text-muted);flex-shrink:0;transition:transform .15s ease;}
    .table-accordion tr.open .row-chevron{transform:rotate(180deg);}

    .table-accordion td:not(.row-summary){
      display:none;padding-left:14px;padding-right:14px;
    }
    .table-accordion tr.open td:not(.row-summary){display:block;}
    .table-accordion tr.open td.accordion-hide{display:none!important;}
    .table-accordion tr.open td:last-child{padding-bottom:11px;}
  }

  .status-pill{display:inline-flex;align-items:center;font-size:11.5px;font-weight:600;padding:3px 10px;border-radius:999px;background:var(--surface-2);color:var(--text-secondary);}
  .status-pill.good{background:color-mix(in srgb, var(--status-good) 14%, white);color:var(--status-good);}
  .status-pill.warning{background:color-mix(in srgb, var(--status-warning) 16%, white);color:var(--status-warning);}
  .status-pill.critical{background:color-mix(in srgb, var(--status-critical) 14%, white);color:var(--status-critical);}
  .status-pill.neutral{background:var(--surface-2);color:var(--text-muted);}
  .table-link{display:inline-flex;align-items:center;gap:3px;font-size:12.5px;font-weight:600;color:var(--sidebar-bg);}
  .table-link .icon{width:13px;height:13px;}

  /* tarjetas de suministro — no una línea plana */
  .entity-cards{display:flex;flex-direction:column;gap:10px;}
  .entity-card{border:1px solid var(--border);border-radius:var(--radius-sm);padding:12px 15px;background:var(--surface);}
  .entity-card-head{display:flex;justify-content:space-between;align-items:center;gap:8px;margin-bottom:6px;}
  .entity-card-nis{font-size:12px;font-weight:600;color:var(--text-secondary);}
  .entity-card-title{font-size:14px;font-weight:600;margin:0;}
  .entity-card-sub{font-size:12px;color:var(--text-muted);margin:3px 0 8px;}
  .entity-card-action{display:inline-flex;align-items:center;gap:4px;font-size:12.5px;font-weight:600;color:var(--sidebar-bg);}
  .entity-card-action .icon{width:14px;height:14px;}

  .ficha-rows{display:flex;flex-direction:column;gap:8px;}
  .ficha-row{display:flex;justify-content:space-between;align-items:center;gap:10px;border:1px solid var(--border);border-radius:var(--radius-sm);padding:10px 13px;font-size:13px;}
  .ficha-row.dashed{border-style:dashed;border-color:var(--border-strong);color:var(--text-secondary);}
  .ficha-row .value{color:var(--text-secondary);font-size:12px;flex-shrink:0;}

  /* alerta de modo consulta — azul informativo fijo, no sigue el
     selector de marca (a diferencia de "Editar asociado", que sí). */
  .info-alert{display:flex;gap:9px;align-items:flex-start;background:#eaf1fd;border:1px solid #c9dcf7;border-radius:var(--radius-sm);padding:11px 13px;margin-top:16px;}
  .info-alert .icon{color:#1d4fa8;margin-top:1px;width:16px;height:16px;}
  .info-alert p{margin:0;font-size:12.5px;color:#1d4fa8;}

  /* ---------- Menú de Asociados y servicios (tarjetas → páginas internas) ---------- */
  .module-head{flex-wrap:wrap;}
  .asoc-help-btn{margin-left:auto;}
  .asoc-help-btn .icon:first-child{color:var(--sidebar-bg);}

  .asoc-menu-grid{display:grid;grid-template-columns:repeat(2,1fr);gap:14px;}
  .asoc-menu-card{display:flex;align-items:center;gap:14px;background:var(--surface);border:1px solid var(--border);border-radius:var(--radius);padding:16px 18px;box-shadow:var(--shadow);text-decoration:none;color:inherit;}
  .asoc-menu-card:hover{border-color:var(--border-strong);background:var(--surface-2);}
  .asoc-menu-icon{width:44px;height:44px;border-radius:12px;background:var(--brand-accent-bg);color:var(--sidebar-bg);display:flex;align-items:center;justify-content:center;flex-shrink:0;}
  .asoc-menu-icon .icon{width:22px;height:22px;}
  .asoc-menu-icon-lg{width:46px;height:46px;}
  .asoc-menu-text{flex:1;min-width:0;display:flex;flex-direction:column;gap:3px;}
  .asoc-menu-text b{font-size:14.5px;color:var(--text);font-weight:700;}
  .asoc-menu-text span{font-size:12.5px;color:var(--text-muted);}
  .asoc-menu-chevron{color:var(--text-muted);width:16px;height:16px;flex-shrink:0;}
  .asoc-menu-card:hover .asoc-menu-chevron{color:var(--sidebar-bg);}

  /* Globito flotante para los íconos del sidebar colapsado (ver
     initSidebarTooltips en dashboard.js). Es un único elemento compartido
     que vive fuera del sidebar (base.html, #icon-tooltip) y se posiciona
     con getBoundingClientRect() al pasar el mouse o el foco por un ítem.
     No puede armarse con un <span> position:absolute DENTRO de cada
     .nav-item porque el sidebar necesita overflow-y:auto para poder
     scrollear un menú largo, y por especificación CSS eso obliga a que
     overflow-x TAMBIÉN recorte (no hay forma de dejar solo un eje
     "visible") — cualquier globito que se dibuje saliendo por el borde
     derecho del sidebar quedaría cortado. */
  .icon-tooltip{
    position:fixed;transform:translateY(-50%);
    background:var(--sidebar-bg-active);color:var(--sidebar-text-active);
    font-size:12.5px;font-weight:600;white-space:nowrap;
    padding:7px 12px;border-radius:var(--radius-sm);box-shadow:var(--shadow);
    opacity:0;visibility:hidden;pointer-events:none;
    transition:opacity .12s ease;
    z-index:1000;
  }
  .icon-tooltip.visible{opacity:1;visibility:visible;}

  /* ---------- Sidebar en reposo: solo íconos + isologo compacto.
     Pasar el cursor (o entrar por teclado) sobre un ícono muestra solo el
     globito de arriba con el nombre de esa opción — el sidebar en sí
     sigue angosto. Para expandirlo del todo hay que "pinearlo" con el
     botón hamburguesa del topbar (#menu-btn, ver dashboard.js), que
     agrega/saca la clase .pinned y la guarda en localStorage para que el
     estado se mantenga al navegar entre páginas. Solo aplica en
     escritorio: en mobile el sidebar ya es un cajón aparte que se abre
     con el botón de menú. ---------- */
  @media (min-width: 861px){
    .sidebar{width:80px;}
    .sidebar.pinned{width:252px;}

    .brand{justify-content:center;}
    .sidebar.pinned .brand{justify-content:flex-start;}
    .brand-logo-full{display:none;}
    .brand-logo-icon{display:block;}
    .sidebar.pinned .brand-logo-full{display:block;}
    .sidebar.pinned .brand-logo-icon{display:none;}

    .nav-item{justify-content:center;padding:9px 0;}
    /* Colapsado: el nombre del ítem lo muestra el globito compartido de
       arriba (dashboard.js), así que el <span> de acá se oculta nomás. */
    .nav-item span{display:none;}

    .sidebar.pinned .nav-item{justify-content:flex-start;padding:9px 10px;}
    .sidebar.pinned .nav-item span{display:inline;}

    .sidebar-divider, .sidebar-meta{display:none;}
    .energy-bar{display:none;}
    .sidebar.pinned .sidebar-divider{display:block;}
    .sidebar.pinned .energy-bar{display:block;}
    .sidebar.pinned .sidebar-meta{display:flex;}

    /* Buscador: solo tiene sentido si hay dónde escribir texto, así que
       se oculta colapsado igual que el resto del contenido con texto. */
    .sidebar-search-wrap{display:none;}
    .sidebar.pinned .sidebar-search-wrap{display:block;}
  }

  @media (max-width: 1080px){
    .stat-grid{grid-template-columns:repeat(2,1fr);}
    .row-2{grid-template-columns:1fr;}
    .row-3{grid-template-columns:1fr;}
    .module-items{grid-template-columns:1fr;}
    .asoc-menu-grid{grid-template-columns:1fr;}
  }
  @media (max-width: 860px){
    .ficha-summary{grid-template-columns:repeat(2,1fr);}
    .info-grid{grid-template-columns:1fr;}
    .info-card-fields{grid-template-columns:1fr;}
    .ficha-header{gap:12px;}
    .ficha-actions{width:100%;}
    .ficha-actions .btn-primary{flex:1;justify-content:center;}
    .sidebar{position:fixed;left:0;top:0;z-index:20;transform:translateX(-100%);box-shadow:0 0 0 100vmax rgba(0,0,0,0);}
    .sidebar.open{transform:translateX(0);box-shadow:20px 0 60px rgba(0,0,0,.35);}
    .menu-btn{display:flex;}
    .topbar-search-wrap{max-width:none;}
    .search kbd{display:none;}
    .user-chip .who{display:none;}
    .topbar{padding:10px 14px;gap:8px;}
    .stat-grid{grid-template-columns:1fr;}
    .quick-grid{grid-template-columns:1fr;}
    .asoc-help-btn{margin-left:0;}
  }
  .scrim{display:none;position:fixed;inset:0;background:rgba(10,14,30,.45);z-index:15;}
  .scrim.open{display:block;}

  .logout-form{display:contents;margin:0;}

  /* ---------- Login (pantalla de autenticación, sin sidebar/topbar) ----------
     Fondo con degradé azul → verde (los dos colores de marca fijos, no
     reactivos al selector azul/verde del sistema — acá todavía no hay sesión
     iniciada). Tarjeta blanca centrada, con el mismo sistema tipográfico y
     los mismos íconos del resto de GELETRIC. */
  .auth-shell{min-height:100vh;width:100%;display:flex;align-items:center;justify-content:center;padding:24px;background:linear-gradient(135deg, #244c97 0%, #1b6b4c 100%);}
  .auth-card{width:100%;max-width:400px;background:var(--surface);border-radius:var(--radius);box-shadow:0 8px 40px rgba(10,20,50,.25);padding:36px 32px 32px;display:flex;flex-direction:column;align-items:center;text-align:center;}
  .auth-logo{width:100%;max-width:190px;height:auto;display:block;margin-bottom:18px;}
  .auth-title{font-size:19px;font-weight:700;margin:0;}
  .auth-sub{font-size:13px;color:var(--text-secondary);margin:6px 0 0;}

  .auth-form{width:100%;display:flex;flex-direction:column;gap:16px;margin-top:22px;text-align:left;}
  .auth-field{display:flex;flex-direction:column;gap:6px;}
  .auth-field[hidden]{display:none;}
  .auth-field-label{font-size:12.5px;font-weight:600;color:var(--text-secondary);}
  .auth-input-wrap{display:flex;align-items:center;gap:8px;border:1px solid var(--border);border-radius:var(--radius-sm);padding:10px 12px;background:var(--surface-2);}
  .auth-input-wrap:focus-within{border-color:var(--sidebar-bg);background:var(--surface);}
  .auth-input-wrap.error{border-color:var(--status-critical);}
  .auth-input-wrap .icon{color:var(--text-muted);flex-shrink:0;}
  .auth-input{border:none;background:none;outline:none;font-family:var(--font-body);font-size:13.5px;color:var(--text);width:100%;}
  .auth-field-error{font-size:11.5px;color:var(--status-critical);}

  /* Ojito para mostrar/ocultar la contraseña del login — mismo <span
     class="auth-input-wrap"> de siempre, solo se agrega un tercer hijo
     (el ícono y el <input> ya eran los primeros dos) así que el flex
     existente lo acomoda solo, sin tocar el layout del resto del form. */
  .auth-pw-toggle{display:flex;align-items:center;justify-content:center;background:none;border:none;padding:0;margin:0;color:var(--text-muted);cursor:pointer;flex-shrink:0;}
  .auth-pw-toggle:hover{color:var(--text-secondary);}
  .auth-pw-toggle .icon{width:18px;height:18px;}

  .auth-row{display:flex;justify-content:space-between;align-items:center;gap:10px;flex-wrap:wrap;}
  .auth-check{display:flex;align-items:center;gap:7px;font-size:12.5px;color:var(--text-secondary);cursor:pointer;}
  .auth-link{font-size:12.5px;font-weight:600;color:var(--sidebar-bg);}

  /* ---------- Cartel de alerta reutilizable (errores de formulario y avisos) ----------
     Distinto de .info-alert (que es un aviso fijo, siempre celeste, solo
     para la Ficha del asociado): este cambia de color según el estado. */
  .alert-banner{display:flex;gap:9px;align-items:flex-start;border-radius:var(--radius-sm);padding:11px 13px;margin-bottom:14px;}
  .alert-banner:last-child{margin-bottom:0;}
  .alert-banner p{margin:0;font-size:12.5px;}
  .alert-banner .icon{width:16px;height:16px;margin-top:1px;flex-shrink:0;}
  .alert-banner.critical{background:color-mix(in srgb, var(--status-critical) 10%, white);border:1px solid color-mix(in srgb, var(--status-critical) 28%, var(--border));}
  .alert-banner.critical .icon, .alert-banner.critical p{color:var(--status-critical);}
  .alert-banner.warning{background:color-mix(in srgb, var(--status-warning) 12%, white);border:1px solid color-mix(in srgb, var(--status-warning) 30%, var(--border));}
  .alert-banner.warning .icon, .alert-banner.warning p{color:var(--status-warning);}
  .alert-banner.good{background:color-mix(in srgb, var(--status-good) 10%, white);border:1px solid color-mix(in srgb, var(--status-good) 28%, var(--border));}
  .alert-banner.good .icon, .alert-banner.good p{color:var(--status-good);}

  /* ---------- Wizard reutilizable (pasos de un proceso largo) ----------
     Estados por paso: done (completado, verde con check), active (paso
     actual, color de marca), pendiente (sin clase extra, gris/mudo). La
     línea entre dos pasos se pinta de verde automáticamente cuando el paso
     anterior está "done" (selector de hermano adyacente, sin JS). */
  .wizard{display:flex;align-items:flex-start;}
  .wizard-step{flex:1;display:flex;flex-direction:column;align-items:center;gap:8px;position:relative;text-align:center;padding:0 4px;}
  .wizard-step:not(:first-child)::before{content:"";position:absolute;top:16px;left:-50%;width:100%;height:2px;background:var(--border-strong);z-index:0;}
  .wizard-step.done + .wizard-step::before{background:var(--status-good);}
  .wizard-step-dot{width:32px;height:32px;border-radius:999px;display:flex;align-items:center;justify-content:center;font-family:var(--font-display);font-size:13px;font-weight:700;background:var(--surface-2);border:1px solid var(--border-strong);color:var(--text-muted);position:relative;z-index:1;flex-shrink:0;}
  .wizard-step-dot .icon{width:15px;height:15px;}
  .wizard-step.active .wizard-step-dot{background:var(--sidebar-bg);border-color:var(--sidebar-bg);color:#fff;}
  .wizard-step.done .wizard-step-dot{background:var(--status-good);border-color:var(--status-good);color:#fff;}
  .wizard-step-label{font-size:12px;color:var(--text-muted);}
  .wizard-step.active .wizard-step-label{color:var(--text);font-weight:600;}
  .wizard-step.done .wizard-step-label{color:var(--text-secondary);}

  @media (max-width: 480px){
    .auth-card{padding:28px 20px 24px;}
    .wizard{flex-direction:column;align-items:flex-start;gap:14px;}
    .wizard-step{flex-direction:row;text-align:left;padding:0;width:100%;}
    .wizard-step::before{display:none;}
  }

  /* ---------- Listado de asociados (buscador + filtros) ----------
     Reutiliza el mismo lenguaje visual que el resto del sistema (icono +
     input tipo .auth-input-wrap, tabla .ficha-table, .status-pill,
     .table-link) — acá el <select> es funcional: filtra de verdad vía GET,
     sin JS ni lógica de más. */
  .list-toolbar{display:flex;flex-direction:column;align-items:stretch;gap:14px;margin-bottom:16px;}
  .list-search{display:flex;align-items:center;gap:8px;border:1px solid var(--border);border-radius:var(--radius-sm);padding:8px 12px;background:var(--surface-2);width:100%;}
  .list-search .icon{color:var(--text-muted);flex-shrink:0;}
  .list-search input{border:none;background:none;outline:none;font-family:var(--font-body);font-size:13.5px;color:var(--text);width:100%;}
  .list-select{border:1px solid var(--border);border-radius:var(--radius-sm);padding:8px 10px;background:var(--surface-2);font-family:var(--font-body);font-size:13px;color:var(--text-secondary);cursor:pointer;}
  .list-count{font-size:12px;color:var(--text-muted);margin:0 0 10px;}

  /* ---------- Filtros colapsables (componente reutilizable) ----------
     Lo que va DENTRO del bloque colapsable se envuelve en un
     <div class="list-filters-panel" data-filters-panel>: en desktop
     display:contents hace que sus hijos (acá, los <select> y los botones
     Filtrar/Limpiar) se comporten como si ese div no existiera — el
     .list-toolbar de siempre, sin ningún cambio. En mobile se oculta por
     default y se muestra/oculta con un botón
     <button data-filters-toggle aria-controls="…">, ver
     initFiltersToggle en dashboard.js. Lo único que cada tabla decide que
     quede SIEMPRE visible afuera de ese div (acá, el buscador) se deja
     fuera del wrapper. Mismo mecanismo reutilizable para cualquier otro
     listado del sistema. */
  .list-filters-panel{display:contents;}
  .filters-toggle{display:none;}

  @media (max-width: 860px){
    .list-toolbar{flex-direction:column;align-items:stretch;}

    .filters-toggle{
      display:flex;align-items:center;gap:8px;width:100%;
      background:var(--surface-2);border:1px solid var(--border);border-radius:var(--radius-btn);
      color:var(--text);font-family:var(--font-body);font-size:13px;font-weight:600;
      padding:9px 14px;cursor:pointer;
    }
    .filters-toggle .icon{color:var(--sidebar-bg);flex-shrink:0;}
    .filters-toggle span{flex:1;text-align:left;}
    .filters-toggle-chev{transition:transform .15s ease;flex-shrink:0;}
    .filters-toggle[aria-expanded="true"] .filters-toggle-chev{transform:rotate(180deg);}
    .filters-toggle.active{border-color:var(--sidebar-bg);}
    .filters-toggle.active::after{content:"";width:7px;height:7px;border-radius:999px;background:var(--brand-green);flex-shrink:0;}

    .list-filters-panel:not(.open){display:none;}
    .list-filters-panel.open{display:flex;flex-direction:column;gap:10px;width:100%;margin-top:10px;}
    .list-filters-panel .list-select{width:100%;}
  }

  /* ---------- Filtros avanzados ("+ Agregar filtro") ----------
     Cada filtro agregado es un "field" propio — label arriba (con la ×
     para sacarlo del todo alineada a la derecha) y el control debajo —
     ya no un chip con etiqueta + valor + quitar amontonados en la misma
     caja. Los fields se acomodan con flex-wrap, cada uno con el ancho
     que le resulta natural según su tipo: un <select> sin width fijo ya
     se ensancha solo según su opción más larga (por eso "Condición de
     IVA" sale más ancho que "Localidad" sin tener que pedírselo a mano).
     Arrancan sin mostrarse — el botón "+ Agregar filtro" (un
     .btn-dropdown del Button System, ver más arriba) lista los filtros
     que todavía faltan agregar, y elegir uno hace aparecer su field
     (dashboard.js, initDynamicFilterBuilder) sacándolo de esa lista, para
     que no se pueda agregar el mismo filtro dos veces; sacarlo con la ×
     lo devuelve al menú. Los que ya vienen activos por la querystring se
     renderizan server-side (ver asociados_list.html) con esta misma
     estructura, así que al recargar la página se reconstruyen sin
     depender de que el JS haya corrido.

     Agregar, quitar o completar un filtro NO dispara ningún envío por sí
     solo (ver dashboard.js: ya no hay ningún auto-submit en los
     controles) — la búsqueda se ejecuta recién al presionar "Filtrar",
     para poder armar varios criterios antes de consultar. Mientras tanto
     "visible" (si el filtro se dibuja) y "active" (si tiene un valor
     real, ver views.asociados_list) son cosas distintas: un filtro
     agregado y todavía vacío sigue "visible" después de un "Filtrar". */
  .filter-fields-row{display:flex;flex-wrap:wrap;gap:14px 18px;align-items:flex-end;}
  .filter-field{display:inline-flex;flex-direction:column;gap:4px;}
  .filter-field-head{display:flex;align-items:center;justify-content:space-between;gap:10px;}
  .filter-field-label{font-size:12px;font-weight:600;color:var(--text-secondary);white-space:nowrap;}
  .filter-field-remove{
    display:flex;align-items:center;justify-content:center;flex-shrink:0;
    background:none;border:none;padding:2px;margin:0;color:var(--text-muted);cursor:pointer;
  }
  .filter-field-remove:hover{color:var(--status-critical);}
  .filter-field-remove .icon{width:13px;height:13px;}

  .filter-field-control{
    border:1px solid var(--border);border-radius:var(--radius-sm);background:var(--surface-2);
    font-family:var(--font-body);font-size:13px;color:var(--text);
    height:32px;padding:0 10px;
  }
  .filter-field-control:focus{outline:none;border-color:var(--sidebar-bg);background:var(--surface);}

  .filter-field-select-wrap{position:relative;display:inline-flex;}
  select.filter-field-control{
    appearance:none;-webkit-appearance:none;-moz-appearance:none;cursor:pointer;
    padding-right:28px;min-width:110px;color:var(--text-secondary);
  }
  .filter-field-chevron{
    position:absolute;right:8px;top:50%;transform:translateY(-50%);
    width:14px;height:14px;color:var(--text-muted);pointer-events:none;
  }

  input.filter-field-control{cursor:text;}
  .filter-field-input{width:220px;}

  .filter-field-daterange{display:flex;align-items:center;gap:6px;}
  .filter-field-daterange .filter-field-control{width:128px;padding:0 8px;cursor:pointer;}
  .filter-field-daterange-sep{color:var(--text-muted);font-size:12px;flex-shrink:0;}

  .filter-fields-actions{display:flex;align-items:center;gap:10px;flex-wrap:wrap;}
  .btn-dropdown-item[hidden]{display:none;}

  @media (max-width: 860px){
    .filter-fields-row{flex-direction:column;align-items:stretch;gap:12px;}
    .filter-field{width:100%;}
    .filter-field-control{width:100%;}
    .filter-field-select-wrap{width:100%;}
    .filter-field-input{width:100%;}
    .filter-field-daterange{width:100%;}
    .filter-field-daterange .filter-field-control{flex:1;width:auto;}
  }
