/**
 * Viviaza © 2026 — Todos los derechos reservados.
 *
 * Tipo de archivo: CSS (BUNDLE bloqueante)
 * Nombre del archivo: _critical_core.css
 * Versión nueva: 1.0.0
 * Tipo de cambio: major (archivo nuevo — fusión de _tokens + _base + _components)
 * Fecha de creación: 28/05/2026
 * Fecha de modificación: 28/05/2026
 *
 * Descripción: Fusión física de los 3 CSS fundacionales
 *   (_tokens.css v1.1.0 + _base.css v1.0.2 + _components.css v1.1.0)
 *   en un único archivo bloqueante. Antes los 3 cargaban por separado y
 *   PSI mostraba que se encadenaban secuencialmente (270 ms + 810 ms +
 *   810 ms = 1,507 ms en mobile slow 4G). Al unirlos, el navegador
 *   descarga UN solo archivo en ~700 ms.
 *
 *   IMPORTANTE: Los 3 archivos originales SIGUEN EXISTIENDO porque
 *   muchas páginas del panel/admin todavía los referencian individualmente.
 *   Este bundle es ADICIONAL, no reemplazo. _header.php carga solo este
 *   bundle para el rendering público. Si modificas algún token/base/comp,
 *   debes regenerar este bundle también (o cambiar al archivo original).
 *
 *   Cómo regenerar: bash → cat _tokens.css _base.css _components.css
 *   > _critical_core.css (manteniendo este header).
 *
 * Estado: listo para producción
 */

/* ============================================================
   ============================================================
   BLOQUE 1 — _tokens.css (variables CSS globales)
   ============================================================
   ============================================================ */

/* ============================================================
   :root — Variables globales
   Se aplica al elemento raíz <html>; todas las descendientes
   (es decir, TODO el documento) heredan estos valores.
============================================================ */

