/* ==========================================================================
   Aldecort · Estilos propios del CRM
   Se carga en index.html la ÚLTIMA, justo después de css/aldecort-tema.css,
   así que gana los empates de especificidad. No se editan
   tokens.css ni css/panel.css: lo nuevo va aquí.
   Contrato (lo siguen todas las pantallas del CRM):
     - Toda clase lleva el prefijo crm-. Eso no evita los empates: antes de
       añadir un selector que toque elementos del panel o de Syncfusion,
       comprueba que no pisa una regla de panel.css ni de
       aldecort-tema.css (como pasó con las casillas de las tablas).
     - El color de un proceso llega como propiedad inline --proc, ya saneado
       con SaneadoCrm.Color (#RRGGBB o gris): style="--proc:#0085BD".
     - Los tintes se calculan con color-mix(in srgb, var(--proc) N%, white).
     - El color de marca sale de las variables --crm-brand-*, definidas en
       css/aldecort-tema.css.

   1. Muestra de color de un proceso
   2. Leyenda de procesos
   3. Pantalla Oportunidades: disposición (aside y zona principal)
   4. Tarjetas del aside: resumen de actividad y filtros
   5. Barra de la vista
   6. Vista Lista: tabla ancha y compacta, pastilla de proceso, probabilidad,
      «Acciones» fija y paginador
   7. Estados de la pantalla: error de carga
   8. Diálogo de oportunidad: filas etiqueta + campo, campos, avisos, alto fijo
      y pie siempre a la vista
   9. Utilidades: texto de usuario que se parte (crm-texto-ajustado)
  10. Vistas Mes y Semana: rejilla del mes, agenda, semana y tarjeta de
      oportunidad
  11. Arrastrar y soltar: el día de destino resaltado, nada de lo de dentro
      de los días recibe el puntero y la tarjeta arrastrada atenuada
  12. Pestañas del diálogo, notas y seguimiento: pestañas Datos, Notas y
      Seguimiento, editor de Notas, línea de tiempo y nota nueva
  13. Interruptor de los formularios (InterruptorCrm)
  14. Parámetros: aviso de oportunidades en días ocultos (Oportunidades) y
      página Parámetros
  15. Cuentas de correo: formulario con los campos desplazables y resultado
      de la prueba de envío
  16. Simulador epoxi fuera de su pantalla: enlace «Simulaciones (N)» del
      diálogo de oportunidad y vista previa de Maestros → Colores Aldecort
  17. Empresas y Contactos: listas (nombre que abre, línea de datos en la
      tarjeta estrecha) y formularios (tarjeta «Información básica», grupos
      repetibles de teléfonos, correos y direcciones, avisos de contactos)
   ========================================================================== */

/* ── 1. Muestra de color (tabla y formulario de Procesos de venta) ──────── */
/* Con borde piedra: un color muy claro (#FFFFFF) se sigue viendo sobre blanco. */
.crm-muestra {
  display: inline-block; flex: 0 0 auto;
  width: 1rem; height: 1rem;
  border: 1px solid var(--color-border); border-radius: var(--radius-sm);
  background: var(--proc);
}

/* ── 2. Leyenda de procesos (LeyendaProcesos) ───────────────────────────── */
.crm-leyenda {
  display: flex; flex-wrap: wrap; gap: 0.5rem 1.25rem;
  margin: 0; padding: 0; list-style: none;
}
.crm-leyenda li {
  display: inline-flex; align-items: center; gap: 0.5rem; min-width: 0;
  font-size: 0.875rem; overflow-wrap: anywhere;
}
.crm-leyenda-punto {
  flex: 0 0 auto; width: 0.75rem; height: 0.75rem;
  border: 1px solid var(--color-border); border-radius: 9999px;
  background: var(--proc);
}

/* ── 3. Pantalla Oportunidades: disposición ─────────────────────────────── */
/* Todo el ancho: sin el tope de 1280 px de .ag-main-inner (panel.css, 0,1,0). Con :has(.crm-page) esta
   regla pesa 0,2,0 y gana sin depender del orden de carga. */
.ag-main-inner:has(.crm-page) { max-width: none; }

/* Contenedor de consultas crm-pagina: el aside (320 px) va a la izquierda cuando .crm-page mide 1000 px o más, y encima
   si no. Con nombre, porque dentro hay otro contenedor (crm-lista, sección 6) y una consulta sin nombre usaría el más
   cercano. Las capas fijas (diálogos, toasts) se ponen fuera de .crm-page. */
