/* --- DESIGN SYSTEM & VARIABLES --- */
:root {
    /* Colors: single light theme. White base reads as a clean, premium
       factory, matching the B2B/industrial clients (Ford, agro, indústria)
       better than the streetwear-coded dark theme the site used to ship —
       there is no dark mode or toggle anymore (removed 2026-08). */
    --color-bg: #ffffff;
    --color-bg-alt: #f6f6f4;
    --color-surface: #ffffff;
    --color-surface-hover: #f0f0ee;
    --color-border: #e2e2df;
    /* --color-border is 1.3:1 on white — fine as a decorative divider between
       cards and their own tinted section background, but not enough for a
       boundary that's the *only* signal of a control's shape (WCAG 1.4.11
       Non-text Contrast requires 3:1). Used where border alone marks the
       edge of an interactive control, e.g. the contact form's text inputs
       sitting on the white .glass card. */
    --color-border-strong: #8f8f8c;

    --color-text: #161616;
    --color-text-muted: #5c5c5c;

    /* Cinza dos títulos: o texto que *não* está em destaque dentro de um
       h1/h2. Ver .text-gradient — sem uma cor de marca, o destaque passou a
       ser feito por contraste tonal dentro do próprio título. 5,3:1 no
       branco e 5,0:1 na banda --color-bg-alt, acima do AA em ambos. */
    --color-title-muted: #6e6e6e;

    --color-primary: #0a0a0a;
    --color-primary-hover: #333333;

    /* Grafite no lugar do azul petróleo. O site é preto/branco/cinza desde
       2026-08 (pedido do cliente, item 1 do brief): a marca vende para
       empresas, eventos, agro e indústria, e o azul era o único ponto de cor
       de uma página que já era neutra em tudo o mais.
       Estes dois tokens continuam significando "destaque de marca" — botão
       primário, borda superior de seção, faixa CTA — só que agora em tinta,
       não em matiz. Um tom mais claro que --color-graphite (#121212) de
       propósito, para a faixa CTA não se confundir com navbar e footer. */
    --color-accent: #2b2b2b;
    --color-accent-hover: #454545;

    /* Graphite: the deliberate dark bookend on navbar/footer/mobile dropdown,
       set against the otherwise all-white page (see their own comments). */
    --color-graphite: #121212;

    /* Typography */
    --font-sans: 'Outfit', -apple-system, BlinkMacSystemFont, sans-serif;

    /* Spacing */
    --space-1: 0.5rem;
    --space-2: 1rem;
    --space-3: 1.5rem;
    --space-4: 2rem;
    --space-6: 3rem;
    --space-8: 4rem;
    --space-12: 6rem;
    --space-14: 7.5rem;
    --space-16: 8rem;

    /* Effects */
    --radius-sm: 4px;
    --radius-md: 8px;
    --radius-lg: 16px;
    --radius-full: 9999px;

    --transition-fast: 0.15s ease;
    --transition-normal: 0.3s ease;
    --transition-slow: 0.6s cubic-bezier(0.16, 1, 0.3, 1);
}

/* --- RESET --- */
* {
    margin: 0;
    padding: 0;
    box-sizing: border-box;
}

html {
    scroll-behavior: smooth;
    /* Belt-and-suspenders with body's overflow-x below: a fixed-position element's
       100% width can resolve against html's overflowed content width instead of
       the true viewport in some engines (seen here via the Elfsight widget's
       off-screen carousel items), pushing the navbar wider than the screen. */
    overflow-x: hidden;
}

body {
    background-color: var(--color-bg);
    color: var(--color-text);
    font-family: var(--font-sans);
    line-height: 1.6;
    overflow-x: hidden;
}

a {
    color: inherit;
    text-decoration: none;
    transition: color var(--transition-normal);
}

ul {
    list-style: none;
}

img,
video {
    max-width: 100%;
    display: block;
}

/* --- UTILITIES --- */
/* 1440px, não 1200 (2026-08-12). O gatilho foi o hero: numa tela de 1900px o
   vídeo ocupava ~32% da largura contra os ~46% da projeção que o cliente
   montou, e dentro de um container de 1200 não havia como crescer. Alargar só
   o hero deixaria a navbar (que usa este mesmo .container) ~120px mais estreita
   que o conteúdo logo abaixo dela — as duas peças mais visíveis da página
   desalinhadas entre si. Alargar tudo mantém o alinhamento e ainda elimina a
   exceção: a seção "5 Passos" já usava 1440 desde que o carrossel foi
   calibrado.

   O que segura a medida de leitura não é este teto e sim os max-width locais
   (.section-description, .hero-subtitle e afins) — se um parágrafo novo esticar
   demais numa tela larga, o lugar de resolver é lá, não aqui. */
.container {
    width: 100%;
    max-width: 1440px;
    margin: 0 auto;
    padding: 0 var(--space-4);
}

.text-center {
    text-align: center;
}

/* Skip link — invisível até receber foco por teclado (Tab a partir da barra
   de endereço). Deixa quem navega sem mouse/leitor de tela pular a navbar
   inteira e ir direto pro conteúdo, em vez de tabular por todos os links
   do menu a cada carregamento de página. */
.skip-link {
    position: absolute;
    top: -100%;
    left: var(--space-4);
    z-index: 200;
    background: var(--color-primary);
    color: #ffffff;
    padding: var(--space-2) var(--space-4);
    border-radius: var(--radius-md);
    font-weight: 600;
    transition: top var(--transition-fast);
}

.skip-link:focus {
    top: var(--space-2);
}

.section-padding {
    padding: var(--space-14) 0;
}

/* O navbar é `position: fixed`, então um salto de âncora (#passos, #contato,
   links do menu/rodapé) parava a seção em top:0 e os ~74px da barra comiam todo
   o respiro do topo — o título encostava na barra. Compensa a altura da barra
   já rolada (73,6px no desktop; 60px no mobile, ver breakpoint) mais uma folga.
   Vale junto com o `scroll-behavior: smooth` já definido no html. */
section[id] {
    scroll-margin-top: 6rem;
}

/* Não é mais gradiente — o nome ficou por causa dos 9 títulos que já usam a
   classe no HTML.

   Antes era um degradê de dois tons do azul de marca. Sem cor de marca, um
   degradê cinza sobre um título quase preto seria *menos* tinta que o texto
   ao redor: o trecho em destaque leria como apagado, o oposto do que a
   classe existe para fazer.

   A solução é inverter quem se destaca: o trecho marcado fica no preto mais
   forte da página e o *resto* do título recai para --color-title-muted (ver
   .section-title / .hero-title). O destaque continua sendo o ponto mais
   escuro da linha, agora por contraste tonal em vez de matiz.

   O -webkit-text-fill-color precisa voltar explicitamente: sem isso o
   `transparent` da regra antiga sobreviveria e o texto sumiria. */
.text-gradient {
    color: var(--color-primary);
    -webkit-text-fill-color: var(--color-primary);
}

/* Era glassmorphism (translúcido + backdrop-filter), herdado do tema escuro.
   Com um tema só, todo fundo atrás do card é chapado: o blur não tem o que
   desfocar e ainda custa caro em 56 cards do configurador. Virou superfície
   sólida — quem precisa destacar fica sobre uma seção tonalizada. */
.glass {
    background: var(--color-surface);
    border: 1px solid var(--color-border);
}

/* --- TYPOGRAPHY --- */
h1,
h2,
h3,
h4 {
    line-height: 1.1;
    font-weight: 700;
    letter-spacing: -0.02em;
}

/* Cinza, e não o --color-text do corpo: o trecho em <span class="text-gradient">
   é que fica preto. Ver o comentário da .text-gradient. */
.section-title {
    font-size: clamp(2rem, 4vw, 3.5rem);
    margin-bottom: var(--space-4);
    color: var(--color-title-muted);
}

.section-subtitle {
    font-size: 1.125rem;
    color: var(--color-text-muted);
    text-transform: uppercase;
    letter-spacing: 0.1em;
}

.section-description {
    font-size: 1.25rem;
    color: var(--color-text-muted);
    max-width: 600px;
    margin: 0 auto var(--space-8);
}

/* --- BUTTONS --- */
.btn {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: var(--space-2);
    padding: var(--space-2) var(--space-4);
    border-radius: var(--radius-full);
    font-weight: 600;
    cursor: pointer;
    border: none;
    transition: all var(--transition-normal);
}

/* Caixa alta só nos CTAs primários (pedido do cliente, 2026-08-11: o "Solicitar
   Orçamento" precisava saltar mais). Fica na classe, e não no texto do HTML,
   para o conteúdo continuar legível na fonte e nos leitores de tela. Os
   secundários (catálogo, "tirar uma dúvida", fallback) ficam em caixa mista de
   propósito — se tudo grita, nada grita. */
.btn-primary {
    background-color: var(--color-accent);
    color: #ffffff;
    text-transform: uppercase;
    letter-spacing: 0.06em;
    font-weight: 700;
}

/* Havia aqui uma varredura de brilho (um ::after com gradiente rotacionado,
   clipado por overflow: hidden) que o cliente reprovou em 2026-08-11: lia como
   um corte atravessando o botão, não como brilho. A causa era a geometria — um
   linear-gradient(115deg) dentro de uma caixa de 40% × 200% tem o eixo quase na
   horizontal, então a transição entre as paradas de cor virava uma faixa reta
   cruzando a pílula. Não vale recalibrar o ângulo: o hover já muda a cor, eleva
   o botão e projeta sombra, três sinais para um gesto só. Se algum dia voltar um
   efeito decorativo aqui, ele precisa de `position: relative` e
   `overflow: hidden` de volta no .btn-primary. */