:root {

  /* ========================================================
     PALETA "FRESCO EQUILIBRADO" (aprobada 19/05/2026)
     60-30-10: primary 60% / accent 10% / action 30%
  ======================================================== */

  /* Primario — Azul medianoche
     Uso: header, footer, titulares, estructura.
     Da seriedad y confianza institucional. */
  --c-primary:        #1B2C4F;
  --c-primary-dark:   #14213B;     /* hover oscuro */
  --c-primary-soft:   #2E4470;     /* gradientes, fondos secundarios */

  /* Acento — Coral terracota
     Uso: badges, micro-detalles, calidez, hover decorativo.
     Aporta humanidad sin ser ruidoso. */
  --c-accent:         #E07856;
  --c-accent-dark:    #C7613F;     /* hover */
  --c-accent-soft:    rgba(224, 120, 86, 0.10);  /* fondos sutiles */

  /* Acción — Teal moderno
     Uso: CTAs principales (Publicar, Buscar, Enviar), links de
     acción, indicadores de "todo bien". Tono refrescante. */
  --c-action:         #0EA5A0;
  --c-action-dark:    #0B8580;     /* hover */
  --c-action-cta:       #0A7D79;   /* CTA accesible: 4.97:1 con texto blanco (WCAG AA). Igual que --c-action pero un pelín más oscuro para pasar contraste en botones. */
  --c-action-cta-hover: #086B68;   /* hover del CTA accesible: 6.34:1 */
  --c-action-soft:    rgba(14, 165, 160, 0.10); /* fondos sutiles */

  /* ========================================================
     FONDOS
  ======================================================== */
  --c-bg:             #F8F5F0;     /* fondo de página — crema cálido */
  --c-bg-alt:         #FFFFFF;     /* tarjetas, bloques claros */
  --c-bg-soft:        #F1ECE3;     /* bandas de sección, alternancia */
  --c-bg-dark:        var(--c-primary);  /* alias para bandas oscuras */

  /* ========================================================
     TEXTO
  ======================================================== */
  --c-text:           #1F2937;     /* texto principal — alto contraste */
  --c-text-dim:       #64748B;     /* metadatos, captions */
  --c-text-muted:     #94A3B8;     /* placeholder, disabled */
  --c-text-on-dark:   #FFFFFF;     /* texto sobre fondos oscuros */
  --c-text-on-dark-dim: rgba(255, 255, 255, 0.78);

  /* ========================================================
     BORDES Y DIVISORES
  ======================================================== */
  --c-border:         #E5E0D6;     /* borde sutil tono crema */
  --c-border-strong:  #D6CFC0;     /* borde marcado */
  --c-border-on-dark: rgba(255, 255, 255, 0.10);

  /* ========================================================
     ESTADOS UTILITARIOS (avisos, validación de formularios)
  ======================================================== */
  --c-success:        #10B981;
  --c-success-soft:   rgba(16, 185, 129, 0.10);
  --c-warning:        #F5A623;     /* también para estrellas de rating */
  --c-warning-soft:   rgba(245, 166, 35, 0.12);
  --c-danger:         #DC2626;
  --c-danger-soft:    rgba(220, 38, 38, 0.10);
  --c-info:           #3B82F6;
  --c-info-soft:      rgba(59, 130, 246, 0.10);

  /* Marcas externas (mantener oficial) */
  --c-whatsapp:       #25D366;
  --c-facebook:       #1877F2;

  /* ========================================================
     TIPOGRAFÍA DUAL
     - Fraunces: titulares, precios destacados (toque editorial)
     - Manrope:  UI, cuerpo, botones, formularios
     - Mono:     códigos internos (IYM-2847, etc.)
  ======================================================== */

  /* Los "Fallback" están declarados en includes/critical_css.php con
     @font-face local('Arial')/local('Times New Roman') + métricas
     ajustadas. Se posicionan ANTES de los nativos para que cuando el
     web font aún no cargó, el navegador use el fallback ajustado y NO
     haga shift al hacer swap. */
  --font-serif: 'Fraunces', 'Fraunces Fallback', 'Times New Roman', Georgia, serif;
  --font-sans:  'Manrope', 'Manrope Fallback', -apple-system, BlinkMacSystemFont,
                'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif;
  --font-mono:  'SF Mono', Menlo, Consolas, 'Liberation Mono',
                'Courier New', monospace;

  /* Pesos (consistentes en todo el sitio) */
  --fw-regular:  400;
  --fw-medium:   500;
  --fw-semibold: 600;
  --fw-bold:     700;
  --fw-black:    800;

  /* Escala tipográfica (basada en 16px = 1rem) */
  --fs-xs:    0.75rem;    /* 12px — caption */
  --fs-sm:    0.875rem;   /* 14px — small */
  --fs-base:  1rem;       /* 16px — body */
  --fs-md:    1.125rem;   /* 18px — lead */
  --fs-lg:    1.25rem;    /* 20px — h5 */
  --fs-xl:    1.5rem;     /* 24px — h4 */
  --fs-2xl:   2rem;       /* 32px — h3 */
  --fs-3xl:   2.5rem;     /* 40px — h2 */
  --fs-4xl:   3rem;       /* 48px — h1 mobile */
  --fs-5xl:   3.75rem;    /* 60px — h1 desktop */

  /* Altura de línea */
  --lh-tight:   1.15;     /* titulares */
  --lh-snug:    1.3;      /* subtítulos */
  --lh-normal:  1.5;      /* cuerpo */
  --lh-relaxed: 1.7;      /* descripciones largas */

  /* ========================================================
     SOMBRAS — elevación visual (tinte azul medianoche)
  ======================================================== */

  --shadow-xs:    0 1px 2px rgba(27, 44, 79, 0.05);
  --shadow-sm:    0 2px 6px rgba(27, 44, 79, 0.06);
  --shadow:       0 4px 12px rgba(27, 44, 79, 0.08);
  --shadow-md:    0 8px 20px rgba(27, 44, 79, 0.10);
  --shadow-lg:    0 16px 40px rgba(27, 44, 79, 0.14);
  --shadow-xl:    0 24px 56px rgba(27, 44, 79, 0.18);

  /* Sombra de hover con tinte teal (acción) */
  --shadow-hover: 0 10px 24px rgba(14, 165, 160, 0.15);

  /* Foco accesible (focus-visible) */
  --shadow-focus: 0 0 0 3px var(--c-action-soft);

  /* ========================================================
     RADIOS DE BORDE
  ======================================================== */

  --radius-xs:   4px;
  --radius-sm:   6px;
  --radius:      10px;
  --radius-md:   12px;
  --radius-lg:   16px;
  --radius-xl:   24px;
  --radius-pill: 9999px;     /* píldoras y círculos */

  /* ========================================================
     LAYOUT Y ESPACIADO
  ======================================================== */

  --max-width:        1280px;     /* contenido normal */
  --max-width-wide:   1440px;     /* hero, mapas, listados anchos */
  --max-width-narrow: 960px;      /* artículos, formularios */
  --max-width-read:   720px;      /* texto largo legible */

  --header-height:    72px;
  --header-height-mobile: 60px;

  /* Sistema de espaciado (escala de 4) */
  --space-1:   4px;
  --space-2:   8px;
  --space-3:   12px;
  --space-4:   16px;
  --space-5:   20px;
  --space-6:   24px;
  --space-8:   32px;
  --space-10:  40px;
  --space-12:  48px;
  --space-16:  64px;
  --space-20:  80px;
  --space-24:  96px;

  /* Padding lateral común (responsive) */
  --container-padding-mobile:  16px;
  --container-padding-tablet:  24px;
  --container-padding-desktop: 32px;

  /* ========================================================
     TRANSICIONES Y ANIMACIONES
     Cortas para no afectar INP (Core Web Vital).
  ======================================================== */

  --transition-fast:  150ms cubic-bezier(0.4, 0, 0.2, 1);
  --transition:       200ms cubic-bezier(0.4, 0, 0.2, 1);
  --transition-slow:  300ms cubic-bezier(0.4, 0, 0.2, 1);
  --ease-bounce:      cubic-bezier(0.68, -0.55, 0.265, 1.55);

  /* ========================================================
     Z-INDEX — orden de capas
     Definir aquí evita conflictos por todo el sitio.
  ======================================================== */

  --z-base:        1;
  --z-dropdown:    100;
  --z-sticky:      200;
  --z-header:      300;
  --z-overlay:     800;
  --z-modal:       900;
  --z-toast:       950;
  --z-tooltip:     999;

  /* ========================================================
     BREAKPOINTS (para referencia — las @media queries
     usan estos valores directamente).
       sm:  640px   — móvil grande
       md:  768px   — tablet
       lg:  1024px  — desktop
       xl:  1280px  — desktop grande
       2xl: 1536px  — pantalla amplia
  ======================================================== */

  --bp-sm:  640px;
  --bp-md:  768px;
  --bp-lg:  1024px;
  --bp-xl:  1280px;
  --bp-2xl: 1536px;

  /* ========================================================
     ASPECTOS — CLS (Cumulative Layout Shift) prevention
     Reservar proporción antes de que carguen imágenes.
  ======================================================== */

  --aspect-card-photo:  4 / 3;     /* tarjeta de propiedad */
  --aspect-hero-photo:  16 / 9;    /* hero del home */
  --aspect-gallery:     3 / 2;     /* galería del anuncio */
  --aspect-square:      1 / 1;     /* avatares, miniaturas */

  /* ========================================================
     ESQUEMA DE COLOR — preparado para modo oscuro futuro
     (No implementado aún; solo declarado para que cuando
     activemos prefers-color-scheme: dark sea trivial.)
  ======================================================== */

  color-scheme: light;
}