.crm-page { container-type: inline-size; container-name: crm-pagina; }
.crm-disposicion { display: grid; grid-template-columns: minmax(0, 1fr); gap: 1.5rem; align-items: start; }
/* Una tabla ancha no ensancha su columna: se desplaza dentro de su caja (sección 6). */
.crm-disposicion > * { min-width: 0; }
@container crm-pagina (min-width: 1000px) {
  .crm-disposicion { grid-template-columns: 320px minmax(0, 1fr); }
  /* Plegado: el lateral desaparece y su sitio es un carril de 1,75 rem; el calendario se queda con el resto. */
  .crm-disposicion--plegada { grid-template-columns: 1.75rem minmax(0, 1fr); gap: 0.75rem; }
}
/* Pliegue del lateral. El atributo hidden no gana a display: grid de .crm-aside sin esta regla (0,2,0). */
.crm-aside[hidden] { display: none; }
.crm-disposicion { position: relative; }
.crm-riel { display: none; }
/* Pantalla estrecha (el lateral va encima): una barra a todo el ancho, encima del lateral, con el texto a la vista. */
.crm-plegar {
  order: -1; display: flex; align-items: center; justify-content: center; gap: 0.5rem; width: 100%; min-height: 2.5rem;
  padding: 0.375rem 0.75rem; font: inherit; font-size: 0.875rem; font-weight: 500; color: var(--color-foreground);
  background: var(--color-card); border: 1px solid var(--color-border); border-radius: var(--radius-lg);
  box-shadow: var(--shadow-card); cursor: pointer;
}
.crm-plegar:hover { background: var(--bs-secondary-bg); }
.crm-plegar:focus-visible { outline: none; box-shadow: var(--focus-ring); }
/* El icono es «« (plegar a la izquierda); encima del contenido, plegar es hacia arriba y desplegar, hacia abajo. */
.crm-plegar-icono { font-size: 0.875rem; color: var(--color-muted-foreground); transform: rotate(90deg); }
.crm-disposicion--plegada .crm-plegar-icono { transform: rotate(-90deg); }
.crm-plegar-punto {
  width: 0.5rem; height: 0.5rem; border-radius: 50%; background: var(--crm-brand-500, #0085bd); flex: 0 0 auto;
}
@container crm-pagina (min-width: 1000px) {
  /* Pantalla ancha: una pestaña blanca de 1,75 × 2,75 rem centrada sobre el borde derecho del lateral (la línea de su
     caja pasa por la mitad del botón, que deja libre el hueco hacia el calendario) y, plegado, en el carril gris. Solo el
     icono: el texto sigue ahí, oculto, para el lector de pantalla. */
  .crm-plegar {
    position: absolute; top: 1.25rem; left: 320px; transform: translateX(-50%); z-index: 2;
    order: 0; width: 1.75rem; min-height: 2.75rem; height: 2.75rem; padding: 0;
    border-radius: 0.625rem; box-shadow: 0 1px 4px rgba(15, 23, 42, 0.18);
  }
  .crm-disposicion--plegada .crm-plegar { left: 0.875rem; }
  .crm-plegar-icono { transform: none; font-size: 1rem; }
  .crm-disposicion--plegada .crm-plegar-icono { transform: rotate(180deg); }
  .crm-plegar-texto {
    position: absolute; width: 1px; height: 1px; margin: -1px; padding: 0; overflow: hidden; clip: rect(0, 0, 0, 0);
    white-space: nowrap; border: 0;
  }
  .crm-plegar-punto { position: absolute; top: 0.3rem; right: 0.3rem; }
  .crm-riel {
    display: block; align-self: stretch; min-height: 8rem; background: var(--bs-secondary-bg);
    border-radius: var(--radius-lg);
  }
}
/* Encima del contenido, las tarjetas del aside se reparten en columnas; en los 320 px del lateral cabe una. */
.crm-aside {
  display: grid; gap: 1rem; align-items: start;
  grid-template-columns: repeat(auto-fit, minmax(min(100%, 17rem), 1fr));
}

/* ── 4. Tarjetas del aside: resumen de actividad y filtros ─────────────── */
.crm-panel {
  padding: 1rem; background: var(--color-card);
  border: 1px solid var(--color-border); border-radius: var(--radius-lg); box-shadow: var(--shadow-card);
}
/* Título de tarjeta como etiqueta: 12 px, 600, mayúsculas, tinta gris (4,8:1 sobre blanco). Es un h2: esta regla
   (0,1,0) pisa la de h2 de tokens.css (0,0,1). */
.crm-panel-titulo {
  margin: 0 0 0.75rem; font-size: 0.75rem; font-weight: 600; line-height: 1.3;
  text-transform: uppercase; letter-spacing: 0.025em; color: var(--color-muted-foreground);
}
/* Título y «Limpiar» en una fila de alto fijo: no salta al aparecer el botón. */
.crm-panel-cabecera {
  display: flex; align-items: center; justify-content: space-between; gap: 0.5rem;
  min-height: 2.25rem; margin-bottom: 0.5rem;
}
.crm-panel-cabecera .crm-panel-titulo { margin-bottom: 0; }

/* Fichas del resumen. Cada color fija fondo, borde y texto; contraste del texto sobre su fondo (WCAG AA, 4,5:1):
   c1 azul 8,4:1 · c2 esmeralda 7,3:1 · c3 violeta 8,2:1 · c4 ámbar 8,8:1. */
.crm-fichas {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(8.5rem, 1fr)); gap: 0.625rem;
  margin: 0; padding: 0; list-style: none;
}
.crm-ficha {
  display: flex; flex-direction: column; gap: 0.375rem; min-width: 0;
  padding: 0.625rem 0.75rem; border: 1px solid var(--crm-ficha-borde); border-radius: var(--radius-lg);
  background: var(--crm-ficha-fondo); color: var(--crm-ficha-texto);
}
.crm-ficha-numero { font-size: 1.25rem; font-weight: 700; line-height: 1; font-variant-numeric: tabular-nums; }
.crm-ficha-nombre {
  display: flex; align-items: center; gap: 0.375rem; min-width: 0;
  font-size: 0.75rem; font-weight: 500; line-height: 1.3; overflow-wrap: anywhere;
}
.crm-ficha--c1 { --crm-ficha-fondo: var(--crm-brand-50); --crm-ficha-borde: var(--crm-brand-200); --crm-ficha-texto: var(--crm-brand-800); }
.crm-ficha--c2 { --crm-ficha-fondo: #ECFDF5; --crm-ficha-borde: #A7F3D0; --crm-ficha-texto: #065F46; }
.crm-ficha--c3 { --crm-ficha-fondo: #F5F3FF; --crm-ficha-borde: #DDD6FE; --crm-ficha-texto: #5B21B6; }
.crm-ficha--c4 { --crm-ficha-fondo: var(--warning-surface); --crm-ficha-borde: var(--warning-border); --crm-ficha-texto: var(--warning); }

/* Campos de los filtros, uno debajo de otro. */
.crm-campo + .crm-campo { margin-top: 0.75rem; }
/* tokens.css deja .form-select (0,1,0) con 0.75rem a la derecha y el texto largo pasaría bajo la flecha:
   se recupera el hueco de Bootstrap (2.25rem). 0,2,0, sin empate. */
.crm-campo .form-select { padding-right: 2.25rem; }

/* ── 5. Barra de la vista ───────────────────────────────────────────────── */
.crm-barra {
  display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 0.75rem;
  margin-bottom: 1rem; padding: 0.75rem 1rem; background: var(--color-card);
  border: 1px solid var(--color-border); border-radius: var(--radius-lg); box-shadow: var(--shadow-card);
}
.crm-barra-inicio { display: flex; flex-wrap: wrap; align-items: center; gap: 0.75rem; min-width: 0; }
.crm-barra-titulo { min-width: 0; overflow-wrap: anywhere; }
/* Flechas de solo icono, cuadradas. 0,2,0: no empata con el relleno de .btn (0,1,0). */
.crm-barra .crm-barra-flecha { width: 2.5rem; --bs-btn-padding-x: 0; }
/* Iconos de los botones outline en el azul de marca, como los de Syncfusion en el panel (4,8:1 sobre blanco). */
.crm-barra .btn-outline-secondary > i,
.crm-paginador .btn-outline-secondary > i,
.crm-aviso .btn-outline-secondary > i { color: var(--color-primary); }

/* ── 6. Vista Lista ─────────────────────────────────────────────────────── */
/* La tarjeta es el contenedor de consultas crm-lista: la tabla se adapta al ancho de la tarjeta, no al de la ventana
   (tabla compacta, al final de esta sección). */
.crm-lista {
  container-type: inline-size; container-name: crm-lista;
  overflow: hidden; background: var(--color-card);
  border: 1px solid var(--color-border); border-radius: var(--radius-lg); box-shadow: var(--shadow-card);
}
/* La tabla se desplaza dentro de su caja, y solo en horizontal: la página nunca tiene desplazamiento horizontal. Sin
   overflow-y: hidden, el caption oculto (visually-hidden: 1 px con margen de -1 px) deja el cuadro de la tabla 1 px más
   bajo que sus filas, y ese píxel sacaba una barra vertical de 15 px que también apartaba «Acciones» del borde. */
.crm-lista-scroll { overflow-x: auto; overflow-y: hidden; }
.crm-lista-vacia {
  display: flex; flex-direction: column; align-items: center; gap: 0.5rem;
  padding: 3rem 1rem; text-align: center; color: var(--color-muted-foreground);
}
.crm-lista-vacia > i { font-size: 1.75rem; }
.crm-lista-vacia > p { margin: 0; font-weight: 500; }
/* Con OnEditar conectado, toda la fila abre la oportunidad. */
.crm-tabla tr.crm-fila-clicable { cursor: pointer; }

.crm-lista-oportunidad { display: flex; flex-direction: column; gap: 0.125rem; min-width: 12rem; max-width: 26rem; }
.crm-lista-titulo { font-weight: 600; overflow-wrap: anywhere; }
/* Icono, empresa y (contacto) en una fila flexible: el espacio lo da column-gap, no los espacios del marcado. */
.crm-lista-empresa { display: flex; flex-wrap: wrap; align-items: baseline; column-gap: 0.375rem; font-size: 0.8125rem; }
.crm-lista-empresa > span { min-width: 0; overflow-wrap: anywhere; }
/* La empresa cabe siempre al lado de su icono: el edificio (0,75 em) y el hueco (0,375rem) suman unos 16 px, menos que
   los 1,5 em (19,5 px) que se le dejan. Un nombre largo se parte junto al icono en vez de bajar entero a la línea
   siguiente y dejarlo solo arriba. El contacto sigue bajando si no cabe. */
.crm-lista-empresa > i + span { max-width: calc(100% - 1.5em); }
.crm-lista-empresa > i { color: var(--color-muted-foreground); }
.crm-lista-contacto { color: var(--color-muted-foreground); }
/* Línea de metadatos de la primera celda (acción, proceso y persona, con el marcado de sus columnas): solo se muestra
   en la tabla compacta. */
.crm-lista-meta { display: none; flex-wrap: wrap; align-items: center; gap: 0.25rem 0.5rem; margin-top: 0.25rem; }

/* Acción: chip neutro con el icono del tipo. */
.crm-chip {
  display: inline-flex; align-items: center; gap: 0.375rem;
  padding: 0.125rem 0.5rem; border: 1px solid var(--color-border); border-radius: var(--radius-sm);
  background: var(--color-muted); font-size: 0.75rem; font-weight: 500; line-height: 1.25rem; white-space: nowrap;
}
.crm-chip > i { color: var(--color-muted-foreground); }

/* Proceso: tinte del color del proceso (--proc, ya saneado) y un punto con el color puro. El texto va en tinta navy:
   sobre un tinte del 12 % el contraste es de 13,6:1 o más sea cual sea el color (el peor, el negro puro). El borde es
   el tinte del 40 % oscurecido un 20 % hacia la tinta navy: con un color muy claro ya no se pierde (#FFFFFF da un gris
   de 1,53:1 sobre blanco, más que el borde piedra del panel, 1,23:1) y con los de las semillas queda entre 2,0 y 2,5:1,
   suave como antes. El punto lleva el anillo piedra de la leyenda, por la misma razón. */
.crm-pastilla {
  display: inline-flex; align-items: center; gap: 0.375rem;
  padding: 0.125rem 0.625rem; border-radius: 9999px;
  border: 1px solid color-mix(in srgb, color-mix(in srgb, var(--proc) 40%, white) 80%, var(--color-foreground));
  background: color-mix(in srgb, var(--proc) 12%, white);
  color: var(--color-foreground); font-size: 0.75rem; font-weight: 600; line-height: 1.25rem; white-space: nowrap;
}
.crm-pastilla::before {
  content: ""; flex: 0 0 auto; width: 0.5rem; height: 0.5rem; border-radius: 9999px; background: var(--proc);
  box-shadow: inset 0 0 0 1px var(--color-border);
}

/* Etapa y probabilidad: barra de 0 a 100 en el azul 500 (no es texto: 3,35:1 contra el carril) y el número como texto. */
.crm-lista-etapa { display: block; font-weight: 500; }
.crm-prob-fila { display: flex; align-items: center; gap: 0.5rem; margin-top: 0.25rem; }
.crm-prob {
  display: block; flex: 0 0 auto; width: 5rem; height: 0.375rem; overflow: hidden;
  border-radius: 9999px; background: var(--color-border);
}
.crm-prob-relleno { display: block; height: 100%; border-radius: inherit; background: var(--crm-brand-500); }
.crm-prob-texto { font-size: 0.75rem; color: var(--color-muted-foreground); font-variant-numeric: tabular-nums; white-space: nowrap; }

/* Asignado a: todas las personas separadas por comas. Se parten por los espacios (white-space: normal explícito, por si
   la celda heredara un nowrap) y un nombre sin espacios muy largo, donde haga falta: con varias personas la columna no
   se ensancha más de 16rem (en la tabla ancha; en la compacta van en la línea de metadatos, que ya se parte) y el icono
   queda a la altura de la primera línea. Con una sola persona de nombre corto se ve como antes, en una línea. */
.crm-lista-persona { display: inline-flex; align-items: baseline; gap: 0.375rem; white-space: normal; }
.crm-lista-persona > i { flex: 0 0 auto; color: var(--color-muted-foreground); }
.crm-lista-persona > span { min-width: 0; overflow-wrap: anywhere; }
.crm-tabla td.crm-col-meta > .crm-lista-persona { max-width: 16rem; }

/* «Acciones», siempre a la vista: fija al borde derecho de .crm-lista-scroll, la caja que se desplaza más cercana (el
   overflow: hidden de .crm-lista está por encima y no la afecta). Bootstrap pinta el hover (y la cebra, si la hubiera)
   con un box-shadow inset de 9999px que lee --bs-table-bg-state y --bs-table-bg-type: se conserva esa capa y encima va
   la línea piedra de la izquierda. 0,2,0 frente a 0,1,1 de .table>:not(caption)>*>* (Bootstrap). */
.crm-tabla .crm-col-acciones {
  position: sticky; right: 0; z-index: 1;
  box-shadow: inset 1px 0 0 var(--color-border),
    inset 0 0 0 9999px var(--bs-table-bg-state, var(--bs-table-bg-type, var(--bs-table-accent-bg)));
}
/* Fondo opaco bajo esa capa: lo que pasa por debajo al desplazar no se transparenta. La cabecera ya lo tiene (gris
   piedra de .table > thead > tr > th, tokens.css, 0,1,3). 0,2,3 frente a 0,1,1 de Bootstrap. */
.crm-tabla > tbody > tr > td.crm-col-acciones { background-color: var(--color-card); }

/* Acciones de fila: botones fantasma de solo icono. 0,2,0: no empata con el relleno de .btn-sm (0,1,0). */
.crm-tabla .crm-accion-fila { width: 2.25rem; --bs-btn-padding-x: 0; }
.crm-accion-fila > i { color: var(--color-muted-foreground); }
.crm-accion-fila:hover > i, .crm-accion-fila:focus-visible > i { color: var(--color-foreground); }
.crm-accion-fila.crm-accion-fila--eliminar:hover > i,
.crm-accion-fila.crm-accion-fila--eliminar:focus-visible > i { color: var(--color-destructive); }

/* Paginador: el rango a la izquierda; Anterior, la página y Siguiente a la derecha. */
.crm-paginador {
  display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 0.5rem 1rem;
  padding: 0.75rem 1rem; border-top: 1px solid var(--color-border);
}
.crm-paginador-rango { margin: 0; font-size: 0.875rem; color: var(--color-muted-foreground); font-variant-numeric: tabular-nums; }
.crm-paginador-botones { display: flex; flex-wrap: wrap; align-items: center; gap: 0.75rem; }
.crm-paginador-pagina { font-size: 0.875rem; font-variant-numeric: tabular-nums; white-space: nowrap; }
/* En la primera y la última página el botón sigue enfocable (aria-disabled), pero se ve desactivado y no cambia al pasar
   por encima. 0,3,0: por encima de las reglas de .btn y .btn-outline-secondary. */
.crm-paginador .btn[aria-disabled="true"] {
  opacity: 0.5; cursor: not-allowed;
  --bs-btn-hover-bg: var(--bs-btn-bg); --bs-btn-hover-border-color: var(--bs-btn-border-color);
  --bs-btn-active-bg: var(--bs-btn-bg); --bs-btn-active-border-color: var(--bs-btn-border-color);
}

/* Tabla compacta: con la tarjeta por debajo de 80,5rem (1288 px con la letra a 16 px) no caben las 8 columnas (con los
   nombres largos del mock piden 1286 px). Acción, Proceso y Asignado a (crm-col-meta) se ocultan con display: none, que
   también las quita a los lectores de pantalla, y su contenido pasa a la línea de metadatos de la primera celda. Con las
   cabeceras partibles, 0,75rem a cada lado de las celdas, la primera columna de 14rem y la barra de 4rem, la tabla pide
   unos 695 px y cabe en la lista de un portátil de 1366 px (717 px). La etapa se parte por los espacios, como siempre:
   partirla también dentro de las palabras ahorraría 8 px pero cortaría «Producto/servici-o». En rem: el umbral sigue
   a la letra del usuario. */
@container crm-lista (width < 80.5rem) {
  .crm-tabla .crm-col-meta { display: none; }
  .crm-lista-meta { display: flex; }
  /* Un nombre muy largo se parte dentro de su ficha o su pastilla en vez de ensanchar la columna. */
  .crm-lista-meta > .crm-chip, .crm-lista-meta > .crm-pastilla,
  .crm-lista-meta > .crm-lista-persona { white-space: normal; overflow-wrap: anywhere; }
  /* 0,2,3 frente a 0,1,3 de tokens.css (white-space: nowrap y 1rem a cada lado en th y td). */
  .crm-lista .crm-tabla > thead > tr > th { white-space: normal; }
  .crm-lista .crm-tabla > thead > tr > th,
  .crm-lista .crm-tabla > tbody > tr > td { padding-left: 0.75rem; padding-right: 0.75rem; }
  .crm-lista-oportunidad { min-width: 14rem; }
  .crm-prob { width: 4rem; }
}
/* Segundo escalón: con la tarjeta por debajo de 43,5rem (696 px) tampoco cabe la tabla compacta. Pasa con la ventana
   entre unos 1303 y 1344 px, con el aside al lado y la lista de 656 a 695 px: la tabla pedía 695-703 px y «Acciones»,
   fija, tapaba hasta 36 px de «Importe». Con 0,5rem a cada lado de las celdas, la primera columna de 12rem y la barra
   de 3,5rem, pide unos 630 px (medido en Chrome con 1.250.000,00 € en la página). */
@container crm-lista (width < 43.5rem) {
  .crm-lista .crm-tabla > thead > tr > th,
  .crm-lista .crm-tabla > tbody > tr > td { padding-left: 0.5rem; padding-right: 0.5rem; }
  .crm-lista-oportunidad { min-width: 12rem; }
  .crm-prob { width: 3.5rem; }
}

/* ── 7. Estados de la pantalla: error de carga ──────────────────────────── */
.crm-aviso {
  display: flex; align-items: flex-start; gap: 0.75rem; max-width: 40rem;
  padding: 1rem 1.25rem; background: var(--color-card);
  border: 1px solid var(--color-border); border-radius: var(--radius-lg); box-shadow: var(--shadow-card);
}
.crm-aviso-icono { flex: 0 0 auto; margin-top: 0.125rem; font-size: 1.125rem; color: var(--color-destructive); }
.crm-aviso-titulo { margin: 0; font-weight: 600; }
.crm-aviso-texto { margin: 0.25rem 0 0.75rem; overflow-wrap: anywhere; }

/* ── 8. Diálogo de oportunidad (OportunidadDialog) ──────────────────────── */
/* Leyenda de los obligatorios, sobre el formulario. Los p llevan margen de Bootstrap (p, 0,0,1): estas reglas (0,1,0)
   fijan el suyo. */
.crm-form-leyenda { margin: 0 0 1rem; font-size: 0.8125rem; color: var(--color-muted-foreground); }
/* Una fila por campo: la etiqueta encima en pantallas estrechas; desde 640 px, tres columnas, con la etiqueta en la
   primera y el campo en las otras dos (como el HTML de referencia). Los mensajes van bajo su campo, en su columna. */
.crm-form-fila { display: grid; grid-template-columns: minmax(0, 1fr); gap: 0.375rem 1rem; }
.crm-form-fila + .crm-form-fila { margin-top: 1rem; }
.crm-form-control { min-width: 0; }
.crm-etiqueta { font-size: 0.875rem; font-weight: 500; line-height: 1.25rem; color: var(--color-foreground); }
.crm-obligatorio { margin-left: 0.125rem; }
@media (min-width: 640px) {
  .crm-form-fila { grid-template-columns: repeat(3, minmax(0, 1fr)); align-items: start; }
  /* A la altura del texto del campo (40 px de alto). */
  .crm-form-fila > .crm-etiqueta { padding-top: 0.625rem; }
  .crm-form-fila > .crm-form-control { grid-column: span 2; }
}

/* Los campos son .form-control y .form-select (aspecto de tokens.css); estas reglas solo ajustan lo propio. */
/* Hueco de la flecha (el de Bootstrap), que .form-select de tokens.css (0,1,0) deja en 0.75rem: 0,2,0. */
.form-select.crm-input { padding-right: 2.25rem; }
/* Probabilidad y fecha, valores cortos, sin ocupar toda la fila: 0,2,0 frente al width: 100% de Bootstrap (0,1,0). */
.crm-form .crm-input-corto { width: 11rem; max-width: 100%; }
/* Importe y moneda en una fila: el importe crece y la moneda tiene ancho fijo (la etiqueta oculta de la moneda es
   absolute: no ocupa sitio en la fila). */
.crm-importe { display: flex; gap: 0.5rem; }
.crm-importe > .crm-input:first-child { flex: 1 1 auto; min-width: 0; }
.crm-importe > .crm-moneda { flex: 0 0 7.5rem; }
/* Modo consulta: los campos de texto van en solo lectura (se pueden seleccionar y copiar) con el fondo de los
   desactivados (el de .form-control:disabled y .form-select:disabled de Bootstrap). 0,3,0: por encima de
   .form-control:focus de Bootstrap (0,2,0), que lo devolvería a blanco al enfocarlos. */
.form-control.crm-input[readonly] { background-color: var(--bs-secondary-bg); }

/* Aviso bajo un desplegable sin maestros activos, en el ámbar de los estados (--warning, unos 9:1 sobre blanco). */
.crm-form-aviso {
  display: flex; align-items: baseline; gap: 0.375rem;
  margin: 0.375rem 0 0; font-size: 0.8125rem; color: var(--warning);
}
/* Personas asignadas: desplegable de selección múltiple (SfMultiSelect en modo casillas). Una sola fila: con varias personas el
   campo muestra sus nombres separados por comas y, si no caben, «+N más». Su lista se abre fuera del diálogo. Con errores
   lleva «invalid» (borde rojo, como los demás campos). Syncfusion pinta su borde con «border: … !important» y un selector de
   (0,5,0), que no deja pasar el .invalid de tokens.css: este lo supera (0,6,0). */
.crm-multiselect.e-input-group { min-height: 2.5rem; border-radius: var(--radius-md); }
.crm-multiselect.invalid.e-input-group.e-control-wrapper:not(.e-float-icon-left):not(.e-float-input) {
  border-color: var(--color-destructive) !important;
}
/* Ayuda bajo el desplegable y aviso del máximo. La ayuda, en gris (4,8:1 sobre blanco); el aviso, en tinta. El aviso es una
   región role="status" que está siempre en el DOM y visible (si apareciera con display: none → visible, los lectores de
   pantalla no lo anunciarían): vacío, solo pierde su margen y no mide nada. */
.crm-form-ayuda { margin: 0.375rem 0 0; font-size: 0.8125rem; color: var(--color-muted-foreground); }
.crm-form-ayuda--aviso { display: flex; align-items: baseline; gap: 0.375rem; color: var(--color-foreground); }
.crm-form-ayuda--aviso:empty { margin: 0; }

/* Contador de la nota nueva del seguimiento, en gris (4,8:1 sobre blanco). */
.crm-contador {
  margin: 0.25rem 0 0; font-size: 0.75rem; text-align: right;
  color: var(--color-muted-foreground); font-variant-numeric: tabular-nums;
}

/* Alto fijo: el diálogo mide lo mismo en todas sus pestañas (no «salta» al cambiar de una a otra) y el panel de la
   pestaña ocupa todo lo que dejan la cabecera, las pestañas y el pie. Syncfusion pinta el alto del SfDialog en línea
   (auto): este lleva !important para ganarle. Su max-height, también en línea y calculado sobre la ventana, sigue
   mandando en una ventana muy baja. Con dvh, en el móvil no cuentan las barras del navegador; la primera declaración es
   para los navegadores que no lo entienden. Hasta 640 px de ancho, casi toda la pantalla. */
.e-dialog.crm-dialogo { height: min(85vh, 760px) !important; height: min(85dvh, 760px) !important; }
@media (max-width: 640px) {
  .e-dialog.crm-dialogo { height: calc(100vh - 2rem) !important; height: calc(100dvh - 2rem) !important; }
}
/* Dentro, una columna: panel.css ya hace columnas flex (flex: 1 1 auto y min-height: 0) del contenido del diálogo, del
   form y de .row.material. Las pestañas y el pie miden lo suyo y el panel visible se queda el resto; lo que se desplaza
   es el panel (Datos y Seguimiento), no el contenido del diálogo, así que el pie se ve siempre. El panel deja 4 px de
   aire alrededor para el anillo de foco de los campos (sobresale 4 px y el desplazamiento lo recortaría); el margen
   negativo lo devuelve a la línea del contenido. */
/* .row.material trae de Bootstrap flex-wrap: wrap: en columna y con un alto definido, lo que no cabe en la columna salta a
   otra a su derecha (el panel quedaba fuera del diálogo). Sin salto: una sola columna. */
.crm-dialogo .row.material { flex-wrap: nowrap; }
.crm-dialogo .crm-pestanas,
.crm-dialogo .footer-form { flex: 0 0 auto; }
.crm-dialogo .crm-panel-pestana {
  flex: 1 1 auto; min-height: 0; margin: -4px -4px 0; padding: 4px;
  overflow-y: auto; overscroll-behavior: contain;
}
/* «Eliminar», a la izquierda del pie, con el texto en tinta y el icono en el rojo de error (no es texto: 3,8:1). */
.footer-form .crm-dialogo-eliminar { margin-right: auto; }
.crm-dialogo-eliminar > i { color: var(--color-destructive); }

/* ── 9. Utilidades ──────────────────────────────────────────────────────── */
/* Texto de usuario en una caja estrecha: una palabra muy larga (un título de 150 caracteres sin espacios) se parte donde
   haga falta en vez de salirse de la caja. La llevan el cuerpo de ConfirmDeleteDialog (en él, overflow-wrap valía normal)
   y el texto de los toasts de ToastsCrm. Va en el propio elemento, así que gana a lo que herede: el break-word que
   tailwind3.css da al contenido de los toasts (.e-toast-content) se queda en su word-break. Nadie más fija overflow-wrap
   en esos elementos (ni el panel, ni los tokens, ni Bootstrap, ni Syncfusion). */
.crm-texto-ajustado { overflow-wrap: anywhere; }
/* El texto de un toast puede traer varias líneas (el mensaje de la API y, debajo, cada error de validación): se respetan los
   saltos de línea, que si no se ven pegados en una sola. */
.e-toast-content .crm-texto-ajustado { white-space: pre-line; }

/* ── 10. Vistas Mes y Semana (VistaMes, VistaSemana y TarjetaOportunidad) ── */
/* La tarjeta de la vista es el contenedor de consultas crm-calendario: la rejilla se adapta al ancho de la tarjeta, no al
   de la ventana. A 1366 px la zona principal mide unos 717 px (menú de 240 y aside de 320): siete columnas de unos 100 px,
   donde una tarjeta compacta enseña el icono, unas 10 letras de la empresa (con puntos suspensivos) y la persona. Por
   debajo de 40rem (640 px de contenido con la letra a 16 px) las columnas bajarían de unos 90 px y la empresa de unas 8
   letras: el mes pasa a agenda y la semana apila sus días (consulta al final de la sección). En rem: el umbral sigue a la
   letra del usuario, como las tarjetas.
   Anillo de foco: el de tokens.css (--focus-ring, 2 px blanco y 2 px de marca, en px) sobresale 4 px. Recortan
   esta tarjeta (overflow: hidden) y la lista de tarjetas de cada día (se desplaza): todo lo enfocable queda a 4 px o más
   de sus bordes (el relleno de 4 px de los días y de la lista). Nada de lo enfocable lleva box-shadow propio: pisaría el
   anillo, que es un box-shadow de :focus-visible con la misma especificidad (0,1,0). */
.crm-calendario {
  container-type: inline-size; container-name: crm-calendario;
  overflow: hidden; background: var(--color-card);
  border: 1px solid var(--color-border); border-radius: var(--radius-lg); box-shadow: var(--shadow-card);
}
/* Columnas de la rejilla del mes, de su cabecera y de la semana: --crm-columnas, que VistaMes y VistaSemana ponen inline en
   .crm-calendario (DiasVisibles.Columnas: 7, o 6 y 5 si los parámetros ocultan los sábados y/o los domingos). Sin ella,
   7. El umbral de la agenda (40rem, al final de la sección) no cambia: con menos columnas, cada una es más ancha. */

/* Mes. La cabecera Lun … Dom va con aria-hidden: cada día se anuncia con su nombre completo. Tinta navy sobre gris
   piedra, como la cabecera de la tabla de la Lista (la tinta gris no llega a AA ahí). */
.crm-mes-cabecera {
  display: grid; grid-template-columns: repeat(var(--crm-columnas, 7), minmax(0, 1fr));
  background: var(--color-muted); border-bottom: 1px solid var(--color-border);
}
.crm-mes-cabecera > span {
  padding: 0.5rem 0.25rem; text-align: center;
  font-size: 0.75rem; font-weight: 600; line-height: 1.3; text-transform: uppercase; letter-spacing: 0.025em;
}
/* Las líneas de la rejilla son el fondo piedra que asoma entre los días (1 px). Todas las filas miden lo que la más alta
   (1fr con alto automático), como en el HTML de referencia. */
.crm-mes-dias {
  display: grid; grid-template-columns: repeat(var(--crm-columnas, 7), minmax(0, 1fr)); grid-auto-rows: minmax(6.5rem, 1fr);
  gap: 1px; background: var(--color-border);
}
.crm-dia { display: flex; flex-direction: column; gap: 0.125rem; min-width: 0; padding: 4px; background: var(--color-card); }
.crm-dia--clicable { cursor: pointer; }
/* Con el ratón encima, el gris piedra mezclado a medias con el blanco y ya OPACO (#F8FAFC): translúcido dejaría ver el
   gris de las líneas de la rejilla y se vería más oscuro (#EAEFF5) que en la agenda, donde detrás hay blanco. */
.crm-dia--clicable:not(.crm-dia--hoy):hover { background: color-mix(in srgb, var(--color-muted) 50%, var(--color-card)); }
.crm-dia-cabecera { display: flex; align-items: center; gap: 0.25rem; min-height: 1.5rem; }
.crm-dia-numero {
  display: inline-flex; align-items: center; justify-content: center; min-width: 1.5rem; height: 1.5rem; padding: 0 0.25rem;
  border-radius: 9999px; font-size: 0.75rem; font-weight: 600; line-height: 1; font-variant-numeric: tabular-nums;
}
/* Días de otros meses: el mismo gris opaco del hover (#F8FAFC), número gris y tarjetas al 70 %. Son inertes (atributo
   inert): ni foco, ni clic, ni lectores de pantalla, así que su texto no tendría que llegar a AA (WCAG 1.4.3: parte de un
   componente inactivo); aun así llega, medido sobre lo que se pinta (la opacidad compone tinta y tinte sobre el día): el
   número, 4,55:1; las tarjetas, 5,5:1 o más (el peor proceso, el negro puro). */
.crm-dia--fuera { background: color-mix(in srgb, var(--color-muted) 50%, var(--color-card)); }
.crm-dia--fuera .crm-dia-numero { color: var(--color-muted-foreground); font-weight: 500; }
.crm-dia--fuera .crm-eventos { opacity: 0.7; }
/* Hoy: fondo azul 50 y el número (o la fecha de la agenda) en el azul 600 con texto blanco (4,8:1, AA). Después de las
   reglas de otros meses: hoy puede ser uno de ellos (el 2 de octubre en la rejilla de septiembre) y se sigue resaltando. */
.crm-dia--hoy { background: var(--crm-brand-50); }
.crm-dia--hoy .crm-dia-numero,
.crm-dia--hoy .crm-dia-fecha-valor { background: var(--crm-brand-600); color: #fff; }
/* Encabezado de la agenda («Lun 21 sep»): solo en el contenedor estrecho. */
.crm-dia-fecha { display: none; align-items: baseline; gap: 0.375rem; font-size: 0.875rem; font-weight: 600; line-height: 1.5; }
.crm-dia-fecha-valor { padding: 0 0.5rem; border-radius: 9999px; }

/* «+» del día: un <button> de verdad, con nombre «Agregar oportunidad el dd/mm/aaaa». Invisible hasta que el ratón pasa por
   el día o el foco entra en él (:focus-within), pero siempre en el orden de tabulación: se oculta con opacity, no con
   display ni visibility. En pantallas sin ratón (táctiles), siempre visible. 24 px: el mínimo de WCAG 2.5.8. Gris sobre
   blanco, 4,8:1; sobre el azul 50 de hoy el gris se queda en 4,49:1 (su texto «Agregar» de la agenda no llegaría a AA),
   así que ahí va en el azul 800 (8,4:1). */
.crm-dia-agregar {
  display: inline-flex; align-items: center; justify-content: center; gap: 0.25rem; flex: 0 0 auto;
  min-width: 1.5rem; height: 1.5rem; margin-left: auto; padding: 0;
  border: 1px solid transparent; border-radius: var(--radius-sm); background: transparent;
  color: var(--color-muted-foreground); font-size: 0.75rem; font-weight: 500; line-height: 1;
  opacity: 0; transition: opacity 150ms;
}
.crm-dia--hoy .crm-dia-agregar { color: var(--crm-brand-800); }
.crm-dia:hover .crm-dia-agregar, .crm-dia:focus-within .crm-dia-agregar { opacity: 1; }
/* Después de la de hoy, con la misma especificidad (0,2,0): al pasar el ratón manda esta (azul 700 sobre azul 50, 6,2:1). */
.crm-dia-agregar:hover { border-color: var(--crm-brand-200); background: var(--crm-brand-50); color: var(--crm-brand-700); }
@media (hover: none) { .crm-dia-agregar { opacity: 1; } }
.crm-dia-agregar-texto { display: none; }

/* Tarjetas de un día: se desplazan dentro del día cuando no caben, sin pasar el desplazamiento a la página. 4 px de
   relleno para el anillo de foco; el margen negativo las devuelve a la línea del encabezado. En el mes caben dos tarjetas
   y asoma la tercera. */
.crm-eventos {
  display: flex; flex-direction: column; gap: 0.25rem; min-height: 0;
  margin: 0 -4px; padding: 4px; overflow-y: auto; overscroll-behavior: contain; scrollbar-width: thin;
}
.crm-mes-dias .crm-eventos { max-height: 6.75rem; }
.crm-agenda-vacia {
  display: none; margin: 0; padding: 2rem 1rem; text-align: center; font-weight: 500; color: var(--color-muted-foreground);
}

/* Semana: siete columnas (o las de --crm-columnas), cada una con su encabezado (día y fecha), sus tarjetas detalladas y
   «Añadir» al pie. */
.crm-semana { display: grid; grid-template-columns: repeat(var(--crm-columnas, 7), minmax(0, 1fr)); gap: 1px; background: var(--color-border); }
.crm-semana-dia {
  display: flex; flex-direction: column; gap: 0.375rem; min-width: 0; min-height: 12rem;
  padding: 4px; background: var(--color-card);
}
.crm-semana-dia--hoy { background: var(--crm-brand-50); }
.crm-semana-cabecera {
  display: flex; flex-direction: column; align-items: flex-start; gap: 0.125rem;
  padding: 0.25rem 0.25rem 0.375rem; border-bottom: 1px solid var(--color-border);
}
/* El nombre del día y «Añadir», en gris: 4,8:1 sobre blanco. Sobre el azul 50 de hoy el gris se queda en 4,49:1 y no
   llega a AA: ahí van en el azul 800 (8,4:1). */
.crm-semana-nombre {
  font-size: 0.75rem; font-weight: 600; line-height: 1.3; text-transform: uppercase; letter-spacing: 0.025em;
  color: var(--color-muted-foreground);
}
.crm-semana-fecha { margin-left: -0.375rem; padding: 0 0.375rem; border-radius: 9999px; font-size: 0.875rem; font-weight: 700; line-height: 1.5; }
.crm-semana-dia--hoy .crm-semana-fecha { background: var(--crm-brand-600); color: #fff; }
.crm-semana .crm-eventos { flex: 0 1 auto; max-height: 26rem; }
/* «Añadir»: botón secundario discontinuo, al pie del día (margin-top: auto), alineado en las siete columnas. */
.crm-semana-anadir {
  display: flex; align-items: center; justify-content: center; gap: 0.375rem; width: 100%; min-height: 2rem;
  margin-top: auto; padding: 0.25rem 0.5rem;
  border: 1px dashed var(--color-input); border-radius: var(--radius-md); background: transparent;
  color: var(--color-muted-foreground); font-size: 0.75rem; font-weight: 500; line-height: 1.3;
}
.crm-semana-dia--hoy .crm-semana-nombre, .crm-semana-dia--hoy .crm-semana-anadir { color: var(--crm-brand-800); }
/* Después de la de hoy, con la misma especificidad (0,2,0): al pasar el ratón manda esta (azul 700 sobre azul 50, 6,2:1). */
.crm-semana-anadir:hover { border-color: var(--crm-brand-500); background: var(--crm-brand-50); color: var(--crm-brand-700); }

/* Tarjeta de oportunidad: fondo y borde con el color del proceso (--proc, ya saneado), como la pastilla de la Lista
   (tinte del 12 % y borde del 40 % oscurecido un 20 % hacia la tinta: un proceso blanco sigue viéndose). Texto en tinta
   navy: 13,6:1 o más sobre el tinte sea cual sea el color (el peor, el negro puro), y 11:1 en hover (tinte del 20 %). Una
   línea por dato, recortada con puntos suspensivos: el texto completo está en el title. */
.crm-evento {
  display: flex; flex-direction: column; gap: 0.0625rem; flex: 0 0 auto; min-width: 0;
  padding: 0.25rem 0.375rem; border-radius: var(--radius-md);
  border: 1px solid color-mix(in srgb, color-mix(in srgb, var(--proc) 40%, white) 80%, var(--color-foreground));
  background: color-mix(in srgb, var(--proc) 12%, white);
  color: var(--color-foreground); font-size: 0.6875rem; line-height: 1.3; cursor: pointer; scroll-margin: 4px;
}
.crm-evento:hover { background: color-mix(in srgb, var(--proc) 20%, white); }
.crm-evento-linea { display: flex; align-items: center; gap: 0.25rem; min-width: 0; }
.crm-evento-linea > i { flex: 0 0 auto; font-size: 0.625rem; }
.crm-evento-texto { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.crm-evento-empresa { font-weight: 600; }
/* «+N» tras la primera persona (TarjetaOportunidad): en la misma línea y sin recortarse nunca (si no cabe todo, se recorta
   el nombre); la tarjeta no crece en alto. Las demás personas están en el title y el nombre accesible. */
.crm-evento-mas { flex: 0 0 auto; font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }
/* Semana: importe y probabilidad bajo una línea fina; si no caben juntos, la probabilidad baja de línea. El importe no se
   recorta nunca: la moneda tiene que verse siempre («45.000,00 …» se confundiría entre € y US$). Entre la cifra y la moneda
   va un espacio normal (CalendarioVistas.ImporteDeTarjeta), así que si no caben en una línea la moneda baja a la siguiente
   («125.000,00» y debajo «US$»). Solo si la cifra sola no cabe se parte (overflow-wrap: anywhere, el último recurso): con
   la tarjeta de 1366 px quedan unos 75 px y caben enteras hasta las de «1.250.000,00» (72 px); con el contenedor mínimo
   de 40rem (64,6 px), o en un día cuya lista se desplaza (su barra quita 10 px), esa se parte. */
.crm-evento--detallada { padding: 0.375rem 0.5rem; font-size: 0.75rem; }
.crm-evento-datos {
  display: flex; flex-wrap: wrap; align-items: baseline; justify-content: space-between; gap: 0 0.375rem;
  margin-top: 0.125rem; padding-top: 0.125rem; border-top: 1px solid color-mix(in srgb, var(--proc) 25%, white);
}
.crm-evento-importe {
  min-width: 0; font-weight: 700; font-variant-numeric: tabular-nums; white-space: normal; overflow-wrap: anywhere;
}
.crm-evento-prob { font-variant-numeric: tabular-nums; white-space: nowrap; }

/* Contenedor estrecho (menos de 40rem): el mes pasa a una agenda y la semana apila sus días. La agenda es el MISMO
   marcado: se ocultan (display: none, que también los quita a los lectores de pantalla) la cabecera Lun … Dom y los días
   sin crm-dia--agenda (los de otros meses y los que no tienen oportunidades salvo hoy); el número deja paso a «Lun 21
   sep» y el «+» se ve siempre, con su texto «Agregar». Cada tarjeta y cada botón siguen una sola vez en el DOM. El
   margen de -1 px esconde bajo el borde de la tarjeta la línea superior del primer día. */
@container crm-calendario (width < 40rem) {
  .crm-mes-cabecera { display: none; }
  .crm-mes-dias { grid-template-columns: minmax(0, 1fr); grid-auto-rows: auto; gap: 0; margin-top: -1px; background: none; }
  .crm-dia { gap: 0.375rem; padding: 0.625rem 0.75rem 0.75rem; border-top: 1px solid var(--color-border); }
  .crm-dia:not(.crm-dia--agenda) { display: none; }
  .crm-dia-numero { display: none; }
  .crm-dia-fecha { display: inline-flex; }
  .crm-dia-agregar { opacity: 1; height: 2rem; padding: 0 0.625rem; border-color: var(--color-input); }
  .crm-dia-agregar-texto { display: inline; }
  .crm-mes-dias .crm-eventos { max-height: none; overflow: visible; }
  .crm-mes-dias .crm-evento { padding: 0.375rem 0.5rem; font-size: 0.75rem; }
  .crm-agenda-vacia { display: block; }

  .crm-semana { grid-template-columns: minmax(0, 1fr); }
  .crm-semana-dia { min-height: 0; padding: 0.625rem 0.75rem 0.75rem; }
  .crm-semana-cabecera { flex-direction: row; align-items: baseline; gap: 0.5rem; }
  .crm-semana .crm-eventos { max-height: none; overflow: visible; }
}

/* ── 11. Arrastrar y soltar (crm-dnd.js, VistaMes, VistaSemana y TarjetaOportunidad) ── */
/* Mientras se arrastra una tarjeta, crm-dnd.js pone crm-arrastrando en su .crm-calendario y data-crm-arrastrada en la
   tarjeta, fuera de Blazor y un instante DESPUÉS del dragstart (Chrome cancela el arrastre si, en el propio dragstart, la
   tarjeta deja de recibir el puntero), y los quita en dragend, drop y pagehide. Mientras tanto:
   - Nada de lo que hay dentro de un día recibe el puntero (tarjetas, «+», «Añadir», encabezados): los dragenter y dragleave
     salen solo de los propios días, sin parpadeos al pasar por encima de su contenido. Los días de otros meses son inertes
     y tampoco lo reciben: no se resaltan ni admiten la tarjeta.
   - El día bajo el cursor (crm-dia--sobre, crm-semana-dia--sobre: EstadoArrastre.FechaSobre) lleva un borde discontinuo de
     2 px en el azul 600 y el fondo azul 50: no solo color (WCAG 1.4.1). El borde es un outline hacia dentro, a 1 px del
     borde del día y dentro de su relleno (4 px en la rejilla): no mueve nada y no lo recorta ni el overflow de la tarjeta
     del calendario ni el margen de -1 px de la agenda, que esconde bajo el borde de la tarjeta el primer píxel del primer
     día. Igual en el mes, en la semana y en la agenda (el mismo marcado). Solo con crm-arrastrando: si un dragend no
     llegara a .NET, el resaltado no se queda a la vista.
     0,3,0: por encima del hover de los días (.crm-dia--clicable:not(.crm-dia--hoy):hover, también 0,3,0, pero antes) y del
     fondo de hoy.
   - Sobre el azul 50, el gris del «+» («Agregar» en la agenda), del nombre del día y de «Añadir» se queda en 4,49:1 y no
     llega a AA: ahí van en el azul 800 (8,4:1), como en el día de hoy.
   - La tarjeta que se arrastra, al 70 %, como las de otros meses (su texto sigue por encima de 4,5:1).
   Sin transiciones: el resaltado aparece y desaparece al instante, también con prefers-reduced-motion. */
.crm-arrastrando .crm-dia *,
.crm-arrastrando .crm-semana-dia * { pointer-events: none; }
.crm-arrastrando .crm-dia.crm-dia--sobre,
.crm-arrastrando .crm-semana-dia.crm-semana-dia--sobre {
  outline: 2px dashed var(--crm-brand-600); outline-offset: -3px; background: var(--crm-brand-50);
}
.crm-arrastrando .crm-dia--sobre .crm-dia-agregar,
.crm-arrastrando .crm-semana-dia--sobre .crm-semana-nombre,
.crm-arrastrando .crm-semana-dia--sobre .crm-semana-anadir { color: var(--crm-brand-800); }
.crm-arrastrando .crm-evento[data-crm-arrastrada] { opacity: 0.7; }

/* ── 12. Pestañas del diálogo, notas y seguimiento (OportunidadDialog, NotasOportunidad y SeguimientoOportunidad) ── */
/* Pestañas Datos, Notas y «Seguimiento (N)»: botones nativos con role="tab" (sin .btn ni .e-btn: ninguna otra regla los
   toca). La elegida, con el texto en el azul 700 (6,2:1 sobre blanco y sobre el azul 50), en negrita y con una barra de
   3 px en el azul 600: no solo el color la distingue (WCAG 1.4.1). Las demás, en gris (4,8:1 sobre blanco). La barra tapa
   el borde inferior de la lista (margin-bottom: -1px). El panel que no se ve lleva el atributo hidden (display: none
   !important de Bootstrap), que gana al display: flex del panel de Notas. */
.crm-pestanas {
  display: flex; gap: 0.25rem; margin: 0 0 1rem;
  border-bottom: 1px solid var(--color-border);
}
.crm-pestana {
  margin: 0 0 -1px; padding: 0.5rem 0.75rem;
  border: 0; border-bottom: 3px solid transparent; border-radius: var(--radius-sm) var(--radius-sm) 0 0;
  background: none; color: var(--color-muted-foreground);
  font-size: 0.875rem; font-weight: 500; line-height: 1.25rem; white-space: nowrap; cursor: pointer;
}
.crm-pestana:hover { color: var(--color-foreground); background: var(--crm-brand-50); }
/* Después del hover y con su misma especificidad (0,2,0): la elegida conserva su color al pasar el ratón. */
.crm-pestana[aria-selected="true"] { color: var(--crm-brand-700); border-bottom-color: var(--crm-brand-600); font-weight: 600; }
/* Anillo de foco en el azul 500 (no es texto: 3:1 frente al blanco), hacia dentro: no lo recorta el desplazamiento del
   contenido del diálogo. El panel de Seguimiento es enfocable (tabindex="0") y lleva el mismo anillo. */
.crm-pestana:focus-visible,
.crm-panel-pestana:focus-visible { outline: 2px solid var(--crm-brand-500); outline-offset: -2px; }
/* Pestaña con errores de validación (su texto oculto, «, con errores», va en su nombre accesible): un icono de aviso en el
   rojo de error (no es texto: 3,8:1 sobre blanco, más de los 3:1 de WCAG 1.4.11), que se ve también en la elegida. */
.crm-pestana-error { margin-left: 0.375rem; color: var(--color-destructive); }

/* Notas: el editor (SfRichTextEditor) llena el panel. El panel y .crm-notas son columnas flex; el editor crece desde 0
   (flex-basis 0, un alto definido para el 100 % de dentro) y no baja de 10rem (en una ventana muy baja, el panel se
   desplaza). Dentro, Syncfusion ya hace una columna (.e-rte-container, alto 100 %) con la barra arriba y el área
   (.e-rte-content) creciendo; el área editable (.e-content, que es la que se desplaza) mide el 100 % de esta. */
.crm-dialogo .crm-panel-pestana--notas { display: flex; flex-direction: column; }
.crm-notas { display: flex; flex-direction: column; flex: 1 1 auto; min-height: 0; }
.crm-notas .e-richtexteditor.crm-notas-editor { flex: 1 1 0; min-height: 10rem; }
.crm-notas .e-rte-content { flex: 1 1 0; min-height: 0; }
/* Tamaño de fuente: como en el resto de la barra, un icono («Aa» y el desplegable) en vez del texto «Tamaño de fuente» (o el
   tamaño elegido, «18pt»). El texto sigue en el DOM con font-size 0, así que el botón conserva su nombre accesible. El
   envoltorio trae un ancho en línea (60 px): se anula. */
.crm-notas .e-font-size-tbar-btn .e-rte-dropdown-btn-text-wrapper { width: auto !important; }
.crm-notas .e-font-size-tbar-btn .e-rte-dropdown-btn-text { font-size: 0; }
.crm-notas .e-font-size-tbar-btn .e-rte-dropdown-btn-text::before { content: "Aa"; font-size: 0.9375rem; line-height: 1; }
/* Borde y esquinas de los campos del formulario (el borde del editor está en .e-rte-container). Con el foco en el área
   editable, el anillo del panel alrededor de todo el editor: el suyo (:focus-visible de tokens.css) quedaría recortado
   por el área que se desplaza. En la barra, cada botón lleva el suyo. */
.crm-notas .e-rte-container { border-color: var(--color-input); border-radius: var(--radius-md); overflow: hidden; }
.crm-notas .e-rte-content .e-content:focus-visible { box-shadow: none; }
.crm-notas .e-rte-container:has(.e-rte-content .e-content:focus) { box-shadow: var(--focus-ring); }
/* Con errores, el borde rojo de los campos con «invalid». 0,3,0 frente a 0,2,0 de la regla anterior. */
.crm-notas .crm-notas-editor--error .e-rte-container { border-color: var(--color-destructive); }
/* Modo consulta: el fondo de los campos de solo lectura (.form-control.crm-input[readonly], sección 8). */
.crm-notas .crm-notas-editor--lectura .e-rte-content { background-color: var(--bs-secondary-bg); }
.crm-notas .crm-form-mensajes:not(:empty) { margin-top: 0.375rem; }

/* Seguimiento: estados (cargando, sin actividad y error), línea de tiempo y nota nueva, uno debajo de otro. Los p llevan
   margen de Bootstrap (p, 0,0,1): estas reglas (0,1,0) fijan el suyo. */
.crm-seg { display: flex; flex-direction: column; gap: 1rem; min-width: 0; }
.crm-seg-estado { margin: 0; font-size: 0.875rem; color: var(--color-muted-foreground); }
/* Error de carga: el mismo contenido que .crm-aviso (icono, título, texto y «Reintentar»), sin sombra ni ancho máximo. */
.crm-seg-error {
  display: flex; align-items: flex-start; gap: 0.75rem; min-width: 0;
  padding: 0.75rem 1rem; border: 1px solid var(--color-border); border-radius: var(--radius-lg);
}
/* Línea de tiempo: el icono en un círculo azul 50 (el icono, en el azul 700) y una línea que une los círculos. */
.crm-seg-lista { margin: 0; padding: 0; list-style: none; }
.crm-seg-entrada { position: relative; display: grid; grid-template-columns: 2rem minmax(0, 1fr); gap: 0 0.75rem; padding-bottom: 1rem; }
.crm-seg-entrada:last-child { padding-bottom: 0; }
.crm-seg-entrada:not(:last-child)::before {
  content: ""; position: absolute; top: 2rem; bottom: 0; left: calc(1rem - 1px);
  width: 2px; background: var(--color-border);
}
.crm-seg-icono {
  display: inline-flex; align-items: center; justify-content: center; width: 2rem; height: 2rem;
  border-radius: 9999px; background: var(--crm-brand-50); color: var(--crm-brand-700); font-size: 0.875rem;
}
/* El texto de cada entrada se parte dentro de su columna (crm-texto-ajustado en el título, los cambios y la nota): una
   empresa de 150 caracteres, una nota de 2000 sin espacios o una URL larga nunca ensanchan el diálogo. */
.crm-seg-cuerpo { min-width: 0; padding-top: 0.25rem; }
/* Título y fecha: en la misma línea si caben; si no, la fecha baja entera (sin partirse). */
.crm-seg-cabecera { display: flex; flex-wrap: wrap; align-items: baseline; gap: 0 0.5rem; margin: 0; }
.crm-seg-titulo { min-width: 0; font-weight: 600; }
.crm-seg-fecha { font-size: 0.8125rem; color: var(--color-muted-foreground); font-variant-numeric: tabular-nums; white-space: nowrap; }
/* Cambios «Campo: antes → después». Un importe lleva un espacio normal antes de la moneda (SeguimientoVista): si no cabe,
   la moneda baja de línea en vez de recortarse. */
.crm-seg-cambios { margin: 0.25rem 0 0; padding: 0; list-style: none; font-size: 0.875rem; }
.crm-seg-campo { font-weight: 500; }
/* Nota: su texto tal cual, con sus saltos de línea, sobre el gris de los fondos suaves (tinta navy, 15:1 o más). */
.crm-seg-nota-texto {
  margin: 0.375rem 0 0; padding: 0.5rem 0.75rem; border-radius: var(--radius-md);
  background: var(--color-muted); font-size: 0.875rem; white-space: pre-wrap;
}
/* Nueva nota: etiqueta, cuadro, contador, mensaje y «Añadir nota» (a la derecha), separada de la línea de tiempo. */
.crm-seg-nueva { display: flex; flex-direction: column; gap: 0.375rem; padding-top: 1rem; border-top: 1px solid var(--color-border); }
.crm-seg-nueva .crm-contador { margin: 0; }
.crm-seg-nueva-acciones { display: flex; justify-content: flex-end; }

/* ── 13. Interruptor de los formularios (InterruptorCrm) ───────────────── */
/* Casilla nativa (input type="checkbox" role="switch") dibujada como interruptor: pista de 2,25 × 1,25 rem y tirador
   blanco de 0,875rem. Contraste de la pista contra el blanco del diálogo (WCAG 1.4.11 pide 3:1): apagada, la tinta gris
   #64748B, 4,76:1; encendida, el azul 600, 4,84:1; el tirador blanco contrasta lo mismo sobre cada una. Nada del panel ni
   de Bootstrap da estilo a una casilla sin .form-check-input; el :focus-visible general de tokens.css (0,1,0)
   lo fija aquí .crm-interruptor:focus-visible (0,2,0). */
.crm-interruptor {
  appearance: none; -webkit-appearance: none;
  position: relative; flex: 0 0 auto; width: 2.25rem; height: 1.25rem; margin: 0;
  border-radius: 9999px; background-color: var(--color-muted-foreground);
  cursor: pointer; transition: background-color 150ms ease;
}
.crm-interruptor::before {
  content: ""; position: absolute; top: 0.1875rem; left: 0.1875rem; width: 0.875rem; height: 0.875rem;
  border-radius: 9999px; background-color: #fff; box-shadow: 0 1px 2px rgb(15 23 42 / 0.3);
  transition: transform 150ms ease;
}
.crm-interruptor:checked { background-color: var(--crm-brand-600); }
.crm-interruptor:checked::before { transform: translateX(1rem); }
/* Foco con el teclado: el anillo del panel (2 px blanco y 2 px del azul 500, --focus-ring). */
.crm-interruptor:focus-visible { outline: 2px solid transparent; box-shadow: var(--focus-ring); }
.crm-interruptor:disabled,
.crm-interruptor:disabled + .crm-interruptor-texto { opacity: 0.5; cursor: not-allowed; }
/* El texto es su <label>: pulsarlo cambia el interruptor. */
.crm-interruptor-texto { margin: 0; cursor: pointer; }
/* Con contraste forzado (Windows) el fondo desaparece: borde y tirador en los colores del sistema. */
@media (forced-colors: active) {
  .crm-interruptor { border: 1px solid CanvasText; }
  .crm-interruptor::before { background-color: CanvasText; }
}
@media (prefers-reduced-motion: reduce) {
  .crm-interruptor, .crm-interruptor::before { transition: none; }
}

/* ── 14. Parámetros (aviso del calendario y página Parámetros) ─────────── */
/* Aviso sobre el calendario cuando hay oportunidades en sábados o domingos ocultos. Es una región role="status" que está
   siempre en el DOM (también en Lista, vacía): si apareciera de golpe, los lectores de pantalla no la anunciarían. Vacía
   no mide nada; con aviso (crm-ocultas--visible), una franja informativa: fondo azul 50 y borde azul 200, texto en tinta
   navy (15:1 o más) y el icono y el enlace a Parámetros (solo Admin) en el azul 700 (6,2:1 sobre el azul 50). El enlace
   va subrayado: no solo el color lo distingue del texto (WCAG 1.4.1). */
.crm-ocultas--visible {
  display: flex; align-items: baseline; gap: 0.5rem;
  margin-bottom: 1rem; padding: 0.625rem 0.875rem;
  border: 1px solid var(--crm-brand-200); border-radius: var(--radius-lg); background: var(--crm-brand-50);
  font-size: 0.875rem; line-height: 1.5;
}
.crm-ocultas-icono { flex: 0 0 auto; color: var(--crm-brand-700); }
.crm-ocultas-texto { margin: 0; min-width: 0; overflow-wrap: anywhere; }
/* «Configuración › Parámetros»: azul 700 y subrayado; al pasar el ratón, azul 800. El anillo de foco es el de tokens.css. */
.crm-ocultas a { color: var(--crm-brand-700); text-decoration: underline; text-underline-offset: 0.15em; }
.crm-ocultas a:hover { color: var(--crm-brand-800); }

/* Página Parámetros: una tarjeta por sección (crm-panel, con su título de etiqueta) con el ancho de un formulario, como
   Datos de empresa. Cada parámetro es un InterruptorCrm (su .form-group): entre uno y otro, una línea fina. */
.crm-parametros { display: grid; gap: 1rem; max-width: 40rem; }
.crm-parametros .form-group { margin: 0; }
.crm-parametros .form-group + .form-group { margin-top: 0.875rem; padding-top: 0.875rem; border-top: 1px solid var(--color-border); }
/* Tarjeta «Simulador de pavimentos»: la API Key (etiqueta, estado, campo con el botón de mostrar a su derecha, ayuda y,
   abajo a la derecha, Quitar y Guardar). El campo se encoge y el botón no: en 320 px caben los dos. */
.crm-apikey { display: grid; gap: 0.5rem; }
.crm-apikey-estado {
  display: flex; align-items: baseline; gap: 0.375rem; margin: 0;
  font-size: 0.875rem; color: var(--color-muted-foreground); overflow-wrap: anywhere;
}
.crm-apikey-estado .crm-apikey-estado--ok { color: var(--crm-brand-700); }
.crm-apikey-campo { display: flex; gap: 0.5rem; align-items: stretch; }
.crm-apikey-campo > .crm-input { flex: 1 1 auto; min-width: 0; }
.crm-apikey-ojo { flex: 0 0 auto; }
.crm-apikey .crm-form-ayuda { margin: 0; }
.crm-apikey-acciones { display: flex; flex-wrap: wrap; justify-content: flex-end; gap: 0.5rem; }
/* Debajo, la URL del modelo: separada de la API Key con la misma línea fina que hay entre los interruptores del
   calendario. La URL en uso, completa y seleccionable, se parte donde haga falta para no salirse en 320 px. */
.crm-urlmodelo { display: grid; gap: 0.5rem; }
.crm-apikey + .crm-urlmodelo { margin-top: 0.875rem; padding-top: 0.875rem; border-top: 1px solid var(--color-border); }
.crm-urlmodelo .crm-form-ayuda { margin: 0; }
.crm-urlmodelo-actual {
  display: block; font-size: 0.8125rem; color: var(--color-foreground); overflow-wrap: anywhere; user-select: text;
}
/* Arriba del todo (cambio 2026-10-15), la cuenta de servicio de Google: etiqueta, estado, ayuda y, abajo a la derecha,
   Quitar y «Subir fichero .json» (la acción primaria de la tarjeta: una <label class="btn btn-primary"> con el InputFile
   oculto a la vista dentro; como no es ella la que recibe el foco, el anillo sale con :focus-within). La API Key queda
   debajo con la misma línea fina. Las notas «No se usa…» y «Ajustada…» llevan un icono de información. */
.crm-cuentaservicio { display: grid; gap: 0.5rem; }
.crm-cuentaservicio .crm-form-ayuda { margin: 0; }
.crm-cuentaservicio .crm-etiqueta { margin: 0; }
.crm-cuentaservicio + .crm-apikey { margin-top: 0.875rem; padding-top: 0.875rem; border-top: 1px solid var(--color-border); }
.crm-cuentaservicio-subir { position: relative; margin: 0; }
.crm-cuentaservicio-subir > i { margin-right: 0.375rem; }
.crm-cuentaservicio-subir:focus-within { box-shadow: var(--focus-ring); }
.crm-simulador-nota { display: flex; align-items: baseline; gap: 0.375rem; }
.crm-simulador-nota > i { color: var(--crm-brand-700); flex: 0 0 auto; }
/* Sección «Borrado de objetos (simulador)» (cambio 2026-10-15 (3)): proveedor, token y versión de Replicate, cada uno con
   las piezas de la API Key (.crm-apikey), separados por la misma línea fina; debajo, la nota y las acciones. */
.crm-borrado { display: grid; gap: 0.875rem; }
.crm-borrado .crm-apikey + .crm-apikey { padding-top: 0.875rem; border-top: 1px solid var(--color-border); }
.crm-borrado .crm-simulador-nota { margin: 0; }

/* ── 15. Cuentas de correo (FormCuentaCorreo y DialogoPruebaCorreo) ────── */
/* La misma disposición la usa el formulario de Maestros → Hitos de obra (FormHitoObra, clase crm-dialogo-hito). */
/* El formulario de una cuenta es más alto que muchas ventanas. Como en el diálogo de oportunidad (sección 8): una sola
   columna (sin el flex-wrap: wrap de .row.material, que con el alto limitado mandaba los interruptores a una segunda
   columna fuera del diálogo); los campos se desplazan dentro de su caja y el pie (Cancelar, Guardar) se ve siempre. La
   caja deja 4 px de aire para el anillo de foco de los campos y el margen negativo la devuelve a la línea del contenido. */
.crm-dialogo-cuenta .row.material,
.crm-dialogo-hito .row.material { flex-wrap: nowrap; }
.crm-dialogo-cuenta .footer-form,
.crm-dialogo-hito .footer-form { flex: 0 0 auto; }
.crm-dialogo-cuenta .crm-dialogo-campos,
.crm-dialogo-hito .crm-dialogo-campos {
  flex: 1 1 auto; min-height: 0; margin: -4px -4px 0; padding: 4px;
  overflow-y: auto; overscroll-behavior: contain;
}

/* Resultado de la prueba de envío, dentro del diálogo: .alert-success (verde) o .alert-danger (rojo) de tokens.css. El
   motivo de un fallo puede traer varias líneas (el mensaje de la API y, debajo, cada error de validación): se respetan los
   saltos de línea, como en los toasts (sección 9). */
.crm-prueba-resultado .alert { white-space: pre-line; }

/* ── 16. Simulador epoxi fuera de su pantalla (OportunidadDialog y FormColorAldecort) ── */
/* «Simulaciones (N)» junto al título del diálogo de oportunidad. panel.css pinta todo lo de la cabecera
   (.e-dialog .e-dlg-header *, 0,2,0) como el título: esta regla (0,2,0, cargada después) lo devuelve a tamaño de texto y
   color de enlace de la marca. Sin icono: esa misma regla le cambiaría la fuente. */
.crm-dialogo .crm-dialogo-simulaciones {
  margin-left: 0.75rem; font-size: 0.875rem; font-weight: 500;
  color: var(--crm-brand-700); text-decoration: none; white-space: nowrap;
}
.crm-dialogo .crm-dialogo-simulaciones:hover { color: var(--crm-brand-800); text-decoration: underline; }
.crm-dialogo .crm-dialogo-simulaciones:focus-visible {
  outline: 2px solid var(--crm-brand-500); outline-offset: 2px; border-radius: var(--radius-sm);
}

/* Vista previa del color en el formulario de Colores Aldecort: la muestra de la sección 1, más grande (0,1,0, después). */
.crm-muestra-grande { width: 3rem; height: 3rem; border-radius: var(--radius-md); }

/* ── 17. Empresas y Contactos (Pages/Clientes, EmpresaDialog, ContactoDialog y sus grupos) ── */
/* Listas: la tarjeta, la tabla, el paginador y «Acciones» fija son los de la vista Lista (sección 6). El nombre es un
   botón que abre la ficha (Enter con el teclado); parece texto en negrita y se subraya al pasar el ratón. */
.crm-cli-celda-nombre { display: flex; flex-direction: column; gap: 0.125rem; min-width: 12rem; max-width: 26rem; }
.crm-cli-nombre {
  padding: 0; border: 0; background: none; text-align: left;
  font-weight: 600; color: var(--color-foreground); overflow-wrap: anywhere; cursor: pointer;
}
.crm-cli-nombre:hover { color: var(--crm-brand-700); text-decoration: underline; }
.crm-cli-nombre:focus-visible { outline: 2px solid var(--crm-brand-500); outline-offset: 2px; border-radius: var(--radius-sm); }
/* Enlace del sitio web: azul 700 (6,2:1 sobre blanco), partible. */
.crm-cli-web a { color: var(--crm-brand-700); overflow-wrap: anywhere; }
.crm-cli-web a:hover { color: var(--crm-brand-800); }
/* Línea de datos bajo el nombre: solo en la tarjeta estrecha, cuando se ocultan sus columnas (gris, 4,8:1 sobre blanco). */
.crm-cli-meta {
  display: none; flex-wrap: wrap; align-items: baseline; gap: 0.125rem 0.75rem;
  font-size: 0.8125rem; color: var(--color-muted-foreground);
}
.crm-cli-meta > span { min-width: 0; overflow-wrap: anywhere; }
/* Siete columnas caben desde unos 60rem de tarjeta (un portátil con el menú abierto); por debajo quedan el nombre, el
   número de contactos (en Empresas) y «Acciones», con el resto en la línea de datos. En rem: el umbral sigue a la letra
   del usuario. */
@container crm-lista (width < 60rem) {
  .crm-cli-tabla .crm-cli-col-meta { display: none; }
  .crm-cli-meta { display: flex; }
}

/* Formularios: un diálogo de alto fijo (el de la oportunidad, crm-dialogo, sección 8) en el que se desplazan los campos y
   el pie se ve siempre. La caja deja 4 px de aire para el anillo de foco; el margen negativo la devuelve a su sitio. */
.crm-cli-dialogo .crm-cli-campos {
  flex: 1 1 auto; min-height: 0; margin: -4px -4px 0; padding: 4px;
  overflow-y: auto; overscroll-behavior: contain;
}
/* Tarjeta «Información básica» (como la de la pantalla de referencia): título y filas etiqueta | campo. */
.crm-cli-tarjeta {
  padding: 1rem; background: var(--color-card);
  border: 1px solid var(--color-border); border-radius: var(--radius-lg);
}
.crm-cli-tarjeta-titulo { margin: 0 0 0.75rem; font-size: 1rem; font-weight: 600; line-height: 1.3; color: var(--color-foreground); }

/* Grupos repetibles: un fieldset con la misma rejilla que .crm-form-fila (sección 8). Su legend va flotada (Bootstrap ya
   lo hace): así no se pinta sobre el borde, es un elemento más de la rejilla, a la izquierda como las etiquetas, y sigue
   dando nombre al grupo. */
.crm-cli-grupo {
  display: grid; grid-template-columns: minmax(0, 1fr); gap: 0.375rem 1rem;
  min-inline-size: 0; margin: 0; padding: 0; border: 0;
}
.crm-form-fila + .crm-cli-grupo, .crm-cli-grupo + .crm-form-fila, .crm-cli-grupo + .crm-cli-grupo { margin-top: 1rem; }
.crm-cli-grupo > legend { float: left; width: auto; margin: 0; padding: 0; }
@media (min-width: 640px) {
  .crm-cli-grupo { grid-template-columns: repeat(3, minmax(0, 1fr)); align-items: start; }
  .crm-cli-grupo > legend { padding-top: 0.625rem; }
  .crm-cli-grupo > .crm-form-control { grid-column: span 2; }
  /* «Sin teléfonos» y la lista de contactos en consulta, a la altura de la etiqueta. */
  .crm-cli-vacio, .crm-cli-contactos { padding-top: 0.625rem; }
}
.crm-cli-vacio { margin: 0; font-size: 0.875rem; color: var(--color-muted-foreground); }

/* Fila de teléfono o correo: los campos en una línea que se parte si no cabe (en el móvil, «Principal» y «Quitar» bajan). */
.crm-cli-fila + .crm-cli-fila { margin-top: 0.5rem; }
.crm-cli-fila-campos { display: flex; flex-wrap: wrap; align-items: center; gap: 0.5rem; }
.crm-cli-fila-campos > .crm-cli-pais { flex: 0 0 7.5rem; }
.crm-cli-fila-campos > .crm-cli-numero,
.crm-cli-fila-campos > .crm-cli-correo { flex: 1 1 9rem; min-width: 0; }
/* «Principal»: radio nativo con su texto como etiqueta (pulsar el texto lo marca). */
.crm-cli-principal {
  display: inline-flex; align-items: center; gap: 0.375rem; margin: 0;
  font-size: 0.875rem; white-space: nowrap; cursor: pointer;
}
.crm-cli-principal > input { width: 1rem; height: 1rem; margin: 0; accent-color: var(--crm-brand-600); cursor: pointer; }
.crm-cli-principal > input:disabled { cursor: default; }
/* «Quitar» de solo icono, cuadrado; el icono en gris y, al pasar o con el foco, en el rojo de error (no es texto). */
.btn.crm-cli-quitar { width: 2.25rem; --bs-btn-padding-x: 0; }
.crm-cli-quitar > i { color: var(--color-muted-foreground); }
.crm-cli-quitar:hover > i, .crm-cli-quitar:focus-visible > i { color: var(--color-destructive); }
.crm-cli-anadir { margin-top: 0.5rem; }
.crm-cli-anadir > i { color: var(--color-primary); }

/* Direcciones: filas plegables con borde. La cabecera es el botón de plegar (flecha, «Dirección N» y un resumen gris
   que se corta con puntos suspensivos), el radio y «Quitar». */
.crm-cli-dir { border: 1px solid var(--color-border); border-radius: var(--radius-md); background: var(--color-card); }
.crm-cli-dir + .crm-cli-dir { margin-top: 0.5rem; }
.crm-cli-dir-cabecera { display: flex; align-items: center; gap: 0.5rem; padding: 0.25rem 0.375rem 0.25rem 0.25rem; }
.crm-cli-dir-plegar {
  flex: 1 1 auto; min-width: 0; display: flex; align-items: center; gap: 0.5rem; min-height: 2.25rem;
  padding: 0.25rem 0.5rem; border: 0; border-radius: var(--radius-sm); background: transparent;
  text-align: left; font-size: 0.875rem; color: var(--color-foreground);
}
.crm-cli-dir-plegar:hover { background: var(--color-muted); }
/* Anillo hacia dentro: la caja que se desplaza no lo recorta. */
.crm-cli-dir-plegar:focus-visible { outline: 2px solid var(--crm-brand-500); outline-offset: -2px; }
.crm-cli-dir-flecha { flex: 0 0 auto; font-size: 0.75rem; color: var(--color-muted-foreground); transition: transform 150ms; }
.crm-cli-dir--abierta .crm-cli-dir-flecha { transform: rotate(90deg); }
@media (prefers-reduced-motion: reduce) { .crm-cli-dir-flecha { transition: none; } }
.crm-cli-dir-titulo { flex: 0 0 auto; font-weight: 500; white-space: nowrap; }
.crm-cli-dir-resumen { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; color: var(--color-muted-foreground); }
.crm-cli-dir-error > i { color: var(--color-destructive); }
/* Panel: dos columnas (etiqueta y calle a todo el ancho); una en pantallas estrechas. El atributo hidden no gana a
   display: grid sin esta regla. */
.crm-cli-dir-panel {
  display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0.25rem 0.75rem;
  padding: 0.25rem 0.75rem 0.75rem;
}
.crm-cli-dir-panel[hidden] { display: none; }
.crm-cli-dir-campo { min-width: 0; }
.crm-cli-dir-campo--ancho { grid-column: 1 / -1; }
.crm-cli-dir-etiqueta { display: block; margin-bottom: 0.25rem; font-size: 0.8125rem; font-weight: 500; }
@media (max-width: 479px) {
  .crm-cli-dir-panel { grid-template-columns: minmax(0, 1fr); }
}

/* Contactos de una empresa: avisos de movimiento (región role="status", vacía si no hay) y «Nuevo contacto». */
.crm-cli-avisos ul {
  display: grid; gap: 0.25rem; margin: 0.375rem 0 0; padding: 0; list-style: none;
  font-size: 0.8125rem; color: var(--color-foreground);
}
.crm-cli-avisos li { display: flex; align-items: baseline; gap: 0.375rem; overflow-wrap: anywhere; }
.crm-cli-avisos li > i { flex: 0 0 auto; color: var(--crm-brand-700); }
.crm-cli-nuevo-contacto { margin-top: 0.5rem; }
.crm-cli-nuevo-contacto > i { color: var(--color-primary); }
/* En consulta: la lista de contactos con su cargo, correo y teléfono separados por «·» (decorativo: no se lee). */
.crm-cli-contactos { display: grid; gap: 0.375rem; margin: 0; padding-left: 0; list-style: none; font-size: 0.875rem; }
.crm-cli-contacto-nombre { font-weight: 500; }
.crm-cli-contacto-dato { color: var(--color-muted-foreground); }
.crm-cli-contacto-dato::before { content: " · "; content: " · " / ""; }
/* Empresa de un contacto (SfDropDownList): misma altura y esquinas que los demás campos. */
.crm-cli-desplegable.e-input-group { min-height: 2.5rem; border-radius: var(--radius-md); }

/* ── 18. Menú lateral en grupos desplegables (LeftSidebar y Crm/MenuLateral.cs) ───────────────────────── */
/* Cada grupo es un botón (título, icono y flecha) con su lista debajo. El botón tiene el aspecto de una fila del menú
   (40 px, esquinas y hover de .nav-link, tokens.css) pero con el texto en 600; la lista se sangra con una línea guía. El
   atributo hidden no gana a display: flex de .ag-nav sin la regla [hidden] (0,2,0). */
.ag-grupo + .ag-grupo { margin-top: 0.25rem; }
.ag-grupo-boton {
  display: flex; align-items: center; gap: 0.625rem; width: 100%; min-height: 2.5rem; padding: 0 0.75rem;
  border: 0; border-radius: var(--radius-md); background: transparent; color: var(--color-foreground);
  font: inherit; font-size: 0.875rem; font-weight: 600; text-align: left; cursor: pointer;
}
.ag-grupo-boton:hover { background: hsl(var(--muted) / 0.6); }
.ag-grupo-boton:focus-visible { outline: none; box-shadow: var(--focus-ring); }
.ag-grupo-icono { width: 1rem; text-align: center; font-size: 1rem; color: var(--color-muted-foreground); }
.ag-grupo--activo > .ag-grupo-boton .ag-grupo-icono { color: var(--color-foreground); }
.ag-grupo-titulo { flex: 1 1 auto; min-width: 0; }
.ag-grupo-flecha { font-size: 0.75rem; color: var(--color-muted-foreground); transition: transform 150ms ease; }
.ag-grupo-boton[aria-expanded="true"] .ag-grupo-flecha { transform: rotate(180deg); }
.ag-nav--grupo { margin: 0.125rem 0 0.375rem 1.125rem; padding-left: 0.5rem; border-left: 1px solid var(--color-border); }
.ag-nav--grupo[hidden] { display: none; }
@media (prefers-reduced-motion: reduce) {
  .ag-grupo-flecha { transition: none; }
}
