Search code examples
javascriptreactjstypescriptanimationframer-motion

why isnt my framer motion animation not triggering on unmount?


I'm trying to use the framer motion library to add an animation on component unmount but it's not working. I'm using the exit and initial prop values but there is no animation visible.

My app.tsx file:

import React, { useEffect, useState } from 'react';
import logo from './logo.svg';
import './App.css';
import Loader from './Components/Loader';
import { AnimatePresence, motion } from 'framer-motion';

const App: React.FC = () => {
  const [loading, setLoading] = useState<boolean>(true);

  useEffect(() => {
    setTimeout(() => setLoading(false), 5000);
  });

  return (
    <div className="App">
      <AnimatePresence exitBeforeEnter>
        {
          loading ?
            <Loader/> 
            :
            <header className="App-header">
              <img src={logo} className="App-logo" alt="logo" />
            </header>
        }
      </AnimatePresence>
    </div>
  );
};

export default App;

my loader component that I want to add the unmount animation to:

import { motion } from 'framer-motion';
import React from 'react';
import './style.css';

const Loader: React.FC = () => {
  return (
    <motion.div 
      initial={{ opacity: 1 }}
      exit={{ opacity: 0 }}
    >
      <div className={'loader'}>
        <h1>Loading...</h1>
        <p>Some last minute bug fixes..</p>
      </div>
    </motion.div>
  );
};

export default Loader;

Solution

  • From the docs:

    Child motion components must each have a unique key prop so AnimatePresence can track their presence in the tree.

    Any string will work as long as it's unique:

    <AnimatePresence exitBeforeEnter>
        {
          loading ?
            <Loader key="loader"/> 
            :
            <header className="App-header" key="header">
              <img src={logo} className="App-logo" alt="logo" />
            </header>
        }
      </AnimatePresence>