.btn-primary:hover {
    background-color: var(--color-accent-hover);
    transform: translateY(-2px);
    /* Sombra neutra: a rgba(14,75,94,…) daqui era resto do accent azul-petróleo
       e destoava desde que a paleta virou monocromática. */
    box-shadow: 0 6px 18px rgba(0, 0, 0, 0.28);
}

/* Mesmo padrão do resto do arquivo: sem movimento, a sombra e a troca de cor
   sozinhas já marcam o hover. */
@media (prefers-reduced-motion: reduce) {
    .btn-primary:hover {
        transform: none;
    }
}

.btn-secondary {
    background-color: transparent;
    color: var(--color-text);
    border: 1px solid var(--color-border);
}

.btn-secondary:hover {
    background-color: var(--color-surface-hover);
    border-color: var(--color-text-muted);
}

.btn-large {
    padding: var(--space-4) var(--space-8);
    font-size: 1.125rem;
}

/* O CTA do hero é o único botão da primeira dobra: ganha sombra em repouso (os
   demais só no hover) para ler como elemento clicável antes de qualquer
   interação. */
.hero-cta .btn-primary {
    box-shadow: 0 4px 14px rgba(0, 0, 0, 0.22);
    /* 26rem = a largura de tinta da fileira de selos logo abaixo (415px na raiz
       de 16px). No tamanho natural o botão media 361px contra os 415px dos
       selos: as duas peças partiam da mesma margem esquerda mas fechavam em
       pontos diferentes, e o centro do botão caía 27px à esquerda do centro dos
       selos. Alargar até a borda direita deles fecha o retângulo dos dois lados
       sem tirar o botão do eixo esquerdo que título, subtítulo e selos
       compartilham — centralizar o botão seria pior, ele viraria o único
       elemento da coluna fora dessa margem.
       O `min()` é o que segura a regra: `min-width` ganha de `max-width` na
       cascata, então um teto separado não impediria o transbordo — abaixo de
       ~1100px o 100% assume e o botão volta a caber na coluna (onde ele já
       ocupava a largura toda). Em rem, e não px, porque a largura dos selos
       também é ditada por texto: se a raiz mudar, os dois escalam juntos. */
    min-width: min(100%, 26rem);
}

.btn-block {
    width: 100%;
}

.btn:disabled {
    opacity: 0.6;
    cursor: not-allowed;
}

.btn-primary:disabled:hover {
    transform: none;
    box-shadow: none;
}

/* --- NAVBAR --- */
/* Grafite translúcido, e não branco: sobre a página branca o navbar branco não
   se separava do conteúdo, e o blur só deixava um borrão cinza do texto passando
   por baixo. O escuro ancora o topo e faz o logo aparecer. É a "faixa em grafite"
   que o PDF sugeriu para separar áreas. */
.navbar {
    position: fixed;
    top: 0;
    left: 0;
    width: 100%;
    z-index: 100;
    /* Resting padding trimmed from --space-4 (2rem) to --space-3 (1.5rem):
       the fuller value made the bar feel oversized before any scroll had
       happened. Still noticeably shrinks to --space-2 (1rem) on scroll. */
    padding: var(--space-3) 0;
    background: color-mix(in srgb, var(--color-graphite) 88%, transparent);
    backdrop-filter: blur(12px);
    -webkit-backdrop-filter: blur(12px);
    transition: padding var(--transition-normal), background-color var(--transition-normal);
    /* Padding é propriedade de layout, e a transição de fato roda um layout por
       frame enquanto interpola (medido: 367 layouts contra 64 sem animar). O que
       mantém isso barato não é a frequência da troca de classe — é o escopo:
       position:fixed tira o elemento do fluxo (o reflow não cascateia para a
       página) e `contain: layout style` limita o recálculo a ~15 nós aqui dentro.
       Medido com CPU 6x lenta: 8ms por transição, ~1,3ms em hardware real,
       diluídos em 300ms de animação — 0,4% do orçamento de frame, zero frames
       perdidos. Trocar por scaleY/translateY eliminaria o layout, mas quebraria
       o backdrop-filter, o posicionamento do dropdown mobile e a área de clique.
       Não `paint`: o dropdown mobile transborda esta caixa de propósito, e a
       contenção de pintura o cortaria. */
    contain: layout style;
}

.navbar.scrolled {
    background: color-mix(in srgb, var(--color-graphite) 95%, transparent);
    padding: var(--space-2) 0;
}

/* Menu mobile aberto: a barra fica 100% opaca, igual ao dropdown que desce
   dela. Translúcida (88/95% + blur) contra um dropdown sólido, as duas
   superfícies encostadas ficavam em tons visivelmente diferentes e a emenda
   aparecia como uma faixa atravessando o logo e o X. Same-color em ambas =
   um bloco só. Vence .scrolled por vir depois com a mesma especificidade. */
.navbar.menu-open,
.navbar.menu-open.scrolled {
    background: var(--color-graphite);
}

/* Logo é preto sobre transparente — inverte para branco no topo escuro. */
.navbar .logo-img {
    filter: invert(1);
}

/* O `.btn` padrão (~58px de altura) é o item mais alto da barra e sozinho
   dita a altura toda do navbar em repouso, já que logo e links de texto são
   bem mais baixos. Fica compacto aqui em vez de mexer em `.btn` (usado também
   no hero e no formulário). Restaurado ao padding padrão no dropdown mobile,
   onde o alvo de toque de ~44px importa mais que a altura da barra fixa — ver
   o breakpoint de 768px abaixo.

   Invertido em 2026-08-11: branco com texto grafite, ao contrário de todo outro
   .btn-primary do site. Ele herdava `background: var(--color-accent)` (#2b2b2b)
   sobre uma barra `rgba(18,18,18,.88)` — grafite sobre grafite, poucos pontos de
   luminância separando os dois. Era por isso que sumia e não lia como botão: o
   que identifica um botão à distância é o contraste da superfície contra o
   fundo, não o texto dentro dela. Como a barra é escura, a superfície de
   destaque tem de ser clara. O :hover clareia mais um degrau em vez de
   escurecer, senão andaria de volta na direção do fundo.

   Atenção à escala de espaçamento ao mexer neste padding: ela pula números
   (1, 2, 3, 4, 6, 8, 12, 14, 16) e **não existe `--space-5`**. Um `var()` que
   não resolve invalida a declaração inteira no tempo de computação, e `padding`
   cai para o valor inicial — zero, não o valor herdado do `.btn`. Foi o que
   aconteceu aqui numa primeira tentativa: o botão perdeu todo o padding e virou
   um adesivo colado no texto. */
.navbar .btn-nav {
    padding: var(--space-1) var(--space-4);
    /* #f4f4f4 e não #fff puro (recomendação do designer, 2026-08-11): sobre a
       barra grafite o branco puro é o ponto de maior luminância da tela inteira
       e brigava com o logo, que é o elemento que deveria ganhar. Um degrau
       abaixo mantém o contraste que faz o botão existir e devolve a primazia
       ao logo. Peso 600, não os 700 herdados do .btn-primary: em caixa alta
       sobre fundo claro, 700 fecha demais o miolo das letras. */
    background-color: #f4f4f4;
    color: #111111;
    font-weight: 600;
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.28);
}

.navbar .btn-nav:hover {
    background-color: #eaeaea;
    box-shadow: 0 4px 14px rgba(0, 0, 0, 0.35);
}

/* O anel de foco padrão do site é escuro e desapareceria nesta barra. */
.navbar .btn-nav:focus-visible {
    outline: 2px solid #ffffff;
    outline-offset: 3px;
}

/* O `gap` de --space-6 (48px) entre os itens já era folgado; o que faltava era
   área clicável. Sem padding, o alvo tinha só a altura da caixa de texto (~19px)
   e o hover disparava/soltava em pixels de diferença. O padding vertical não
   mexe na altura da barra, que é ditada pelo .btn-nav, mais alto. */
.navbar .nav-links a:not(.btn) {
    position: relative;
    padding: var(--space-1) 0;
    color: rgba(255, 255, 255, 0.72);
    transition: color var(--transition-fast);
}

/* Sublinhado animado no hover — reforça o link sem precisar de cor nova.
   Só faz sentido na barra desktop; no dropdown mobile os links já têm um
   divisor (border-bottom) por baixo, então o traço fica desligado ali
   (ver breakpoint de 768px). */
.navbar .nav-links a:not(.btn)::after {
    content: '';
    position: absolute;
    left: 0;
    /* Acompanha o padding vertical do link: com a caixa maior, o antigo -4px
       jogaria o traço longe demais do texto. */
    bottom: calc(var(--space-1) - 4px);
    width: 100%;
    height: 1px;
    background: #ffffff;
    transform: scaleX(0);
    transform-origin: left;
    transition: transform var(--transition-fast);
}

.navbar .nav-links a:not(.btn):hover {
    color: #ffffff;
}

.navbar .nav-links a:not(.btn):hover::after {
    transform: scaleX(1);
}

.navbar .menu-toggle {
    color: #ffffff;
}

/* Anel de foco branco para os controles que ficam sobre o grafite. O padrão
   do site é `2px solid var(--color-primary)` (#0a0a0a), que sobre a barra
   escura fica invisível — sem uma regra própria, o navegador desenhava o
   anel default dele (aquele retângulo alaranjado em volta do X). */
.navbar .menu-toggle:focus-visible,
.navbar .nav-links a:focus-visible {
    outline: 2px solid #ffffff;
    /* 1px, não 3px: o botão de menu já encosta na borda direita da tela
       (padding + margin negativa), e um offset maior jogava o anel para fora
       do viewport. */
    outline-offset: 1px;
    border-radius: var(--radius-sm);
}

