Framer Motion i Animacje Web
Framer Motion dla React, GSAP ScrollTrigger, CSS scroll-driven animations i Web Animations API — od prostych do zaawansowanych animacji.
6 narzędzi do animacji webowych
Framer Motion, GSAP, CSS animations, Scroll-driven, WAAPI i Motion One — każde narzędzie optymalizuje inny case użycia.
| Narzędzie | Rozmiar | Typ | Mocne strony | Kiedy |
|---|---|---|---|---|
| Framer Motion | ~40KB | React library | Layout, gestures, declarative | React SPA, complex UI animations |
| GSAP + ScrollTrigger | ~50KB | Vanilla JS | Timelines, ScrollTrigger, SVG | Scroll storytelling, complex sequences |
| CSS Transitions/Animations | 0KB | Native CSS | GPU, no JS, best performance | Hover, simple state changes |
| CSS Scroll-driven | 0KB | Native CSS 2024 | Scroll bez JS, Chrome 115+ | Modern browsers, scroll effects |
| Web Animations API | 0KB | Native Web API | GPU, imperativo, compositable | Custom animation libraries |
| Motion One | ~3KB | WAAPI wrapper | Tiny, WAAPI-based, timeline | Vanilla JS, bundle size critical |
Często zadawane pytania
Co to jest Framer Motion i jak działa animacja w React?
Framer Motion: biblioteka animacji dla React (Matt Perry, Framer, 2019). Declarative API. Physics-based animations. Gesture support. Layout animations. motion component: zamień div na motion.div. Dodaj animate, initial, transition props. motion.div initial={{opacity: 0, y: 20}} animate={{opacity: 1, y: 0}} transition={{duration: 0.5}}. Kluczowe koncepty: initial — stan startowy. animate — stan docelowy. exit — stan przy unmount (wymaga AnimatePresence). transition — duration, delay, ease, type. variants — nazwane stany animacji. const variants = {hidden: {opacity: 0}, visible: {opacity: 1}}. motion.div variants={variants} initial='hidden' animate='visible'. Stagger children: staggerChildren: 0.1 w transition parentu — dzieci animują się po kolei. AnimatePresence: animacja przy unmount. Wrap warunkowych komponentów. key prop — identyfikuje element dla exit animation. Layout animations: motion.div layout — automatycznie animuje zmiany layoutu. layoutId — shared element transition (morph między elementami). Drag: motion.div drag dragConstraints={{left: -100, right: 100}}. dragElastic, dragMomentum, onDrag, onDragEnd. Gestures: whileHover, whileTap, whileFocus, whileDrag — animacje na gesture. Scroll animations: useScroll() — scrollY/scrollX/scrollYProgress. motion.div style={{opacity: scrollYProgress}}. useTransform(scrollYProgress, [0, 1], [0, 1]).
Framer Motion — zaawansowane: spring, useAnimate i Reorder?
Spring physics: type: 'spring'. stiffness (200), damping (10), mass (1). Bez duration — fizyka określa czas. Naturalnie wyglądające animacje. stiffness: 300 = szybka. stiffness: 50 = wolna. Tween: type: 'tween' (domyślny). ease: 'linear' / 'easeIn' / 'easeOut' / 'easeInOut' / 'circOut' / cubicBezier([.17,.67,.83,.67]). Inertia: type: 'inertia' dla momentum po drag. useAnimate hook (Framer Motion 10+): const [scope, animate] = useAnimate(). animate(scope, {opacity: 1}). animate(scope.current.querySelector('.child'), {x: 100}). Sekwencje: await animate(element, {opacity: 0}). await animate(element, {x: 100}). Reorder.Group i Reorder.Item: drag-to-reorder listy. Automatyczna animacja przy zmianie kolejności. axis='y' lub axis='x'. Bez własnej logiki sortowania (Reorder zarządza). MotionValue: useMotionValue(0) — reaktywna wartość animacji. useTransform(motionValue, [0, 100], [0, 1]) — mapowanie wartości. motionValue.set(50) — programmatyczna zmiana. useSpring(motionValue, {stiffness: 200}) — spring na motionValue. Viewport animations: motion.div whileInView={{opacity: 1}} initial={{opacity: 0}} viewport={{once: true, margin: '-100px'}}. Brak potrzeby Intersection Observer. Performans: GPU-accelerated (transform, opacity). will-change: auto. useReducedMotion() — respektuj user preference. Framer Motion 11: mini bundle (bez 3D). Optimized scroll. View transitions.
GSAP — GreenSock Animation Platform, kiedy zamiast Framer Motion?
GSAP: profesjonalna biblioteka animacji JS (GreenSock, 1998/2008). Obsługuje non-React, React, vanilla JS, Canvas, SVG. Gsap.to(element, {duration: 1, x: 100, opacity: 0, ease: 'power2.out'}). gsap.from() — animuj od. gsap.fromTo() — od do. gsap.set() — bez animacji. Timeline: const tl = gsap.timeline(). tl.to('.box', {x: 100}).to('.text', {opacity: 0}, '-=0.3'). Offset: '+=0.5' (po poprzedniej + 0.5s), '-=0.3' (przed końcem), '<' (równolegle). Plugins GSAP (większość bezpłatna): ScrollTrigger: animacje na scroll. gsap.registerPlugin(ScrollTrigger). scrollTrigger: {trigger: '.section', start: 'top 80%', toggleActions: 'play none none reverse'}. SplitText (premium): animuj litery / słowa / linie. Flip Plugin: animacje layoutu (jak Framer Motion layout). DrawSVG, MorphSVG (premium). GSAP vs Framer Motion: GSAP — więcej kontroli, ScrollTrigger (niezastąpiony), non-React, SVG, timeline. Framer Motion — React-native DX, layout animations, declarative, gestures, prostszy. GSAP React: useGSAP hook (@gsap/react). Scope + revert. Cleanup automatyczny. Kiedy GSAP: kompleksowe animacje scroll. SVG animations. Timeline z wieloma elementami. Non-React projekty. Kiedy Framer Motion: React SPA. Proste animacje. Gesture-driven UI. Layout animations. Shared element transitions.
CSS animations i transitions — kiedy nie potrzebujesz biblioteki?
CSS Transitions: transition: opacity 0.3s ease, transform 0.2s ease. Przy hover, :focus, klasa zmiana. Najlepsza wydajność — GPU, nie blokuje JS thread. CSS Animations: @keyframes fadeIn {from {opacity: 0} to {opacity: 1}}. animation: fadeIn 0.5s ease forwards. animation-delay, animation-iteration-count, animation-fill-mode. Nowe CSS Properties 2024: scroll-driven animations: animation-timeline: scroll(). animation-range: entry 0% 100%. Brak JS potrzebny dla animacji scroll. @starting-style: animacja przy display:none -> display:block przejście. transition-behavior: allow-discrete. view-transition-name + @view-transition: cross-document transitions. Wreszcie bez JS. animation-composition: add / accumulate. CSS @layer: kaskada animacji. prefers-reduced-motion: @media (prefers-reduced-motion: reduce). Szanuj preferencje użytkownika. Kiedy CSS wystarczy: hover states, button feedback. Simple fade/slide przy route change. Loading spinners. Toast notifications. Skeleton screens. Kiedy potrzebujesz biblioteki: shared element transitions (bez View Transitions API). Gesture-driven animations. Physics-based spring. Complex sequenced animations. Imperatywne animacje. Tailwind animacje: animate-spin, animate-bounce, animate-ping, animate-pulse. tailwindcss-animate plugin. cn() do warunkowego stosowania. Radix UI + Tailwind: data-[state=open]:animate-in data-[state=closed]:animate-out. Wbudowane w shadcn/ui.
Performans animacji — GPU acceleration, Layout Thrashing i will-change?
Jak przeglądarka renderuje: Style -> Layout -> Paint -> Composite. Animacja transform/opacity: tylko Composite (GPU). Animacja width/height/top/left: Layout + Paint + Composite (wolne). Zasada: animuj TYLKO transform i opacity dla GPU acceleration. transform: translateX(100px) translate zamiast left: 100px. opacity zamiast visibility. Layout Thrashing: odczyt i zapis DOM na przemian -> przeglądarka re-layoutuje co iterację. Złe: element.style.width = element.offsetWidth + 10 + 'px' (w pętli). Dobre: batchuj odczyty, potem zapisy. requestAnimationFrame: synchronizuj z browser repaint. Nie setTimeout dla animacji. cancelAnimationFrame dla cleanup. will-change: hint dla GPU. will-change: transform na animowanych elementach. Nie używaj na wszystkim (zbędne zasoby GPU). will-change: auto po animacji przez JS. Composite layers: każdy will-change tworzy layer. Zbyt wiele = memory issues. Narzędzia: Chrome DevTools -> Performance -> record. Framerate (60fps = 16ms per frame). Long Tasks (czerwone). Layer panel — composite layers. Rendering panel — FPS meter. Web Animations API (WAAPI): element.animate([{opacity: 0}, {opacity: 1}], {duration: 500, easing: 'ease'}). Native, GPU, bez bibliotek. Framer Motion używa WAAPI. React 18 + useTransition: startTransition dla non-urgent updates. Nie blokuj animacji heavy re-renderami. useDeferredValue — defer expensive renders. Wirtualizacja: nie animuj 1000 elementów jednocześnie. react-virtual + animate only visible.
Powiązane artykuły
Skontaktuj się z nami
Porozmawiajmy o Twoim projekcie. Bezpłatna wycena w ciągu 24 godzin.
Wyślij zapytanie
Telefon
+48 790 814 814
Pon-Pt: 9:00 - 18:00
adam@fotz.pl
Odpowiadamy w ciągu 24h
Adres
Plac Wolności 16
61-739 Poznań
Godziny pracy
Wolisz porozmawiać?
Zadzwoń teraz i porozmawiaj z naszym specjalistą o Twoim projekcie.
Zadzwoń teraz