/* ==========================================================================
   Fruites Jiménez — hoja de estilos
   Concepto: "el mercado a las 5 de la madrugada"
   Tokens y dirección: ver PLAN-IMPLEMENTACION.md
   ========================================================================== */

/* ---------- Tokens ---------- */
:root {
  --paper: #ffffff;
  --paper-tint: #f3f7eb;
  --ink: #1f2a16;
  --ink-soft: #46543a;
  --board: #212e17;
  --board-line: #38492a;
  --naranja: #f08a00;
  --naranja-deep: #b25f00;
  --verde: #85bb3a;
  --verde-deep: #4f7d1b;
  --linea: #dce5ce;

  --font-display: "Bricolage Grotesque", "Arial Black", sans-serif;
  --font-body: "Instrument Sans", "Segoe UI", sans-serif;
  --font-mono: "IBM Plex Mono", "Consolas", monospace;

  --wrap: 1120px;
  --radius: 10px;
  --sombra: 0 12px 32px rgba(31, 42, 22, 0.10);
}

/* ---------- Reset ligero ---------- */
*, *::before, *::after { box-sizing: border-box; }
* { margin: 0; }
/* scroll-padding-top = altura de la cabecera sticky + holgura. Va por tramos porque la
   cabecera no mide lo mismo en todos: 68px a partir de 1121, 112px entre 861 y 1120
   —donde la navegación baja a una segunda fila— y 60px por debajo de 861. Con un solo
   valor de 80px, en el tramo de dos filas el borde de la sección quedaba 32px por
   debajo de la cabecera al pulsar un ancla.
   Los tres valores tienen que quedar POR ENCIMA del umbral del scroll-spy
   (altura de cabecera + 28 en capcalera.js), o al pulsar se marcaría la sección
   anterior. Ver CLAUDE.md §6.5. */
html { scroll-behavior: smooth; scroll-padding-top: 80px; overflow-x: clip; }
@media (max-width: 1120px) and (min-width: 861px) { html { scroll-padding-top: 124px; } }
@media (max-width: 860px) { html { scroll-padding-top: 72px; } }
body {
  font-family: var(--font-body);
  font-size: 1.0625rem;
  line-height: 1.6;
  color: var(--ink);
  background: var(--paper);
  -webkit-font-smoothing: antialiased;
}
img, svg { display: block; max-width: 100%; }
input, button, select, textarea { font: inherit; color: inherit; }
ul { padding: 0; }

/* ---------- Utilidades ---------- */
.wrap { max-width: var(--wrap); margin-inline: auto; padding-inline: clamp(1.1rem, 4vw, 2rem); }
.u-naranja { color: var(--naranja); }
.visually-hidden {
  position: absolute; width: 1px; height: 1px;
  clip-path: inset(50%); overflow: hidden; white-space: nowrap;
}
.skip-link {
  position: absolute; left: 1rem; top: -3.5rem; z-index: 100;
  background: var(--ink); color: var(--paper);
  padding: 0.6rem 1rem; border-radius: 0 0 var(--radius) var(--radius);
  text-decoration: none; transition: top 0.15s ease;
}
.skip-link:focus { top: 0; }

:focus-visible {
  outline: 3px solid var(--naranja);
  outline-offset: 2px;
  border-radius: 2px;
}
/* Destinos del skip-link: reciben el foco por programa para que el siguiente Tab siga
   desde el contenido, pero no son controles. Un anillo naranja rodeando media pantalla
   sería ruido. Los elementos que sí se tabulan llevan tabindex="0" y no entran aquí. */
[tabindex="-1"]:focus, [tabindex="-1"]:focus-visible { outline: none; }

/* ---------- Tipografía ---------- */
/* Los titulares van en cuerpos grandes (el h2 llega a 3rem) y el catalán trae palabras
   largas: «Instal·lacions», «magatzem», «col·lectivitats». En una pantalla de 320px con
   el texto ampliado al 200% ninguna de esas cabe en una línea, y sin poder partirlas
   ensanchaban la maquetación. `break-word` solo rompe cuando no hay más remedio, así que
   al tamaño normal no cambia ni un salto de línea. */
h1, h2, h3, h4 {
  font-family: var(--font-display);
  line-height: 1.05;
  letter-spacing: -0.01em;
  text-wrap: balance;
  overflow-wrap: break-word;
}
h2 { font-size: clamp(1.9rem, 4.2vw, 3rem); font-weight: 800; }
h3 { font-size: 1.25rem; font-weight: 700; line-height: 1.2; }

.eyebrow {
  font-family: var(--font-mono);
  overflow-wrap: break-word;
  font-size: 0.78rem;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--verde-deep);
  margin-bottom: 0.9rem;
}
.eyebrow--board { color: var(--verde); }

.section-sub {
  max-width: 46ch;
  color: var(--ink-soft);
  margin-top: 0.9rem;
}

/* ---------- Botones ---------- */
.btn {
  display: inline-block;
  font-weight: 600;
  text-decoration: none;
  text-align: center;
  border: 2px solid transparent;
  border-radius: 999px;
  padding: 0.62rem 1.35rem;
  cursor: pointer;
  /* con el texto ampliado, «Contacta'ns per a col·lectivitats» no cabe en una línea de
     móvil: que parta la palabra antes que ensanchar la tarjeta y sacar la página de la
     pantalla. `break-word` solo rompe cuando no hay más remedio; `anywhere` partiría
     también donde sí cabe. */
  max-width: 100%;
  overflow-wrap: break-word;
  transition: transform 0.12s ease, background-color 0.15s ease,
              color 0.15s ease, border-color 0.15s ease;
}
.btn:active { transform: scale(0.97); }