/* ============================================================
   FALLBACK PARA NAVEGADORES MUY ANTIGUOS (>2020)
   Si un usuario llega con un navegador que no soporta CSS
   variables (raro hoy), garantizamos contenido legible.
============================================================ */

@supports not (--c-primary: #1B2C4F) {
  body {
    background: #F8F5F0;
    color: #1F2937;
    font-family: 'Manrope', -apple-system, BlinkMacSystemFont, sans-serif;
  }
}

/* ============================================================
   ============================================================
   BLOQUE 2 — _base.css (reset + base + body + utilities)
   ============================================================
   ============================================================ */

/* ============================================================
   RESET MODERNO Y MÍNIMO
   Solo lo imprescindible. Cero magia.
============================================================ */

*,
*::before,
*::after {
  box-sizing: border-box;
}

/* Quitar margins/paddings nativos predecibles que solo estorban */
html,
body,
h1, h2, h3, h4, h5, h6,
p, ul, ol, li,
figure, blockquote, dl, dd {
  margin: 0;
}

ul, ol {
  padding: 0;
  list-style: none;
}

/* ============================================================
   <HTML> Y <BODY> — Configuración del documento raíz
============================================================ */

html {
  /* Tamaño base 16px estándar — todo lo demás escala desde aquí.
     NO usar font-size en px aquí (rompe el zoom del usuario). */
  font-size: 100%;

  /* Scroll suave para anchors. */
  scroll-behavior: smooth;

  /* Optimizar el padding superior cuando hay header sticky
     y un anchor (#section) lleva ahí — no queda tapado. */
  scroll-padding-top: calc(var(--header-height) + var(--space-4));

  /* Prevenir scroll horizontal accidental. */
  overflow-x: hidden;

  /* Mejor renderizado de fuente en macOS/iOS. */
  -webkit-text-size-adjust: 100%;
  -moz-text-size-adjust: 100%;
  text-size-adjust: 100%;
}

body {
  min-width: 320px;             /* mínimo soportado: iPhone SE */
  min-height: 100vh;
  min-height: 100dvh;           /* dynamic viewport — móviles modernos */

  background: var(--c-bg);
  color: var(--c-text);

  font-family: var(--font-sans);
  font-size: var(--fs-base);
  font-weight: var(--fw-regular);
  line-height: var(--lh-normal);

  /* Subpixel antialiasing — texto más nítido */
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  text-rendering: optimizeLegibility;

  /* Anclaje del flujo: el contenido empuja al footer hacia abajo */
  display: flex;
  flex-direction: column;
}

main {
  flex: 1 0 auto;     /* main crece para empujar footer al fondo */
}

/* ============================================================
   TITULARES — Fraunces (serif) por defecto
   Cada componente puede sobrescribir si necesita sans.
============================================================ */

h1, h2, h3, h4, h5, h6 {
  font-family: var(--font-serif);
  font-weight: var(--fw-bold);
  color: var(--c-primary);
  line-height: var(--lh-tight);
  letter-spacing: -0.015em;
  text-wrap: balance;           /* evita huérfanas en titulares (Chrome 114+) */
}

h1 {
  font-size: var(--fs-4xl);
  font-weight: var(--fw-black);
  letter-spacing: -0.025em;
}

h2 {
  font-size: var(--fs-3xl);
}

h3 {
  font-size: var(--fs-2xl);
}

h4 {
  font-size: var(--fs-xl);
}

h5 {
  font-size: var(--fs-lg);
}

h6 {
  font-size: var(--fs-md);
}

/* Desktop: titulares más grandes */
@media (min-width: 768px) {
  h1 {
    font-size: var(--fs-5xl);
  }
}

/* ============================================================
   PÁRRAFOS Y TEXTOS
============================================================ */

p {
  line-height: var(--lh-normal);
  text-wrap: pretty;            /* mejor flujo en párrafos (Chrome 117+) */
}

p + p {
  margin-top: var(--space-3);   /* espacio natural entre párrafos */
}

strong, b {
  font-weight: var(--fw-bold);
  color: var(--c-text);
}

small {
  font-size: var(--fs-sm);
  color: var(--c-text-dim);
}

mark {
  background: var(--c-warning-soft);
  color: var(--c-text);
  padding: 0 0.2em;
  border-radius: var(--radius-xs);
}

code, kbd, pre {
  font-family: var(--font-mono);
  font-size: 0.9em;
}

code {
  background: var(--c-bg-soft);
  padding: 0.15em 0.4em;
  border-radius: var(--radius-xs);
}

