/* =========================================================================
   MeAuren — MOVIMENTO: a linguagem de movimento do produto, num lugar só.

   TESE — "a mesa acendendo": a luz chega antes do conteúdo. Nada salta;
   tudo emerge, de baixo e da esquerda. A ficção entra devagar; o sistema
   responde na hora.

   TRÊS NÍVEIS, com durações que não se misturam:
     1. CENA  (--dur-cena)  hero, sessão de exemplo, atmosfera da Comunidade
     2. BLOCO (--dur-bloco) títulos, parágrafos, cards, listas
     3. MICRO (--dur-micro) botões, links, abas, ícones, foco

   REGRA DE OURO: tudo o que esconde conteúdo mora sob `html.mov`, que só
   existe quando js/movimento.js roda. Sem JS, a página chega inteira.

   Esta folha carrega DEPOIS de app.css e landing.css, de propósito.
   ========================================================================= */

:root{
  /* os tempos de micro/comp/scene vêm de tokens.css; aqui ficam os que faltavam */
  --dur-bloco:520ms;
  --dur-cena:900ms;
  --mov-escada:70ms;                      /* passo entre irmãos (o JS repete o valor) */
  --ease-saida:cubic-bezier(.4,0,1,1);    /* sair é mais seco que entrar */
}

/* nenhuma animação de entrada pode empurrar a página para os lados */
#landing{overflow-x:clip;}

/* =========================================================================
   NÍVEL 2 — REVEAL DE BLOCO
   Um só observer no JS; aqui só as variações de linguagem. Evita-se que
   todas as seções entrem igual: cada uma tem a sua pequena diferença.
   ========================================================================= */
/* sem `will-change`: são dezenas de blocos esperando reveal ao mesmo tempo, e
   avisar todos de uma vez criaria dezenas de camadas na GPU antes de qualquer
   animação começar. translate3d já promove o que precisa, na hora certa. */
html.mov [data-mov]{
  opacity:0;
  transform:translate3d(var(--mov-x,0),var(--mov-y,18px),0);
  transition:opacity var(--dur-bloco) var(--ease),transform var(--dur-bloco) var(--ease);
  transition-delay:var(--mov-d,0ms);
}
html.mov [data-mov].in{opacity:1;transform:none;}

/* cena: bloco narrativo grande, mais lento e com mais caminho */
html.mov [data-mov="cena"]{--mov-y:30px;
  transition-duration:var(--dur-cena);
  transition-timing-function:var(--ease-expo);}

/* imagem: só luz e um respiro de escala — nada de deformar arte */
html.mov [data-mov="imagem"]{--mov-y:0px;transform:scale(1.035);
  transition:opacity var(--dur-cena) var(--ease-expo),transform var(--dur-cena) var(--ease-expo);}
html.mov [data-mov="imagem"].in{transform:none;}

/* coluna: entra do lado, para dizer "isto está ao lado daquilo" */
html.mov [data-mov="coluna"]{--mov-y:0px;--mov-x:-16px;}
html.mov [data-mov="coluna"][data-mov-lado="direita"]{--mov-x:16px;}

/* linha: o fio de cima acende da esquerda e apaga, e a linha aparece atrás.
   É a tese literal — a luz chega antes do conteúdo. */
html.mov [data-mov="linha"]{position:relative;--mov-y:12px;}
html.mov [data-mov="linha"]::before{
  content:"";position:absolute;left:0;right:0;top:-1px;height:1px;
  background:rgba(237,235,231,.38);transform:scaleX(0);transform-origin:left center;
  pointer-events:none;opacity:0;}
html.mov [data-mov="linha"].in::before{animation:mvFio 820ms var(--ease-expo) var(--mov-d,0ms) both;}
@keyframes mvFio{
  0%{transform:scaleX(0);opacity:.95;}
  62%{transform:scaleX(1);opacity:.95;}
  100%{transform:scaleX(1);opacity:0;}
}
:root[data-theme="claro"] html.mov [data-mov="linha"]::before{background:rgba(26,28,32,.32);}

