Motion Reference
Motion is a production-ready animation library for React. Use it for fluid animations, gestures, and layout transitions.
Import
import { Plus, X } from "lucide-react";
interface Item {
id: string;
text: string;
}
const containerVariants = {
hidden: { opacity: 0 },
visible: {
opacity: 1,
transition: { staggerChildren: 0.1 },
},
};
const itemVariants = {
hidden: { opacity: 0, scale: 0.8 },
visible: { opacity: 1, scale: 1 },
exit: { opacity: 0, scale: 0.8, transition: { duration: 0.2 } },
};
export default function App() {
const [items, setItems] = React.useState<Item[]>([]);
const addItem = () => {
setItems(prev => [...prev, { id: crypto.randomUUID(), text: `Item ${prev.length + 1}` }]);
};
const removeItem = (id: string) => {
setItems(prev => prev.filter(item => item.id !== id));
};
return (
<div>
<motion.div
whileHover={ { scale: 1.02 }}
whileTap={ { scale: 0.98 }}
>
<button onClick={addItem} className="w-full">
<Plus className="w-4 h-4" />
Add item
</button>
</motion.div>
<motion.div
variants={containerVariants}
initial="hidden"
animate="visible"
className="space-y-2"
>
<AnimatePresence mode="popLayout">
{items.map(item => (
<motion.div
key={item.id}
variants={itemVariants}
exit="exit"
layout
>
<div className="p-4 flex justify-between items-center">
<span>{item.text}</span>
<motion.button
whileHover={ { scale: 1.1 }}
whileTap={ { scale: 0.9 }}
onClick={() => removeItem(item.id)}
className="text-muted-foreground hover:text-destructive"
>
<X className="w-4 h-4" />
</motion.button>
</div>
</motion.div>
))}
</AnimatePresence>
</motion.div>
</div>
);
}
AnimatePresence Modes
// "sync" (default) - All enter/exit animations happen simultaneously
<AnimatePresence mode="sync">
// "wait" - Wait for exit animation to complete before entering
<AnimatePresence mode="wait">
// "popLayout" - Exiting items are removed from layout flow immediately
<AnimatePresence mode="popLayout">
Best Practices
- Use spring animations for natural-feeling motion on physical properties
- Use AnimatePresence for exit animations
- Use layout prop for smooth layout transitions
- Use variants for coordinated animations
- Keep animations subtle - 0.2-0.5s duration for most UI animations
- Use whileHover/whileTap for interactive feedback