/* ============================================================
   ENLACES — Acción por defecto (teal), no subrayados.
   Usamos `:where()` para que TODA la regla tenga especificidad 0,
   así cualquier .clase específica (ficha-dev-sidebar, btn--primary,
   etc.) pueda sobreescribir el color sin pelear con la cascada.
   Excluye .btn como salvaguarda extra.
============================================================ */

a:where(:not(.btn)) {
  color: var(--c-action);
  text-decoration: none;
  transition: color var(--transition-fast);
}

a:where(:not(.btn)):hover {
  color: var(--c-action-dark);
}

/* Subrayar solo dentro de texto en párrafos (legibilidad). */
p a,
li a {
  text-decoration: underline;
  text-decoration-thickness: 1px;
  text-underline-offset: 2px;
}

/* ============================================================
   IMÁGENES Y MEDIA — clave para CLS y LCP
============================================================ */

img,
picture,
video,
canvas,
svg {
  display: block;
  max-width: 100%;
  height: auto;
}

/* Si la imagen no tiene width/height explícito, este aspect-ratio
   actúa como salvavidas para prevenir CLS. Cada componente debe
   declarar sus propias dimensiones cuando las conozca. */
img:not([width]):not([height]) {
  aspect-ratio: var(--aspect-square);
  object-fit: cover;
}

/* Imágenes con loading=lazy se desvanecen elegantemente al cargar */
img[loading="lazy"] {
  background: var(--c-bg-soft);
}

/* ============================================================
   FORMULARIOS — heredan tipografía del body
============================================================ */

button,
input,
select,
textarea {
  font: inherit;
  color: inherit;
}

button {
  background: none;
  border: none;
  cursor: pointer;
  padding: 0;
}

button:disabled,
input:disabled,
select:disabled,
textarea:disabled {
  cursor: not-allowed;
  opacity: 0.6;
}

textarea {
  resize: vertical;
  min-height: 80px;
}

/* Placeholder consistente y discreto */
::placeholder {
  color: var(--c-text-muted);
  opacity: 1;     /* Firefox reduce opacidad por defecto */
}

/* ============================================================
   TABLAS
============================================================ */

table {
  border-collapse: collapse;
  width: 100%;
}

th, td {
  padding: var(--space-3) var(--space-4);
  text-align: left;
  border-bottom: 1px solid var(--c-border);
}

th {
  font-weight: var(--fw-bold);
  color: var(--c-primary);
}

/* ============================================================
   HORIZONTAL RULE
============================================================ */

hr {
  border: none;
  border-top: 1px solid var(--c-border);
  margin: var(--space-8) 0;
}

/* ============================================================
   ACCESIBILIDAD — Foco visible cuando se navega con teclado
   :focus-visible solo aplica si el usuario está usando teclado,
   no cuando hace click con el ratón (mejor UX).
============================================================ */

:focus {
  outline: none;
}

:focus-visible {
  outline: 2px solid var(--c-action);
  outline-offset: 2px;
  border-radius: var(--radius-xs);
}

/* En elementos que ya tienen su propio focus visual */
button:focus-visible,
a:focus-visible,
input:focus-visible,
select:focus-visible,
textarea:focus-visible {
  box-shadow: var(--shadow-focus);
}

/* ============================================================
   RESPETO A PREFERENCIAS DEL USUARIO
   prefers-reduced-motion: el usuario activó "reducir movimiento"
   en su sistema (Windows/macOS/iOS). Honramos su decisión.
============================================================ */

@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
}

/* ============================================================
   UTILIDADES BÁSICAS (solo las imprescindibles)
============================================================ */

/* Ocultar visualmente pero accesible a screen readers */
.sr-only {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip: rect(0, 0, 0, 0);
  white-space: nowrap;
  border: 0;
}

/* Mostrar al recibir foco (skip-link pattern) */
.sr-only:focus {
  position: static;
  width: auto;
  height: auto;
  margin: 0;
  clip: auto;
  white-space: normal;
}

/* Contenedor estándar centrado con padding responsive */
.container {
  width: 100%;
  max-width: var(--max-width);
  margin-inline: auto;
  padding-inline: var(--container-padding-mobile);
}

@media (min-width: 768px) {
  .container { padding-inline: var(--container-padding-tablet); }
}

@media (min-width: 1024px) {
  .container { padding-inline: var(--container-padding-desktop); }
}

/* Variante ancha (mapas, hero) */
.container-wide {
  max-width: var(--max-width-wide);
}

/* Variante angosta (artículos, formularios) */
.container-narrow {
  max-width: var(--max-width-narrow);
}

/* Variante lectura (texto largo) */
.container-read {
  max-width: var(--max-width-read);
}

/* ============================================================
   ============================================================
   BLOQUE 3 — _components.css (btn + badge + input + rating + ...)
   ============================================================
   ============================================================ */


/* ============================================================
   .btn — Botones (sistema unificado)
============================================================ */

.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: var(--space-2);

  padding: 10px 20px;
  border-radius: var(--radius);
  border: 1px solid transparent;

  font-family: var(--font-sans);
  font-size: var(--fs-sm);
  font-weight: var(--fw-bold);
  line-height: 1;
  white-space: nowrap;
  text-decoration: none;

  cursor: pointer;
  transition: background-color var(--transition),
              color var(--transition),
              border-color var(--transition),
              box-shadow var(--transition),
              transform var(--transition-fast);

  /* Para que no se desfigure cuando se le aplican icon spinners */
  user-select: none;
  -webkit-tap-highlight-color: transparent;
}

