[React] Framer-motion 라이브러리 기본 사용법 2

예빈·2023년 4월 6일
1

React

목록 보기
6/6
post-thumbnail

Overview

Framer Motion is a simple yet powerful motion library for React.
It powers the amazing animations and interactions in Framer, the web builder for creative pros. Zero code, maximum speed.
In this quick overview, we'll take a look at some of the APIs that Motion offers.

Framer-motion 라이브러리 기본 사용법 1 보러가기

두 번째로 쓰는 Framer-motion 라이브러리 글이다.
사용할 수 있는 기능이 많아서 글을 여러 개로 나누게 되었는데, 이번 글에서는 AnimatePresenceexit 애니메이션 적용하는 방법에 대해 알아보려고 한다.

AnimatePresence란?

우선 공식문서에 쓰여 있는 내용은 아래와 같다.

Animate components when they're removed from the React tree.

AnimatePresence allows components to animate out when they're removed from the React tree.
It's required to enable exit animations because React lacks a lifecycle method that:
1. Notifies components when they're going to be unmounted and
2. Allows them to defer that unmounting until after an operation is complete (for instance an animation).
공식문서 바로가기

한국어로 풀어 써보자. React에서 컴포넌트가 제거될 때 애니메이션이 실행되는 동안 삭제를 연기한다.
쉽게 말하자면 컴포넌트가 제거될 때 애니메이션 효과를 줄 수 있다!

기본 사용법

import { AnimatePresence, motion } from "framer-motion";
import { useState } from "react";

const MyComponent = () => {
  const [view, setView] = useState(true);

  return (
    <>
      <AnimatePresence>
        {view ? (
          <motion.div
            className="box"
            exit={{ opacity: 0, rotate: 360, scale: 0 }}
          ></motion.div>
        ) : null}
      </AnimatePresence>
      <div className="btn" onClick={() => setView((view) => !view)}>
        Click me
      </div>
    </>
  );
};

export default MyComponent;

우선 "framer-motion" 에서 AnimatePresenceimport 한다.
그리고 제거 애니메이션을 줄 컴포넌트 바깥을 <AnimatePresence> 로 감싸준다.
현재 코드는 Click me 부분을 클릭할 때 view 값을 변경하고 있는데, 이 변수의 값에 따라 <motion.div> 를 노출할지 말지 결정할 것이다.

// 방법 1
<AnimatePresence>
  {view ? (
	<motion.div
	  className="box"
	  exit={{ opacity: 0, rotate: 360, scale: 0 }}
    ></motion.div>
  ) : null}
</AnimatePresence>

// 방법 2
<AnimatePresence>
  {view && (
	<motion.div
	  className="box"
	  exit={{ opacity: 0, rotate: 360, scale: 0 }}
    ></motion.div>
  )}
</AnimatePresence>

이렇게 두 가지 방법으로 쓸 수 있는데, 뭐가 더 나은 코드인지는 잘 모르겠지만 동일하게 작동하는 것으로 보인다.
지금 작성한 코드는 exit={{ opacity: 0, rotate: 360, scale: 0 }} 옵션이 적용되어 있으므로, 컴포넌트가 사라질 때 작아지면서 회전하고 불투명도가 0이 될 것으로 예상할 수 있다.
그러면 결과는 어떨까?

클릭하는 모습을 보여주고 싶어서 모바일/태블릿 환경에서 테스트했다.
예상처럼 잘 작동하는 것을 볼 수 있다.

5. exit, 천천히 사라지는 애니메이션 적용

이 기능을 활용해서 아래에서 천천히 나타나고 사라지는 컴포넌트를 만들어 보자.
이전 글에서 언급했던 initial , animate , transition 속성도 함께 활용해볼 것이다.

import { AnimatePresence, motion } from "framer-motion";
import { useState } from "react";

const MyComponent = () => {
  const [view, setView] = useState(true);

  return (
    <>
      <AnimatePresence>
        {view ? (
          <motion.div
            className="box"
            initial={{ opacity: 0, y: 50 }}
            animate={{ opacity: 1, y: 0 }}
            transition={{ duration: 2 }}
            exit={{ opacity: 0, y: 50 }}
          ></motion.div>
        ) : null}
      </AnimatePresence>
      <div className="btn" onClick={() => setView((view) => !view)}>
        Click me
      </div>
    </>
  );
};

export default MyComponent;

옵션은 복잡한 부분이 없어서 설명은 생략하고, 결과를 확인해보자.

이런 식으로 천천히 나타나고 사라지는 컴포넌트를 만들었다.
이번 프로젝트에서는 이런 방식으로 모달에 애니메이션을 적용했었다.

처음 나타날 때는 위로 스윽 올라오는 느낌을 주고, 닫을 때는 그 자리에서 불투명도만 조정해서 바로 사라지는 것처럼 조정해주었다.
정말 좋은 기능이라 생각보다 설명이 좀 길어졌는데, 한번 사용해 보면 AnimatePresence 가 없는 세상으로 돌아갈 수 없다.
다음 글에서 variants 에 관해 알아보도록 하자.

0개의 댓글