.btn-primary {
  background: var(--naranja);
  color: var(--ink);
}
.btn-primary:hover { background: #ffa227; }

.btn-ghost {
  border-color: var(--ink);
  color: var(--ink);
  background: transparent;
}
.btn-ghost:hover { background: var(--ink); color: var(--paper); }

.btn-line {
  border-color: var(--verde-deep);
  color: var(--verde-deep);
  background: transparent;
}
.btn-line:hover { background: var(--verde-deep); color: var(--paper); }

.btn-big { padding: 0.85rem 1.8rem; font-size: 1.05rem; }

/* ---------- Barra de utilidades (nivel 1) ----------
   Servicio, no navegación: estado de la atención telefónica y teléfono. El conmutador
   de idioma que había aquí se retiró el 2026-09-09 (la web es solo en catalán, §5).
   No es sticky — se va con el scroll para que lo que se queda pegado sea solo la
   cabecera. Registro de albarán: monoespaciada sobre tinta. */
.topbar {
  background: var(--ink);
  color: #dfe8d1;
  font-family: var(--font-mono);
  font-size: 0.75rem;
  letter-spacing: 0.02em;
}
.topbar-in {
  display: flex; align-items: center; justify-content: space-between;
  gap: 1rem;
  min-height: 34px;
}
.topbar a { color: inherit; text-decoration: none; }

/* estado de apertura: el punto es el único color de la barra */
.topbar-estat { display: flex; align-items: center; gap: 0.45rem; min-width: 0; }
.topbar-estat[hidden] { display: none; }
.estat-text { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.estat-punt {
  width: 7px; height: 7px; border-radius: 50%;
  background: #9dab88; flex-shrink: 0;
}
.es-obert  .estat-punt { background: var(--verde); box-shadow: 0 0 0 3px rgba(133, 187, 58, 0.22); }
.es-aviat  .estat-punt { background: var(--naranja); }
.es-tancat .estat-punt { background: #9dab88; }

.topbar-eines { display: flex; align-items: center; gap: 1rem; flex-shrink: 0; }

.topbar-tel {
  display: inline-flex; align-items: center; gap: 0.4rem;
  font-weight: 600;
  padding-block: 0.2rem;
  border-bottom: 1px solid transparent;
}
.topbar-tel svg { width: 14px; height: 14px; flex-shrink: 0; }
.topbar-tel:hover { color: var(--paper); border-bottom-color: var(--verde); }

/* ---------- Cabecera (nivel 2, sticky) ---------- */
.header {
  position: sticky; top: 0; z-index: 50;
  background: rgba(255, 255, 255, 0.94);
  backdrop-filter: blur(8px);
  border-bottom: 1px solid var(--linea);
}
.header.is-scrolled { box-shadow: 0 4px 18px rgba(31, 42, 22, 0.08); }

/* tres grupos separados por espacio, no por adorno: marca | navegación | acciones */
/* `flex-wrap` es un seguro, no una decisión de maquetación: con el texto al tamaño normal
   sobran 8px en el peor ancho (medido a 320, 360, 375 y 390), así que nunca llega a
   plegarse. Solo salta cuando el visitante amplía el texto —a 200% la etiqueta larga del
   CTA mide 292px— y sin él la barra desbordaba a lo ancho incluso a 1440px. Plegar es
   peor que caber, pero mucho mejor que sacar la página de la pantalla. */
.header-in {
  display: flex; align-items: center; flex-wrap: wrap;
  gap: clamp(1.2rem, 3vw, 2.6rem);
  min-height: 68px;
}

.brand {
  display: flex; align-items: center; gap: 0.5rem;
  text-decoration: none; color: var(--ink);
  flex-shrink: 0;
}
.brand-logo { width: 38px; height: 43px; flex-shrink: 0; }
.brand-name {
  font-family: var(--font-display);
  font-weight: 800;
  font-size: 1.15rem;
  letter-spacing: -0.01em;
  white-space: nowrap;
}
.brand-name em { font-style: normal; color: var(--naranja-deep); }

/* la navegación ocupa el centro y empuja las acciones al extremo */
.nav { margin-right: auto; }
.nav-links {
  display: flex; gap: clamp(0.9rem, 1.8vw, 1.6rem); list-style: none;
}
.nav-links a {
  position: relative;
  display: block;
  text-decoration: none; color: var(--ink-soft);
  font-weight: 500; font-size: 0.95rem;
  white-space: nowrap;
  padding-block: 0.35rem;
  transition: color 0.15s ease;
}
/* subrayado que crece desde el centro: sin salto de layout al pasar por encima */
.nav-links a::after {
  content: "";
  position: absolute; left: 0; right: 0; bottom: 0;
  height: 2px; background: var(--naranja);
  transform: scaleX(0);
  transition: transform 0.18s ease;
}
.nav-links a:hover { color: var(--ink); }
.nav-links a:hover::after { transform: scaleX(1); }
/* sección en pantalla: el tic de marca — «lo de ahora, encendido» */
.nav-links a.is-actiu { color: var(--ink); font-weight: 600; }
.nav-links a.is-actiu::after { transform: scaleX(1); }

/* enlaces que solo existen dentro del menú desplegable */
.nav-nomes-mobil { display: none; }

.nav-toggle {
  display: none;
  align-items: center; gap: 0.5rem;
  background: none; border: 1px solid var(--linea);
  border-radius: 999px; padding: 0.4rem 0.9rem;
  font-weight: 600; font-size: 0.9rem; cursor: pointer;
}
.nav-toggle-bar {
  width: 16px; height: 2px; background: var(--ink);
  position: relative;
  transition: background-color 0.15s ease;
}
.nav-toggle-bar::before, .nav-toggle-bar::after {
  content: ""; position: absolute; left: 0;
  width: 16px; height: 2px; background: var(--ink);
  transition: transform 0.18s ease, top 0.18s ease;
}
.nav-toggle-bar::before { top: -5px; }
.nav-toggle-bar::after { top: 5px; }
/* abierto: las tres barras se convierten en una X */
.nav-toggle.is-open .nav-toggle-bar { background: transparent; }
.nav-toggle.is-open .nav-toggle-bar::before { top: 0; transform: rotate(45deg); }
.nav-toggle.is-open .nav-toggle-bar::after  { top: 0; transform: rotate(-45deg); }

/* acciones: secundaria de línea + primaria naranja, en ese orden de lectura */
.header-cta { display: flex; align-items: center; gap: 0.6rem; flex-shrink: 0; }
.header-cta .btn { white-space: nowrap; padding-inline: 1.15rem; }
/* .btn-comandes / .nav-comandes: latentes. El área de comandes está oculta (CLAUDE.md §9);
   se conservan para cuando se vuelva a enlazar. */
.btn-comandes { padding-block: 0.5rem; font-size: 0.92rem; border-width: 1.5px; }

/* en anchos medios la navegación pasa a una segunda fila en vez de comprimirse */
@media (max-width: 1120px) and (min-width: 861px) {
  .header-in { flex-wrap: wrap; padding-block: 0.5rem; row-gap: 0; min-height: 0; }
  .nav { order: 3; width: 100%; margin-right: 0; }
  .nav-links { padding-bottom: 0.55rem; }
  .header-cta { margin-left: auto; }
}

/* ---------- Héroe ---------- */
.hero {
  position: relative;
  overflow: hidden;
  padding-block: clamp(3.5rem, 9vw, 7rem) clamp(3rem, 7vw, 5.5rem);
  background:
    radial-gradient(1200px 600px at 85% 0%, rgba(133, 187, 58, 0.07), transparent 60%),
    var(--paper);
}

.hero-ring {
  position: absolute;
  top: 50%; right: -12%;
  width: clamp(340px, 46vw, 640px);
  transform: translateY(-52%);
  color: var(--naranja);
  opacity: 0.9;
  pointer-events: none;
}
.ring-path {
  stroke-dasharray: 1;
  stroke-dashoffset: 1;
  animation: trazo 1.1s cubic-bezier(0.6, 0, 0.3, 1) 0.15s forwards;
}
.leaf-path {
  stroke-dasharray: 1;
  stroke-dashoffset: 1;
  animation: trazo 0.7s ease-out 1.05s forwards;
}
.leaf-path--2 { animation-delay: 1.2s; }
@keyframes trazo { to { stroke-dashoffset: 0; } }

.hero-in { position: relative; }

.hero-title {
  font-size: clamp(2.6rem, 7.2vw, 5.2rem);
  font-weight: 800;
  line-height: 0.98;
  letter-spacing: -0.02em;
  max-width: 12ch;
  /* el titular es lo más grande de la página: con el texto ampliado, una palabra suya no
     cabe en una línea de 320px y ensanchaba la maquetación entera */
  overflow-wrap: break-word;
  animation: sube 0.7s cubic-bezier(0.2, 0.7, 0.2, 1) both;
}
@keyframes sube {
  from { opacity: 0; transform: translateY(18px); }
  to { opacity: 1; transform: none; }
}

.hero-sub {
  max-width: 44ch;
  margin-top: 1.4rem;
  font-size: 1.13rem;
  color: var(--ink-soft);
  animation: sube 0.7s cubic-bezier(0.2, 0.7, 0.2, 1) 0.12s both;
}

.hero-actions {
  display: flex; flex-wrap: wrap; gap: 0.9rem;
  margin-top: 2rem;
  animation: sube 0.7s cubic-bezier(0.2, 0.7, 0.2, 1) 0.22s both;
}

/* Ticket albarán */
.ticket {
  margin-top: 2.8rem;
  max-width: 420px;
  background: var(--paper);
  border: 1px solid var(--linea);
  border-radius: 6px;
  box-shadow: var(--sombra);
  font-family: var(--font-mono);
  animation: sube 0.7s cubic-bezier(0.2, 0.7, 0.2, 1) 0.34s both;
}
.ticket-head {
  padding: 0.7rem 1.1rem;
  font-size: 0.82rem;
  font-weight: 600;
  letter-spacing: 0.08em;
  border-bottom: 1px dashed var(--linea);
  color: var(--naranja-deep);
}
.ticket-body { padding: 0.9rem 1.1rem; display: grid; gap: 0.45rem; }
.ticket-body > div { display: flex; justify-content: space-between; gap: 1rem; }
.ticket-body dt { color: var(--ink-soft); font-size: 0.85rem; }
.ticket-body dd { font-weight: 600; font-size: 0.85rem; text-align: right; }
.ticket-foot {
  padding: 0.6rem 1.1rem;
  font-size: 0.75rem;
  color: var(--ink-soft);
  border-top: 1px dashed var(--linea);
}

/* ---------- Línea de pesaje (cifras) ---------- */
.scale-strip {
  background: var(--ink);
  color: var(--paper);
  border-block: 4px solid var(--naranja);
}
.scale-in {
  display: flex; flex-wrap: wrap;
  justify-content: space-between;
  gap: 0.8rem 2.2rem;
  padding-block: 1.1rem;
  font-family: var(--font-mono);
  font-size: 0.85rem;
  letter-spacing: 0.02em;
}
.scale-in p { color: rgba(255, 255, 255, 0.75); }
.scale-in b { color: var(--verde); font-weight: 600; margin-right: 0.4rem; }
/* cuando la cifra cierra la celda («Des del 1958») el aire sobra por la derecha */
.scale-in b:last-child { margin-right: 0; }

/* ---------- Secciones ---------- */
.section { padding-block: clamp(3.5rem, 8vw, 6rem); }
.section--tint { background: var(--paper-tint); }
.section--board { background: var(--board); color: #f2f5ea; }
.section--board h2 { color: #fff; }
.section--board .section-sub { color: #b9c6a6; }
.section-head { margin-bottom: clamp(2rem, 5vw, 3rem); }

/* ---------- Productos ---------- */
.cat-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
  gap: 1.2rem;
}
.cat-card {
  border: 1px solid var(--linea);
  border-radius: var(--radius);
  padding: 1.5rem 1.4rem;
  background: var(--paper);
}

/* Mismo caso que en segmentos: la tarjeta lleva también .reveal y `.js .reveal` (0,2,0)
   le ganaba a `.cat-card` (0,1,0) —y a `.cat-card:hover` (0,2,0), por orden—, así que ni
   la transición ni el translateY del hover llegaban a verse nunca. La transición se
   declara aquí con el peso suficiente, conservando los tiempos de la entrada. */
#productos .reveal {
  transition: opacity 0.55s ease, transform 0.55s cubic-bezier(0.2, 0.7, 0.2, 1),
              scale 0.18s ease, filter 0.18s ease,
              border-color 0.15s ease, box-shadow 0.15s ease;
}

/* La familia apuntada se adelanta y las otras tres se van fuera de foco, igual que en
   la rejilla de segmentos (ver GUIA-ESTETICA §7). Aquí el borde es verde, no naranja:
   estas tarjetas informan, no son una acción. El desplazamiento de 3px se sustituye por
   la escala, que es la propiedad que no se pisa con la animación de entrada.
   Estas tarjetas no contienen nada enfocable, así que no hay pareja de teclado. */
@media (hover: hover) {
  .cat-card:hover {
    scale: 1.03;
    z-index: 1;
    box-shadow: var(--sombra);
    border-color: var(--verde);
  }
  .cat-grid:hover .cat-card:not(:hover) { filter: blur(1px) opacity(0.5); }
}
.cat-icon { width: 42px; height: 42px; color: var(--naranja); margin-bottom: 1rem; }
.cat-card h3 { margin-bottom: 0.8rem; }
.chip-list { list-style: none; display: flex; flex-wrap: wrap; gap: 0.4rem; }
.chip-list li {
  font-family: var(--font-mono);
  font-size: 0.74rem;
  padding: 0.22rem 0.6rem;
  border: 1px solid var(--linea);
  border-radius: 999px;
  color: var(--ink-soft);
  background: var(--paper-tint);
}

/* El ultimo chip de cada familia avisa de que la lista es una muestra, no el surtido
   entero. Linea discontinua y verde para que no se lea como un producto mas. El selector
   lleva el `li` porque `.chip-list li` ya es (0,1,1) y una clase sola no le ganaria. */
.chip-list li.chip-list-mes {
  border-style: dashed;
  border-color: var(--verde);
  background: transparent;
  color: var(--verde-deep);
  font-weight: 600;
}

/* Cierre de la seccion: misma pieza que .seg-particulars en segmentos, porque hace el
   mismo trabajo —matizar lo de arriba y mandar al telefono— y conviene que se reconozca. */
.cat-nota {
  margin-top: 1.6rem;
  padding: 0.9rem 1.1rem;
  border-left: 3px solid var(--verde);
  background: var(--paper-tint);
  border-radius: 0 var(--radius) var(--radius) 0;
  color: var(--ink-soft);
  font-size: 0.95rem;
}
.cat-nota a {
  color: var(--verde-deep);
  text-decoration-color: var(--verde);
  text-underline-offset: 2px;
  font-weight: 600;
}
.cat-nota a:hover { color: var(--ink); }

/* ---------- Pizarra de temporada ---------- */
.mes-actual-label {
  color: var(--naranja);
  font-weight: 600;
}

.cal-filtros {
  display: flex; flex-wrap: wrap; gap: 0.5rem;
  margin-bottom: 1.4rem;
}
.chip {
  font-family: var(--font-mono);
  font-size: 0.8rem;
  font-weight: 500;
  padding: 0.35rem 0.95rem;
  border-radius: 999px;
  border: 1px solid var(--board-line);
  background: transparent;
  color: #cdd8bc;
  cursor: pointer;
  transition: background-color 0.15s ease, color 0.15s ease, border-color 0.15s ease;
}
.chip:hover { border-color: var(--verde); color: #fff; }
.chip.is-active {
  background: var(--verde);
  border-color: var(--verde);
  color: var(--ink);
  font-weight: 600;
}

.cal-scroll {
  overflow-x: auto;
  border: 1px solid var(--board-line);
  border-radius: var(--radius);
  -webkit-overflow-scrolling: touch;
}
.cal-table {
  border-collapse: collapse;
  width: 100%;
  min-width: 720px;
  font-family: var(--font-mono);
  font-size: 0.82rem;
}
.cal-table th, .cal-table td {
  padding: 0.55rem 0.5rem;
  border-bottom: 1px solid var(--board-line);
  text-align: center;
}
.cal-table thead th {
  font-weight: 600;
  font-size: 0.72rem;
  letter-spacing: 0.08em;
  color: #aebb99;
  border-bottom: 2px solid var(--board-line);
}
/* La columna de producto se queda fija al desplazar la tabla. Sin esto, en móvil el
   visitante llega al mes de hoy —lo coloca main.js → calendarioAlMes()— y ve una rejilla
   de puntos sin saber de qué producto es cada fila. El fondo tiene que ser opaco (antes
   se veía --board por transparencia) y el hairline de la derecha es el mismo
   --board-line del resto de la tabla. */
.cal-prod-th, .cal-prod {
  text-align: left !important;
  white-space: nowrap;
  padding-left: 1rem !important;
  position: sticky;
  left: 0;
  z-index: 1;
  background: var(--board);
  border-right: 1px solid var(--board-line);
}
.cal-prod { color: #f2f5ea; font-weight: 500; }
/* En móvil el `nowrap` deja la columna de producto en 251px de los 283 que mide la caja:
   con la columna fija, eso significaba no ver ni un mes entero. Se le pone anchura y se
   le permite partir —«Préssec i nectarina» pasa a dos líneas— en vez de recortar con
   puntos suspensivos: el nombre del producto es el dato que da sentido a la fila.
   El corte de 620 ya existe en este fichero. */
@media (max-width: 620px) {
  .cal-prod-th, .cal-prod { white-space: normal; width: 7.5rem; }
}
.cal-table tbody tr:last-child th,
.cal-table tbody tr:last-child td { border-bottom: none; }
.cal-table tbody tr:hover { background: rgba(133, 187, 58, 0.07); }
/* la celda fija es opaca: el hover de la fila se le pinta encima en dos capas para no
   inventar un color nuevo —es el mismo rgba de siempre sobre --board */
.cal-table tbody tr:hover .cal-prod {
  background: linear-gradient(rgba(133, 187, 58, 0.07), rgba(133, 187, 58, 0.07)), var(--board);
}

.cal-table .is-hoy {
  background: rgba(240, 138, 0, 0.14);
}
.cal-table thead .is-hoy {
  color: var(--naranja);
  border-bottom-color: var(--naranja);
}

.dot {
  display: inline-block;
  width: 11px; height: 11px;
  border-radius: 50%;
}
.dot--alta { background: var(--naranja); }
.dot--disp { border: 2px solid var(--verde); background: transparent; }

.cal-leyenda {
  margin-top: 1.1rem;
  font-family: var(--font-mono);
  font-size: 0.78rem;
  color: #b9c6a6;
  display: flex; flex-wrap: wrap; align-items: center; gap: 0.5rem 0.7rem;
}
.cal-leyenda-sep { opacity: 0.5; }

.cal-row-hidden { display: none; }

.cal-noscript {
  padding: 1rem 1.2rem;
  font-family: var(--font-mono);
  font-size: 0.85rem;
  color: #dfe8d1;
}
.cal-noscript a { color: var(--verde); }

/* ---------- Por qué nosotros ---------- */
.why-grid {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 1.2rem;
}
/* `minmax(0, 1fr)` y no `1fr`: con `1fr` el mínimo de la columna es su min-content, así
   que una palabra larga del h3 ensancha la rejilla y saca la página de la pantalla. Se ve
   con el texto ampliado al 200%, donde «intermediaris» mide 286px en un hueco de 285.
   Mismo motivo en .seg-grid, .contacto-grid, .faq-grid, .form-row--2col y .footer-in. */
@media (max-width: 620px) {
  .why-grid { grid-template-columns: minmax(0, 1fr); }
}
/* El filete verde de arriba ya no es el color del borde, sino una capa de fondo que
   ocupa exactamente los 4px que el borde transparente reserva. Se hace así para poder
   dibujarlo al entrar animando `background-size`: el fondo lo recorta el border-radius
   de la propia tarjeta, con lo que el filete conserva las esquinas redondeadas que tenía
   como borde. Un ::before no valía: al vivir en la zona del borde (top:-4px) lo recorta
   el overflow, y sin overflow sus esquinas rectas asomaban por fuera de la curva. */
.why-card {
  background-color: var(--paper);
  background-image: linear-gradient(var(--verde), var(--verde));
  background-repeat: no-repeat;
  background-position: left top;
  background-size: 100% 4px;
  border-radius: var(--radius);
  padding: 1.5rem 1.4rem;
  border-top: 4px solid transparent;
}
.why-card h3 { margin-bottom: 0.6rem; }
.why-card p { color: var(--ink-soft); font-size: 0.98rem; }

/* Entrada escalonada (GUIA-ESTETICA §7: una sola entrada orquestada, retardos de ~0.1s).
   Las cinco piezas llevan .reveal, y `.js .reveal` (0,2,0) declara `transition` en atajo
   —lo que pone `transition-delay` a 0 y se comería el escalonado—. Es el mismo choque ya
   documentado para #productos y #segmentos, así que se redeclara con peso de sección
   conservando los tiempos de la entrada. */
#empresa .reveal {
  transition: opacity 0.55s ease var(--retard, 0s),
              transform 0.55s cubic-bezier(0.2, 0.7, 0.2, 1) var(--retard, 0s);
}
.why-card:nth-child(2) { --retard: 0.1s; }
.why-card:nth-child(3) { --retard: 0.2s; }
.why-card:nth-child(4) { --retard: 0.3s; }

/* La tarjeta sube y, cuando ya ha llegado, se traza el filete: primero la caja, luego la
   línea. El retardo propio del filete va en la lista, no en `transition-delay`, porque
   ese es único para todas las propiedades. */
#empresa .why-card.reveal {
  transition: opacity 0.55s ease var(--retard, 0s),
              transform 0.55s cubic-bezier(0.2, 0.7, 0.2, 1) var(--retard, 0s),
              background-size 0.6s cubic-bezier(0.2, 0.7, 0.2, 1)
                calc(var(--retard, 0s) + 0.22s);
}
.js .why-card.reveal { background-size: 0 4px; }
.js .why-card.reveal.is-visible { background-size: 100% 4px; }
/* Con JS pero sin IntersectionObserver o con movimiento reducido: ya dibujado. */
.js.no-observer .why-card.reveal { background-size: 100% 4px; }

/* En una columna (≤620) las tarjetas ya no entran juntas: cada una aparece cuando le
   toca al hacer scroll, y un retardo acumulado se leería como lentitud, no como ritmo. */
@media (max-width: 620px) {
  /* Mismo peso que las reglas de arriba (0,2,0): con un simple `.why-card` (0,1,0) el
     reset no llegaba a aplicarse nunca. */
  .why-card:nth-child(2),
  .why-card:nth-child(3),
  .why-card:nth-child(4) { --retard: 0s; }
}

/* ---------- Calidad ---------- */
.cert-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
  gap: 1.2rem;
}
.cert-card {
  border: 1px solid var(--linea);
  border-radius: var(--radius);
  padding: 1.5rem 1.4rem;
}
.cert-card h3 { margin-bottom: 0.6rem; }
.cert-card p { color: var(--ink-soft); font-size: 0.98rem; }
.cert-num {
  margin-top: 0.9rem;
  font-family: var(--font-mono);
  font-size: 0.74rem !important;
  letter-spacing: 0.04em;
  color: var(--verde-deep) !important;
  border: 1px dashed var(--verde);
  border-radius: 4px;
  padding: 0.3rem 0.6rem;
  display: inline-block;
}

/* Entrada escalonada, misma gramática que «Com treballem» (GUIA-ESTETICA §7): primero
   aterriza la tarjeta y después llega el detalle, con el mismo desfase de 0.22s. Aquí el
   detalle no es un filete —estas tarjetas no lo llevan— sino el chip: es la prueba de lo
   que afirma el titular, así que es lo último que se posa, como un sello.
   Se redeclara la transición con peso de sección porque `.js .reveal` (0,2,0) la declara
   en atajo y pondría los retardos a 0. */
#calidad .reveal {
  transition: opacity 0.55s ease var(--retard, 0s),
              transform 0.55s cubic-bezier(0.2, 0.7, 0.2, 1) var(--retard, 0s);
}
.cert-card:nth-child(2) { --retard: 0.1s; }
.cert-card:nth-child(3) { --retard: 0.2s; }

/* El chip hereda el --retard de su tarjeta y le suma su propio desfase. Se mueve con
   opacity/transform y no con márgenes, para que la altura de la tarjeta no cambie ni un
   píxel mientras entra. */
.js .cert-card.reveal .cert-num {
  opacity: 0;
  transform: translateY(6px);
  transition: opacity 0.5s ease calc(var(--retard, 0s) + 0.22s),
              transform 0.5s cubic-bezier(0.2, 0.7, 0.2, 1)
                calc(var(--retard, 0s) + 0.22s);
}
.js .cert-card.reveal.is-visible .cert-num { opacity: 1; transform: none; }
/* Con JS pero sin IntersectionObserver o con movimiento reducido: el chip ya puesto. */
.js.no-observer .cert-card.reveal .cert-num { opacity: 1; transform: none; }

/* La rejilla es `auto-fit` y no tiene corte propio: medido, cae a una columna sola entre
   los 604 y los 584px de viewport. El corte de 620 (ya existente en el fichero) cubre toda esa zona, y ahí el
   escalonado sobra porque las tarjetas ya entran de una en una.
   Mismo peso que las reglas de arriba (0,2,0): con `.cert-card` a secas no se aplicaría. */
@media (max-width: 620px) {
  .cert-card:nth-child(2),
  .cert-card:nth-child(3) { --retard: 0s; }
}

/* ---------- Instalaciones ---------- */
.fotos-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
  gap: 1.2rem;
}
.foto-ph-area {
  aspect-ratio: 4 / 3;
  border-radius: var(--radius);
  border: 1px solid var(--linea);
  background:
    repeating-linear-gradient(-45deg,
      rgba(133, 187, 58, 0.10) 0 14px,
      rgba(255, 255, 255, 0) 14px 28px),
    var(--paper);
  display: grid;
  place-items: center;
}
.foto-ph-area span {
  font-family: var(--font-mono);
  font-size: 0.75rem;
  letter-spacing: 0.1em;
  color: var(--ink-soft);
  border: 1px dashed var(--verde-deep);
  border-radius: 4px;
  padding: 0.35rem 0.8rem;
  background: var(--paper);
}
.foto-ph figcaption {
  margin-top: 0.7rem;
  font-size: 0.9rem;
  color: var(--ink-soft);
}

/* ---------- Segmentos ---------- */
/* cuatro perfiles: 2×2 como .why-grid, para no dejar una tarjeta huérfana */
.seg-grid {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 1.2rem;
}
@media (max-width: 620px) {
  .seg-grid { grid-template-columns: minmax(0, 1fr); }
}
.seg-card {
  border: 1px solid var(--linea);
  border-radius: var(--radius);
  padding: 1.7rem 1.5rem;
  display: flex; flex-direction: column; gap: 0.8rem;
}

/* Las tres piezas de esta sección llevan también .reveal, y `.js .reveal` (0,2,0) le
   ganaba en especificidad a `.seg-card` (0,1,0): la transición de la tarjeta no llegaba
   a aplicarse nunca y el hover cambiaba de golpe. Se declara aquí una sola vez, con los
   tiempos del reveal para la entrada (opacity/transform) y los de micro-hover para lo
   demás. */
#segmentos .reveal {
  transition: opacity 0.55s ease, transform 0.55s cubic-bezier(0.2, 0.7, 0.2, 1),
              scale 0.18s ease, filter 0.18s ease,
              border-color 0.15s ease, box-shadow 0.15s ease;
}