.btn:active {
  transform: translateY(1px);
}

.btn:disabled,
.btn.is-disabled {
  cursor: not-allowed;
  opacity: 0.55;
  pointer-events: none;
}

/* Loading state — pulso sutil */
.btn.is-loading {
  cursor: wait;
  pointer-events: none;
  position: relative;
  color: transparent;
}

.btn.is-loading::after {
  content: '';
  position: absolute;
  width: 16px;
  height: 16px;
  border: 2px solid currentColor;
  border-top-color: transparent;
  border-radius: 50%;
  animation: btn-spin 0.6s linear infinite;
  color: var(--c-text-on-dark);
}

@keyframes btn-spin {
  to { transform: rotate(360deg); }
}

/* -------- Variantes -------- */

/* PRIMARIO — acción principal (Publicar, Buscar, Enviar) */
.btn--primary {
  background: var(--c-action-cta); /* teal accesible (4.97:1) — antes --c-action fallaba WCAG (3.04:1) */
  color: var(--c-text-on-dark);
}
.btn--primary:hover {
  background: var(--c-action-cta-hover);
  box-shadow: var(--shadow-hover);
}

/* SECUNDARIO — acción importante pero no central */
.btn--secondary {
  background: var(--c-primary);
  color: var(--c-text-on-dark);
}
.btn--secondary:hover {
  background: var(--c-primary-dark);
  box-shadow: var(--shadow);
}

/* ACENTO — destacar algo cálido (Premium, Promoción) */
.btn--accent {
  background: var(--c-accent);
  color: var(--c-text-on-dark);
}
.btn--accent:hover {
  background: var(--c-accent-dark);
  box-shadow: 0 6px 14px rgba(224, 120, 86, 0.30);
}

/* OUTLINE — alternativa elegante */
.btn--outline {
  background: transparent;
  color: var(--c-primary);
  border-color: var(--c-border-strong);
}
.btn--outline:hover {
  background: var(--c-primary);
  color: var(--c-text-on-dark);
  border-color: var(--c-primary);
}

/* GHOST — botón fantasma (usable sobre fondos cualquier color) */
.btn--ghost {
  background: transparent;
  color: var(--c-text);
  border-color: var(--c-border);
}
.btn--ghost:hover {
  background: var(--c-bg-soft);
  border-color: var(--c-border-strong);
}

/* SOBRE OSCURO — para usar dentro del header */
.btn--on-dark {
  background: rgba(255, 255, 255, 0.06);
  color: var(--c-text-on-dark);
  border-color: rgba(255, 255, 255, 0.20);
}
.btn--on-dark:hover {
  background: var(--c-accent);
  border-color: var(--c-accent);
}

/* WHATSAPP — marca oficial */
.btn--whatsapp {
  background: var(--c-whatsapp);
  color: var(--c-text-on-dark);
}
.btn--whatsapp:hover {
  background: #1FB957;
}

/* PELIGRO — eliminar, cancelar */
.btn--danger {
  background: var(--c-danger);
  color: var(--c-text-on-dark);
}
.btn--danger:hover {
  background: #B91C1C;
}

/* -------- Tamaños -------- */

.btn--sm {
  padding: 6px 12px;
  font-size: var(--fs-xs);
  border-radius: var(--radius-sm);
}

.btn--lg {
  padding: 14px 28px;
  font-size: var(--fs-base);
}

.btn--xl {
  padding: 18px 36px;
  font-size: var(--fs-md);
}

/* -------- Modificadores -------- */

.btn--block {
  display: flex;
  width: 100%;
}

.btn--pill {
  border-radius: var(--radius-pill);
}

.btn--icon-only {
  padding: 10px;
  aspect-ratio: 1;
}

.btn__icon {
  font-size: 1.05em;
  flex-shrink: 0;
}

/* ============================================================
   .badge — Etiquetas inline (Verificado, Nuevo, Premium)
============================================================ */

.badge {
  display: inline-flex;
  align-items: center;
  gap: 5px;

  padding: 4px 10px;
  border-radius: var(--radius-pill);

  font-family: var(--font-sans);
  font-size: var(--fs-xs);
  font-weight: var(--fw-black);
  line-height: 1;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  white-space: nowrap;
}

.badge--primary {
  background: var(--c-primary);
  color: var(--c-text-on-dark);
}

.badge--accent {
  background: var(--c-accent);
  color: var(--c-text-on-dark);
}

.badge--action {
  background: var(--c-action);
  color: var(--c-text-on-dark);
}

.badge--success {
  background: var(--c-success-soft);
  color: var(--c-success);
}

.badge--warning {
  background: var(--c-warning-soft);
  color: #B45309;     /* texto warning más oscuro para contraste */
}

.badge--danger {
  background: var(--c-danger-soft);
  color: var(--c-danger);
}

.badge--soft {
  background: var(--c-bg-soft);
  color: var(--c-primary);
  border: 1px solid var(--c-border);
}

.badge--outline {
  background: transparent;
  color: var(--c-primary);
  border: 1px solid var(--c-border-strong);
}

/* Sin uppercase (para badges con texto largo) */
.badge--regular {
  text-transform: none;
  letter-spacing: 0;
  font-weight: var(--fw-bold);
}

/* ============================================================
   .chip — Filtros activos / tags removibles
   (similar a badge pero clickeable y a veces con × para quitar)
============================================================ */

