Transitions & Animations
Animate elements entering, leaving, and changing using Vue's built-in <Transition> and <TransitionGroup> components.
The <Transition> Component
Wrapping a single element (typically one toggled by v-if or v-show) in <Transition> automatically applies CSS classes as it enters and leaves, which you define the animation for in your own stylesheet.
<template> <button @click="show = !show">Toggle</button> <Transition name="fade"> <p v-if="show">Hello there!</p> </Transition></template>CSS Transition Classes
Vue applies a predictable set of classes, prefixed with the name you gave the <Transition>, at each phase of entering and leaving.
| Class | Applied During |
|---|---|
| fade-enter-from | The very start of entering (removed on the next frame) |
| fade-enter-active | The entire entering phase — define your transition/duration here |
| fade-enter-to | The end state of entering |
| fade-leave-from | The very start of leaving |
| fade-leave-active | The entire leaving phase |
| fade-leave-to | The end state of leaving (usually the "hidden" appearance) |
A Fade Transition Example
<style scoped>.fade-enter-active,.fade-leave-active { transition: opacity 0.3s ease;}
.fade-enter-from,.fade-leave-to { opacity: 0;}</style>In practice you almost always only need to define the -active (duration/easing) and -from (starting state) classes; -enter-to and -leave-from usually match the element's natural resting state.
Animating Lists with <TransitionGroup>
<TransitionGroup> applies the same enter/leave animation to every item in a v-for list, and additionally animates items moving position (e.g. after a sort or filter) when combined with a move class.
<template> <TransitionGroup name="list" tag="ul"> <li v-for="item in items" :key="item.id">{{ item.text }}</li> </TransitionGroup></template>
<style scoped>.list-enter-active, .list-leave-active { transition: all 0.3s ease; }.list-enter-from, .list-leave-to { opacity: 0; transform: translateX(20px); }.list-move { transition: transform 0.3s ease; }</style>Common Beginner Mistakes
<Transition> expects exactly one root element (or one toggled by v-if/v-else) inside it — for lists, use <TransitionGroup> instead.
Without a stable key, Vue can't correctly track which specific item is entering, leaving, or moving.
FAQs
Yes — <Transition> also supports JavaScript hooks (@before-enter, @enter, @leave) for integrating with animation libraries like GSAP.
Yes, by default a <span>, though the tag prop lets you specify a different element (like "ul" for a list, as shown above).
Summary
<Transition> and <TransitionGroup> give you CSS-class-driven animations for elements and lists, without hand-writing the enter/leave logic yourself. With advanced template features covered, the next section moves into routing and state management for multi-page apps.