/* La tarjeta apuntada se adelanta —crece un punto, borde naranja y sombra— y las otras
   tres se van fuera de foco. El resto de la sección (titular y nota del particular) no
   se toca: es texto que se lee, no una opción que se elige.
   Dos detalles que no son capricho: el atenuado va en `filter: opacity()` y la escala
   en `scale`, no en `opacity` ni en `transform`, porque esas dos las usa el reveal de
   entrada y se pisarían entre ellas.
   Todo el bloque vive dentro de `hover: hover`: en táctil el navegador mantiene el
   :hover después de tocar y las tarjetas se quedaban desenfocadas. */
@media (hover: hover) {
  .seg-card:hover {
    border-color: var(--naranja);
    box-shadow: var(--sombra);
    scale: 1.03;
    z-index: 1;
  }
  .seg-grid:hover .seg-card:not(:hover) { filter: blur(1px) opacity(0.5); }
}

/* Con teclado manda la tarjeta enfocada, con el mismo trato. Es `:focus-visible` y no
   `:focus-within`: al tocar el botón con el dedo, el foco se queda en él y las tarjetas
   habrían permanecido desenfocadas después del toque. */
.seg-card:has(:focus-visible) {
  border-color: var(--naranja);
  box-shadow: var(--sombra);
  scale: 1.03;
  z-index: 1;
}
.seg-grid:has(.seg-card :focus-visible) .seg-card:not(:has(:focus-visible)) {
  filter: blur(1px) opacity(0.5);
}
.seg-card p { color: var(--ink-soft); flex-grow: 1; }
.seg-card .btn { align-self: flex-start; }