.chip {
  display: inline-flex;
  align-items: center;
  gap: 6px;

  padding: 6px 12px;
  border-radius: var(--radius-pill);
  background: var(--c-bg-alt);
  border: 1px solid var(--c-border);

  font-family: var(--font-sans);
  font-size: var(--fs-sm);
  font-weight: var(--fw-semibold);
  color: var(--c-text);

  cursor: pointer;
  transition: all var(--transition-fast);
}

.chip:hover {
  background: var(--c-bg-soft);
  border-color: var(--c-border-strong);
}

.chip.is-active {
  background: var(--c-primary);
  border-color: var(--c-primary);
  color: var(--c-text-on-dark);
}

.chip__close {
  width: 16px;
  height: 16px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border-radius: var(--radius-pill);
  background: rgba(0, 0, 0, 0.1);
  font-size: 10px;
  margin-right: -4px;
}

.chip__close:hover {
  background: rgba(0, 0, 0, 0.2);
}

/* ============================================================
   .input / .select / .textarea — Campos de formulario base
============================================================ */

.input,
.select,
.textarea {
  width: 100%;
  padding: 11px 14px;

  background: var(--c-bg-alt);
  border: 1px solid var(--c-border);
  border-radius: var(--radius);

  font-family: var(--font-sans);
  font-size: var(--fs-base);
  font-weight: var(--fw-regular);
  color: var(--c-text);
  line-height: 1.4;

  transition: border-color var(--transition-fast),
              box-shadow var(--transition-fast);

  /* Quitar estilos nativos antiguos */
  appearance: none;
  -webkit-appearance: none;
  -moz-appearance: none;
}

.input:hover,
.select:hover,
.textarea:hover {
  border-color: var(--c-border-strong);
}

.input:focus,
.select:focus,
.textarea:focus {
  outline: none;
  border-color: var(--c-action);
  box-shadow: var(--shadow-focus);
}

.input--error {
  border-color: var(--c-danger);
}

.input--error:focus {
  box-shadow: 0 0 0 3px var(--c-danger-soft);
}

/* Select con flechita propia (consistente entre navegadores) */
.select {
  background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='12' height='8' viewBox='0 0 12 8' fill='none'><path d='M1 1.5L6 6.5L11 1.5' stroke='%2364748B' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/></svg>");
  background-repeat: no-repeat;
  background-position: right 14px center;
  padding-right: 36px;
  cursor: pointer;
}

.textarea {
  min-height: 96px;
  resize: vertical;
  line-height: var(--lh-normal);
}

/* Label de formulario */
.label {
  display: block;
  font-family: var(--font-sans);
  font-size: var(--fs-sm);
  font-weight: var(--fw-bold);
  color: var(--c-primary);
  margin-bottom: 6px;
}

.label--required::after {
  content: ' *';
  color: var(--c-danger);
}

/* Texto de ayuda debajo de un input */
.field-help {
  display: block;
  font-size: var(--fs-xs);
  color: var(--c-text-dim);
  margin-top: 6px;
}

.field-error {
  display: block;
  font-size: var(--fs-xs);
  color: var(--c-danger);
  margin-top: 6px;
  font-weight: var(--fw-semibold);
}

/* ============================================================
   .card — Tarjeta genérica (base para tarjetas específicas)
============================================================ */

.card {
  background: var(--c-bg-alt);
  border: 1px solid var(--c-border);
  border-radius: var(--radius-md);
  box-shadow: var(--shadow-xs);
  overflow: hidden;
  transition: transform var(--transition),
              box-shadow var(--transition),
              border-color var(--transition);
}

.card--interactive {
  cursor: pointer;
}

.card--interactive:hover {
  transform: translateY(-3px);
  box-shadow: var(--shadow-md);
  border-color: var(--c-action);
}

.card__body {
  padding: var(--space-5);
}

.card__title {
  font-family: var(--font-serif);
  font-size: var(--fs-lg);
  font-weight: var(--fw-bold);
  color: var(--c-primary);
  margin-bottom: var(--space-2);
  line-height: var(--lh-snug);
}

.card__text {
  color: var(--c-text-dim);
  font-size: var(--fs-sm);
  line-height: var(--lh-normal);
}

/* ============================================================
   .divider — Separadores visuales
============================================================ */

.divider {
  border: none;
  border-top: 1px solid var(--c-border);
  margin: var(--space-6) 0;
}

.divider--text {
  display: flex;
  align-items: center;
  text-align: center;
  margin: var(--space-5) 0;
  color: var(--c-text-dim);
  font-size: var(--fs-xs);
  font-weight: var(--fw-semibold);
  text-transform: uppercase;
  letter-spacing: 0.05em;
}

.divider--text::before,
.divider--text::after {
  content: '';
  flex: 1;
  border-top: 1px solid var(--c-border);
}

.divider--text::before { margin-right: var(--space-3); }
.divider--text::after  { margin-left:  var(--space-3); }

/* ============================================================
   .skeleton — Estado de carga (placeholder animado)
   Mejora la percepción de velocidad (sin cambiar LCP real,
   da feedback visual de que algo está cargando).
============================================================ */

.skeleton {
  display: block;
  background: linear-gradient(
    90deg,
    var(--c-bg-soft) 0%,
    var(--c-border) 50%,
    var(--c-bg-soft) 100%
  );
  background-size: 200% 100%;
  animation: skeleton-pulse 1.4s ease-in-out infinite;
  border-radius: var(--radius-sm);
}

