/* ============================================================
   LA HOJA DEL LADO PUBLICO (buscador, ficha, favoritos, comparacion)
   ============================================================
   Estaba EN LINEA dentro de header.php, 48 KB que viajaban en cada pagina
   publica. Se saco a un archivo el 2026-09-17 por un motivo concreto: la
   pantalla del INVENTARIO SIN CONEXION (8.98) tiene que verse EXACTAMENTE
   igual que el buscador, y para eso necesita este mismo CSS — no una copia,
   que es como acaban separandose dos disenos. Lo pidio el usuario al ver que
   la pantalla sin red tenia otra estetica.

   Va en el MISMO SITIO donde estaba el <style>, asi que el orden de cascada
   no cambia: entra despues de Bootstrap y antes de lo que venga detras.
   ============================================================ */
        .flyer-clickable {
            cursor: pointer;
            transition: transform 0.2s ease-in-out;
        }

        .flyer-clickable:hover {
            transform: scale(1.03);
        }

        /* Esos <span> son HUECOS que rellenan solos la campana, Doroty y el botón de
           instalar la app. Vacíos miden 0, pero siguen siendo hijos del flex y el gap
           se aplica a sus dos lados: al instalar la app desaparecía el botón y quedaba
           una separación de más en la fila. Vacío = no está. */
        .offcanvas-header .d-flex > span:empty { display: none; }

        .fab-up {
            position: fixed;
            bottom: 30px;
            right: 30px;
            z-index: 1050;
            background-color: #d4af37;
            color: white;
            border: none;
            display: none;
            transition: opacity 0.3s;
        }

        .fab-up:hover {
            background-color: #b5952f;
            color: white;
        }

        /* En el teléfono el botón de subir se sienta justo encima de la última línea
           del pie y tapaba "© Dorata Realty Tesoro. Todos los derechos reservados".
           El botón mide 56 px y se separa 20 del borde, así que el pie termina con
           sitio de sobra por debajo. En PC no hace falta: ahí el pie es ancho y el
           texto va centrado, lejos de la esquina. */
        @media (max-width: 575.98px) {
            .fab-up { bottom: 20px; right: 20px; }
            /* 'body footer.py-5' y no 'footer' a secas: py-5 de Bootstrap trae su
               padding con !important, así que a igual especificidad ganaba él y esta
               regla no hacía nada. Es la misma trampa del .d-flex del editor de flyers:
               contra un !important de Bootstrap hay que subir la especificidad. */
            body footer.py-5 { padding-bottom: 6.5rem !important; }
        }

        /* ===== Tarjeta de inmueble (rediseño) =====
           4:3: la tarjeta muestra la FOTO de la propiedad, no el flyer. El 3:4 vertical
           de antes venía de que el flyer es 9:16; con fotos apaisadas dejaba franjas y
           alargaba la tarjeta de más. */
        /* display:block porque ahora es un <a> (enlace a /propiedad/<slug>): en línea
           no respetaría el aspect-ratio ni contendría bien lo posicionado encima. */
        .prop-img-wrap { display: block; position: relative; aspect-ratio: 4/3; overflow: hidden; cursor: pointer; background: #e2e8f0; }
        /* Cuántas fotos tiene (solo si hay más de una): invita a abrir la galería. */
        .prop-fotos {
            position: absolute; top: 10px; right: 60px;
            background: rgba(34,37,42,.82); color: #fff;
            font-size: .72rem; font-weight: 600; padding: 3px 9px; border-radius: 20px;
            display: inline-flex; align-items: center; gap: 5px;
        }
        .prop-img { width: 100%; height: 100%; object-fit: cover; object-position: center; display: block; transition: transform .3s ease; }
        .prop-img-wrap:hover .prop-img { transform: scale(1.04); }
        .prop-badges { position: absolute; top: 10px; left: 10px; display: flex; flex-direction: column; gap: 5px; align-items: flex-start; }
        .pb { font-size: 0.72rem; font-weight: 600; padding: 3px 11px; border-radius: 20px; box-shadow: 0 1px 4px rgba(0,0,0,.2); }
        .pb-tipo { background: #22252a; color: #fff; }
        .pb-op { background: #d4af37; color: #3a2e07; }
        /* Uso del inmueble. Va entre el tipo y la operación, y con un tono propio para
           que se distingan de un vistazo las tres píldoras. */
        .pb-uso { background: #fff; color: #22252a; border: 1px solid rgba(0,0,0,.15); }
        .prop-avatar { position: absolute; top: 10px; right: 10px; width: 42px; height: 42px; border-radius: 50%; border: 2px solid #fff; background: #d4af37; color: #3a2e07; font-weight: 600; font-size: 1rem; display: flex; align-items: center; justify-content: center; overflow: hidden; padding: 0; cursor: pointer; box-shadow: 0 0 0 2px #d4af37, 0 2px 6px rgba(0,0,0,.3); }
        .anillo-oro { border: 3px solid #fff !important; box-shadow: 0 0 0 3px #d4af37 !important; }
        .dir-item { display: flex; align-items: center; gap: 12px; width: 100%; background: #fff; border: 1px solid #eee; border-radius: 12px; padding: 8px 12px; margin-bottom: 8px; text-align: left; }
        .dir-item:hover { background: #f9fafb; }
        .dir-avatar { width: 46px; height: 46px; border-radius: 50%; flex-shrink: 0; background: #d4af37; color: #3a2e07; display: flex; align-items: center; justify-content: center; font-weight: 600; overflow: hidden; }
        .dir-avatar img { width: 100%; height: 100%; object-fit: cover; }
        .dir-nombre { font-weight: 600; font-size: 0.95rem; color: #22252a; }
        /* Descargar el directorio como vCard: area de toque comoda en el telefono. */
        .dir-vcard { width: 38px; height: 38px; border-radius: 10px; border: 1px solid #eee;
            display: inline-flex; align-items: center; justify-content: center;
            color: #d4af37; text-decoration: none; font-size: 1.05rem; flex-shrink: 0; }
        .dir-vcard:hover { background: #faf6e9; border-color: #d4af37; color: #b8952f; }
        .prop-avatar img { width: 100%; height: 100%; object-fit: cover; }
        /* Precio y costo por m2 apilados en la esquina de la foto: el precio abajo
           (donde estaba siempre) y el costo por m2 encima. La caja es la que se
           posiciona; el precio ya no, o se saldria de la columna. */
        .prop-precio-caja { position: absolute; bottom: 10px; left: 10px; display: flex; flex-direction: column; align-items: flex-start; gap: 5px; }
        .prop-precio { background: rgba(34,37,42,.9); color: #fff; font-weight: 600; font-size: 1rem; padding: 5px 14px; border-radius: 8px; }
        .prop-icons { position: absolute; bottom: 10px; right: 10px; display: flex; gap: 6px; }
        .prop-ic { width: 34px; height: 34px; border-radius: 50%; border: none; background: rgba(255,255,255,.92); color: #22252a; display: flex; align-items: center; justify-content: center; font-size: 1rem; cursor: pointer; }
        .prop-ic:hover { background: #fff; color: #d4af37; }
        /* Guardada en Favoritos / Comparación: el botón se rellena de dorado. */
        .prop-ic.activo { background: #d4af37; color: #3a2e07; }

        /* ---------- Contadores de Favoritos y Comparación (barra de arriba) ---------- */
        .navbar-der { display: flex; align-items: center; gap: 10px; }
        [data-seleccion] { display: flex; align-items: center; gap: 8px; }
        .sel-cuenta {
            position: relative; width: 40px; height: 40px; border-radius: 12px;
            display: inline-flex; align-items: center; justify-content: center;
            background: rgba(212,175,55,.16); color: #b8860b; font-size: 1.05rem; text-decoration: none;
        }
        .sel-cuenta:hover { background: #d4af37; color: #3a2e07; }
        /* La cuenta va en una pastilla oscura sobre el icono: se lee de un vistazo
           sin ensanchar el botón, que en el teléfono compite con el menú. */
        .sel-num {
            position: absolute; top: -5px; right: -5px; min-width: 18px; height: 18px; padding: 0 4px;
            border-radius: 20px; background: #22252a; color: #fff;
            font-size: .68rem; font-weight: 700; line-height: 18px; text-align: center;
        }
        [data-bs-theme="dark"] .sel-num { background: #f1f1f1; color: #22252a; }

        /* ---------- Páginas de Favoritos y Comparación ---------- */
        .sel-cabecera { display: flex; align-items: center; justify-content: space-between; gap: 12px; flex-wrap: wrap; margin-bottom: 18px; }
        .sel-titulo { font-size: 1.25rem; font-weight: 700; margin: 0; }
        .sel-titulo i { color: #d4af37; }
        .sel-volver { color: var(--bs-secondary-color); text-decoration: none; font-size: .88rem; font-weight: 600; }
        .sel-volver:hover { color: #b8860b; }
        /* Vaciar la lista. Va en la cabecera, junto al titulo, y NO pegado al contador
           de la barra de arriba: ahi un aspa junto al numero se pulsa sin querer y borra
           veinte propiedades guardadas sin que te enteres. Aqui hay que venir a proposito,
           y ademas pregunta antes. En rojo apagado: es destructivo, pero no es la accion
           principal de la pantalla. */
        .sel-limpiar { background: none; border: 1px solid var(--bs-border-color); color: var(--bs-secondary-color);
            font-size: .82rem; font-weight: 600; padding: 6px 12px; border-radius: 8px; cursor: pointer;
            display: inline-flex; align-items: center; gap: 6px; font-family: inherit; }
        .sel-limpiar:hover { color: #c0392b; border-color: #c0392b; }
        .sel-acciones { display: flex; align-items: center; gap: 12px; flex-wrap: wrap; }
        .sel-aviso {
            display: flex; align-items: center; gap: 9px; margin-bottom: 16px;
            background: rgba(212,175,55,.14); color: #b8860b;
            border-radius: 11px; padding: 10px 14px; font-size: .86rem; font-weight: 600;
        }
        .sel-vacio { text-align: center; padding: 48px 16px; color: var(--bs-secondary-color); }
        .sel-vacio i { font-size: 2.6rem; color: #d4af37; display: block; margin-bottom: 12px; }
        .sel-vacio p { margin: 0 0 6px; font-size: 1rem; }
        .sel-ayuda { font-size: .86rem; }
        .sel-btn {
            display: inline-block; margin-top: 14px; padding: 10px 22px; border-radius: 30px;
            background: #d4af37; color: #3a2e07; text-decoration: none; font-weight: 700; font-size: .9rem;
        }
        .sel-btn:hover { background: #b8860b; color: #fff; }

        /* ---------- Tabla comparativa ---------- */
        /* Se desplaza de lado dentro de su marco, NO la página entera. */
        .cmp-marco { overflow-x: auto; -webkit-overflow-scrolling: touch; margin-bottom: 26px; }
        .cmp-tabla { border-collapse: separate; border-spacing: 0; width: 100%; min-width: 520px; font-size: .88rem; }
        .cmp-tabla th, .cmp-tabla td { padding: 10px 12px; border-bottom: 1px solid var(--bs-border-color); text-align: center; vertical-align: middle; }
        /* La primera columna (los nombres de los datos) se queda fija al desplazar:
           sin ella, a la tercera columna ya no se sabe qué se está mirando. */
        .cmp-fija {
            position: sticky; left: 0; z-index: 2;
            background: var(--bs-body-bg); text-align: left !important;
            font-weight: 600; color: var(--bs-secondary-color); white-space: nowrap;
            box-shadow: 1px 0 0 var(--bs-border-color);
        }
        .cmp-fija i { color: #b8860b; margin-right: 7px; }
        /* En el teléfono la columna de nombres se llevaba media pantalla. Se queda el
           icono con una etiqueta mínima debajo: con SOLO el icono no se distinguiría
           "precio por m² construido" de "construcción" (las dos son una casa). */
        @media (max-width: 575.98px) {
            .cmp-fija { width: 80px; min-width: 80px; padding: 8px 6px; text-align: center !important; }
            .cmp-fija i { display: block; margin: 0 0 3px; font-size: 1.25rem; }
            .cmp-fija .lbl-corta { font-size: .74rem; line-height: 1.15; display: block; white-space: normal; }
            .cmp-tabla { min-width: 0; }
            .cmp-tabla th, .cmp-tabla td { padding: 9px 8px; }
        }
        /* El vértice va CENTRADO: la alineación arriba es para que las fotos de las
           columnas arranquen a la misma altura, pero aquí solo hay un icono y dejaba
           un hueco enorme debajo.
           Ojo al selector: hace falta ".cmp-tabla thead th.cmp-esquina" porque
           ".cmp-esquina" a secas pierde contra ".cmp-tabla thead th", que tiene más
           peso (una clase y dos elementos), y la regla no se aplicaba. */
        .cmp-esquina { z-index: 3; }
        .cmp-tabla thead th.cmp-esquina { vertical-align: middle; }
        /* La cabecera se alinea ARRIBA: cada columna tiene distinta cantidad de
           etiquetas de punto fuerte, y centrada en vertical cada foto quedaba a una
           altura distinta. Las celdas de datos siguen centradas. */
        .cmp-tabla thead th { vertical-align: top; }
        .cmp-col { min-width: 150px; position: relative; background: var(--bs-body-bg); }
        .cmp-col a { text-decoration: none; color: inherit; display: block; }
        .cmp-foto { width: 100%; max-width: 150px; aspect-ratio: 4/3; object-fit: cover; border-radius: 10px; display: block; margin: 0 auto 6px; }
        .cmp-codigo { display: block; font-weight: 700; font-size: .8rem; }
        .cmp-tipo { display: block; font-size: .75rem; color: var(--bs-secondary-color); font-weight: 500; }
        .cmp-quitar {
            position: absolute; top: 2px; right: 2px; width: 26px; height: 26px; border-radius: 50%;
            border: none; background: rgba(34,37,42,.72); color: #fff; font-size: .7rem; cursor: pointer;
            display: flex; align-items: center; justify-content: center;
        }
        .cmp-quitar:hover { background: #c0392b; }
        .cmp-fuertes { display: flex; flex-wrap: wrap; gap: 4px; justify-content: center; margin-top: 6px; }
        .cmp-chip { font-size: .66rem; font-weight: 700; padding: 2px 7px; border-radius: 20px; background: rgba(212,175,55,.18); color: #b8860b; }
        /* Gana esta fila: se resalta el valor, no la celda entera, para no
           convertir la tabla en un semáforo. */
        .cmp-mejor { background: rgba(212,175,55,.14); font-weight: 700; color: #b8860b; }
        .cmp-texto { font-size: .8rem; text-align: left !important; min-width: 160px; }
        .cmp-wa { display: inline-flex; align-items: center; gap: 6px; background: #25D366; color: #fff; text-decoration: none; padding: 6px 12px; border-radius: 8px; font-size: .8rem; font-weight: 600; }
        .cmp-wa:hover { background: #1da851; color: #fff; }

        /* Directorio y Ubicación, uno al lado del otro. Con uno solo (si no hay
           ubicación cargada), ese ocupa la fila entera él solo. */
        .menu-par { display: flex; gap: 8px; margin-bottom: 1rem; }
        .menu-par .btn { flex: 1 1 0; min-width: 0; margin-bottom: 0 !important; padding-left: .7rem !important; padding-right: .7rem !important; white-space: nowrap; }

        /* Un <button> dentro del menú tiene que calcar al <a> de al lado. */
        /* El color va explícito: sin él, el navegador le pone el suyo de botón (blanco)
           y "Agencias Dorata" resaltaba más que los enlaces de al lado. */
        /* Solo se quitan los adornos del botón: NADA de 'font: inherit', que al ser más
           específico pisaba el tamaño y el color de .menu-link y "Agencias Dorata"
           salía más grande y más blanco que los enlaces de al lado. */
        button.menu-link { background: none; border: none; width: 100%; text-align: left;
            font-family: inherit; cursor: pointer; }

        /* Cargo + salir, en la misma línea. Si no caben, el botón baja solo. */
        /* Cargo y "Salir", SIEMPRE en la misma línea (nowrap): con wrap, un cargo largo
           —"Agente de Bienes y Raíces"— empujaba el botón al renglón de abajo. El cargo
           se parte en dos líneas dentro de su píldora y el botón se queda a la derecha. */
        .cuenta-fila-cargo { display: flex; align-items: center; gap: 8px; flex-wrap: nowrap; margin-top: 6px; }
        .cuenta-fila-cargo .badge { flex: 1 1 auto; min-width: 0; text-align: left; white-space: normal; line-height: 1.3; }
        .cuenta-fila-cargo .cuenta-salir { flex: 0 0 auto; }
        .cuenta-salir {
            display: inline-flex; align-items: center; gap: 5px; text-decoration: none;
            border: 1px solid rgba(220,53,69,.55); color: #dc3545; border-radius: 20px;
            padding: 3px 11px; font-size: .75rem; font-weight: 700; white-space: nowrap;
        }
        .cuenta-salir:hover { background: #dc3545; color: #fff; }

        /* Bloque "Cuenta" del menú: los datos a la izquierda y la foto a la derecha. */
        .cuenta-caja { display: flex; align-items: flex-start; gap: 12px; }
        .cuenta-datos { flex: 1; min-width: 0; }
        .cuenta-codigo { font-weight: 700; font-size: 1rem; color: #d4af37; letter-spacing: .02em; margin-top: 2px; }
        /* Un nombre largo parte de renglón en vez de estirar el menú a lo ancho. */
        .cuenta-nombre { font-weight: 600; overflow-wrap: anywhere; }
        .cuenta-pareja { font-weight: 500; opacity: .85; overflow-wrap: anywhere; }
        .cuenta-avatar { flex-shrink: 0; width: 52px; height: 52px; font-size: .95rem; }


        /* ---------- Radar "de un vistazo" ---------- */
        /* 620 y no 520: el viewBox del radar creció a lo ancho para que las etiquetas
           de los ejes quepan dentro, así que con el ancho de antes el hexágono se
           habría visto un 17% más pequeño en el PC. En el teléfono manda el
           contenedor, que es más estrecho. */
        .cmp-radar-caja { max-width: 620px; margin: 0 auto; }
        .cmp-radar { width: 100%; height: auto; display: block; overflow: visible; }
        .cmp-radar-malla { fill: none; stroke: var(--bs-border-color); stroke-width: 1; }
        .cmp-radar-eje { font-size: 11px; font-weight: 600; fill: var(--bs-secondary-color); }
        .cmp-radar-fig { fill-opacity: .18; stroke-width: 2; transition: fill-opacity .15s, stroke-opacity .15s; }
        /* Con una propiedad enfocada, las demás se apagan (no se ocultan: sirven de
           referencia para ver contra qué se está comparando). */
        .cmp-radar.con-foco .cmp-radar-fig { fill-opacity: .04; stroke-opacity: .25; }
        .cmp-radar.con-foco .cmp-radar-fig.enfocada { fill-opacity: .32; stroke-opacity: 1; }
        .cmp-radar-leyenda { display: flex; flex-wrap: wrap; justify-content: center; gap: 8px; margin: 6px 0 12px; }
        .cmp-leg {
            display: inline-flex; align-items: center; gap: 7px; cursor: pointer;
            border: 1px solid var(--bs-border-color); background: transparent; color: var(--bs-body-color);
            border-radius: 20px; padding: 5px 12px; font-size: .78rem; font-weight: 600;
        }
        .cmp-leg:hover { border-color: #d4af37; }
        .cmp-leg.activa { border-color: #d4af37; background: rgba(212,175,55,.14); color: #b8860b; }
        .cmp-leg-color { width: 11px; height: 11px; border-radius: 50%; flex-shrink: 0; }
        .cmp-radar-nota { text-align: center; }

        /* ---------- Gráfica de precio por m² ---------- */
        /* Compartir la comparación. Solo lo ve quien tiene sesión, así que vive con el
           resto de los estilos de la página y no en una hoja aparte. Los tres botones
           van cuadrados y solo con icono, como los de "Tu catálogo". */
        .cmp-compartir { margin: 0 0 32px; padding: 16px; border-radius: 14px;
            border: 1px solid rgba(212,175,55,.45); background: rgba(212,175,55,.08); }
        .cmp-comp-tit { font-weight: 800; margin-bottom: 6px; }
        .cmp-comp-tit .bi { color: #d4af37; margin-right: 6px; }
        .cmp-comp-p { font-size: .88rem; line-height: 1.5; margin: 0 0 10px; opacity: .85; }
        /* overflow-wrap: el enlace es largo y en el teléfono sacaba scroll horizontal. */
        .cmp-comp-url { font-size: .78rem; background: rgba(0,0,0,.18); border-radius: 9px;
            padding: 8px 10px; margin-bottom: 10px; overflow-wrap: anywhere; }
        .cmp-comp-acc { display: flex; gap: 8px; }
        .cmp-comp-btn { flex: 1; display: inline-flex; align-items: center; justify-content: center;
            padding: 10px; border-radius: 10px; font-size: 1.15rem; cursor: pointer;
            border: 1px solid rgba(128,128,128,.35); background: none; color: inherit;
            text-decoration: none; }
        .cmp-comp-btn.wa { background: #25d366; border-color: #25d366; color: #06331a; }
        .cmp-analisis { margin-bottom: 32px; }
        .cmp-nota { font-size: .82rem; color: var(--bs-secondary-color); margin-bottom: 14px; }
        .cmp-barra-fila { display: flex; align-items: center; gap: 10px; margin-bottom: 8px; }
        /* El ancho lo pone el propio código, no un número fijo: con 120px (92 en el
           teléfono) el código salía cortado con puntos suspensivos, que es justo lo
           que hay que poder leer. La barra se queda con lo que sobre. */
        .cmp-barra-lbl { flex: 0 0 auto; max-width: 46%; font-size: .78rem; font-weight: 600; white-space: nowrap; }
        .cmp-barra-pista { flex: 1; min-width: 0; background: var(--bs-tertiary-bg); border-radius: 20px; height: 22px; overflow: hidden; }
        .cmp-barra { display: block; height: 100%; background: #adb5bd; border-radius: 20px; }
        .cmp-barra.mejor { background: #d4af37; }
        .cmp-barra-val { width: 110px; flex-shrink: 0; text-align: right; font-size: .8rem; font-weight: 700; }
        .cmp-barra-val i { color: #d4af37; }
        @media (max-width: 575.98px) {
            .cmp-barra-fila { gap: 7px; }
            .cmp-barra-lbl { font-size: .72rem; }
            .cmp-barra-val { width: 74px; font-size: .74rem; }
        }
        .prop-share { width: 36px; height: 36px; border-radius: 9px; border: none; background: #d4af37; color: #3a2e07; display: flex; align-items: center; justify-content: center; font-size: 1rem; cursor: pointer; flex-shrink: 0; }
        .prop-share:hover { background: #b8860b; color: #fff; }
        .prop-specs { font-size: 0.78rem; color: #22252a; }
        .prop-specs .spec-label { font-size: 0.6rem; color: #6c757d; font-weight: 600; letter-spacing: .02em; }
        /* Fechas de la tarjeta: actualización a la izquierda, publicación a la derecha.
           Van en gris apagado a propósito: son contexto, no el dato por el que se
           entra a una propiedad. */
        .prop-fechas {
            display: flex; justify-content: space-between; gap: 10px; flex-wrap: wrap;
            font-size: .68rem; color: #6c757d; padding-top: 6px;
        }
        .prop-fechas i { margin-right: 3px; }
        .prop-specs .spec-ic { color: #b8860b; font-size: 0.92rem; }
        .prop-specs strong { color: #22252a; font-weight: 700; }
        .visor-flyer-img { max-height: 88vh; max-width: 100%; width: auto; }

        /* ===== Menú lateral (navegación limpia) ===== */
        .menu-section-title { font-size: .7rem; letter-spacing: .06em; }
        .menu-nav { display: flex; flex-direction: column; gap: 2px; }
        .menu-link {
            display: flex; align-items: center; gap: 12px;
            padding: 10px 12px; border-radius: 10px;
            color: var(--bs-body-color); text-decoration: none;
            font-weight: 500; font-size: .95rem;
            transition: background-color .15s ease, color .15s ease;
        }
        .menu-link:hover { background: rgba(212,175,55,.14); color: var(--bs-body-color); }
        /* La entrada de Tutoriales lleva la cara de Doroty y una línea que dice para
           qué sirve: es donde está la ayuda, y sin decirlo nadie entra a buscarla. */
        .menu-doroty-cara { width: 22px; flex-shrink: 0; display: flex; }
        .menu-doroty small { display: block; font-size: .74rem; font-weight: 400; opacity: .65; margin-top: 1px; }
        .menu-link > i, .menu-link > .menu-ico {
            width: 22px; text-align: center; color: #d4af37; font-size: 1.05rem; flex-shrink: 0;
        }
        .menu-link > .menu-ico { font-weight: 700; }
        .menu-divider { border-top: 1px solid var(--bs-border-color); margin: 12px 0; }
        .theme-toggle {
            border: 1px solid var(--bs-border-color); background: transparent;
            width: 38px; height: 38px; border-radius: 10px; color: var(--bs-body-color);
            display: flex; align-items: center; justify-content: center; flex-shrink: 0;
        }
        .theme-toggle:hover { background: rgba(212,175,55,.14); color: #d4af37; }

        /* ===== Overrides de modo oscuro para los fondos claros fijos ===== */
        [data-bs-theme="dark"] body.bg-light { background-color: #14161a !important; }
        [data-bs-theme="dark"] .navbar { background-color: #1a1d21 !important; }
        [data-bs-theme="dark"] .bg-light { background-color: #1a1d21 !important; }
        [data-bs-theme="dark"] .bg-white { background-color: #1e2126 !important; }
        [data-bs-theme="dark"] .text-dark { color: var(--bs-body-color) !important; }
        [data-bs-theme="dark"] .dir-item { background: #1e2126; border-color: #2a2e35; }
        [data-bs-theme="dark"] .dir-item:hover { background: #262a31; }
        [data-bs-theme="dark"] .dir-nombre { color: #e9ecef; }
        [data-bs-theme="dark"] .dir-vcard { border-color: #2a2e35; }
        [data-bs-theme="dark"] .dir-vcard:hover { background: #33291a; }
        [data-bs-theme="dark"] .prop-specs,
        [data-bs-theme="dark"] .prop-specs strong { color: #e9ecef; }
        [data-bs-theme="dark"] .badge.border-dark { border-color: #6c757d !important; }

        /* Costo por m2 (tarjeta y ficha). Dorado del sistema, sin fondo solido: es un
           dato de apoyo y no debe competir con el precio. Color y fondo PROPIOS en los
           dos temas: un fondo sin color hereda el del tema y se vuelve ilegible. */
        .prop-pm2 { background: rgba(212,175,55,.16); color: #8a6d1f; font-weight: 600; }
        .prop-pm2 .pm2-que { font-weight: 400; opacity: .75; }
        [data-bs-theme="dark"] .prop-pm2 { background: rgba(212,175,55,.18); color: #e2c467; }
        /* Sobre la FOTO el dorado translucido no se lee (la foto pone el fondo): ahi
           lleva la misma caja oscura del precio, con el texto en dorado. No cambia con
           el tema, porque la foto tampoco. */
        .prop-pm2-foto { background: rgba(34,37,42,.9) !important; color: #e2c467 !important; font-size: .74rem; padding: 3px 10px; border-radius: 7px; }

        /* Logo segun el tema: el blanco solo en oscuro (en claro la barra es clara). */
        .navbar-brand .logo-dark { display: none; }
        [data-bs-theme="dark"] .navbar-brand .logo-light { display: none; }
        [data-bs-theme="dark"] .navbar-brand .logo-dark { display: inline; }

        /* Pie: el footer es oscuro en los DOS temas, pero el logo a color se ve
           apagado sobre negro, asi que en oscuro se usa el de letras blancas (y ahi
           ya no hace falta la caja blanca detras). Clases propias: las del navbar
           estan acotadas a .navbar-brand. */

        /* ===== Redes sociales (menu y pie). Mismas piezas en los dos sitios. ===== */
        .redes-fila { display: flex; gap: 10px; flex-wrap: wrap; }
        .red-ico {
            width: 38px; height: 38px; border-radius: 50%;
            display: inline-flex; align-items: center; justify-content: center;
            background: rgba(212,175,55,.14); color: #d4af37;
            font-size: 1.05rem; text-decoration: none; flex-shrink: 0;
            transition: background-color .15s ease, color .15s ease;
        }
        .red-ico:hover { background: #d4af37; color: #3a2e07; }
        .redes-menu { justify-content: center; }
        .redes-pie { justify-content: center; margin-top: 14px; }
        @media (min-width: 768px) { .redes-pie { justify-content: flex-start; } }
        /* ===== Banner de video de la portada =====
           Va de lado a lado: el <body> tiene p-4 (1.5rem), asi que el banner se sale
           de ese margen con margenes negativos — mas fiable que 100vw, que en PC suma
           el ancho de la barra de desplazamiento y provoca scroll horizontal.
           El margen de arriba tambien es negativo para que quede pegado a la cabecera
           (la barra trae mb-4). Proporcion 16:9 en cualquier pantalla. */
        /* Va de lado a lado solo. Antes llevaba márgenes negativos para romper el
           p-4 del <body>, que ya no existe; dejarlos lo sacaría de la pantalla. */
        .video-banner { position: relative; margin: 0 0 1.5rem; background: #000; line-height: 0; }

        /* ---- Banner de bienvenida (Configuración > Banner) ----
           Dos estilos, lo elige el broker: 'banda' es una franja corta cuyos
           mensajes se turnan solos; 'hero' ocupa media pantalla y el mensaje
           cambia según se baja. El color del TEXTO lo calcula el servidor a
           partir del degradado (ver bannerPortada): con un fondo claro, un
           texto blanco fijo no se leería. */
        /* OJO: nada de overflow aquí. Un overflow (aunque sea hidden) convierte al
           elemento en contenedor de scroll y el position:sticky de dentro se calcula
           contra ÉL, con lo que el banner deja de quedarse pegado. Es la misma trampa
           que descolocó la cabecera de la ficha. */
        /* NADA de margen negativo aquí. Se probó para comer el mb-4 de la barra y
           quitar la franja, pero tiraba del banner POR ENCIMA de la cabecera: al
           bajar, la barra aparecía cortada por arriba. La franja se quita por el
           otro lado — a la barra se le retira su margen inferior cuando hay banner
           (clase con-banner). */
        .ban-wrap { position: relative; margin: 0 0 1.5rem; }
        /* La barra pega con el banner: sin margen entre los dos, y sin que nadie
           invada a nadie. */
        nav.navbar.con-banner { margin-bottom: 0 !important; }
        /* En la banda el que manda es .ban-fijo (aquí no es sticky, solo el contenedor):
           lleva el alto y el relleno para que las capas de imagen, que se posicionan
           contra él, queden dentro de la franja y no del tramo entero. */
        .ban-banda .ban-fijo {
            position: relative; width: 100%; min-height: 170px; overflow: hidden;
            display: flex; align-items: center; justify-content: center; padding: 2rem 1.25rem;
        }
        /* La pista es el tramo de página que dura el recorrido: una altura por frase,
           según lo que se haya elegido en el panel (--ban-pista viene del servidor). */
        .ban-hero .ban-pista { height: calc(var(--ban-pista, 3) * 100vh); position: relative; }
        /* El banner se pega DEBAJO de la barra, no encima: los dos son sticky y con
           top:0 se pegaban al mismo borde, así que el banner quedaba tapado por la
           barra (que va con z-index 1020) y el texto salía descentrado.
           --dr-nav lo mide el JS: la barra no tiene el mismo alto en el teléfono
           (87px) que en el escritorio (111px). */
        /* NADA de position:sticky aquí. Con el banner pegado por sticky, el navegador
           del teléfono descolocaba la BARRA superior al bajar (comprobado por el
           usuario: apagando el banner, la barra deja de moverse). Son dos elementos
           pegados compitiendo en la misma página, y uno del alto de la pantalla.
           Ahora el pegado lo gobierna banner.js con tres estados —antes, durante y
           después del tramo— y la barra se queda como único sticky. */
        .ban-hero .ban-fijo {
            position: absolute; top: 0; left: 0; right: 0;
            /* El alto lo fija banner.js en PIXELES (--ban-alto), medido una sola vez.
               Con unidades de viewport —probadas dvh y svh— el navegador del teléfono
               seguía moviendo la barra superior al bajar: la barra de direcciones se
               contrae en el primer scroll, el alto cambia a media maniobra y el
               documento se recalcula arrastrando a la cabecera. En píxeles no hay nada
               que recalcular. El calc() de respaldo solo actúa si el JS no llegó. */
            height: var(--ban-alto, calc(100vh - var(--dr-nav, 0px)));
            display: flex; align-items: center; justify-content: center; padding: 2rem 1.25rem;
        }
        /* Mientras se recorre el tramo: quieto en pantalla, justo bajo la barra. */
        .ban-hero .ban-fijo.pegado { position: fixed; top: var(--dr-nav, 0px); }
        /* Al terminar el recorrido se queda al fondo de su tramo y deja pasar la página. */
        .ban-hero .ban-fijo.abajo  { position: absolute; top: auto; bottom: 0; }
        .ban-dentro { display: grid; justify-items: center; text-align: center; width: 100%; max-width: 1000px; position: relative; z-index: 2; }
        /* Imágenes de fondo: una por frase, cruzándose con opacidad. 'cover' recorta
           por donde haga falta según la pantalla, así que el motivo tiene que ir
           CENTRADO en la imagen — se avisa en el panel. */
        .ban-fondo {
            position: absolute; inset: 0; background-size: cover; background-position: center;
            opacity: 0; transition: opacity .7s ease;
            background-image: var(--ban-img-movil);
        }
        /* En pantallas anchas, la versión apaisada. Una foto vertical de teléfono
           estirada a 1.900 px se ve pixelada, que es lo que pasaba antes de tener
           las dos. Si solo hay una cargada, PHP manda la misma en las dos variables. */
        @media (min-width: 768px) { .ban-fondo { background-image: var(--ban-img-pc); } }
        .ban-fondo.activo { opacity: 1; }
        /* Velo: sin él, una foto clara deja el texto ilegible. Va más oscuro abajo,
           que es donde suele caer el texto. */
        .ban-velo { position: absolute; inset: 0; background: linear-gradient(180deg, rgba(0,0,0,.35) 0%, rgba(0,0,0,.55) 100%); }
        /* La tipografía la elige el broker; --ban-familia la pone el servidor. */
        .ban-msg, .ban-sub { font-family: var(--ban-familia, inherit); }
        /* Los mensajes se apilan en la MISMA celda: así la franja no da saltos de
           alto al cambiar de uno a otro, y el fundido ocurre en el sitio. */
        .ban-msg {
            grid-row: 1; grid-column: 1; margin: 0;
            font-size: clamp(1.5rem, 4.2vw, 3rem); font-weight: 700; line-height: 1.15;
            letter-spacing: -.01em; text-shadow: 0 2px 12px rgba(0,0,0,.25);
            opacity: 0; transform: translateY(10px); transition: opacity .55s ease, transform .55s ease;
            pointer-events: none;
        }
        .ban-msg.activo { opacity: 1; transform: none; }
        /* En el recorrido las frases no solo aparecen: se DESPLAZAN. La que se va sube
           y se desvanece, la que entra viene desde abajo. Lo gobierna banner.js con
           estas dos clases, para que el movimiento acompañe al dedo. */
        /* En el recorrido NO hay transición: la posición de cada frase la calcula
           banner.js en cada fotograma a partir del scroll, para que el texto se
           mueva con el dedo. Una transición aquí lo haría llegar tarde y volvería
           a parecer un salto. */
        .ban-hero .ban-msg.libre { transition: none; will-change: transform, opacity; }
        /* Cómo se cambia de una frase a otra. Lo elige el broker en el panel; el
           servidor pone la clase ban-ef-* en el contenedor. 'sale' es la que se va,
           'entra' el punto de partida de la que llega. */
        .ban-hero .ban-msg.sale  { opacity: 0; transform: translateY(-38px); }
        .ban-hero .ban-msg.entra { opacity: 0; transform: translateY(38px); }
        /* Fundido: sin movimiento, solo se desvanece. */
        .ban-ef-fundido .ban-msg.sale, .ban-ef-fundido .ban-msg.entra { transform: none; }
        /* Zoom: la que entra viene un poco grande y se asienta. */
        .ban-ef-zoom .ban-msg.sale  { transform: scale(.94); }
        .ban-ef-zoom .ban-msg.entra { transform: scale(1.07); }
        /* Lateral: pasan de lado, como diapositivas. */
        .ban-ef-lateral .ban-msg.sale  { transform: translateX(-45px); }
        .ban-ef-lateral .ban-msg.entra { transform: translateX(45px); }
        /* El texto pequeño acompaña a la ÚLTIMA frase: aparece con ella y no antes.
           Lo enciende banner.js (o el servidor, si solo hay una frase). */
        .ban-sub { grid-row: 2; margin: .85rem 0 0; font-size: clamp(.9rem, 1.6vw, 1.05rem); max-width: 46ch;
                   opacity: 0; transition: opacity .5s ease .2s; }
        .ban-sub.visible { opacity: .88; }
        /* Flecha de "sigue bajando": solo en el recorrido, y se apaga al llegar al final. */
        .ban-flecha {
            grid-row: 3; margin-top: 1.6rem; font-size: 1.5rem; opacity: .75;
            animation: banBaja 1.8s ease-in-out infinite; transition: opacity .3s;
        }
        .ban-flecha.oculta { opacity: 0; }
        @keyframes banBaja { 0%,100% { transform: translateY(0); } 50% { transform: translateY(7px); } }
        @media (max-width: 575px) {
            .ban-banda .ban-fijo { min-height: 140px; padding: 1.5rem 1rem; }
            /* En el teléfono el recorrido ocupa casi toda la pantalla de alto, que es
               donde este efecto luce: una franja baja en vertical no se aprecia. */
            .ban-hero .ban-fijo { padding: 1.5rem 1rem; }
            /* En vertical la frase tiene que llenar la pantalla: se mide en vw (ancho)
               y con un mínimo en vh, para que en un teléfono alto no quede un titular
               perdido en medio de un fondo enorme. */
            .ban-msg { font-size: clamp(2.1rem, 11vw, 3.6rem); line-height: 1.1; }
            .ban-hero .ban-msg { font-size: max(clamp(2.1rem, 11vw, 3.6rem), 5.2vh); }
            .ban-sub { font-size: 1rem; margin-top: 1.1rem; }
        }
        /* Quien pide menos animación ve el primer mensaje y ya: sin fundidos. */
        @media (prefers-reduced-motion: reduce) {
            .ban-msg { transition: none; }
        }

        /* Ancho de trabajo del sitio. El .container de Bootstrap corta en 1140px
           (1320 en pantallas muy grandes) y con las tarjetas de 4 en fondo quedaba
           demasiado aire a los lados. Se sube el tope a partir de 992px, que es
           donde empiezan las 4 columnas; por debajo manda Bootstrap.
           El tope existe a propósito: sin él, en un monitor de 2560px la ficha
           descriptiva sale en renglones larguísimos y no hay quien la lea.
           Afecta también a la cabecera, al pie y a la barra de filtros, que usan
           el mismo .container: así todo queda alineado con las tarjetas. */
        @media (min-width: 992px) {
            .container { max-width: 1600px; }
        }

        /* ---------- Paginación del listado ---------- */
        .pag-nav { display: flex; flex-direction: column; align-items: center; gap: 10px; margin: 8px 0 32px; }
        .pag-cuenta { font-size: .82rem; color: #6c757d; }
        /* flex-wrap: en el teléfono los números caben en dos renglones antes que
           sacar la página de ancho (el clásico scroll horizontal). */
        .pag-lista { display: flex; flex-wrap: wrap; justify-content: center; gap: 6px; list-style: none; padding: 0; margin: 0; }
        .pag-btn {
            display: flex; align-items: center; justify-content: center;
            min-width: 40px; height: 40px; padding: 0 12px;
            border: 1px solid var(--bs-border-color); border-radius: 10px;
            background: var(--bs-body-bg); color: var(--bs-body-color);
            text-decoration: none; font-weight: 600; font-size: .88rem;
        }
        .pag-btn:hover { border-color: #d4af37; color: #b8860b; }
        .pag-btn.activo { background: #d4af37; border-color: #d4af37; color: #3a2e07; }
        .pag-btn.inactivo { opacity: .4; pointer-events: none; }
        .pag-puntos { display: flex; align-items: center; height: 40px; padding: 0 4px; color: #6c757d; }
        .video-marco { position: relative; width: 100%; aspect-ratio: 16 / 9; }
        .video-marco iframe { position: absolute; inset: 0; width: 100%; height: 100%; border: 0; }
        .video-sonido {
            position: absolute; right: 14px; bottom: 14px; z-index: 2;
            width: 44px; height: 44px; border-radius: 50%; border: none;
            background: rgba(0,0,0,.55); color: #fff; font-size: 1.1rem; line-height: 1;
            display: flex; align-items: center; justify-content: center; cursor: pointer;
        }
        .video-sonido:hover { background: #d4af37; color: #3a2e07; }
        /* El video vive en una ventana (modal), no en un banner: el cuerpo del modal
           es el que posiciona el botón de sonido, así que necesita ser el contenedor
           relativo. Sin esto el botón se iría a la esquina de la pantalla. */
        #modalVideo .modal-body { position: relative; }

        /* Recuadro del mapa (popup de Ubicacion). El iframe se carga al abrir el popup,
           no en cada visita a la portada: ver el script del final de footer.php.
           En PC el popup es ancho y el mapa apaisado; en el telefono el mapa se pone
           VERTICAL (cabe mas calle alrededor del punto en una pantalla estrecha). */
        .mapa-caja { position: relative; width: 100%; aspect-ratio: 16/10; border-radius: 12px; overflow: hidden; background: #e9ecef; }
        .mapa-caja iframe { position: absolute; inset: 0; width: 100%; height: 100%; border: 0; }
        [data-bs-theme="dark"] .mapa-caja { background: #2a2f36; }
        /* Franja propia sobre el mapa. Tapa el chip "Abrir en Maps" que Google pinta
           arriba a la izquierda: confunde, porque el boton bueno es el dorado de abajo.
           Va de lado a lado a proposito — el chip cambia de ancho segun el idioma, y
           cubrir toda la franja es lo unico que lo esconde siempre. NO lleva
           pointer-events:none: asi tambien queda intocable, no solo invisible.
           La atribucion de Google (logo, datos del mapa y Terminos) queda intacta
           abajo, que es donde tiene que estar. */
        .mapa-tapa {
            position: absolute; top: 0; left: 0; right: 0; z-index: 2;
            display: flex; align-items: center; gap: 7px;
            min-height: 46px; padding: 10px 14px;
            background: #fff; color: #22252a;
            font-size: .82rem; font-weight: 600; line-height: 1.25;
            border-bottom: 1px solid rgba(0,0,0,.08);
        }
        .mapa-tapa i { color: #d4af37; flex-shrink: 0; }
        /* Compartir la direccion (cabecera del popup de Ubicacion). */
        .ubi-compartir {
            width: 38px; height: 38px; border-radius: 10px; flex-shrink: 0;
            border: 1px solid var(--bs-border-color); background: transparent;
            color: #d4af37; font-size: 1rem;
            display: inline-flex; align-items: center; justify-content: center;
        }
        .ubi-compartir:hover { background: #d4af37; color: #3a2e07; border-color: #d4af37; }
        .mapa-tapa span { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
        [data-bs-theme="dark"] .mapa-tapa { background: #1e2126; color: #e9ecef; border-bottom-color: #2a2e35; }

        /* Anchos de los popups propios. Bootstrap deja apenas .5rem de margen en el
           telefono y quedaban pegados a los bordes; aqui se les da aire por los cuatro
           lados y se limita el alto para que nunca se salgan de la pantalla. */
        .modal-ubi .modal-dialog { max-width: 680px; }
        .modal-ofi .modal-dialog { max-width: 460px; }
        @media (max-width: 575.98px) {
            .modal-ubi .modal-dialog,
            .modal-ofi .modal-dialog { max-width: none; margin: 1rem; }
            .modal-ubi .modal-content,
            .modal-ofi .modal-content { max-height: calc(100dvh - 2rem); }
            .mapa-caja { aspect-ratio: 3/4; }
        }

        /* Contraste en oscuro: Directorio y codigo de captacion (fondo negro -> blanco). */
        [data-bs-theme="dark"] #btnDirectorio { background: #fff !important; color: #22252a !important; border-color: #fff !important; }
        /* Ubicacion es el boton secundario: en oscuro el borde negro no se veia.
           #btnOficinas ya NO va aquí: dejó de ser una píldora y ahora es un enlace del
           menú ("Agencias Dorata"). Esta regla lo pintaba de blanco con !important y
           resaltaba más que los enlaces de al lado. */
        [data-bs-theme="dark"] #btnUbicacion { color: #fff !important; border-color: rgba(255,255,255,.55) !important; }
        [data-bs-theme="dark"] #btnUbicacion:hover { background: rgba(255,255,255,.12) !important; }

        /* ===== Oficinas de la red (popup del menu) =====
           Mismo lenguaje que el Directorio: tarjeta clara, pastilla dorada con el
           codigo y las lineas de datos con iconos dorados. */
        .ofi-card { position: relative; border: 1px solid #eee; border-radius: 14px; padding: 14px 14px 12px; margin-bottom: 10px; background: #fff; }
        .ofi-card .ofi-badge { position: absolute; top: 10px; right: 10px; background: #d4af37; color: #3a2e07; font-size: .68rem; font-weight: 700; padding: 2px 9px; border-radius: 20px; letter-spacing: .03em; }
        .ofi-card .ofi-tit { font-weight: 700; font-size: .95rem; color: #22252a; padding-right: 52px; margin-bottom: 8px; }
        .ofi-card .ofi-dato { display: flex; gap: 8px; font-size: .8rem; color: #5a6270; margin-bottom: 5px; line-height: 1.4; }
        .ofi-card .ofi-dato:last-child { margin-bottom: 0; }
        .ofi-card .ofi-dato i { color: #d4af37; flex-shrink: 0; margin-top: 2px; }
        .ofi-card .ofi-dato a { color: inherit; text-decoration: none; word-break: break-word; }
        .ofi-card .ofi-dato a:hover { color: #b8860b; }
        .ofi-card .ofi-mapa-btn {
            display: flex; align-items: center; justify-content: center; gap: 7px;
            width: 100%; margin-top: 10px; padding: 7px 12px;
            border: 1px solid #d4af37; border-radius: 9px; background: transparent;
            color: #b8860b; font-size: .8rem; font-weight: 600; cursor: pointer;
        }
        .ofi-card .ofi-mapa-btn:hover { background: #d4af37; color: #3a2e07; }
        [data-bs-theme="dark"] .ofi-card { background: #1e2126; border-color: #2a2e35; }
        [data-bs-theme="dark"] .ofi-card .ofi-mapa-btn { color: #e0b34d; }
        [data-bs-theme="dark"] .ofi-card .ofi-mapa-btn:hover { color: #3a2e07; }
        [data-bs-theme="dark"] .ofi-card .ofi-tit { color: #e9ecef; }
        [data-bs-theme="dark"] .ofi-card .ofi-dato { color: #9aa4b2; }
        [data-bs-theme="dark"] .prop-card .badge.bg-dark { background: #fff !important; color: #22252a !important; }
        /* El ancla a la que se salta al buscar. 'scroll-margin-top' es lo que evita
           que la barra superior (sticky, ~87px) tape la primera línea del resultado. */
        .ancla-buscar { display: block; height: 0; scroll-margin-top: 100px; }

        /* Barra donde se escribe la búsqueda y fichas de lo entendido. */
        .busca-natural input { font-size: .95rem; }
        .busca-natural input:focus { box-shadow: none; }
        .q-chips { display: flex; flex-wrap: wrap; gap: 6px; align-items: center; border-top: 1px dashed #e5e7eb; margin-top: 6px; }
        .q-chips-tit { font-size: .72rem; color: #6c757d; font-weight: 600; }
        .q-chip { display: inline-flex; align-items: center; gap: 5px; font-size: .74rem; font-weight: 600;
                  background: rgba(212,175,55,.16); color: #8a6d1f; border-radius: 20px; padding: 3px 10px; text-decoration: none; }
        .q-chip:hover { background: rgba(212,175,55,.30); color: #6b5416; }
        [data-bs-theme="dark"] .q-chips { border-top-color: #2a2e35; }
        [data-bs-theme="dark"] .q-chip { background: rgba(212,175,55,.18); color: #e2c467; }
        [data-bs-theme="dark"] #filterPlaceholder { background: #1e2126 !important; border-color: #2a2e35 !important; }
        [data-bs-theme="dark"] .busca-natural input { background: transparent; color: #e8eaed; }

        /* Barra "Abrir Filtros" (aparece al bajar): borde/letras/icono en blanco. */

        /* Ventanas de privacidad y condiciones. En PC ocupan una altura cómoda; en el
           teléfono el modal va a pantalla completa (modal-fullscreen-sm-down) y el cuerpo
           toma TODO el alto que queda. Antes era un 75vh fijo, que en el teléfono dejaba
           una franja muerta abajo y encogía el área de lectura. */
        .legal-body { height: min(78vh, 760px); overflow: hidden; padding: 0; }
        .legal-body iframe { width: 100%; height: 100%; border: none; display: block; }
        @media (max-width: 575.98px) {
            .legal-body { height: auto; flex: 1 1 auto; min-height: 0; }
        }