.navbar-content {
    display: flex;
    justify-content: space-between;
    align-items: center;
}

.logo-img {
    height: 28px;
    width: auto;
}

.footer-logo-img {
    height: 32px;
    /* Preto sobre transparente, igual ao do navbar — inverte para o rodapé escuro. */
    filter: invert(1);
}

.nav-links {
    display: flex;
    align-items: center;
    gap: var(--space-6);
}

.nav-links a:not(.btn) {
    font-weight: 500;
    color: var(--color-text-muted);
}

.nav-links a:not(.btn):hover {
    color: var(--color-primary);
}

.menu-toggle {
    display: none;
    background: none;
    border: none;
    color: var(--color-primary);
    cursor: pointer;
    /* Icon-only button — padding grows the tap target toward the ~44px
       guideline; the matching negative margin keeps the glyph's visual
       position flush with the edge it sat at before. */
    padding: var(--space-2);
    margin: calc(var(--space-2) * -1);
}

/* --- HERO SECTION (static, per client request) --- */
.hero {
    /* min-height: 100vh, not a padding trim. Padding was tuned down twice
       before (--space-8 → --space-6 here) to narrow the gap between the
       hero's bottom and .brands's accent top border, but "narrower" still
       broke on whatever viewport height wasn't tested against — the border
       kept resurfacing as a stray line with nothing attached to it on first
       paint. Pinning the hero to the full viewport guarantees .brands (and
       its border) starts below the fold on any screen, so it only appears
       once the visitor actually scrolls. */
    min-height: 100vh;
    display: flex;
    align-items: center;
    /* 144px em cima contra 48px embaixo parece desequilibrado e é justamente o
       contrário: a navbar é fixa e tem 90px, então ela come o topo. O ar que
       sobra visível é 144-90 = 54px acima contra 48px abaixo — praticamente
       igual, com uma sobra mínima em cima, que é o viés óptico correto.

       Era `--space-16 + --space-4` (160px), que dava 70 contra 48. Como o
       `align-items: center` reparte a folga restante meio a meio, essa
       diferença não diluía com a altura da tela: sobrava 22px a mais em cima em
       805px, 905px e 985px de viewport, sempre igual. Se a altura da navbar
       mudar, este número tem que mudar junto — é a única coisa que segura o
       equilíbrio. */
    padding: calc(var(--space-12) + var(--space-6)) 0 var(--space-6);
}

/* Sem override de largura aqui: o hero usa o .container padrão, que foi a 1440
   justamente por causa dele. */

.hero-grid {
    display: grid;
    /* Coluna de texto de 42% (era 38%) e gap de --space-6 (era --space-8).
       Os dois atacam o mesmo problema apontado pelo designer: a faixa de texto
       era estreita demais para o corpo do H1, o que empurrava o título para
       mais linhas curtas e ainda assim sobrava vão embaixo. Mais largura deixa
       o título respirar na horizontal, e o gap menor aproxima as duas colunas —
       o vídeo encolhe junto (ele é `1fr` com teto de 640px), o que reduz a
       altura da linha e, por tabela, o vão vertical. */
    grid-template-columns: minmax(300px, 42%) 1fr;
    gap: var(--space-6);
    /* `stretch` (padrão), não `start`. Era `start` porque a coluna de texto —
       H1 de 4 linhas + subtítulo + CTA + selo do Google + linha de confiança —
       ficava ~90px MAIS ALTA que o vídeo quadrado. Em 2026-08-11 caíram o selo,
       a linha de confiança e a palavra "personalizados" (que tirou uma linha do
       H1), e a relação se inverteu: agora o texto é bem mais baixo que o vídeo,
       e o vão que sobrava embaixo virou o buraco que o cliente apontou. Com as
       duas colunas esticadas até a mesma altura, o `margin-top: auto` do
       .hero-cta ancora o botão na base — o H1 encosta na borda de cima do vídeo
       e o botão na de baixo, fechando o retângulo.

       O corte 4:3 de 2026-08-12 chegou a quebrar esse encaixe (o vídeo ficou
       mais baixo que o texto), e as duas mudanças da mesma leva o refizeram:
       o container de 1440 devolveu altura ao vídeo e os selos de confiança
       alongaram a coluna de texto. Em 1884px de viewport as duas colunas medem
       ~605px — o encaixe voltou a ser exato, por coincidência calibrada. Quem
       mexer em qualquer um dos quatro (proporção do vídeo, largura do
       container, coluna de texto, selos) reabre a folga. */
    align-items: stretch;
    width: 100%;
}

/* Acima de 1200px o container do hero vai a 1440 e sobra largura, então a
   coluna de texto volta aos 38% de origem: 38% de 1376px ainda dão 523px de
   faixa — mais do que os 477px que os 42% rendiam no container de 1200, ou
   seja, a queixa do designer sobre o H1 apertado continua resolvida — e os
   ~90px que saem daqui vão para o vídeo. Também conserta a quebra do título,
   que a 42% virava "identidade da sua / marca" e deixava uma palavra órfã na
   última linha. Abaixo de 1200px o container é a própria viewport e não há
   folga para doar, então lá seguem valendo os 42%. */
@media (min-width: 1200px) {
    .hero-grid {
        grid-template-columns: minmax(300px, 38%) 1fr;
    }
}

/* Coluna flex só para o `margin-top: auto` do CTA ter contra o que empurrar.
   Sem `align-items`: no padrão `stretch` os filhos seguem ocupando a largura
   toda e quebram linha igual a antes. Trocar por `flex-start` os encolheria
   para `fit-content` e mudaria a quebra do H1. */
.hero-content {
    display: flex;
    flex-direction: column;
    text-align: left;
}

/* Entrelinha e espacejamento mais fechados que os do resto dos títulos (a regra
   h1..h4 usa 1.1 / -0.02em): o cliente marcou justamente os buracos entre as
   linhas e entre as palavras deste título. Como ele quebra em 4 linhas no
   desktop, o afrouxamento herdado somava, e o bloco perdia a leitura de massa
   única. Fica local ao .hero-title — mexer na regra compartilhada apertaria os
   9 .section-title junto. */
.hero-title {
    /* Subiu de clamp(2.5rem, 4.5vw, 4rem). Hierarquia era a primeira queixa do
       designer, e o título é a peça que a define: com o subtítulo em até
       1.375rem, o salto anterior no topo da escala era de ~2,9x e agora é de
       ~3,3x. O ganho de altura também come parte do vão acima do botão. */
    font-size: clamp(2.75rem, 5vw, 4.5rem);
    line-height: 0.98;
    letter-spacing: -0.035em;
    word-spacing: -0.04em;
    margin-bottom: var(--space-4);
    color: var(--color-title-muted);
}

.hero-subtitle {
    font-size: clamp(1.125rem, 2vw, 1.375rem);
    color: var(--color-text-muted);
    margin-bottom: var(--space-8);
}

/* `margin-top: auto` come toda a folga entre o subtítulo e o botão, ancorando o
   CTA na base da coluna — é o que alinha o botão com a borda inferior do vídeo.
   O `margin-bottom: var(--space-8)` do subtítulo continua valendo como piso
   mínimo caso a coluna de texto fique tão alta quanto o vídeo (telas estreitas,
   fonte maior), aí o auto simplesmente resolve para zero. */
.hero-cta {
    display: flex;
    margin-top: auto;
}

/* O selo da nota do Google (.hero-rating*) foi removido com o HTML dele em
   2026-08-11 e não voltou. Se voltar, o histórico do git tem as regras — e a
   decisão de pintar as estrelas em grafite, não dourado, para não quebrar a
   paleta monocromática.

   Os selos de confiança abaixo saíram na mesma leva e voltaram em 2026-08-12
   com outra forma: eram duas linhas de texto corrido com ícone de 16px, agora
   são três itens com ícone de 28px e duas linhas empilhadas (rótulo forte +
   complemento), como na projeção do cliente. Ficam DEPOIS do .hero-cta no DOM
   de propósito: o `margin-top: auto` do CTA empurra o conjunto CTA+selos para
   a base da coluna, então quem encosta na borda de baixo do vídeo passa a ser
   esta lista, não o botão. */
.hero-trust {
    display: flex;
    flex-wrap: wrap;
    gap: var(--space-2) var(--space-4);
    margin-top: var(--space-3);
}

.hero-trust li {
    display: flex;
    align-items: center;
    gap: var(--space-1);
}

/* `svg`, não `i`: o lucide.createIcons() substitui o <i data-lucide> por um
   <svg> novo, então uma regra escrita só para `i` para de valer no instante em
   que os ícones renderizam. O stroke fino segura o peso — a 28px o traço
   padrão de 2px do lucide competia com o botão logo acima. */
.hero-trust svg {
    width: 28px;
    height: 28px;
    stroke-width: 1.5;
    color: var(--color-accent);
    flex-shrink: 0;
}

.hero-trust-text {
    display: flex;
    flex-direction: column;
    line-height: 1.3;
    font-size: 0.8125rem;
    color: var(--color-text-muted);
}

.hero-trust-text strong {
    font-weight: 700;
    color: var(--color-primary);
}

.hero-image {
    display: flex;
    align-items: center;
    justify-content: center;
}