@keyframes skeleton-pulse {
  0%   { background-position: 200% 0; }
  100% { background-position: -200% 0; }
}

.skeleton--text {
  height: 1em;
  margin-bottom: 0.5em;
}

.skeleton--title {
  height: 1.5em;
  width: 60%;
  margin-bottom: 1em;
}

.skeleton--image {
  aspect-ratio: var(--aspect-card-photo);
  width: 100%;
}

/* ============================================================
   .avatar — Foto circular de usuario / inmobiliaria
============================================================ */

.avatar {
  display: inline-block;
  width: 40px;
  height: 40px;
  border-radius: 50%;
  object-fit: cover;
  background: var(--c-bg-soft);
  border: 1px solid var(--c-border);
}

.avatar--sm { width: 32px; height: 32px; }
.avatar--lg { width: 64px; height: 64px; }
.avatar--xl { width: 96px; height: 96px; }

.avatar--ring {
  border: 3px solid var(--c-action);
  padding: 0;
}

/* ============================================================
   .rating — Estrellas de reputación / calidad (UNIFICADO)
   ------------------------------------------------------------
   FUENTE ÚNICA para cualquier rating con estrellas del sitio.
   Sustituye a .calidad-actual__estrellas y .tarjeta-rating
   (que ahora son wrappers que ENVUELVEN un .rating).

   Uso básico (HTML):
     <span class="rating rating--md">
       <i class="fa-solid fa-star"></i>
       <i class="fa-solid fa-star"></i>
       <i class="fa-solid fa-star"></i>
       <i class="fa-solid fa-star"></i>
       <i class="fa-solid fa-star-half-stroke"></i>
       <span class="rating__score">4.6 · 1 reseña</span>
     </span>

   Variantes de tamaño:
     .rating--sm  → tarjetas, pies, chips     (fs-xs)
     .rating--md  → vendedor en anuncio.php   (fs-sm)  [DEFAULT]
     .rating--lg  → calidad-actual            (fs-md)

   Las estrellas SIEMPRE van en dorado var(--c-warning). El
   texto auxiliar va en gris oscuro (--c-text-dim).
============================================================ */

.rating {
  display: inline-flex;
  align-items: center;
  gap: 3px;
  color: var(--c-warning);        /* dorado #F5A623 — heredado por <i> */
  line-height: 1;
}

.rating i,
.rating .fa-solid,
.rating .fa-regular {
  color: var(--c-warning);        /* refuerzo: por si algún ancestro hereda otro color */
}