/* =========================================================================
   SPLIT POR PALAVRA — só em TÍTULO, a ideia do Split Text sem biblioteca e
   sem perder a semântica: o texto continua texto, a quebra de linha continua
   do navegador, e por isso não há layout shift nem estrago ao redimensionar.

   Corpo de texto NÃO é dividido: parágrafo animado palavra a palavra faz a
   leitura esperar a animação e soa a máquina de escrever. Ele entra em
   `[data-mov="texto"]`, mais abaixo — fade curto e um passo de subida.
   ========================================================================= */
/* o padding com margem negativa existe para a máscara não cortar acento
   (NÃO, NINGUÉM, SESSÃO) */
html.mov .mv-split .mv-w{display:inline-block;overflow:hidden;vertical-align:top;
  padding:.26em .04em .1em;margin:-.26em -.04em -.1em;}
html.mov .mv-split .mv-w>i{display:inline-block;font-style:inherit;color:inherit;
  transform:translate3d(0,110%,0);transition:transform 760ms var(--ease-expo);}
html.mov .mv-split.in .mv-w>i{transform:none;}

/* parágrafo de apoio: discreto, curto, e nunca competindo com o título que
   acabou de sair. É o nível mais baixo da hierarquia de texto. */
html.mov [data-mov="texto"]{--mov-y:12px;transition-duration:400ms;}

/* =========================================================================
   NÍVEL 1 — HERO: a única entrada com tempo próprio.
   Ordem: luz da sala → título → descrição → ação → ação secundária →
   nota → pilares. Teto de ~1,1s. Nada trava, nada vira tela de carregamento:
   os botões já respondem ao clique desde o primeiro quadro.
   ========================================================================= */
/* a sala acende: a arte já está lá, só mais escura. Não é splash. */
html.mov body.na-landing #landing .lhero::after{
  content:"";position:absolute;inset:0;z-index:-1;pointer-events:none;
  background:var(--night);opacity:.72;
  transition:opacity 1100ms var(--ease-expo);}
html.mov body.mv-hero #landing .lhero::after{opacity:0;}

html.mov body.na-landing #landing .lhero-texto>*,
html.mov body.na-landing #landing .lhero-texto .cta>*,
html.mov body.na-landing #landing .pilares li{
  opacity:0;transform:translate3d(0,22px,0);
  transition:opacity 700ms var(--ease-expo),transform 700ms var(--ease-expo);
  transition-delay:var(--h-d,0ms);}
html.mov body.mv-hero #landing .lhero-texto>*,
html.mov body.mv-hero #landing .lhero-texto .cta>*,
html.mov body.mv-hero #landing .pilares li{opacity:1;transform:none;}

/* o .cta é revelado pelos filhos, não como bloco */
html.mov body.na-landing #landing .lhero-texto>.cta{opacity:1;transform:none;transition:none;}

html.mov #landing .lhero h1{--h-d:60ms;}
html.mov #landing .lhero .lede{--h-d:340ms;}
html.mov #landing .lhero .cta>*:nth-child(1){--h-d:480ms;}
html.mov #landing .lhero .cta>*:nth-child(2){--h-d:560ms;}
html.mov #landing .lhero .note{--h-d:640ms;}
html.mov #landing .pilares li:nth-child(1){--h-d:720ms;}
html.mov #landing .pilares li:nth-child(2){--h-d:790ms;}
html.mov #landing .pilares li:nth-child(3){--h-d:860ms;}
html.mov #landing .pilares li:nth-child(4){--h-d:930ms;}

/* Depois da entrada, a abertura responde ao scroll: a arte fica 46px para trás
   ao longo do percurso do hero. A folga de 56px em cima e embaixo existe para
   a arte nunca descolar da borda enquanto se move — o respiro de escala
   continua no <img>, e a paralaxe mora no contêiner, para os dois transforms
   não brigarem pelo mesmo elemento. O JS é quem escreve --par. */
#landing .lhero-arte{top:-56px;bottom:-56px;transform:translate3d(0,var(--par,0px),0);}