/* Moldura do vídeo. Carrega borda, raio e sombra (que ficavam no próprio
   <video>) porque a legenda .hero-media-caption é posicionada por cima e
   precisa ser recortada pelos mesmos cantos arredondados — daí o
   `overflow: hidden` aqui em vez de um border-radius no vídeo.

   Sombra rebaixada de 0 24px 48px / .16 e borda hairline acrescentada
   (recomendação do designer, 2026-08-11). A sombra pesada fazia o vídeo
   flutuar sobre a página em vez de pertencer a ela, e sem borda o fundo claro
   do próprio vídeo se dissolvia no branco da seção — a peça parecia não ter
   limite de um dos lados. A borda resolve o limite; a sombra fica só como
   profundidade, não como elevação. */
.hero-media {
    position: relative;
    width: 100%;
    /* Subiu de 640px junto com o container de 1440: sem folgar o teto, a coluna
       mais larga não chegava ao vídeo — ele continuava travado no mesmo tamanho
       e só ganhava margem branca em volta. Na prática o teto quase nunca morde
       (a coluna resolve para ~750px em 1900px de tela); ele existe para o vídeo
       não virar um bloco desproporcional em telas muito largas. */
    max-width: 820px;
    margin: 0;
    overflow: hidden;
    border-radius: var(--radius-lg);
    border: 1px solid var(--color-border);
    box-shadow: 0 18px 40px rgba(0, 0, 0, 0.10);
    background-color: var(--color-bg-alt);
}

/* O arquivo é o 1:1 do cliente, em qualquer largura de tela (o 9:16 saiu de uso
   em 2026-08-12 — ver o handler 10 do main.js). Não existe master mais largo:
   os .mov originais já vêm cortados. O retângulo 4:3 do desktop (pedido em
   2026-08-12, a partir de uma referência do cliente) é portanto um corte do
   quadrado feito aqui pelo `object-fit: cover`, que come 25% da altura.

   `object-position` fica em `top`, não no centro: o vídeo é uma montagem de
   ~12 planos e em quase todos o boné encosta no topo do quadro. Centrado, o
   corte decepa a copa e a marca bordada — que é justamente o produto: some o
   "Running", o topo do HUFF, o "SERTANEJINHO DO TELÓ" e a aba da viseira VW.
   Ancorando no topo, os 270px que saem vêm todos de baixo, onde só há queixo,
   pescoço e fundo vazio. Valores intermediários foram testados quadro a quadro
   (contact sheet com `fps=1,crop=1080:810:0:Y,tile=8x3`) e tanto 20% quanto
   40% ainda cortavam pelo menos três planos — só o topo salva todos. Refaça
   essa conferência se o cliente trocar o arquivo.

   No mobile este 4:3 vira 1:1, que é o corte nativo do arquivo — lá o cover não
   tira nada e o `object-position` acima fica sem efeito. Reserva a caixa antes
   do vídeo carregar, evitando salto de layout. */
.hero-image video {
    display: block;
    width: 100%;
    aspect-ratio: 4 / 3;
    object-fit: cover;
    object-position: center top;
}

/* Legenda sobre o vídeo (referência do cliente, 2026-08-12). O degradê não é
   decoração: o vídeo alterna planos de fundo branco e de fundo preto, então
   texto branco solto sumiria na metade dos quadros. A faixa escura garante
   contraste em qualquer frame sem precisar escurecer a peça inteira.

   Sem botão de play de propósito, embora a referência mostre um: o vídeo é
   autoplay/loop/mudo e o arquivo não tem faixa de áudio, então o botão não
   teria o que controlar — seria um alvo de clique que não faz nada. */
.hero-media-caption {
    position: absolute;
    left: 0;
    right: 0;
    bottom: 0;
    padding: var(--space-8) var(--space-3) var(--space-3);
    background: linear-gradient(to top,
            rgba(0, 0, 0, 0.78) 0%,
            rgba(0, 0, 0, 0.45) 45%,
            rgba(0, 0, 0, 0) 100%);
    /* A barra vertical vem da referência e é o que amarra as duas linhas num
       bloco só. Fica na figcaption (e não num wrapper extra) via padding do
       lado esquerdo do texto. */
    display: flex;
    flex-direction: column;
    pointer-events: none;
}

.hero-media-kicker,
.hero-media-note {
    border-left: 2px solid rgba(255, 255, 255, 0.9);
    padding-left: var(--space-1);
}

.hero-media-kicker {
    /* Caixa alta pela CSS, não no HTML — mesma razão do .btn-primary: o texto
       segue legível na marcação e o leitor de tela não soletra letra a letra. */
    text-transform: uppercase;
    letter-spacing: 0.08em;
    font-size: 0.8125rem;
    font-weight: 700;
    line-height: 1.4;
    color: #fff;
    padding-bottom: 2px;
}

.hero-media-note {
    font-size: 0.9375rem;
    line-height: 1.4;
    color: rgba(255, 255, 255, 0.86);
    padding-top: 2px;
}

/* --- BRANDS --- */
/* Logos soltas sobre uma faixa levemente tonalizada, em vez de um card por marca:
   as logos são coloridas (pedido do cliente) e 16 chips liam como tabela, não
   como mural de marcas. */
.brands {
    /* Sem borda de topo (removida de propósito): a transição hero → brands já
       troca layout inteiro — foto grande de produto vira grade de logos — e
       esse salto sozinho já lê como "seção nova". Empilhar a linha de accent
       em cima disso duplicava o sinal e quebrava a sensação de rolagem
       contínua. Mantém --space-8 de respiro no topo mesmo sem a borda pra
       ancorar e --space-12 embaixo, que é o único respiro entre as logos e os
       5 Passos desde que a faixa CTA que ficava aí no meio foi removida. */
    padding: var(--space-8) 0 var(--space-12);
    background: var(--color-bg-alt);
    position: relative;
    z-index: 1;
}

/* Flex em vez de grid porque o número de logos varia conforme o cliente manda
   arquivos novos: assim a última linha fica centralizada em vez de deixar um
   buraco à direita quando a contagem não é múltipla de 4. */
.brands-grid {
    display: flex;
    flex-wrap: wrap;
    justify-content: center;
    gap: var(--space-8) var(--space-6);
    margin-top: var(--space-8);
}

.brand-item {
    display: flex;
    align-items: center;
    justify-content: center;
    flex: 0 0 calc(25% - var(--space-6));
    height: 56px;
}

/* Cada arquivo vem com uma quantidade diferente de margem embutida — o viewBox
   do Serasa é um quadrado 700x700 para um logotipo horizontal, por exemplo — o
   que faria a mesma altura de caixa render tamanhos ópticos bem diferentes.
   `--logo-scale` corrige isso caso a caso, sem reeditar os arquivos. */
.brand-item img {
    width: 100%;
    height: 100%;
    object-fit: contain;
    transform: scale(var(--logo-scale, 1));
    transition: opacity var(--transition-normal);
}

.brand-item:hover img {
    opacity: 0.65;
}

/* --- SECTIONS --- */
main section {
    background-color: var(--color-bg);
    position: relative;
    z-index: 1;
}

/* A seção "Por que escolher a Union Fabril?" (.benefits-grid / .benefit-*) foi
   removida em 2026-08-11 a pedido do cliente, junto com as regras que a
   estilizavam. As duas fotos que ela usava continuam em assets/union/. */

/* --- COMO FUNCIONA --- */
/* Branca de propósito, e não tonalizada como era antes: com o formulário
   movido para logo depois dos 5 Passos, esta seção passou a vir logo abaixo de
   .contact, que é tonalizada. Duas bandas alt coladas leriam como um bloco só —
   é a mesma regra de ritmo do CLAUDE.md, só que a vizinhança mudou. É por isso
   que os cards .how-path abaixo carregam borda e sombra: sobre a seção branca,
   um card branco sem contorno não delimitaria nada. */

/* A lista numerada .how-steps ("Como funciona?", 4 passos) foi removida em
   2026-08-12 junto com as regras .how-step*: o bloco .how-choice abaixo passou
   a ser o conteúdo único da seção. */

/* Substituiu o par .how-note em 2026-08-12 (referência enviada pelo cliente).
   A referência distinguia os dois caminhos por matiz (verde x preto); como a
   página é monocromática, a distinção virou contorno x chapado. Só três coisas
   mudam entre os cards (círculo do ícone, tag e faixa do topo), justamente as
   que carregam cor na referência. */

/* O selo circular acima do título é decorativo (o <h2> logo abaixo já diz o que
   é), daí o aria-hidden no HTML. */
.how-choice-mark {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 56px;
    height: 56px;
    margin-bottom: var(--space-3);
    border-radius: var(--radius-full);
    background: var(--color-bg-alt);
    border: 1px solid var(--color-border);
    color: var(--color-accent);
}

.how-choice-mark svg {
    width: 24px;
    height: 24px;
}

/* Travado bem abaixo do container de 1440: são só duas frases por card, e na
   largura cheia cada uma cabia numa linha só, deixando o card com metade da
   caixa vazia. É o padrão do CLAUDE.md — quem lê largo demais em tela grande
   ganha teto local, o container não volta a encolher. */
.how-choice-grid {
    display: grid;
    grid-template-columns: repeat(2, 1fr);
    gap: var(--space-4);
    align-items: stretch;
    max-width: 1040px;
    margin: 0 auto;
}

/* Branco sobre a seção branca: aqui quem delimita é a borda mais a sombra
   baixa, como na referência. O card não pode ser --color-bg-alt porque o
   rodapé "Ideal para" usa esse tom para se destacar dentro dele — tonalizar o
   card inteiro apagaria a faixa. */
