7 mars 2025 (updated: 7 mars 2025)
Chapters
Animasjoner er et must-have i dagens webutvikling, da de hever UX og prosjektkvalitet. Lær om Framer Motion, et kraftig React-bibliotek for animasjoner.
Animasjoner er en veldig viktig aspekt ved å lage moderne webapplikasjoner, spesielt når det gjelder å forbedre brukeropplevelsen eller trekke oppmerksomhet til nøkkelområder i applikasjonsgrensesnittet. Godt utførte animasjoner vil forbedre kvaliteten på prosjektet, øke dets appell, og til slutt få brukerne til å komme tilbake oftere. Imidlertid er ikke opprettelsen av animasjoner alltid enkel. I denne artikkelen deler jeg min erfaring med Framer Motion, et åpen kildekode-bibliotek som akselererer opprettelsen av animasjoner i React-miljøet.
Animasjoner kan deles inn i flere grunnleggende typer:
Fade in/out - Det animerte elementet blir gradvis mer synlig/usynlig. Denne effekten kan ofte sees mens man ruller nedover en nettside. Et eksempel på en Fade in-animasjon:
Slide in/out - Det animerte elementet beveger seg på skjermen. Slide in/out-animasjoner kombineres ofte med Fade in/out-animasjoner. Et eksempel på en Slide in + Fade in-animasjon:
Rotate and Scale - Rotate-animasjoner er der elementet roterer rundt sin egen akse, mens i Scale-animasjoner reduserer eller øker det animerte elementet størrelsen sin. Et eksempel på en animasjon der knappen øker i størrelse ved hover, og ved klikk roterer den rundt sin egen akse:
Dessa animationer kan betraktes som grunnleggende. Imidlertid er det ingenting som hindrer oss i å kombinere disse animasjonene og skape mer avanserte og komplekse effekter som vil tiltrekke brukerens oppmerksomhet og interesse.
For å lage høykvalitets komplekse animasjoner, vil vi oftest trenge spesielle, dedikerte biblioteker som vil forenkle og akselerere denne prosessen betydelig. Et slikt bibliotek i React.js-miljøet er Framer Motion.
Framer Motion er et åpen kildekode-bibliotek som gjør det enkelt og raskt å lage animasjoner i React-miljøet. Ved å bruke de samme konseptene som React, muliggjør det blant annet animasjon av elementer som fjernes fra DOM-treet, håndtering av komponentstatus og deres animasjonsstatus gjennom spesiallagde hooks, oppretting av egendefinerte hooks, eller reduksjon av pakkestørrelse gjennom asynkron animasjonslasting.
De viktigste og mest brukte komponentene i Framer Motion-biblioteket er motion-komponentene. Som vi kan lese i dokumentasjonen, “Motion-komponenter er DOM-primitiver optimalisert for 60fps animasjon og bevegelser.” Kort sagt, motion-komponenter er ekvivalente med vanlige HTML-elementer som div, p, h1, button, beriket med spesielle props som gjør animasjon enkel.
De mest brukte props inkluderer initial, som lar oss sette egenskapene som animasjonen skal starte fra, animate - der vi spesifiserer egenskapene som vårt animerte element skal strebe etter under animasjonen, og exit, som spesifiserer hva som skal skje med det animerte elementet når det fjernes fra DOM-treet.
La oss anta at vi ønsker å ha en blå firkant som endrer farge til grønn, øker i størrelse og roterer 360 grader under animasjonen. For å oppnå denne effekten ved hjelp av Framer Motion, trenger vi bare noen få ekstra linjer med kode.
Som du kan se, en enkel sak! Vi setter de innledende verdiene og de som vårt element skal animere til, og det er det!
Som du kan se i eksemplet ovenfor, brukte vi en egenskap kalt transition. Takket være den kan vi enkelt spesifisere, blant annet, typen animasjon, tid, forsinkelse, osv.
Det finnes flere typer animasjoner tilgjengelig. I vårt eksempel brukte vi spring-animasjoner, som ga animasjonen et mer realistisk utseende. Animasjoner kan også konfigureres på mange måter. Vi har muligheten til å endre egenskaper som masse, sprett, demping, stivhet eller hastighet. For eksempel, ved å endre masseegenskapen til en høyere verdi, vil objektet oppføre seg med større masse og bevegelsen vil være mye tregere. De tilgjengelige spring-animasjonsegenskapene kan sjekkes her.
Den ovennevnte animasjonen vil starte umiddelbart når elementet blir gjengitt, det vil si etter at siden er oppdatert. Hva med situasjoner der vi ønsker at elementet vårt skal animere som respons på rulling, det vil si bare når det vises i vårt synsfelt? Alt vi trenger å gjøre er å endre animate-egenskapen til whileInView.
Som du kan se, vi byttet animate-egenskapen til whileInView. Vår firkant begynner å animere først når den vises i synsfeltet. Vi la også til viewport once = true-attributtet slik at firkanten vår ikke animerer igjen når den rulles av og vises igjen i synsfeltet. Du kan også se hvordan firkanten oppfører seg når vi øker masseegenskapen.
Disse eksemplene var bare enkle animasjoner med ett element. Hva om vi ønsker at animasjonene skal gjelde for et større antall komponenter? Må vi bruke den animerte objektet på hvert element vi ønsker å animere? Og hva om vi ønsker at elementene våre skal animere med en viss tidsforsinkelse fra det sist animerte elementet? Må vi jobbe rundt forsinkelsesegenskapen hver gang? For å svare på dette spørsmålet, la oss se på variants-egenskapen. Variants lar oss definere animasjoner som sprer seg gjennom DOM-treet. La oss se på følgende eksempel.
Som vi kan se i eksemplet ovenfor, setter vi ikke animate-egenskapen som et enkelt objekt, men bruker i stedet variants-egenskapen.
Vi definerer offScreen og onScreen varianter og animerer listen vår ved å endre opasiteten. Deretter bruker vi det faktum at disse variantene sprer seg nedover i DOM-treet og spesifiserer hva som skal skje med hvert enkelt listeelement - Square-komponentene. I tillegg, ved å bruke varianter, har vi muligheten til å håndtere barna til det animerte elementet, for eksempel ved å bruke staggerChildren-egenskapen. Dette vil føre til at hvert påfølgende element i listen vår vises med en spesifisert forsinkelse fra det forrige. Du kan lese mer om varianter her.
De ovennevnte eksemplene viser bare den grunnleggende funksjonaliteten vi får ved å bruke Framer Motion. Jeg oppfordrer deg til å bli kjent med dokumentasjonen og se hva mer biblioteket har å tilby.
Jeg nevnte tidligere at Framer Motion lar oss animere elementer som fjernes fra DOM-treet. Dette er sant, men vi vil diskutere det i neste kapittel.
Å animere elementer under deres fjerning er veldig enkelt. Alt vi trenger å gjøre er å pakke vår animerte komponent i en spesiell wrapper kalt AnimatePresence. Wrapperen lar oss forsinke avmonteringsoperasjonen til animasjonen er ferdig, men hvis vi vil at komponenten vår skal være animert, må vi huske å definere exit animasjonen.
For å demonstrere hvordan vi kan bruke AnimatePresence, vil vi lage en enkel applikasjon ved hjelp av Next.js rammeverket. Applikasjonen vil ha to sider, og overganger mellom dem vil bli animert. Så, la oss lage noen Sideoverganger.
La oss begynne med å generere prosjektet og installere de nødvendige bibliotekene. Instruksjonen for å opprette et nytt prosjekt ved hjelp av Next.js kan finnes her. Vi vil også bruke TypeScript i prosjektet, så jeg anbefaler å generere prosjektet med --typescript flagget.
Ok, vi har prosjektet, la oss nå installere de nødvendige bibliotekene. I tillegg til Framer Motion-biblioteket, vil vi også bruke Tailwind CSS, som vil la oss raskt style uten å måtte lage CSS-filer. For å installere Framer Motion-biblioteket, bare lim inn npm i framer-motion i konsollen og installer det. Installeringen av Tailwind er litt mer komplisert, og de fullstendige instruksjonene kan finnes her. Vår interesse ligger i trinn 2-4.
Først, la oss redigere vår pages/index.tsx fil. Vi vil vise en enkel header og tre kort som vil være lenker til vår neste side. Hver av komponentene vil ha animasjoner definert ved hjelp av varianter. For å gjøre koden lettere å lese i tilfelle av et blogginnlegg, vil jeg sette alt i én fil. index.tsx filen ser slik ut:
De nevnte kortene er lenker til vår andre side, som vi nå vil lage. I mappen pages, legg til en fil [id].tsx. På denne siden vil vi ha en kort tekst sammen med en lenke som returnerer til Hjem-siden. Hele filen ser slik ut:
Hvis vi nå kjører prosjektet, vil vi dessverre merke at animasjonene våre ikke fungerer. Dette skyldes at vi har opprettet varianter påEnter og initial og tildelt dem til elementene våre, men vi har ikke definert hvilke spesifikke egenskaper varianter refererer til, som i eksempelet med SquareList ovenfor. Det vil vi gjøre nå i en egen komponent.
La oss lage en Layout-komponent. La oss rendre den nevnte AnimatePresence i den.
Vår nye komponent vil være en wrapper for hele applikasjonen. Det er et div-element her som vil animere overgangen vår fra en side til en annen. Vi definerer de tidligere nevnte variantene her og tildeler dem de riktige egenskapene. Vi vet nå at varianter har evnen til å spre seg dypt inn i DOM-treet, så alle elementer har tilgang til endringer i varianter inntil de definerer sine egne egenskaper, som animate.
Under onExit animasjonen, i tillegg til å endre opacitet, vil vi bruke clipPath-egenskapen for å lage en utskjæringsanimasjon av siden vår fra venstre til høyre. Vi må også huske at for at et element skal bli riktig animert før det avmonteres, må vi gi det en unik nøkkel-egenskap som vil tillate AnimatePresence å spore elementets tilstedeværelse i DOM-treet. Den nyopprettede komponenten rendres i _app.tsx filen.
Hvis vi nå kjører prosjektet vårt, bør vi se følgende effekt:
Som du kan se, har vi med suksess laget en enkel overgangsanimasjon mellom sider. I tillegg har hvert av våre elementer en Fade in og Slide in animasjon. Jeg anbefaler sterkt å eksperimentere med den tilgjengelige koden og sjekke hvordan den reagerer på endringer.
Som vi kan se, er Framer Motion et veldig brukervennlig bibliotek for å lage animasjoner i React. Det tilbyr mange komponenter og funksjonalitet som betydelig fremskynder prosessen med å lage animasjoner. De fleste av disse ble ikke diskutert igjen, men jeg oppfordrer deg sterkt til å gjøre deg kjent med dem. Det er også verdt å nevne den godt skrevne dokumentasjonen som betydelig forenkler arbeidet.
Er det verdt å vurdere Framer Motion som et bibliotek for animasjon? Absolutt! Men før vi tar et endelig valg, må vi huske at til tross for at Framer Motion er et flott bibliotek, har det mye konkurranse å vurdere, som Gsap, React-spring, blant andre.
11 mars 2025 • Maria Pradiuszyk