/* =========================================================================
   SEÇÕES DA APRESENTAÇÃO — a mesma língua, sotaques diferentes
   ========================================================================= */

/* --- "Não é um chat que finge ser mestre": a comparação é o argumento.
       A coluna do chatbot entra plana (ela não faz nada). A do Mestre Auren
       sobe, e cada item é confirmado por um sinal em ciano. --- */
html.mov #landing .contrast .col-a[data-mov]{--mov-y:0px;}
html.mov #landing .contrast .col-b[data-mov]{--mov-y:26px;--mov-d:160ms;}
html.mov #landing .contrast .col-b li{
  opacity:0;transform:translate3d(0,10px,0);
  transition:opacity 400ms var(--ease),transform 400ms var(--ease);}
html.mov #landing .contrast .col-b.in li{opacity:1;transform:none;}
html.mov #landing .contrast .col-b li .i{
  opacity:0;transform:scale(.6);
  transition:opacity 240ms var(--ease),transform 240ms var(--ease);}
html.mov #landing .contrast .col-b.in li .i{opacity:1;transform:none;}
html.mov #landing .contrast .col-b.in li:nth-child(1){transition-delay:240ms;}
html.mov #landing .contrast .col-b.in li:nth-child(2){transition-delay:330ms;}
html.mov #landing .contrast .col-b.in li:nth-child(3){transition-delay:420ms;}
html.mov #landing .contrast .col-b.in li:nth-child(4){transition-delay:510ms;}
html.mov #landing .contrast .col-b.in li:nth-child(5){transition-delay:600ms;}
html.mov #landing .contrast .col-b.in li:nth-child(1) .i{transition-delay:400ms;}
html.mov #landing .contrast .col-b.in li:nth-child(2) .i{transition-delay:490ms;}
html.mov #landing .contrast .col-b.in li:nth-child(3) .i{transition-delay:580ms;}
html.mov #landing .contrast .col-b.in li:nth-child(4) .i{transition-delay:670ms;}
html.mov #landing .contrast .col-b.in li:nth-child(5) .i{transition-delay:760ms;}

/* --- campanhas: uma coleção de aventuras chegando, não cards pulando.
       O hover da arte (scale 1.035) já vive em landing.css e fica como está. --- */
html.mov #landing .capa[data-mov]{--mov-y:24px;}
html.mov #landing .capa .capa-txt>*{
  opacity:0;transform:translate3d(0,12px,0);
  transition:opacity 420ms var(--ease),transform 420ms var(--ease);}
html.mov #landing .capa.in .capa-txt>*{opacity:1;transform:none;}
html.mov #landing .capa.in .capa-txt>*:nth-child(1){transition-delay:180ms;}
html.mov #landing .capa.in .capa-txt>*:nth-child(2){transition-delay:250ms;}
html.mov #landing .capa.in .capa-txt>*:nth-child(3){transition-delay:320ms;}
html.mov #landing .capa.in .capa-txt>*:nth-child(4){transition-delay:390ms;}
#landing .capa .btn{transition:background-color var(--dur-micro),border-color var(--dur-micro),transform var(--dur-micro) var(--ease);}
#landing .capa:hover .btn{border-color:rgba(237,235,231,.32);}

/* --- a mesa: seis recursos que chegam em ordem, com o fio acendendo antes.
       O ícone entra por último, pequeno: é organização, não espetáculo. --- */
html.mov #landing .recursos li .i{
  opacity:0;transform:translate3d(-6px,0,0);
  transition:opacity 340ms var(--ease),transform 340ms var(--ease);
  transition-delay:calc(var(--mov-d,0ms) + 260ms);}
html.mov #landing .recursos li.in .i{opacity:1;transform:none;}

/* --- para quem: os três blocos entram em sequência curta --- */
html.mov #landing .split>div[data-mov]{--mov-y:16px;}

/* --- planos: entram juntos, sem deslocamento vertical no hover.
       O card destacado chega depois, porque ele é a conclusão. --- */
