這篇要來介紹一下一些能用 React 實現一些動畫效果的函式庫,首先介紹的就是本篇的主角 React Transition Group,
React Transition Group 目前有四種元件,分別是:
接著我們來一一介紹它們吧!
使用這個元件可以透過一些 api 去訂閱元件的狀態,常用在 mount 和 unmount 過渡動畫的元件。
此元件有四種狀態:
至於改變 Transition 元件的狀態是透過 in 這個 props 屬性。
in 為 true 時,會從 entering 改變到 entered
in 為 false 時,會從 exiting 改變到 exited
當然除了 in 這個 props 屬性外還有其他的屬性,可以參考官方文件,這裡就不一一介紹。
import React, { useState } from "react";
import { Transition } from "react-transition-group";
const duration = 300;
const defaultStyle = {
  transition: `opacity ${duration}ms ease-in-out`,
  opacity: 0,
  padding: 20,
  display: "inline-block",
  backgroundColor: "#8787d8"
};
const transitionStyles = {
  entering: { opacity: 0 },
  entered: { opacity: 1 }
};
const Fade = ({ in: inProp }) => (
  <Transition in={inProp} timeout={duration}>
    {(state) => (
      <div
        style={{
          ...defaultStyle,
          ...transitionStyles[state]
        }}
      >
        I'm A fade Transition!
      </div>
    )}
  </Transition>
);
export default function App() {
  const [show, setShow] = useState(false);
  const handleToggle = () => setShow(!show);
  return (
    <>
      <button onClick={() => handleToggle()}>Click to toggle</button>
      <Fade in={!!show} />
    </>
  );
}
這個元件除了具有 Transition 元件的功能外,可以根據狀態(appear、enter、exit)去切換不同的 className,進而改變樣式。
appear 狀態: 為 false 時當 CSSTransition 元件加載完畢後不執行動畫,為 true 時元件加載完畢則立即執行動畫。
如果要元件初次渲染就有動畫,則需要設成 true。
常見的 className 設定有以下幾種,記得 CSSTransition 元件要設定對應的 className 開頭(以下範例就是 classNames="example") :
/* in 為 true 時: */
.example-enter {
/*   opacity: 0; */
}
.example-enter-active {
/*   opacity: 1; */
/*   transition: opacity 200ms; */
}
/* in 為 false 時: */
.example-exit {
/*   opacity: 1; */
}
.example-exit-active {
/*   opacity: 0; */
/*   transition: opacity 200ms; */
}
<CSSTransition
  in={showMessage}
  timeout={300}
  classNames="example"
  unmountOnExit
  onEnter={() => setShowButton(false)}
  onExited={() => setShowButton(true)}
>
  <!-- ... -->
</CSSTransition>
// App.js
import React, { useState, useEffect } from "react";
import { CSSTransition } from "react-transition-group";
import "./styles.css";
const Fade = ({ children, ...props }) => (
  <CSSTransition {...props} timeout={1000} classNames="fade">
    {children}
  </CSSTransition>
);
export default function App() {
  const [show, setShow] = useState(false);
  useEffect(() => {
    let id = setInterval(() => {
      setShow(!show);
    }, 5000);
    return () => clearInterval(id);
  }, [show]);
  return (
    <Fade in={show}>
      <div className="greeting">Hello world</div>
    </Fade>
  );
}
/* styles.css */
.fade-enter {
  opacity: 0.01;
}
.fade-enter.fade-enter-active {
  opacity: 1;
  transition: opacity 1000ms ease-in;
}
.fade-exit {
  opacity: 1;
}
.fade-exit.fade-exit-active {
  opacity: 0.01;
  transition: opacity 800ms ease-in;
}
.greeting {
  padding: 20px;
  background-color: #ccc;
  width: 200px;
  margin: auto;
  text-align: center;
  border-radius: 4px;
}
這篇先到這邊結束,下篇將會介紹剩下的兩個元件,以下補充一些相關連結。
除了 React Transition Group,React-Motion 也是相當不錯的 React 動畫函式庫!