Skip to content

Transition Group

<TransitionGroup> is a built-in component designed for animating the insertion, removal, and order change of elements or components that are rendered in a list.


<TransitionGroup> supports the same props, CSS transition classes, and JavaScript hook listeners as <Transition> , with the following differences:

  • By default, it doesn’t render a wrapper element. But you can specify an element to be rendered with the tag prop.

  • Transition modes are not available, because we are no longer alternating between mutually exclusive elements.

  • Elements inside are always required to have a unique key attribute.

  • CSS transition classes will be applied to individual elements in the list, not to the group / container itself.


Here is an example of applying enter / leave transitions to a v-for list using <TransitionGroup>:

<TransitionGroup name="list" tag="ul">
<li v-for="item in items" :key="item">
{{ item }}
</li>
</TransitionGroup>

The above demo has some obvious flaws: when an item is inserted or removed, its surrounding items instantly “jump” into place instead of moving smoothly. You can fix this by adding a few additional CSS rules:

<template>
<button @click="insert">Insert at random index</button>
<button @click="reset">Reset</button>
<button @click="shuffle">Shuffle</button>
<TransitionGroup tag="ul" name="fade" class="container">
<li v-for="item in items" class="item" :key="item">
{{ item }}
<button @click="remove(item)">x</button>
</li>
</TransitionGroup>
</template>

Now it looks much better - even animating smoothly when the whole list is shuffled.

Full Example

You can also specify custom transition classes for the moving element by passing the moveClass prop to <TransitionGroup>, just like custom transition classes on <Transition>.


By communicating with JavaScript transitions through data attributes, it’s also possible to stagger transitions in a list. First, we render the index of an item as a data attribute on the DOM element:

<TransitionGroup
tag="ul"
:css="false"
@before-enter="onBeforeEnter"
@enter="onEnter"
@leave="onLeave"
>
<li
v-for="(item, index) in computedList"
:key="item.msg"
:data-index="index"
>
{{ item.msg }}
</li>
</TransitionGroup>

Full Example in the playground