html.mov #landing .plan[data-mov]{--mov-y:22px;}
#landing .plan{transition:border-color var(--dur-comp) var(--ease);}
#landing .plan:hover{border-color:var(--line-2);}
#landing .plan.hi:hover{border-color:var(--line-2);}
#landing .cyc{transition:border-color var(--dur-micro),background-color var(--dur-micro),transform var(--dur-micro) var(--ease);}
#landing .cyc:active{transform:translateY(1px);}

/* --- o que a gente decidiu não fazer: três linhas, uma de cada vez --- */
html.mov #landing .honest-lista p[data-mov]{--mov-y:14px;}

/* =========================================================================
   ACERTOS DE SISTEMA — duas medidas que tinham escapado da folha de estilo
   e só aparecem quando se mede. Não é redesenho: é o valor documentado.
   ========================================================================= */
/* A regra da coluna que não encolhe (DESIGN.md): texto de leitura não passa
   de 78ch. Estas três linhas estavam em 82ch, únicas na página — as outras
   colunas de leitura ficam entre 68 e 70ch. */
#landing .honest-lista p{max-width:68ch;}

/* O raio de contêiner da casa é 10px; 16px é reservado a faixa grande (arte
   sangrada, painel da sessão). Os cards de plano estavam em 16px enquanto os
   cards vizinhos da comparação estavam em 10px — dois grupos de card lado a
   lado com cantos diferentes. */
#landing .plan{border-radius:var(--r-lg);}

/* --- chamada final: a arte volta e o convite sobe --- */
html.mov #landing .lfinal-corpo>*[data-mov]{--mov-y:24px;}

/* =========================================================================
   NÍVEL 3 — MICROINTERAÇÕES
   Resposta imediata (120–250ms). Nada de bounce, nada de elastic.
   ========================================================================= */

/* Navegação da apresentação, em três degraus: parado, onde-você-está, e sob o
   ponteiro. O indicador abre da esquerda, como o fio das listas — é o mesmo
   gesto em outra escala. Sem âmbar: o botão de ação do cabeçalho já é o ponto
   quente da faixa, e a casa só admite um por tela. */
#landing .lk{position:relative;transition:color var(--dur-micro) var(--ease);}
#landing .lk::after{
  content:"";position:absolute;left:0;right:0;bottom:-5px;height:1px;background:currentColor;
  transform:scaleX(0);transform-origin:left center;opacity:1;
  transition:transform var(--dur-comp) var(--ease),opacity var(--dur-micro) var(--ease);}
#landing .lk.aqui{color:var(--ink);}
#landing .lk.aqui::after{transform:scaleX(1);opacity:.38;}
#landing .lk:hover::after,#landing .lk:focus-visible::after{transform:scaleX(1);opacity:1;}

/* âncoras: uma rolagem suave só, a do navegador — nenhum mecanismo paralelo */
@media (prefers-reduced-motion:no-preference){
  html:has(body.na-landing){scroll-behavior:smooth;}
}
#landing section[id],#landing [id^="n-"]{scroll-margin-top:92px;}

/* Botão esperando: um fio percorre a borda de baixo. É de propósito um
   pseudo-elemento posicionado, e não um item na linha do flex — um contador
   girando ao lado do rótulo AUMENTA o botão e empurra o que está ao lado.
   O rótulo não sai, e `aria-busy` diz ao leitor de tela a mesma coisa que o
   fio diz ao olho: a animação nunca é o único sinal. */
/* overflow:hidden para o fio respeitar o canto de 6px do botão, em vez de
   sobrar como duas pontas quadradas nas bordas de baixo */
.btn[aria-busy="true"]{pointer-events:none;cursor:progress;position:relative;overflow:hidden;opacity:.88;}
.btn[aria-busy="true"]::after{
  content:"";position:absolute;left:0;right:0;bottom:0;height:2px;
  background:currentColor;
  animation:mvRespira 1.15s var(--ease) infinite;}

