Skip to main content

motion-web

Implementacao de motion na web sem GSAP - CSS moderno (scroll-driven animations, View Transitions, @starting-style, transition-behavior), e Motion/Framer Motion (AnimatePresence, layout animations, gestos, motion values). Use quando o movimento cabe na plataforma ou no React sem precisar de uma engine de timeline.

الانتقال إلى التثبيت

معلومات المصدر

المستودع
brunoolf/frontend-craft
آخر نشاط في المصدر
٢٧ أغسطس ٢٠٢٦ في ١٨:٢١
لغة SKILL.md المكتشفة
البرتغالية
النجوم
٠
التفرعات
٠

خيارات التثبيت

يُحدَّد Prompt الذي يراجع المصدر أولًا بشكل افتراضي. يمكنك التبديل إلى أمر مباشر أو تنزيل نسخة محلية.

مراجعة ملفات المصدر

اقرأ SKILL.md وأي ملفات مرافقة يعرضها SkillsMP قبل أن تقرر التثبيت.

عرض SKILL.md

SKILL.md
تعليمات المصدر · معاينة للقراءة فقط
name
motion-web
description
Implementacao de motion na web sem GSAP - CSS moderno (scroll-driven animations, View Transitions, @starting-style, transition-behavior), e Motion/Framer Motion (AnimatePresence, layout animations, gestos, motion values). Use quando o movimento cabe na plataforma ou no React sem precisar de uma engine de timeline.
# Motion na web Carregue `motion-principles` antes. Ela decide *se* e *quanto*; esta decide *como*. ## Escolha da ferramenta Suba um degrau só quando o anterior não resolver: | Necessidade | Ferramenta | |---|---| | Hover, foco, toggle, mudança de estado simples | `transition` CSS | | Loop, keyframes, entrada sem JS | `@keyframes` | | Entrada e saída de elemento com estado (React) | Motion `AnimatePresence` | | Elemento que muda de posição no layout | Motion `layout` | | Arrastar, gesto, movimento contínuo ligado a input | Motion values | | Ligado ao progresso do scroll, efeito simples | CSS scroll-driven | | Transição entre páginas ou vistas | View Transitions API | | Sequência complexa, pin de scroll, orquestração fina | GSAP (`gsap-*`) | Cada degrau custa bundle e complexidade. A maioria dos pedidos para em CSS. ## CSS moderno **`@starting-style`** resolve o problema antigo de animar a entrada de um elemento que acabou de existir — inclusive de `display: none` e de camada de topo: ```css .popover { opacity: 1; transition: opacity 200ms ease-out, display 200ms allow-discrete; } @starting-style { .popover { opacity: 0; } } ``` `transition-behavior: allow-discrete` (ou `allow-discrete` na shorthand) é o que permite `display` e `overlay` participarem da transição. Sem isso, a saída pisca. **Scroll-driven animations** rodam fora da main thread — ganho real de suavidade: ```css @keyframes reveal { from { opacity: 0; transform: translateY(16px); } } .card { animation: reveal linear both; animation-timeline: view(); animation-range: entry 10% cover 35%; } ``` `view()` acompanha o elemento cruzando o viewport; `scroll()` acompanha o progresso de um container. Cobre reveal e parallax sem uma linha de JavaScript. Verifique suporte e garanta que o estado sem suporte seja o estado final visível. **View Transitions:** ```js if (!document.startViewTransition) { update(); return } document.startViewTransition(() => update()) ``` Sempre com o caminho de fallback. Use `view-transition-name` em elementos que persistem entre as vistas para obter continuidade — é o que dá a transição de elemento compartilhado sem biblioteca. ## Motion (Framer Motion) **Entrada e saída.** `AnimatePresence` exige `key` estável e o filho direto sendo `motion`: ```jsx <AnimatePresence mode="wait"> {open && ( <motion.div key="panel" initial={{ opacity: 0, y: 8 }} animate={{ opacity: 1, y: 0 }} exit={{ opacity: 0, y: 8 }} transition={{ duration: 0.2, ease: [0.32, 0.72, 0, 1] }} /> )} </AnimatePresence> ``` `mode="wait"` quando a saída e a entrada não devem coexistir. Sem ele, os dois se sobrepõem — às vezes é o que se quer, às vezes é o defeito. **`layout`** anima mudança de posição e tamanho automaticamente, usando a técnica FLIP: transform em vez de propriedades de layout. Use `layoutId` para continuidade entre componentes diferentes — item de lista que vira detalhe. É a ferramenta certa para continuidade e a errada para tudo mais: aplicada amplamente, custa caro. **Spring** para gesto e arraste. Pense em rigidez e amortecimento, não duração. Não use spring em fade puro — não há massa para simular. **`whileInView`** com `viewport={{ once: true }}` para revelação na entrada. Sem `once`, o elemento reanima toda vez que reentra, o que irrita rápido. **`useReducedMotion()`** é o hook oficial. Use-o para trocar o preset de movimento, não para desligar tudo. ## React: o essencial - Toda animação criada em componente é destruída no unmount. - Não anime durante o render. Efeito ou callback de evento. - Objeto de `transition` recriado a cada render vira prop nova toda vez. Extraia para constante fora do componente. - Em Next com App Router, componente que anima é client component. Empurre a fronteira para baixo: marcar a página inteira como client desfaz o benefício do server rendering. ## Armadilhas - Animar altura de `auto`. Use `grid-template-rows: 0fr → 1fr`, ou `max-height` com um teto conhecido, ou `layout` do Motion. - `AnimatePresence` sem `key`, ou com o `motion` não sendo filho direto: a saída simplesmente não roda. - Vários elementos com o mesmo `view-transition-name` na mesma vista quebram a transição inteira. - `backdrop-filter` em container que rola. - `will-change` deixado permanentemente no CSS.
عرض على GitHub