/* nota para el particular: no es una tarjeta más, es una salida lateral */
.seg-particulars {
  margin-top: 1.6rem;
  padding: 0.9rem 1.1rem;
  border-left: 3px solid var(--verde);
  background: var(--paper-tint);
  border-radius: 0 var(--radius) var(--radius) 0;
  color: var(--ink-soft);
  font-size: 0.95rem;
}
/* sobre fondo claro el enlace va en verde profundo, que es el que cumple AA */
.seg-particulars a {
  color: var(--verde-deep);
  text-decoration-color: var(--verde);
  text-underline-offset: 2px;
  font-weight: 600;
}
.seg-particulars a:hover { color: var(--ink); }

/* ---------- Contacto ----------
   La clase .section--tarifa y el id #tarifa son identificadores históricos: la sección
   se titula «Contacte» desde 2026-09-15 (ver BRIEFING-CLIENTE.md §8). */
.section--tarifa {
  background:
    radial-gradient(900px 500px at 10% 0%, rgba(240, 138, 0, 0.08), transparent 55%),
    var(--board);
}

/* Banda de contenido: cada trabajo —pedir, resolver dudas, encontrarnos— va en la
   suya, separada por hairline. Los colores se escriben para fondo CLARO, que es el
   caso general; sobre pizarra se corrigen con .section--board. */