.how-path {
    display: flex;
    flex-direction: column;
    background: var(--color-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    overflow: hidden;
    box-shadow: 0 2px 12px rgba(0, 0, 0, 0.05);
}

/* Os dois caminhos são tratados igual desde 2026-08-12 (pedido do cliente:
   "deixar a primeira parte igual à 2"). Antes o card "seguro" vinha vazado
   (faixa tonalizada, círculo e tag de contorno) contra o "rápido" chapado, para
   separar as duas rotas sem usar matiz numa página monocromática. Agora nada
   distingue visualmente peça-piloto de produção direta — a diferença é só a
   copy. Se voltar a ser preciso separá-los, use vazado x chapado de novo: dois
   cinzas próximos (#5c5c5c x #2b2b2b) já foram testados e somem a 60cm de
   distância. */
.how-path-head {
    display: flex;
    justify-content: center;
    padding: var(--space-4) var(--space-4) var(--space-3);
    background: var(--color-surface);
    border-bottom: 1px solid var(--color-border);
}

.how-path-icon {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 64px;
    height: 64px;
    border-radius: var(--radius-full);
    background: var(--color-accent);
    border: 2px solid var(--color-accent);
    color: #ffffff;
}

.how-path-icon svg {
    width: 30px;
    height: 30px;
}

.how-path-body {
    display: flex;
    flex-direction: column;
    align-items: center;
    text-align: center;
    gap: var(--space-2);
    padding: var(--space-4);
    flex: 1;
}

.how-path-title {
    font-size: 1.5rem;
    color: var(--color-primary);
}

/* Cantos retos de propósito: todo botão do site é pílula (--radius-full), e uma
   tarja grafite em caixa alta com canto arredondado seria lida como CTA — não
   há nada para clicar aqui. */
.how-path-tag {
    display: inline-block;
    padding: 0.4375rem 0.875rem;
    border-radius: var(--radius-sm);
    background: var(--color-accent);
    border: 1px solid var(--color-accent);
    color: #ffffff;
    font-size: 0.8125rem;
    font-weight: 700;
    letter-spacing: 0.04em;
    text-transform: uppercase;
}

.how-path-text {
    color: var(--color-text-muted);
    /* A régua sobre o texto repete o corte da referência e separa o rótulo do
       corpo sem acrescentar mais um elemento ao HTML. */
    padding-top: var(--space-2);
    border-top: 1px solid var(--color-border);
    width: 100%;
}

/* Empurrado para o pé do card para que os dois rodapés fiquem alinhados mesmo
   com textos de alturas diferentes. */
.how-path-note {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    width: 100%;
    margin-top: auto;
    padding: var(--space-2);
    border-radius: var(--radius-md);
    background: var(--color-bg-alt);
    text-align: left;
    color: var(--color-text);
    font-size: 0.9375rem;
}

.how-path-check {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 26px;
    height: 26px;
    flex-shrink: 0;
    border-radius: var(--radius-full);
    background: var(--color-accent);
    color: #ffffff;
}

.how-path-check svg {
    width: 15px;
    height: 15px;
    stroke-width: 3;
}

.how-choice-footer {
    display: flex;
    align-items: center;
    justify-content: center;
    gap: var(--space-1);
    margin-top: var(--space-4);
    color: var(--color-text-muted);
    font-size: 1.0625rem;
}

.how-choice-footer strong {
    color: var(--color-primary);
}

.how-choice-footer svg {
    width: 20px;
    height: 20px;
    flex-shrink: 0;
    color: var(--color-accent);
}

/* --- ABOUT --- */
/* `stretch` + foto absoluta: o arquivo é retrato (1200x1500) e, solto com
   `height: auto`, ficava ~200px mais alto que a coluna de texto ao lado — as
   duas metades não pareciam a mesma seção. Absoluta, a foto não entrega altura
   intrínseca para a linha do grid, então quem define a altura é o texto e a
   imagem preenche exatamente esse espaço via `object-fit: cover`. Uma
   `aspect-ratio` fixa não resolveria: a altura do texto muda com a largura da
   viewport (mais quebras de linha), e o descompasso voltaria com outro sinal. */
.about-container {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: var(--space-12);
    align-items: stretch;
}

.about-text {
    color: var(--color-text-muted);
    font-size: 1.125rem;
    margin-bottom: var(--space-4);
}

.about-image-wrapper {
    position: relative;
    min-height: 380px;
    border-radius: var(--radius-lg);
    overflow: hidden;
}

.about-image {
    position: absolute;
    inset: 0;
    display: block;
    width: 100%;
    height: 100%;
    object-fit: cover;
}

.about-highlights {
    display: flex;
    flex-direction: column;
    gap: var(--space-3);
    margin-bottom: var(--space-6);
}

.about-highlights li {
    display: flex;
    align-items: center;
    gap: var(--space-3);
    color: var(--color-text-muted);
}

.about-highlights strong {
    color: var(--color-text);
}

.about-highlights svg {
    width: 28px;
    height: 28px;
    flex-shrink: 0;
    color: var(--color-accent);
}

.about-address {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    color: var(--color-text-muted);
}

.about-address svg {
    width: 18px;
    height: 18px;
    flex-shrink: 0;
}

/* --- TESTIMONIALS --- */
/* Seção tonalizada para os cards brancos terem contra o que aparecer — o
   cliente pediu faixas separando algumas seções, e é o que dá ritmo à página
   agora que ela é branca de ponta a ponta. */
.testimonials {
    background: var(--color-bg-alt);
    border-top: 1px solid var(--color-border);
    border-bottom: 1px solid var(--color-border);
}

/* Carrossel de depoimentos: .marquee é a janela que esmaece as bordas e ancora
   as setas; .marquee-track é quem rola de verdade (scrollLeft nativo, não
   transform) — dá arrasto por toque de graça e é o que faz o clique num card
   não travar mais nada (ver handler 9 do main.js). .testimonials-grid é um
   "grupo" de cards — sem reduced-motion o JS clona esse grupo uma vez dentro
   da track para o deslocamento ambiente poder dar a volta sem costura: ao
   passar de 100% da largura de um grupo, ele desconta essa largura do
   scrollLeft, e como o clone é pixel-idêntico ao original o salto é invisível.

   Antes disso era uma animação CSS (`transform: translateX(-50%)`) pausada
   por `.marquee-track:hover`. O bug era esse `:hover`: em touch ele gruda
   depois do toque e nunca solta sozinho (não existe "mouseleave" no dedo), e
   um clique num card travava o carrossel pra sempre, sem jeito de destravar.
   Pausa e retomada agora são geridas por JS (handler 9) via pointer events
   explícitos, nunca por :hover puro. */
.marquee {
    position: relative;
    overflow: hidden;
}

.marquee-track {
    display: flex;
    overflow-x: auto;
    scrollbar-width: none;
    -webkit-overflow-scrolling: touch;
}

.marquee-track::-webkit-scrollbar {
    display: none;
}

/* Esmaecimento nas bordas da janela, na cor da própria seção (bg-alt), pra
   os cards parecerem entrar/sair suavemente em vez de cortar em seco. */
.marquee::before,
.marquee::after {
    content: '';
    position: absolute;
    top: 0;
    bottom: 0;
    width: 6rem;
    pointer-events: none;
    z-index: 1;
}

.marquee::before {
    left: 0;
    background: linear-gradient(to right, var(--color-bg-alt), transparent);
}

.marquee::after {
    right: 0;
    background: linear-gradient(to left, var(--color-bg-alt), transparent);
}

/* Setas de avançar/voltar manual, injetadas pelo JS (handler 9) — mesmo
   desenho do .option-arrow dos "5 Passos", mas encostadas na borda (var(--
   space-4)) em vez de meio para fora: o marquee estica até a borda da
   viewport de propósito e não tem o vão de .container ao redor para a seta
   ocupar. O JS esconde as duas quando os cards já cabem inteiros na tela. */
.marquee-arrow {
    position: absolute;
    top: calc(50% - var(--space-1));
    transform: translateY(-50%);
    z-index: 3;
    display: flex;
    align-items: center;
    justify-content: center;
    width: 44px;
    height: 44px;
    border-radius: var(--radius-full);
    border: 1px solid var(--color-border);
    background: var(--color-surface);
    color: var(--color-text);
    cursor: pointer;
    box-shadow: 0 4px 16px rgba(0, 0, 0, 0.14);
    transition: background var(--transition-fast), border-color var(--transition-fast);
}

.marquee-arrow[hidden] {
    display: none;
}

.marquee-arrow svg {
    width: 22px;
    height: 22px;
}

.marquee-arrow:hover {
    background: var(--color-surface-hover);
    border-color: var(--color-text-muted);
}

.marquee-arrow:focus-visible {
    outline: 2px solid var(--color-primary);
    outline-offset: 2px;
}

.marquee-arrow-prev {
    left: var(--space-4);
}

.marquee-arrow-next {
    right: var(--space-4);
}

@media (prefers-reduced-motion: reduce) {
    /* Sem clone nem deslocamento ambiente (o JS não roda o rAF), só a
       rolagem nativa da track — arrastar/setas continuam funcionando. */
    .marquee-arrow {
        transition: none;
    }
}

.testimonials-grid {
    display: flex;
    gap: var(--space-6);
    /* padding-right (não gap) na borda final do grupo: assim os dois grupos
       clonados ficam com a mesma largura total e a costura em -50% cai
       exatamente entre um card e o próximo, sem espaço extra sobrando. */
    padding-right: var(--space-6);
}

.testimonial-card {
    width: min(380px, 85vw);
    flex-shrink: 0;
    padding: var(--space-8);
    border-radius: var(--radius-lg);
    /* Coluna para o rodapé (autor + logo) grudar na base mesmo quando os
       depoimentos têm comprimentos bem diferentes. */
    display: flex;
    flex-direction: column;
    transition: transform var(--transition-normal), box-shadow var(--transition-normal);
}

.testimonial-card:hover {
    transform: translateY(-6px);
    box-shadow: 0 16px 32px -12px rgba(0, 0, 0, 0.16);
}

@media (prefers-reduced-motion: reduce) {
    .testimonial-card {
        transition: box-shadow var(--transition-fast);
    }

    .testimonial-card:hover {
        transform: none;
    }
}

.testimonial-text {
    font-size: 1.125rem;
    margin-bottom: var(--space-6);
    font-style: italic;
    flex-grow: 1;
}

.testimonial-footer {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--space-4);
}