/* abas da Comunidade: o ícone dá um passo à frente ao passar o mouse */
.comu-abas button .i{transition:color var(--dur-micro),transform var(--dur-micro) var(--ease);}
.comu-abas button:hover .i{transform:translateY(-1px);}
.comu-abas button[aria-selected="true"] .i{color:var(--ink);}

/* coluna de navegação do app: o ícone acompanha a linha selecionada */
.vbtn{transition:background-color var(--dur-micro),color var(--dur-micro);}
.vbtn .i{transition:color var(--dur-micro),transform var(--dur-micro) var(--ease);}
.vbtn:hover .i{transform:translateX(1px);}
@media(max-width:899px){.vbtn:hover .i{transform:translateY(-1px);}}

/* cards do app: sobem de camada, não de posição */
.capa,.plan,.beast,.tmpl,.comu-mini{transition:border-color var(--dur-micro),background-color var(--dur-micro);}

/* =========================================================================
   NÍVEL 1 — METAL LÍQUIDO: a atmosfera da Comunidade

   A Comunidade é tela funcional (feed, abas, busca, notificações, publicar).
   Por isso o metal vive atrás de tudo, não recebe ponteiro, mora no topo e
   nas bordas, e o degradê abaixo é o desenho definitivo quando o WebGL não
   existe, falha, perde o contexto, ou o aparelho é fraco.
   ========================================================================= */
#v-comunidade{position:relative;isolation:isolate;}

.metal-host::before{
  content:"";position:absolute;inset:0 0 auto 0;height:min(100%,760px);
  z-index:-2;pointer-events:none;
  background:
    radial-gradient(74% 62% at 8% -6%, color-mix(in srgb,var(--sys) 13%,transparent) 0%, transparent 64%),
    radial-gradient(64% 58% at 96% 2%, color-mix(in srgb,var(--surf-3) 92%,transparent) 0%, transparent 62%),
    linear-gradient(to bottom, color-mix(in srgb,var(--surf-2) 64%,transparent) 0%, transparent 76%);
}
/* O metal sobe do degradê em vez de aparecer de estalo: a classe `pronto` é
   posta pelo JS depois do primeiro quadro desenhado, então nunca há um salto
   de superfície vazia para superfície pintada. */
.metal-cv{
  position:absolute;inset:0 0 auto 0;width:100%;height:min(100%,760px);
  z-index:-1;pointer-events:none;display:block;
  opacity:0;transition:opacity 900ms var(--ease-expo);}
.metal-cv.pronto{opacity:1;}
.metal-cv[hidden]{display:none;}

/* =========================================================================
   ENTRADA DE TELA DO APP — curta, discreta, só quando a tela troca
   ========================================================================= */
@keyframes mvIn{from{opacity:0;transform:translate3d(0,14px,0);}to{opacity:1;transform:none;}}
.mv-enter [data-mv-i]{animation:mvIn .46s var(--ease) both;animation-delay:calc(var(--i,0) * 55ms);}

/* =========================================================================
   SESSÃO — a narração entra; o resto do painel fica quieto.
   O sistema (selo de efeito) chega depois da fala: primeiro o que aconteceu,
   depois o que o sistema fez com aquilo.
   ========================================================================= */
@keyframes mvMsg{from{opacity:0;transform:translate3d(0,10px,0);}to{opacity:1;transform:none;}}
.log .msg:last-child{animation:mvMsg .42s var(--ease) both;}
@keyframes mvChip{from{opacity:0;transform:scale(.92);}to{opacity:1;transform:none;}}
.log .msg:last-child .efx .e{animation:mvChip .44s var(--ease) both;animation-delay:.14s;}

/* espera da IA: identidade em vez de "carregando". O texto continua lá. */
.mv-espera{font-family:var(--fm);font-size:12px;letter-spacing:.07em;color:var(--mut);margin-top:2px;min-height:14px;}
.mv-espera span{animation:mvRespira 2.6s var(--ease) infinite;}
@keyframes mvRespira{0%,100%{opacity:.45;}50%{opacity:1;}}
.savestate.is-saving .savedot{animation:mvRespira 1.1s ease-in-out infinite;}