/* Estrella "vacía" (cuando el rating no llega) — gris suave para distinguir */
.rating i.fa-regular {
  color: var(--c-text-muted, #c5c9d2);
}

/* ----- Variantes de tamaño ----- */
.rating--sm { font-size: var(--fs-xs); gap: 2px; }
.rating--md { font-size: var(--fs-sm); gap: 3px; }
.rating--lg { font-size: var(--fs-md); gap: 4px; }

/* Sin variante explícita → tamaño md por defecto */
.rating:not(.rating--sm):not(.rating--lg) {
  font-size: var(--fs-sm);
}

/* ----- Texto auxiliar (número y reseñas) ----- */
.rating__score {
  color: var(--c-text-dim);
  font-weight: var(--fw-semibold);
  margin-left: var(--space-2);
  font-size: 0.92em;              /* relativo al .rating padre */
}

/* Número grande tipo "4.6" — opcional, para layouts tipo calidad-actual */
.rating__numero {
  font-family: var(--font-serif);
  font-weight: var(--fw-bold);
  color: var(--c-text);
  margin-left: var(--space-2);
  font-size: 1.15em;
}

.rating__detalle {
  color: var(--c-text-dim);
  font-size: 0.85em;
  margin-left: 4px;
}

/* ============================================================
   .price — Precio destacado (Fraunces)
============================================================ */

.price {
  font-family: var(--font-serif);
  font-size: var(--fs-2xl);
  font-weight: var(--fw-bold);
  color: var(--c-primary);
  line-height: 1;
  letter-spacing: -0.02em;
  display: inline-flex;
  align-items: baseline;
  gap: 4px;
}

.price__currency {
  font-family: var(--font-sans);
  font-size: var(--fs-xs);
  font-weight: var(--fw-bold);
  color: var(--c-text-dim);
  letter-spacing: 0.05em;
}

.price__suffix {
  font-family: var(--font-sans);
  font-size: var(--fs-xs);
  font-weight: var(--fw-semibold);
  color: var(--c-text-dim);
}

.price--sm  { font-size: var(--fs-xl); }
.price--lg  { font-size: var(--fs-3xl); }
.price--xl  { font-size: var(--fs-4xl); }

/* ============================================================
   .icon-circle — Icono dentro de círculo de marca
============================================================ */

.icon-circle {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 36px;
  height: 36px;
  border-radius: 50%;
  background: var(--c-action-soft);
  color: var(--c-action);
  flex-shrink: 0;
}

.icon-circle--primary {
  background: rgba(27, 44, 79, 0.10);
  color: var(--c-primary);
}

.icon-circle--accent {
  background: var(--c-accent-soft);
  color: var(--c-accent);
}

.icon-circle--lg {
  width: 48px;
  height: 48px;
  font-size: var(--fs-lg);
}

/* ============================================================
   .alert — Mensaje informativo (éxito, error, info)
============================================================ */

.alert {
  display: flex;
  gap: var(--space-3);
  padding: var(--space-4) var(--space-5);
  border-radius: var(--radius);
  font-size: var(--fs-sm);
  line-height: var(--lh-normal);
  border: 1px solid transparent;
}

.alert__icon {
  flex-shrink: 0;
  font-size: 1.2em;
  margin-top: 1px;
}

.alert__title {
  font-weight: var(--fw-bold);
  margin-bottom: 2px;
  display: block;
}

.alert--success {
  background: var(--c-success-soft);
  color: #047857;
  border-color: rgba(16, 185, 129, 0.20);
}

.alert--warning {
  background: var(--c-warning-soft);
  color: #B45309;
  border-color: rgba(245, 166, 35, 0.30);
}

.alert--danger {
  background: var(--c-danger-soft);
  color: #B91C1C;
  border-color: rgba(220, 38, 38, 0.20);
}

.alert--info {
  background: var(--c-info-soft);
  color: #1E40AF;
  border-color: rgba(59, 130, 246, 0.20);
}

/* ============================================================
   .lazy-mapa — Mapa con carga diferida (click → iframe)
   El usuario ve un placeholder con icono + botón "Ver mapa".
   El iframe pesado solo carga al hacer click.
   Protege LCP/INP y la privacidad (no manda señal a Google
   Maps / OSM hasta que el usuario quiere ver).
============================================================ */

.lazy-mapa {
    position: relative;
    width: 100%;
    aspect-ratio: 16 / 9;
    border-radius: var(--radius-md);
    overflow: hidden;
    background: linear-gradient(135deg, var(--c-bg-soft) 0%, var(--c-border) 100%);
    cursor: pointer;
    transition: box-shadow var(--transition);
}

.lazy-mapa:hover { box-shadow: var(--shadow-md); }

.lazy-mapa--cargado {
    cursor: default;
    background: transparent;
}

.lazy-mapa__placeholder {
    position: absolute;
    inset: 0;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: var(--space-3);
    padding: var(--space-6);
    text-align: center;
    /* Patrón sutil de "mapa" usando radial gradients */
    background-image:
        radial-gradient(circle at 25% 30%, var(--c-action-soft) 0%, transparent 30%),
        radial-gradient(circle at 75% 70%, var(--c-accent-soft) 0%, transparent 30%),
        radial-gradient(circle at 50% 50%, rgba(255,255,255,0.5) 0%, transparent 60%);
}

.lazy-mapa__icono {
    width: 64px;
    height: 64px;
    border-radius: var(--radius-pill);
    background: var(--c-bg-alt);
    color: var(--c-action);
    display: inline-flex;
    align-items: center;
    justify-content: center;
    font-size: var(--fs-xl);
    box-shadow: var(--shadow);
}

.lazy-mapa__boton {
    background: var(--c-primary);
    color: var(--c-text-on-dark);
    border: none;
    padding: 12px 24px;
    border-radius: var(--radius-pill);
    font-family: var(--font-sans);
    font-size: var(--fs-sm);
    font-weight: var(--fw-bold);
    cursor: pointer;
    display: inline-flex;
    align-items: center;
    gap: var(--space-2);
    box-shadow: var(--shadow);
    transition: all var(--transition);
}

.lazy-mapa__boton:hover {
    background: var(--c-primary-dark);
    transform: translateY(-2px);
    box-shadow: var(--shadow-md);
}

.lazy-mapa__nota {
    font-size: var(--fs-xs);
    color: var(--c-text-dim);
    max-width: 320px;
    margin: 0;
    line-height: 1.4;
}

/* ============================================================
   .lazy-video — Video YouTube con carga diferida
   El thumb sí se descarga (es ligero ~30KB) — el iframe pesado
   (~500KB + JS de YouTube) solo carga al hacer click.
============================================================ */

.lazy-video {
    position: relative;
    width: 100%;
    aspect-ratio: 16 / 9;
    border-radius: var(--radius-md);
    overflow: hidden;
    background: #000;
    cursor: pointer;
    transition: box-shadow var(--transition);
}

.lazy-video:hover { box-shadow: var(--shadow-md); }

.lazy-video--cargado { cursor: default; }

.lazy-video__thumb {
    width: 100%;
    height: 100%;
    object-fit: cover;
    display: block;
    transition: filter var(--transition);
}

.lazy-video:hover .lazy-video__thumb {
    filter: brightness(0.85);
}

.lazy-video__boton {
    position: absolute;
    inset: 0;
    display: flex;
    align-items: center;
    justify-content: center;
    background: transparent;
    border: none;
    cursor: pointer;
    padding: 0;
}

.lazy-video__icono {
    width: 68px;
    height: 48px;
    color: rgba(220, 38, 38, 0.9);     /* color YouTube — pero más sobrio */
    transition: transform var(--transition),
                color var(--transition);
    filter: drop-shadow(0 4px 8px rgba(0, 0, 0, 0.5));
}

.lazy-video:hover .lazy-video__icono {
    transform: scale(1.1);
    color: rgb(220, 38, 38);
}

/* ============================================================
   Modificador "hide hasta breakpoint" — útil en muchos sitios
============================================================ */

.hide-mobile { display: initial; }
.show-mobile { display: none; }

@media (max-width: 767px) {
  .hide-mobile { display: none !important; }
  .show-mobile { display: initial !important; }
}