/* Mesmo --logo-scale inline da grade de marcas (index.html): lockup empilhado
   sempre parece menor que um horizontal na mesma altura de caixa, porque a
   altura vira duas linhas de texto em vez de uma. É correção óptica por arquivo,
   não um defeito do SVG — e tem que ser revista quando o cliente troca a arte. */
.testimonial-logo {
    max-height: calc(28px * var(--logo-scale, 1));
    max-width: 90px;
    width: auto;
    object-fit: contain;
    flex-shrink: 0;
}

/* Selo circular para logos entregues como arte com fundo sólido (não PNG
   transparente/SVG de traço). RP Team e D'Lacerda chegaram assim e foram
   recortados em círculo com Pillow antes de virar PNG (ver CLAUDE.md); SóKarretas
   e Kumo chegaram como SVG vetorial no mesmo formato (retângulo/quase-quadrado
   com fundo sólido), então aqui o recorte circular é feito em CSS em vez de
   pré-processar um raster — sem perda de nitidez e sem depender de script. A
   base .testimonial-logo cuida do max-height/--logo-scale; esta classe força a
   caixa a virar quadrada (senão aspect-ratio do SVG de origem vira elipse) e
   troca object-fit para cover, senão o fundo do SVG apareceria como retângulo
   com respiro em vez de preencher o círculo. */
.testimonial-logo--badge {
    width: calc(28px * var(--logo-scale, 1));
    height: calc(28px * var(--logo-scale, 1));
    max-width: none;
    border-radius: var(--radius-full);
    object-fit: cover;
}

/* .testimonial-card.is-placeholder e .testimonial-placeholder-tag saíram em
   2026-08-17: os 2 últimos cards de exemplo viraram depoimentos reais (RP Team,
   D'Lacerda) e não sobrou nenhum placeholder para essas regras estilizarem. Se
   um novo card de exemplo voltar, a regra está no histórico do git. */

.testimonial-author {
    display: flex;
    align-items: center;
    gap: var(--space-4);
}

.author-photo {
    width: 48px;
    height: 48px;
    border-radius: var(--radius-full);
    object-fit: cover;
    flex-shrink: 0;
}

.author-avatar {
    width: 48px;
    height: 48px;
    flex-shrink: 0;
    border-radius: var(--radius-full);
    background: var(--color-border);
    display: flex;
    align-items: center;
    justify-content: center;
    font-weight: bold;
}

.testimonial-author span {
    display: block;
    color: var(--color-text-muted);
    font-size: 0.875rem;
}

/* --- INSTAGRAM --- */
.instagram-feed-container {
    display: flex;
    justify-content: center;
}

/* O iframe do SnapWidget não declara height (snapwidget.js mede o conteúdo e
   ajusta via style inline depois de carregar — ver comentário no index.html).
   Até esse ajuste rodar, height:auto + aspect-ratio serve só de placeholder
   pra reduzir o salto de layout, calculado a partir do layout atual do
   widget (3 colunas x 2 linhas, fotos 1:1) — não é mais a fonte da verdade
   do tamanho final, então não precisa ficar em sincronia perfeita se o
   layout do widget mudar, só razoavelmente próximo. max-width é o que
   segura a largura em telas grandes, já que o iframe em si só pede 100%. */
.snapwidget-widget {
    width: 100%;
    max-width: 765px;
    aspect-ratio: 765 / 510;
    height: auto;
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
}

/* .btn é inline-flex, então margin:auto não centraliza sozinho (auto-margin
   só resolve pra caixas de bloco). Sobrescrevendo pra flex aqui o botão vira
   uma caixa de bloco do tamanho do conteúdo, e margin-inline:auto centraliza
   normalmente dentro do .container. */
.instagram-feed-cta {
    display: flex;
    width: fit-content;
    margin: var(--space-6) auto 0;
}

.instagram-feed-cta svg {
    width: 18px;
    height: 18px;
}

/* O FAQ (.faq-*) foi removido em 2026-08-11 a pedido do cliente. As duas
   informações que só existiam lá — entrega para Brasil/América Latina e
   pagamento via Pix/cartão — foram resgatadas para o rodapé; ver o comentário
   no index.html. */

/* --- CONTACT FORM --- */
/* Mesma lógica dos depoimentos: o card do formulário é branco, então a seção
   precisa ser tonalizada para ele não sumir. */
.contact {
    background: var(--color-bg-alt);
}

.contact-card {
    max-width: 800px;
    margin: 0 auto;
    padding: var(--space-8);
    border-radius: var(--radius-lg);
    box-shadow: 0 2px 12px rgba(0, 0, 0, 0.05);
}

.contact-content {
    text-align: center;
    margin-bottom: var(--space-8);
}

/* Caixa alta como o cliente escreveu o título ("SOLICITE SEU ORÇAMENTO"), mas
   pela CSS: o HTML mantém a caixa mista para o span .text-gradient continuar
   marcando a segunda palavra. */
.contact .section-title {
    text-transform: uppercase;
}

.contact-content p {
    color: var(--color-text-muted);
}

.form-group {
    margin-bottom: var(--space-3);
}

.form-row {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 0 var(--space-4);
}

.form-row .form-group {
    margin-bottom: var(--space-3);
}

.form-group label {
    display: block;
    margin-bottom: var(--space-2);
    font-weight: 600;
    font-size: 0.875rem;
}

.form-hint {
    display: block;
    margin-top: var(--space-1);
    font-size: 0.8125rem;
    color: var(--color-text-muted);
}

.form-group input,
.form-group select,
.form-group textarea {
    width: 100%;
    padding: var(--space-3);
    background: rgba(255, 255, 255, 0.8);
    /* --color-border-strong, not --color-border: the field's near-white fill
       on the white .glass card means this border is the only thing marking
       where the control actually is (WCAG 1.4.11). */
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius-md);
    color: var(--color-text);
    font-family: inherit;
    font-size: 1rem;
    transition: border-color var(--transition-fast);
}

.form-group select {
    appearance: none;
    background-image: url('data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="%231a1a1a" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="6 9 12 15 18 9"></polyline></svg>');
    background-repeat: no-repeat;
    background-position: right 1rem center;
    background-size: 1em;
}

.form-group select option {
    background-color: var(--color-bg-alt);
    color: var(--color-text);
}

fieldset.form-group {
    border: none;
    padding: 0;
    min-width: 0;
}

fieldset.form-group legend {
    padding: 0;
    margin-bottom: var(--space-2);
    font-weight: 600;
    font-size: 0.875rem;
}

.checkbox-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(180px, 1fr));
    gap: var(--space-2);
}

.form-group .checkbox-item {
    display: flex;
    align-items: center;
    gap: var(--space-1);
    /* Vertical padding grows the tap target toward ~44px for the 8-item
       mobile grid, without touching the checkbox/label visual size. */
    padding: var(--space-2) 0;
    font-size: 0.875rem;
    font-weight: 400;
    cursor: pointer;
}

.checkbox-grid input[type="checkbox"] {
    width: auto;
    padding: 0;
    background: none;
    border: none;
    accent-color: var(--color-primary);
    cursor: pointer;
}

.form-group input:focus,
.form-group textarea:focus {
    /* Was `outline: none` with only the 1px border-color as the focus cue —
       too weak for keyboard users and inconsistent with every other
       focus-visible ring on the site (.faq-question, .option-card,
       .form-advanced summary all use a 2px outline + offset). */
    outline: 2px solid var(--color-primary);
    outline-offset: 2px;
    border-color: var(--color-primary);
}

.contact-divider {
    display: flex;
    align-items: center;
    text-align: center;
    color: var(--color-text-muted);
    font-size: 0.875rem;
    margin: var(--space-6) 0;
}

.contact-divider::before,
.contact-divider::after {
    content: '';
    flex: 1;
    border-bottom: 1px solid var(--color-border);
}

.contact-divider span {
    padding: 0 var(--space-3);
}

.pilot-reassurance {
    display: flex;
    align-items: flex-start;
    gap: var(--space-3);
    padding: var(--space-3) var(--space-4);
    margin-bottom: var(--space-6);
    border-radius: var(--radius-md);
    border: 1px solid var(--color-border);
    background: var(--color-bg-alt);
}

.pilot-reassurance-icon {
    flex-shrink: 0;
    width: 20px;
    height: 20px;
    margin-top: 2px;
    color: var(--color-primary);
}

.pilot-reassurance p {
    min-width: 0;
    font-size: 1rem;
    color: var(--color-text-muted);
}

.pilot-reassurance strong {
    color: var(--color-text);
    font-weight: 600;
}

.order-summary {
    padding: var(--space-4);
    margin-bottom: var(--space-4);
    border-radius: var(--radius-md);
    border: 1px solid var(--color-border);
    background: rgba(0, 0, 0, 0.03);
}

.order-summary h3 {
    font-size: 0.875rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.1em;
    color: var(--color-text-muted);
    margin-bottom: var(--space-2);
}

.order-summary ul {
    display: flex;
    flex-direction: column;
    gap: 4px;
}

.order-summary li {
    font-size: 1rem;
}

.order-summary li strong {
    font-weight: 600;
}