/* o Mestre Auren está pensando e você saiu da Sessão: o ícone daquela linha
   respira baixinho, para a cena não parecer parada. Nunca é o único sinal —
   dentro da sessão a espera tem texto ("O Mestre Auren está lendo a cena…").
   (Antes daqui havia um @keyframes que ia de opacity:1 para opacity:1: um
   loop infinito que não desenhava nada. Saiu.) */
body.ia-ocupada #t-sessao .i{animation:mvRespira 2.1s var(--ease) infinite;}

/* =========================================================================
   CELULAR — não é o computador reduzido: é menos movimento, mais leitura.
   ========================================================================= */
@media (max-width:760px){
  html.mov [data-mov]{--mov-y:14px;--mov-x:0px;}
  html.mov [data-mov="cena"]{--mov-y:18px;transition-duration:var(--dur-bloco);}
  html.mov [data-mov="coluna"]{--mov-x:0px;--mov-y:14px;}
  html.mov [data-mov="imagem"]{transform:scale(1.02);}
  /* no celular o hero chega mais rápido: a pessoa já está rolando */
  html.mov #landing .lhero .lede{--h-d:260ms;}
  html.mov #landing .lhero .cta>*:nth-child(1){--h-d:360ms;}
  html.mov #landing .lhero .cta>*:nth-child(2){--h-d:420ms;}
  html.mov #landing .lhero .note{--h-d:480ms;}
  html.mov #landing .pilares li:nth-child(1){--h-d:540ms;}
  html.mov #landing .pilares li:nth-child(2){--h-d:585ms;}
  html.mov #landing .pilares li:nth-child(3){--h-d:630ms;}
  html.mov #landing .pilares li:nth-child(4){--h-d:675ms;}
  html.mov body.na-landing #landing .lhero::after{transition-duration:800ms;}
  /* o fundo fixo da faixa "a mesa" custa caro em rolagem no celular */
  #landing .lmesa::before{background-attachment:scroll;}
  .metal-host::before,.metal-cv{height:min(100%,460px);}
}

/* toque: nada depende de passar o mouse */
@media (hover:none){
  #landing .lk::after{display:none;}
  #landing .capa:hover>img,#landing .capa:hover .capa-duas img{transform:none;}
}

/* =========================================================================
   MOVIMENTO REDUZIDO — o conteúdo chega inteiro e fica.
   O que some: deslocamento espacial, paralaxe, loops decorativos, WebGL.
   O que fica: a mudança de estado (cor, foco, barra de vida), porque isso
   é informação, não enfeite.
   ========================================================================= */
@media (prefers-reduced-motion:reduce){
  html.mov [data-mov],
  html.mov [data-mov].in,
  html.mov body.na-landing #landing .lhero-texto>*,
  html.mov body.na-landing #landing .lhero-texto .cta>*,
  html.mov body.na-landing #landing .pilares li,
  html.mov #landing .contrast .col-b li,
  html.mov #landing .contrast .col-b li .i,
  html.mov #landing .capa .capa-txt>*,
  html.mov #landing .recursos li .i{
    opacity:1!important;transform:none!important;}
  html.mov [data-mov="linha"]::before{display:none;}
  html.mov body.na-landing #landing .lhero::after{opacity:0;transition:none;}
  html.mov .mv-split .mv-w{overflow:visible;padding:0;margin:0;}
  html.mov .mv-split .mv-w>i{opacity:1!important;transform:none!important;}
  #landing .lhero-arte{transform:none!important;}
  .mv-enter [data-mv-i]{animation:none;}
  /* o fio do botão para de respirar, mas continua ali: a espera ainda é
     visível, só não se mexe. */
  .mv-espera span,.savestate.is-saving .savedot,
  body.ia-ocupada #t-sessao .i,
  .btn[aria-busy="true"]::after{animation:none;opacity:1;}
  .log .msg:last-child,.log .msg:last-child .efx .e{animation:none;}
  #landing .lmesa::before{background-attachment:scroll;}
  .metal-cv{display:none;}
}