.bloc + .bloc {
  margin-top: clamp(2.6rem, 6vw, 4rem);
  padding-top: clamp(2.6rem, 6vw, 4rem);
  border-top: 1px solid var(--linea);
}
.section--board .bloc + .bloc { border-top-color: var(--board-line); }
/* título de banda: por debajo del h2 de la sección y por encima del cuerpo */
.bloc-titol {
  font-size: 1.25rem;
  color: var(--ink);
  margin-bottom: 1.2rem;
}
.section--board .bloc-titol { color: #fff; }

.contacto-grid {
  display: grid;
  grid-template-columns: minmax(0, 1.15fr) minmax(0, 0.85fr);
  gap: clamp(2rem, 5vw, 4rem);
  align-items: start;
}

/* el formulario es el objeto principal de la sección: va en panel para que el naranja
   del CTA se apoye en una superficie y no flote sobre el fondo de pizarra */
.contacto-form {
  background: rgba(255, 255, 255, 0.04);
  border: 1px solid var(--board-line);
  border-radius: var(--radius);
  padding: clamp(1.2rem, 3.5vw, 2rem);
}

.form { display: grid; grid-template-columns: minmax(0, 1fr); gap: 1.1rem; }
/* `minmax(0, 1fr)` también aquí: la columna implícita se dimensiona a min-content, y el
   min-content de un <select> es su opción más larga («Col·lectivitats i escoles»), que
   con el texto ampliado desbordaba el panel entero. */
.form-row { display: grid; grid-template-columns: minmax(0, 1fr); gap: 0.4rem; }
.form-row--2col {
  grid-template-columns: 1fr 1fr;
  gap: 1rem;
}
.form-row--2col > div { display: grid; grid-template-columns: minmax(0, 1fr); gap: 0.4rem; }
.form label {
  font-size: 0.88rem;
  font-weight: 600;
  color: #dfe8d1;
}
.form .opt { font-weight: 400; color: #9dab88; }
.form input, .form select, .form textarea {
  background: rgba(255, 255, 255, 0.06);
  border: 1px solid var(--board-line);
  border-radius: 8px;
  /* 0.78rem deja el campo en ~46px: por encima del objetivo táctil mínimo */
  padding: 0.78rem 0.9rem;
  color: #fff;
  width: 100%;
}
.form input::placeholder, .form textarea::placeholder { color: #8a9878; }
.form select { appearance: auto; }
.form select option { color: var(--ink); background: var(--paper); }
.form input:focus-visible, .form select:focus-visible, .form textarea:focus-visible {
  outline: 3px solid var(--naranja);
  outline-offset: 1px;
  border-color: var(--naranja);
}
/* la nota va al lado del botón, no debajo: responde al «¿y ahora qué pasa?» justo
   en el momento de decidir enviarlo */
.form-accio {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.7rem 1.1rem;
  margin-top: 0.3rem;
}
.form-accio .btn { flex-shrink: 0; }
.form-nota {
  font-size: 0.85rem;
  line-height: 1.45;
  color: #b9c6a6;
  max-width: 24ch;
}
.form-ok {
  background: rgba(133, 187, 58, 0.15);
  border: 1px solid var(--verde);
  border-radius: 8px;
  padding: 0.9rem 1.1rem;
  color: #f2f5ea;
  font-size: 0.95rem;
}
.form-ok a { color: var(--verde); font-weight: 600; }

/* ---------- Fichas de canal ----------
   Mientras el área de comandes esté oculta, teléfono, WhatsApp y email SON la vía de
   pedido (CLAUDE.md §9): dejan de ser una tabla etiqueta/valor de 0.95rem y pasan a
   fichas pulsables. Borde neutro y acento verde: la única superficie naranja de la
   sección sigue siendo el botón del formulario. */
.canals-head {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.5rem 0.9rem;
  margin-bottom: 1.1rem;
}
.canals-head .bloc-titol { margin-bottom: 0; }
/* mismo estado que la barra de utilidades, pero aquí el usuario ya está decidiendo:
   comparte los modificadores .es-* y el punto de color con .topbar-estat */
.canal-estat {
  display: inline-flex;
  align-items: center;
  gap: 0.45rem;
  font-family: var(--font-mono);
  font-size: 0.72rem;
  color: #dfe8d1;
  border: 1px solid var(--board-line);
  border-radius: 999px;
  padding: 0.25rem 0.7rem;
}
.canal-estat[hidden] { display: none; }
/* el recorte con puntos suspensivos es de la barra de utilidades, que mide 34px de alto;
   esta píldora vive en una columna y puede crecer, así que el texto se parte en vez de
   desbordar cuando el visitante amplía la letra */
.canal-estat .estat-text { white-space: normal; overflow: visible; }

.canals { list-style: none; display: grid; gap: 0.7rem; }
.canal {
  display: grid;
  grid-template-columns: auto minmax(0, 1fr);
  gap: 0.9rem;
  align-items: center;
  padding: 0.85rem 1rem;
  border: 1px solid var(--board-line);
  border-radius: var(--radius);
  background: rgba(255, 255, 255, 0.03);
  text-decoration: none;
  color: inherit;
  transition: transform 0.12s ease, background-color 0.15s ease, border-color 0.15s ease;
}
.canal:hover {
  transform: translateY(-2px);
  border-color: var(--verde);
  background: rgba(133, 187, 58, 0.10);
}
.canal-icona {
  width: 40px; height: 40px;
  border-radius: 50%;
  display: grid; place-items: center;
  background: rgba(133, 187, 58, 0.14);
  color: var(--verde);
  flex-shrink: 0;
}
.canal-icona svg { width: 21px; height: 21px; }
.canal-tipus {
  display: block;
  font-family: var(--font-mono);
  font-size: 0.7rem;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: #9dab88;
}
/* el email es largo: que parta antes que desbordar a 360px */
.canal-valor {
  display: block;
  font-weight: 600;
  font-size: 1.02rem;
  line-height: 1.25;
  color: #fff;
  overflow-wrap: anywhere;
}
.canal-nota {
  display: block;
  margin-top: 0.15rem;
  font-size: 0.82rem;
  line-height: 1.4;
  color: #b9c6a6;
}

/* resumen de servicio bajo las fichas: mismo lenguaje etiqueta/valor que el pie */
.canal-servei {
  margin-top: 1.4rem;
  padding-top: 1.2rem;
  border-top: 1px solid var(--board-line);
}
.canal-servei h4 { font-size: 0.98rem; color: #fff; margin-bottom: 0.85rem; }
.canal-servei ul { list-style: none; display: grid; gap: 0.8rem; font-size: 0.92rem; }
.canal-servei li { display: grid; gap: 0.1rem; }
.canal-servei li span:not(.contacto-label) { color: #dfe8d1; line-height: 1.45; }

.contacto-label {
  font-family: var(--font-mono);
  font-size: 0.72rem;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: #9dab88;
}

/* ---------- Preguntas frecuentes ----------
   A dos columnas y a todo ancho: antes vivían en el raíl estrecho, que es el peor
   ancho de la página para el contenido que resuelve objeciones. */
.faq-grid { display: grid; gap: 0 clamp(2rem, 5vw, 4rem); }
.faq details {
  border-bottom: 1px solid var(--linea);
}
/* el marcador por defecto queda pegado al margen izquierdo y no dice si abre o cierra:
   se sustituye por +/− a la derecha, alineado con el borde de la banda */
.faq summary {
  cursor: pointer;
  font-weight: 600;
  color: var(--ink);
  list-style: none;
  padding-block: 0.85rem;
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 1rem;
}
.faq summary::-webkit-details-marker { display: none; }
.faq summary::after {
  content: "+";
  font-family: var(--font-mono);
  font-size: 1.15rem;
  line-height: 1;
  color: var(--verde-deep);
  flex-shrink: 0;
}
.faq details[open] summary::after { content: "–"; }
.faq summary:hover { color: var(--verde-deep); }
.faq details p {
  padding-top: 0.2rem;
  padding-bottom: 0.9rem;
  color: var(--ink-soft);
  font-size: 0.95rem;
  max-width: 52ch;
}
/* los enlaces del FAQ van en verde de marca, no en el azul del navegador */
.faq details p a {
  color: var(--verde-deep);
  /* el email de la respuesta no tiene dónde partir y desbordaba a 320px con el texto
     ampliado; `anywhere` además sí reduce el min-content, que es lo que aquí hace falta */
  overflow-wrap: anywhere;
  text-decoration-color: var(--verde);
  text-underline-offset: 2px;
}
.faq details p a:hover { color: var(--ink); }

/* sobre pizarra, los mismos componentes con los neutros de la barra oscura */
.section--board .faq details { border-bottom-color: var(--board-line); }
.section--board .faq summary { color: #f2f5ea; }
.section--board .faq summary:hover,
.section--board .faq summary::after { color: var(--verde); }
.section--board .faq details p { color: #b9c6a6; }
.section--board .faq details p a { color: var(--verde); }
.section--board .faq details p a:hover { color: var(--paper); }

@media (min-width: 760px) {
  .faq-grid { grid-template-columns: minmax(0, 1fr) minmax(0, 1fr); }
}

/* ---------- Mapa de emplazamientos ---------- */
.mapa-cos {
  display: grid;
  gap: 1.2rem;
  align-items: start;
}
/* altura fija, no aspect-ratio: una proporcion crece con el ancho sin techo y a 1120px
   dejaba el marco en ~590px de alto para tres lineas de informacion. Aqui el mapa es
   un dato de contacto mas, asi que va en banda corta. */
.mapa-marc {
  height: 240px;
  border-radius: var(--radius);
  overflow: hidden;
  border: 1px solid var(--linea);
}
.mapa-frame, .mapa-ph { width: 100%; height: 100%; display: block; border: 0; }
/* hueco mientras el cliente no envie su mapa; mismo lenguaje que los foto-ph */
.mapa-ph {
  display: grid;
  place-content: center;
  justify-items: center;
  gap: 0.6rem;
  padding: 1rem;
  text-align: center;
  /* tintado sobre la sección blanca: el hueco tiene que leerse como una superficie
     esperando contenido, no como un agujero del mismo color que la página */
  background: var(--paper-tint);
}
.mapa-ph span {
  font-family: var(--font-mono);
  font-size: 0.75rem;
  letter-spacing: 0.1em;
  color: var(--ink-soft);
  border: 1px dashed var(--verde-deep);
  border-radius: 999px;
  padding: 0.35rem 0.9rem;
}
/* el mismo hueco, ya como boton: es la pantalla previa al iframe de Google. No lleva
   naranja a proposito, que la unica accion naranja de la pagina es el CTA de contacto. */
.mapa-ph--accio {
  font: inherit;
  color: inherit;
  cursor: pointer;
}
/* vale para el aviso del boton y para el <noscript> del hueco */
.mapa-ph small {
  font-size: 0.78rem;
  line-height: 1.4;
  max-width: 34ch;
  color: var(--ink-soft);
}
.mapa-ph a { color: var(--verde-deep); text-decoration-color: var(--verde); text-underline-offset: 2px; }
.mapa-ph a:hover { color: var(--ink); }
.mapa-ph--accio:hover span { color: var(--ink); border-color: var(--ink); }
.mapa-ph--accio:focus-visible { outline: 3px solid var(--naranja); outline-offset: -3px; }
.mapa-punts {
  list-style: none;
  display: grid;
  gap: 1rem;
  font-size: 0.95rem;
}
/* etiqueta encima del dato, tambien en movil: cada punto lleva ya direccion y horario,
   y en la columna de 92px la etiqueta de las tiendas se partia en dos lineas */
.mapa-punts li { display: grid; gap: 0.15rem; }
/* .contacto-label nacio para la pizarra (fichas de canal y pie); aqui vive sobre claro */
.mapa-punts .contacto-label { color: var(--ink-soft); }
.mapa-punts span:not(.contacto-label) { color: var(--ink-soft); }
.mapa-punts a { color: var(--verde-deep); text-decoration-color: var(--verde); text-underline-offset: 2px; }
.mapa-punts a:hover { color: var(--ink); }

@media (min-width: 760px) {
  /* mapa a la izquierda, las tres ubicaciones al lado: el bloque deja de sumar alturas */
  .mapa-cos { grid-template-columns: minmax(0, 1.15fr) minmax(0, 0.85fr); gap: 2rem; }
  .mapa-marc { height: 320px; }
}

/* ---------- Páginas legales ----------
   Aviso legal, privacidad y galetes: son texto largo, así que van en una sola columna
   estrecha (~68 caracteres) dentro del .wrap de siempre. Comparten cabecera secundaria
   y pie con comandes.html; lo único propio es el ancho de lectura y la ficha de datos. */
.legal-hero {
  background: var(--paper-tint);
  border-bottom: 1px solid var(--linea);
  padding-block: clamp(2.2rem, 6vw, 3.6rem) clamp(1.6rem, 4vw, 2.4rem);
}
/* la cabecera de hoja se estrecha al mismo ancho que el cuerpo: si no, el título
   arranca en el borde del wrap y el texto empieza 130px más adentro */
.legal-hero .wrap { max-width: 68ch; }
/* y el aire de sección completa sobra entre dos bloques del mismo documento */
.legal-hero + .section { padding-top: clamp(1.8rem, 4vw, 2.6rem); }
.legal-titol { font-size: clamp(2rem, 5vw, 3rem); font-weight: 800; }
.legal-meta {
  font-family: var(--font-mono);
  font-size: 0.78rem;
  letter-spacing: 0.04em;
  color: var(--ink-soft);
  margin-top: 0.9rem;
}
/* estas páginas todavía no han pasado por un abogado: el aviso lo dice en la propia
   página, no solo en un comentario del código */
.legal-avis {
  max-width: 62ch;
  margin-top: 1.2rem;
  padding: 0.8rem 1rem;
  background: var(--paper);
  border: 1px solid var(--linea);
  border-left: 3px solid var(--naranja);
  border-radius: var(--radius);
  font-size: 0.92rem;
  color: var(--ink-soft);
}

/* `overflow-wrap` en el cuerpo: el email y algún término largo del índice («Responsabilitat»)
   no caben en una línea de 320px con el texto ampliado. */
.legal-cos { max-width: 68ch; overflow-wrap: break-word; }
.legal-cos h2 {
  font-size: clamp(1.3rem, 2.6vw, 1.7rem);
  font-weight: 700;
  line-height: 1.15;
  margin-top: 2.6rem;
  scroll-margin-top: 90px;
}
.legal-cos h3 { margin-top: 1.7rem; }
.legal-cos p,
.legal-cos ul,
.legal-cos ol { margin-top: 0.9rem; color: var(--ink-soft); }
.legal-cos ul,
.legal-cos ol { padding-left: 1.2rem; }
.legal-cos li + li { margin-top: 0.35rem; }
.legal-cos li::marker { color: var(--verde-deep); }
.legal-cos a { color: var(--verde-deep); text-decoration-color: var(--verde); text-underline-offset: 2px; }
.legal-cos a:hover { color: var(--ink); }
.legal-cos strong { color: var(--ink); }

/* índice de la página: la ley obliga a que se encuentre la información, no a que se
   lea entera de arriba abajo */
.legal-index {
  margin-top: 1.4rem;
  padding: 1rem 1.15rem;
  border: 1px solid var(--linea);
  border-radius: var(--radius);
}
.legal-index ol { margin-top: 0.6rem; font-size: 0.95rem; }

/* ficha etiqueta/valor: datos del titular, del responsable o de cada tercero */
.legal-dades {
  display: grid;
  grid-template-columns: max-content minmax(0, 1fr);
  gap: 0.4rem 1.1rem;
  margin-top: 1rem;
}
.legal-dades dt {
  font-family: var(--font-mono);
  font-size: 0.72rem;
  font-weight: 600;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--verde-deep);
  padding-top: 0.22rem;
}
.legal-dades dd { margin: 0; color: var(--ink); overflow-wrap: anywhere; }

.legal-fitxa {
  margin-top: 1rem;
  padding: 1rem 1.15rem;
  border: 1px solid var(--linea);
  border-radius: var(--radius);
}
.legal-fitxa h3 { font-size: 1.05rem; }
.legal-fitxa .legal-dades { margin-top: 0.7rem; }

/* dato del cliente aún sin confirmar. Fondo naranja muy diluido pero texto en tinta:
   el naranja aquí marca, no escribe (ver GUIA-ESTETICA §2). */
.legal-pendent {
  display: inline-block;
  font-family: var(--font-mono);
  font-size: 0.78rem;
  background: rgba(240, 138, 0, 0.16);
  color: var(--ink);
  padding: 0.05rem 0.4rem;
  border-radius: 4px;
}

.legal-nav {
  display: flex;
  flex-wrap: wrap;
  gap: 0.7rem 1.4rem;
  margin-top: 2.8rem;
  padding-top: 1.4rem;
  border-top: 1px solid var(--linea);
  font-size: 0.95rem;
}

@media (max-width: 480px) {
  /* a esta anchura la columna de etiquetas se come el valor: se apilan */
  .legal-dades { grid-template-columns: minmax(0, 1fr); gap: 0.1rem; }
  .legal-dades dd { margin-bottom: 0.7rem; }
  .legal-dades dt { padding-top: 0; }
}

/* ---------- Pie ---------- */
.footer {
  background: var(--ink);
  color: rgba(255, 255, 255, 0.82);
}
.footer-in {
  display: grid;
  grid-template-columns: 1fr auto;
  gap: 2rem 3rem;
  padding-block: 2.6rem 2rem;
}
.brand-name--footer { color: #fff; margin-top: 0.9rem; }
.footer-claim { font-size: 0.92rem; color: rgba(255, 255, 255, 0.6); margin-top: 0.4rem; }
.footer-tel {
  margin-top: 0.9rem;
  font-family: var(--font-mono);
  font-size: 1.02rem;
  font-weight: 600;
  /* la mono abre mucho los dígitos a este cuerpo: el número se leía como seis bloques
     sueltos en vez de como un teléfono. Medido contra tres ajustes: este es el único
     que agrupa 93 · 886 · 10 · 65 sin salir de la mono (GUIA-ESTETICA §3). */
  letter-spacing: -0.07em;
  word-spacing: -0.14em;
}
/* en el pie de la home el enlace lleva el icono del teléfono, como en la barra de
   utilidades. El subrayado va en el <span>: si va en el enlace, cruza también el icono. */
.footer-tel a { color: var(--verde); text-decoration-color: var(--verde); text-underline-offset: 3px; }
.footer-tel a:hover { color: var(--paper); }
.footer-brand .footer-tel a { display: inline-flex; align-items: center; gap: 0.45rem; text-decoration: none; }
.footer-brand .footer-tel svg { width: 16px; height: 16px; flex-shrink: 0; }
.footer-brand .footer-tel a span { text-decoration: underline; text-decoration-color: var(--verde); text-underline-offset: 3px; }

/* datos de administracion: presentes, pero sin competir con el telefono */
.footer-mini {
  list-style: none;
  margin-top: 1rem;
  display: grid;
  gap: 0.3rem;
  font-size: 0.85rem;
}
.footer-mini li { display: grid; gap: 0.1rem; }
.footer-mini a { color: rgba(255, 255, 255, 0.82); text-decoration-color: rgba(133, 187, 58, 0.6); overflow-wrap: anywhere; }
.footer-mini a:hover { color: var(--verde); }

.footer-col h4 {
  font-family: var(--font-mono);
  font-size: 0.74rem;
  font-weight: 600;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: var(--verde);
  margin-bottom: 0.9rem;
}
.footer-col ul { list-style: none; display: grid; gap: 0.45rem; font-size: 0.95rem; }
.footer-col a { color: rgba(255, 255, 255, 0.82); text-decoration-color: rgba(133, 187, 58, 0.6); overflow-wrap: anywhere; }
.footer-col a:hover { color: var(--verde); }
.footer-legal {
  display: flex; flex-wrap: wrap; justify-content: space-between; gap: 0.6rem;
  /* el email es la cadena más larga del pie y no tiene dónde partir: sin esto desborda
     en cuanto el visitante amplía el texto */
  overflow-wrap: anywhere;
  padding-block: 1.1rem;
  border-top: 1px solid rgba(255, 255, 255, 0.12);
  font-size: 0.82rem;
  color: rgba(255, 255, 255, 0.55);
}
.footer-legal a { color: rgba(255, 255, 255, 0.72); text-decoration-color: rgba(133, 187, 58, 0.6); }
.footer-legal a:hover { color: var(--verde); }
/* pie de las páginas legales: sin la rejilla de arriba, la línea no necesita borde */
.footer--curt .footer-legal { border-top: none; padding-block: 1.8rem; }

/* ---------- WhatsApp flotante ---------- */
.wa-float {
  position: fixed;
  right: 1.1rem; bottom: 1.1rem;
  z-index: 60;
  width: 52px; height: 52px;
  border-radius: 50%;
  display: grid; place-items: center;
  background: var(--verde);
  color: var(--ink);
  box-shadow: 0 8px 22px rgba(31, 42, 22, 0.28);
  transition: transform 0.15s ease, background-color 0.15s ease;
}
/* hover #96cc4b: el --verde un punto más claro, igual que #ffa227 lo es del naranja.
   Documentado en GUIA-ESTETICA.md §3. */
.wa-float:hover { transform: translateY(-3px); background: #96cc4b; }
.wa-float svg { width: 27px; height: 27px; }

/* ---------- Reveal por scroll ----------
   Quién pone estas dos clases, y por qué importa:
     .js           la pone el <script> en línea del <head>. Es la que OCULTA, así que sin
                   JavaScript no se oculta nada y la página se lee entera.
     .no-observer  la pone ese mismo script cuando ya sabe que no habrá animación:
                   movimiento reducido, navegador sin IntersectionObserver o ?qa=flat.
                   Decidirlo en el <head> —y no al final del <body>, como se hacía— evita
                   que el CSS y el JS opinen distinto durante el primer pintado.
   Y el seguro: como .js oculta y quien destapa es main.js, si main.js no llegara a
   cargarse la página se quedaría medio en blanco. El script del <head> programa retirar
   .js a los 3 s y main.js lo desarma al arrancar. Por eso aquí no hace falta nada más. */
.js .reveal {
  opacity: 0;
  transform: translateY(16px);
  transition: opacity 0.55s ease, transform 0.55s cubic-bezier(0.2, 0.7, 0.2, 1);
}
.js .reveal.is-visible { opacity: 1; transform: none; }
.js.no-observer .reveal { opacity: 1; transform: none; }

/* ---------- Movimiento reducido ---------- */
@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    animation-delay: 0s !important;
    transition-duration: 0.01ms !important;
  }
  .reveal { opacity: 1; transform: none; }
  .ring-path, .leaf-path { stroke-dashoffset: 0; animation: none; }
  /* el filete de las tarjetas de «Com treballem» ya dibujado, sin trazo */
  .why-card { background-size: 100% 4px; }
  /* el chip de «Qualitat» ya puesto, sin entrada propia */
  .cert-num { opacity: 1; transform: none; }
  /* la tarjeta de segmento deja de crecer; el desenfoque del resto se queda, porque
     marca dónde está el puntero y no es movimiento */
  .seg-card:hover, .seg-card:has(:focus-visible), .cat-card:hover { scale: 1; }
}

/* ---------- Responsive ---------- */
@media (max-width: 960px) {
  .hero-ring { opacity: 0.28; right: -30%; }
  .contacto-grid { grid-template-columns: minmax(0, 1fr); }
}

/* ≤860: la navegación se pliega en un desplegable y las acciones secundarias
   (comandas, teléfono) bajan dentro de él. En la barra solo queda el CTA. */
@media (max-width: 860px) {
  .header-in { padding-block: 0.55rem; gap: 0.7rem; min-height: 60px; }
  .brand { margin-right: auto; }
  .nav { margin-right: 0; }
  .nav-toggle { display: inline-flex; }
  /* panel desplegable bajo la barra: el sticky se queda en una sola fila */
  /* El panel cuelga de la cabecera, que es sticky: lo que sobresalga por debajo del
     viewport NO se alcanza haciendo scroll, porque el panel baja pegado a la cabecera.
     Medido en apaisado: a 568×320 se perdían 42px —el enlace del teléfono entero— y a
     740×360, 2px. Con techo propio y scroll interno el panel siempre se recorre entero.
     El `100vh` va primero como reserva para los navegadores sin `dvh`. Se descuentan
     94px y no 60: el panel cuelga de la cabecera (60px) pero ARRIBA del todo la barra de
     utilidades (34px) todavía está en pantalla, porque no es sticky y solo se va al hacer
     scroll. Con 60px el panel seguía saliéndose 34px justo en el momento en que se abre,
     que es cuando la página está sin desplazar. Descontando los dos, el techo vale para
     el caso peor y sobra holgura una vez se ha bajado.
     `overscroll-behavior` evita que al llegar al final del panel el gesto siga
     arrastrando la página por debajo. */
  .nav-links {
    display: none;
    position: absolute;
    left: 0; right: 0; top: 100%;
    flex-direction: column;
    gap: 0;
    background: var(--paper);
    border-block: 1px solid var(--linea);
    box-shadow: var(--sombra);
    padding: 0.2rem clamp(1.1rem, 4vw, 2rem) 0.7rem;
    max-height: calc(100vh - 94px);
    max-height: calc(100dvh - 94px);
    overflow-y: auto;
    overscroll-behavior: contain;
  }
  .nav-links.is-open { display: flex; }
  .nav-links li + li { border-top: 1px solid var(--linea); }
  .nav-links a { padding: 0.75rem 0.2rem; font-size: 1rem; }
  /* el subrayado animado no tiene sentido en una lista vertical */
  .nav-links a::after { display: none; }
  .nav-links a.is-actiu { color: var(--naranja-deep); }
  .nav-nomes-mobil { display: block; }
  .nav-links a.nav-comandes { color: var(--verde-deep); font-weight: 600; }
  .nav-links a.nav-tel { font-family: var(--font-mono); font-weight: 600; }

  .btn-comandes { display: none; }
  .brand { gap: 0.4rem; margin-right: auto; }
  .brand-logo { width: 32px; height: 36px; }
  .brand-name { font-size: 1.02rem; }
  .header-cta { gap: 0.5rem; }
  .header-cta .btn { padding: 0.45rem 0.8rem; font-size: 0.82rem; white-space: nowrap; }

  .form-row--2col { grid-template-columns: minmax(0, 1fr); }
  .footer-in { grid-template-columns: minmax(0, 1fr); gap: 1.6rem; }
}

/* ≤620: el botón de envío ocupa el ancho del panel —es el objetivo principal— y la
   nota baja debajo en lugar de partirse en dos palabras por línea */
@media (max-width: 620px) {
  /* `minmax(0, 1fr)`, igual que en .form y .form-row: la columna implícita se dimensiona
     al min-content del botón y de la nota. */
  .form-accio { display: grid; grid-template-columns: minmax(0, 1fr); gap: 0.6rem; }
  .form-accio .btn { width: 100%; }
  .form-nota { max-width: none; }
}

/* CTA de cabecera: versión corta solo en pantallas muy estrechas */
.cta-short { display: none; }
@media (max-width: 560px) {
  .cta-full { display: none; }
  .cta-short { display: inline; }
  /* En la home la barra se queda solo con el estado: el teléfono ya está dentro del menú
     desplegable (.nav-tel) y en el botón flotante, así que repetirlo aquí solo aprieta
     una barra de 34px.
     Las demás páginas no tienen ni menú ni flotante —cabecera secundaria, ver
     comandes.html y las tres legales—, así que allí esta es la ÚNICA vía rápida al
     teléfono y se queda. */
  .topbar-tel { display: none; }
  .pagina-comandes .topbar-tel,
  .pagina-legal .topbar-tel { display: inline-flex; }
  /* el botón de menú pasa a icono. El texto se oculta VISUALMENTE, no con
     display:none, o el botón se quedaría sin nombre accesible.
     Al quedarse sin texto el contenido del botón es una barra de 2px, así que el objetivo
     táctil caía a 39×20 —por debajo del mínimo de 24×24 y justo en los anchos de móvil—.
     El mínimo de 40px lo devuelve a la medida del CTA de al lado (39px de alto) y cabe de
     sobra en la cabecera de este tramo: 60px menos 0.55rem de padding arriba y abajo. */
  .nav-toggle {
    padding: 0.5rem 0.65rem;
    min-width: 40px; min-height: 40px;
    justify-content: center;
  }
  .header-in { gap: 0.5rem; }
  .nav-toggle-txt {
    position: absolute; width: 1px; height: 1px;
    clip-path: inset(50%); overflow: hidden; white-space: nowrap;
  }
}

/* solo en las pantallas más estrechas manda el logo. El corte está medido: a 390px
   el nombre convive con el menú y el CTA con 17px de holgura; a 375px solo con 2px,
   que la fuente de reserva se comería mientras carga la webfont. */
@media (max-width: 389px) {
  .header .brand-name { display: none; }

  /* En comandes y en las legales la barra lleva estado Y teléfono (ver el corte de 560),
     y por debajo de 390px no caben en una fila: «Atenem a partir de les 17:00» perdía
     justo la hora. Se parte en dos líneas en vez de recortarse. La barra no es sticky,
     así que crecer 18px solo afecta a lo primero que se ve y se va con el scroll.
     En la home no cambia nada: allí el teléfono ya está oculto desde los 560. */
  .topbar-in { flex-wrap: wrap; justify-content: flex-start; row-gap: 0.1rem; }
  .topbar-estat { flex-basis: 100%; }
  .estat-text { white-space: normal; overflow: visible; }
}