.order-summary-empty {
    color: var(--color-text-muted);
    font-style: italic;
}

.order-summary-empty a {
    color: var(--color-text);
    text-decoration: underline;
}

/* --- CAMPOS AVANÇADOS DO FORMULÁRIO (colapsados por padrão) --- */
.form-advanced {
    margin-bottom: var(--space-4);
    padding: var(--space-3) var(--space-4);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--color-bg-alt);
}

.form-advanced summary {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--space-2);
    cursor: pointer;
    font-weight: 600;
    color: var(--color-text);
    list-style: none;
}

.form-advanced summary::-webkit-details-marker {
    display: none;
}

.form-advanced summary:focus-visible {
    outline: 2px solid var(--color-primary);
    outline-offset: 4px;
}

.form-advanced-icon {
    flex-shrink: 0;
    width: 18px;
    height: 18px;
    color: var(--color-text-muted);
    transition: transform var(--transition-normal);
}

.form-advanced[open] .form-advanced-icon {
    transform: rotate(180deg);
}

.form-advanced[open] summary {
    margin-bottom: var(--space-4);
}

/* Aviso sobre a arte da marca. O cliente pediu um campo de upload; o link wa.me
   não carrega anexo, então o pedido virou instrução. Fica logo acima do submit
   porque é ali que a pessoa decide o que fazer em seguida. */
.form-file-note {
    display: flex;
    align-items: flex-start;
    gap: var(--space-2);
    padding: var(--space-3) var(--space-4);
    margin-bottom: var(--space-4);
    border-radius: var(--radius-md);
    border: 1px dashed var(--color-border-strong);
    background: var(--color-bg-alt);
    font-size: 0.875rem;
    color: var(--color-text-muted);
}

.form-file-note svg {
    flex-shrink: 0;
    width: 18px;
    height: 18px;
    margin-top: 1px;
    color: var(--color-primary);
}

.whatsapp-fallback {
    padding: var(--space-4);
    margin: var(--space-4) 0;
    border-radius: var(--radius-md);
    text-align: center;
}

.whatsapp-fallback p {
    color: var(--color-text-muted);
    font-size: 0.875rem;
    margin-bottom: var(--space-3);
}

/* --- FOOTER --- */
/* Grafite igual ao navbar, fechando a página como o topo abre. Também resolve o
   fato de o rodapé e a seção de contato acima dele terem o mesmo `--color-bg-alt`:
   em claro os dois se fundiam e o rodapé não se separava de nada.
   Os tokens são redefinidos aqui dentro em vez de sobrescrever cada regra — todo
   o CSS abaixo continua usando `var(--color-text-muted)` e afins normalmente. */
.footer {
    background: var(--color-graphite);
    /* Linha clara, e não `var(--color-accent)` como nas outras seções: com a
       paleta monocromática o accent virou grafite (#2b2b2b) e a borda sumia
       dentro do próprio rodapé (#121212). Aqui a régua tem que ser o inverso do
       fundo para continuar marcando a emenda. */
    border-top: 3px solid rgba(255, 255, 255, 0.16);
    padding: var(--space-8) 0 var(--space-4);

    --color-text: #ffffff;
    --color-text-muted: rgba(255, 255, 255, 0.72);
    --color-border: rgba(255, 255, 255, 0.12);
    --color-primary: #ffffff;
    /* Redefinir os tokens não basta: o `color` do body já foi resolvido para o
       cinza escuro e é herdado como valor, não reavaliado. Sem esta linha, o que
       não declara cor própria (o texto de impacto) sairia preto no fundo preto. */
    color: var(--color-text-muted);
}

/* Grid de 3 colunas em vez de flex: com `space-between` + `wrap`, o endereço longo
   empurrava a coluna de links para uma segunda linha e o rodapé ficava torto. */
.footer-content {
    display: grid;
    /* A terceira coluna leva o maior peso: o endereço completo quebrava em duas
       linhas com as colunas equilibradas. A primeira encolheu junto com a saída
       da frase "Catálogo Premium 2026" — sobrou só o logo nela. */
    grid-template-columns: 0.9fr 0.9fr 1.8fr;
    align-items: start;
    margin-bottom: var(--space-8);
    gap: var(--space-8) var(--space-6);
}

.footer-heading {
    font-size: 0.8125rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.1em;
    color: var(--color-text);
    margin-bottom: var(--space-3);
}

.footer-links {
    display: flex;
    flex-direction: column;
    gap: var(--space-2);
}

.footer-links a {
    color: var(--color-text-muted);
    font-size: 0.875rem;
}

.footer-links a:hover {
    color: var(--color-primary);
}

.footer-contact {
    display: flex;
    flex-direction: column;
    gap: var(--space-2);
    font-size: 0.875rem;
    color: var(--color-text-muted);
}

.footer-contact a,
.footer-contact p {
    display: flex;
    /* flex-start em vez de center para o ícone acompanhar a primeira linha
       quando o texto quebrar em duas (o endereço, em telas menores). */
    align-items: flex-start;
    gap: var(--space-2);
    color: var(--color-text-muted);
}

.footer-contact a:hover {
    color: var(--color-primary);
}

/* `svg` além de `i` porque o lucide troca cada <i data-lucide> por um <svg> ao
   renderizar — a regra só com `i` deixava de valer depois do createIcons(). */
.footer-contact i,
.footer-contact svg {
    width: 16px;
    height: 16px;
    flex-shrink: 0;
    /* Desce o ícone até a altura-x da primeira linha, já que o alinhamento é
       pelo topo da caixa de texto e não pela linha de base. */
    margin-top: 0.2em;
}

/* Dado fiscal, não texto de venda: corpo menor e cinza, para identificar a
   empresa sem competir com o contato logo acima. O <address> herda itálico do
   user-agent, que aqui só atrapalha a leitura de CNPJ e inscrição. */
.footer-legal {
    display: flex;
    flex-wrap: wrap;
    justify-content: center;
    gap: var(--space-1) var(--space-3);
    font-style: normal;
    font-size: 0.8125rem;
    line-height: 1.7;
    color: var(--color-text-muted);
    text-align: center;
    margin-bottom: var(--space-4);
    padding-top: var(--space-6);
    border-top: 1px solid var(--color-border);
}

.footer-legal-name {
    font-weight: 600;
    color: var(--color-text);
}

.footer-bottom {
    border-top: 1px solid var(--color-border);
    padding-top: var(--space-4);
    color: var(--color-text-muted);
    font-size: 0.875rem;
}

/* --- ANIMATIONS & REVEALS --- */
.reveal {
    opacity: 0;
    transform: translateY(30px);
    transition: all var(--transition-slow);
}

.reveal.active {
    opacity: 1;
    transform: translateY(0);
}

.delay-1 {
    transition-delay: 0.1s;
}

.delay-2 {
    transition-delay: 0.2s;
}

.delay-3 {
    transition-delay: 0.3s;
}

/* Keep the state change (opacity) as the reveal cue for motion-sensitive
   visitors, but drop the translateY slide — every section on the page uses
   .reveal, so without this the whole page keeps sliding on scroll. */
@media (prefers-reduced-motion: reduce) {
    .reveal {
        transform: none;
        transition: opacity var(--transition-fast);
    }

    .reveal.active {
        transform: none;
    }
}

