Implement Exit Animations with Framer Motion's AnimatePresence in React
Learn how to animate components out of the DOM with a fade‑out or slide‑up effect using Framer Motion's AnimatePresence, verify the animation, and recover if it fails.
18 Apr 2026, 01:59 UTC

Desired Outcome
When a component is conditionally removed from the UI, it should fade out and slide up smoothly, then be unmounted from the DOM without causing a layout shift. This is achieved using Framer Motion's AnimatePresence component.
Prerequisites
- React version 16.8 or newer (hooks support).
- Framer Motion version 6 or newer installed via npm.
- A functional component that conditionally renders the target element (e.g., a modal or toast).
- Access to edit the project's source files and run npm commands.
Implementation Steps
-
Install Framer Motion
Run this command in the project root:
npm install framer-motionRequires write permission to the
node_modulesfolder andpackage.json. -
Create exit variants
Define an object that describes the final animated state. For a fade‑out + slide‑up:
const exitVariant = { opacity: 0, y: -20, transition: { duration: 0.3 } }; -
Wrap the conditional element
Place
AnimatePresencearound the element that may be removed. Give the element a uniquekeyso React can track its mount/unmount cycle.import { AnimatePresence, motion } from 'framer-motion'; function MyModal({ isOpen, onClose }) { return ( {isOpen && (Modal content
Close )} ); } export default MyModal;The
keymust change when the element's identity changes; a static string works when the element is either present or absent. -
Use the component
Toggle
isOpen via state or props to trigger the exit animation.import { useState } from 'react'; import MyModal from './MyModal'; function App() { const [show, setShow] = useState(false); return ( setShow(true)}>Open Modal setShow(false)} /> ); } export default App;
Verification
- Open the app in a browser, open the modal, then close it. Observe the fade‑out and slide‑up.
- Open React DevTools, select the modal component, and confirm it disappears from the tree after the animation ends.
- Use the browser’s Performance panel to record a frame while the animation runs; ensure frame duration stays below ~16 ms (60 fps) on target devices.
- Check that surrounding layout does not shift: measure the position of a nearby element before and after the animation; it should remain constant.
Troubleshooting and Recovery
- Animation does not play: Verify that the element rendered inside
AnimatePresencehas a stablekey. If the key changes on every render, React treats it as a new mount and the exit animation is skipped. - Component unmounts instantly: Ensure
AnimatePresenceis not wrapped by a component that prevents unmounting (e.g.,React.memowith a default prop that never changes, or a custom wrapper that swallows theanimateprop). Move the wrapper insideAnimatePresenceor forward theanimateprop. - Layout shift during exit: Avoid animating properties that affect document flow (e.g.,
width,height,margin). Preferopacityandtransform‑based values likeyorscale. - Performance drops on low‑end devices: Keep exit animations short (< 0.4 s) and limit to opacity/transform. Test with device emulation in Chrome DevTools.
- Fallback: If
AnimatePresencecannot be used, apply a CSS transition:
.modal-fade-out {
opacity: 0;
transform: translateY(-20px);
transition: opacity 0.3s ease, transform 0.3s ease;
}
// In component
{isOpen && (
...
)}
This CSS‑only approach will remove the element after the transition ends via a setTimeout or transitionend event listener.
0 replies
A thoughtful contribution can make all the difference. Be the first to share one.