/* --- MEDIA QUERIES --- */
@media (max-width: 768px) {
    .navbar-content {
        position: relative;
    }

    .nav-links {
        display: none;
        position: absolute;
        /* `100%`, não `calc(100% + 1px)`: aquele 1px era um vão real entre a
           barra e o dropdown, e a página passava por ele — era a "divisória"
           que cortava a região do logo/X. Coladas, as duas superfícies (ambas
           grafite opaco, ver .navbar.menu-open) lêem como um painel só. */
        top: 100%;
        left: 0;
        right: 0;
        flex-direction: column;
        align-items: stretch;
        gap: 0;
        /* Escuro para continuar o navbar, senão os links (brancos) sumiriam
           sobre o dropdown claro. Opaco de propósito: o dropdown transborda a
           caixa do navbar, e o `backdrop-filter` do pai não alcança essa área —
           com qualquer transparência a foto do hero aparece por baixo. */
        background: var(--color-graphite);
        border-radius: 0 0 var(--radius-md) var(--radius-md);
        padding: var(--space-2) var(--space-4) var(--space-4);
    }

    .nav-links.active {
        display: flex;
    }

    .nav-links a:not(.btn) {
        padding: var(--space-3) 0;
        border-bottom: 1px solid rgba(255, 255, 255, 0.12);
    }

    /* O dropdown é grafite opaco igual à barra, então a inversão para branco
       definida no desktop vale aqui também — não precisa ser redeclarada. */
    .nav-links .btn-nav {
        align-self: stretch;
        margin-top: var(--space-3);
        /* Ocupa a largura do dropdown: aqui ele não disputa mais a altura da
           barra fixa, e um botão de largura cheia é alvo de toque melhor que um
           encolhido no canto esquerdo. */
        padding: var(--space-3) var(--space-4);
    }

    .menu-toggle {
        display: block;
    }

    /* Barra rolada mede 60px aqui (contra 73,6px no desktop), então a folga
       do salto de âncora encolhe junto para não sobrar um vão grande. */
    section[id] {
        scroll-margin-top: 5rem;
    }

    .about-container {
        grid-template-columns: 1fr;
    }

    /* Empilhada, a foto não tem mais coluna vizinha para copiar a altura, então
       volta ao fluxo normal com proporção própria — sem isso ela colapsaria no
       `min-height` do desktop. */
    .about-image-wrapper {
        min-height: 0;
    }

    .about-image {
        position: static;
        height: auto;
        aspect-ratio: 4 / 3;
    }

    .footer-content {
        grid-template-columns: 1fr;
        gap: var(--space-6);
    }

    .how-choice-grid {
        grid-template-columns: 1fr;
    }

    /* Empilhados, os dois caminhos deixam de ser lidos lado a lado, então o
       rodapé não precisa mais alinhar com o do vizinho — a folga fixa evita o
       vão grande que o `margin-top: auto` criaria no card de texto curto. */
    .how-path-note {
        margin-top: var(--space-1);
    }

    /* `flex-start`, não o `center` do desktop. O `min-height: 100vh` do .hero
       existe para a borda de topo da .brands não aparecer na primeira tela, mas
       com `align-items: center` toda sobra entre o conteúdo e os 100vh é
       repartida meio a meio — e vira ar ENTRE a navbar e o título.
       Isso ficou visível quando o vídeo encolheu de 485px para 320px em
       2026-08-12: numa tela alta (~1400px de viewport contra ~1050px de
       conteúdo) sobravam ~350px, ou seja ~175px empurrando o H1 para baixo, em
       cima dos 144px de padding que já havia. Num aparelho curto o conteúdo
       passa dos 100vh e não sobra nada, então o problema só aparece em tela
       grande — foi por isso que passou batido na primeira conferência.
       Ancorando no topo, o ar visível acima do título volta a ser só
       padding menos navbar (144 - 76 = 68px) e a sobra inteira cai depois dos
       selos, onde lê como respiro de seção. O 100vh continua valendo, então a
       .brands segue começando abaixo da dobra.
       No desktop o `center` fica: lá a assimetria do padding (144 em cima
       contra 48 embaixo) foi calibrada justamente contra essa repartição. */
    .hero {
        align-items: flex-start;
        /* 120px no lugar dos 144 da regra base (pedido do cliente, 2026-08-12:
           a folga sob a navbar incomodava). Como a navbar é `fixed` e mede 76px
           em repouso no mobile, ela cobre esse tanto do padding sem ocupar
           espaço no fluxo — o ar visível acima do H1 cai de 68px para 44px.
           Sobe TUDO 24px junto, então o CTA também: num aparelho de 360x720 ele
           sai de 76px abaixo da dobra para 52px.
           Só `padding-top`: o rodapé da seção continua em --space-6, e o valor
           do desktop fica onde está, calibrado contra a navbar de ~90px e
           contra o `align-items: center` de lá. */
        padding-top: calc(var(--space-12) + var(--space-3));
    }

    .hero-grid {
        grid-template-columns: 1fr;
        text-align: center;
        /* Zerado porque o `display: contents` abaixo transforma cada filho do
           .hero-content em item deste grid: um gap aqui passaria a valer entre
           título, subtítulo, CTA e selos, e não só entre texto e vídeo. O
           espaçamento vertical volta a ser o `margin-bottom` de cada elemento,
           que é o que já valia quando eles moravam na coluna flex. */
        gap: 0;
    }

    /* A ordem no mobile não é a do DOM: título → vídeo → subtítulo → CTA → selos.
       Antes o vídeo vinha inteiro antes do texto (`order: -1` no .hero-image), e
       a primeira tela do site não dizia o que a Union vende — o H1 começava por
       volta dos 600px e o botão caía bem abaixo da dobra. Título primeiro resolve
       isso, e o subtítulo desce para logo acima do CTA, que é onde ele trabalha
       melhor: é o último texto lido antes do clique.

       O `display: contents` é o que torna isso possível. Título e vídeo estão em
       divs irmãs (.hero-content e .hero-image), então `order` sozinho não
       intercala — dissolvendo a caixa do .hero-content, seus filhos viram itens
       do .hero-grid e passam a ordenar junto com o vídeo. Propriedades herdadas
       (o `text-align: center` acima) atravessam o `contents` normalmente, porque
       herança segue a árvore de elementos, não a de caixas. */
    .hero-content {
        display: contents;
    }

    .hero-title {
        order: 1;
    }

    .hero-image {
        order: 2;
        /* Vão até o subtítulo. O título acima já traz o seu próprio
           `margin-bottom`, então só falta este lado. */
        margin-bottom: var(--space-6);
    }

    .hero-subtitle {
        order: 3;
        /* 32px no lugar dos 64px do desktop. Lá o valor é só um piso — o
           `margin-top: auto` do CTA come a folga toda para ancorar o botão na
           base da coluna. Aqui não há coluna para ancorar, então os 64px valem
           de verdade e destoam do resto do ritmo (32px do título ao vídeo, 48px
           do vídeo ao subtítulo). Fechando esse vão, o topo do botão sobe até a
           linha da dobra num aparelho de 844px de altura: aparece um pedaço da
           pílula, que é o convite para rolar. */
        margin-bottom: var(--space-4);
    }

    .hero-cta {
        order: 4;
        justify-content: center;
        /* O `margin-top: auto` do desktop existe para ancorar o botão na base da
           coluna de texto, encaixando com a borda de baixo do vídeo. Aqui não há
           coluna nem encaixe, e como item de grid o auto ainda resolveria para
           zero (a linha tem a altura do próprio item); explícito para não
           depender disso. */
        margin-top: 0;
    }

    .hero-trust {
        order: 5;
        /* O `text-align: center` do .hero-grid não alcança item de flex — ele
           centraliza a linha DENTRO de cada selo, não os selos dentro da lista.
           Sem isto os três ficavam encostados à esquerda no meio de um hero
           todo centralizado, e a quebra 2+1 deixava o terceiro sozinho embaixo
           do primeiro, parecendo desalinhado em vez de quebrado. */
        justify-content: center;
    }

    /* Quadrado, que é o corte nativo do arquivo — nada de corte por CSS aqui.
       O 9:16 do cliente ficava 273x485 num aparelho de 390px e sozinho comia a
       primeira tela inteira; no mesmo aparelho o quadrado dá ~320x320, ou seja,
       165px de altura devolvidos e ainda 17% mais largo. Foi por isso que o teto
       subiu de 300px/70vw: sem a altura do retrato, a peça pode crescer na
       horizontal sem empurrar nada para fora da dobra. */
    .hero-media {
        max-width: min(360px, 82vw);
    }

    .hero-image video {
        aspect-ratio: 1 / 1;
        object-position: center;
    }

    /* Numa moldura de ~320px a legenda ocupa quase um terço da largura do vídeo
       se mantiver o corpo do desktop. Reduz junto com a moldura. */
    .hero-media-caption {
        padding: var(--space-6) var(--space-2) var(--space-2);
        text-align: left;
    }

    .hero-media-kicker {
        font-size: 0.75rem;
    }

    .hero-media-note {
        font-size: 0.875rem;
    }

    .brands-grid {
        gap: var(--space-6) var(--space-4);
    }

    .brand-item {
        flex-basis: calc(33.333% - var(--space-4));
        height: 48px;
    }

    .contact-card {
        padding: var(--space-4);
    }

    .form-row {
        grid-template-columns: 1fr;
    }

    .section-padding {
        padding: var(--space-8) 0;
    }

    .testimonial-card {
        padding: var(--space-4);
    }

    /* 6rem de esmaecimento em cada ponta come ~190px de uma tela de 375px —
       metade do card visível ficava lavada. Encolhe para uma dica de corte. */
    .marquee::before,
    .marquee::after {
        width: 2rem;
    }

    /* var(--space-4) some dentro da faixa de 2rem acima; puxa para mais perto
       da borda para as duas convivarem sem a seta comer o esmaecimento. */
    .marquee-arrow-prev {
        left: var(--space-2);
    }

    .marquee-arrow-next {
        right: var(--space-2);
    }
}

@media (max-width: 480px) {

    .testimonial-card,
    .contact-card {
        padding: var(--space-3);
    }

    .brand-item {
        flex-basis: calc(50% - var(--space-4));
    }

    /* --- ORÇAMENTO DE LARGURA NO CELULAR ---
       Numa tela de 360px os recuos horizontais se empilham: 32px do
       .container + 24px do .glass + 32px do .pilot-reassurance deixavam 138px
       de texto no bloco mais interno, ou seja ~18 caracteres por linha. Os
       tokens --space-4/--space-8 foram calibrados para uma coluna de 1440px e
       não sobrevivem à soma em telas estreitas. A regra aqui é simples: no
       celular cada nível cede um degrau da escala. Antes de acrescentar mais um
       nível aninhado, some os recuos e veja o que sobra. */
    .container {
        padding: 0 var(--space-3);
    }

    /* 64px de recuo horizontal num botão que já ocupa a largura toda não é
       respiro, é o que forçava "SOLICITAR ORÇAMENTO" a quebrar em duas linhas
       dentro de uma pílula de 122px de altura. Largura cheia já dá a área de
       toque; o recuo grande só sobra para o desktop, onde o botão é do tamanho
       do conteúdo. */
    .btn-large {
        padding: var(--space-3) var(--space-4);
        font-size: 1rem;
    }

    .btn {
        padding-inline: var(--space-3);
    }

    .pilot-reassurance,
    .form-file-note {
        padding: var(--space-3) var(--space-2);
        gap: var(--space-2);
    }

    /* Alvo de toque: os links do rodapé mediam 22px de altura, metade do mínimo
       confortável. O espaçamento sai do `gap` e vai para o padding de cada
       link, então a área clicável cresce para ~44px sem esticar o rodapé nem
       afastar visualmente um item do outro. */
    .footer-links,
    .footer-contact {
        gap: 0;
    }

    .footer-links a,
    .footer-contact a,
    .footer-contact p {
        padding: 0.6875rem 0;
    }
}
