# transition
在我们平时的前端项目开发中,经常会遇到如下需求,一个 DOM 节点的插入和删除或者是显示和隐藏,我们不想让它特别生硬,通常会考虑加一些过渡效果。
Vue.js 除了实现了强大的数据驱动,组件化的能力,也给我们提供了一整套过渡的解决方案。它内置了 <transition> 组件,我们可以利用它配合一些 CSS3 样式很方便地实现过渡动画,也可以利用它配合 JavaScript 的钩子函数实现过渡动画,在下列情形中,可以给任何元素和组件添加 entering/leaving 过渡:
- 条件渲染 (使用
v-if) - 条件展示 (使用
v-show) - 动态组件
- 组件根节点
那么举一个最简单的实例,如下:
let vm = new Vue({
el: '#app',
template: '<div id="demo">' +
'<button v-on:click="show = !show">' +
'Toggle' +
'</button>' +
'<transition :appear="true" name="fade">' +
'<p v-if="show">hello</p>' +
'</transition>' +
'</div>',
data() {
return {
show: true
}
}
})
@前端进阶之旅: 代码已经复制到剪贴板
.fade-enter-active, .fade-leave-active {
transition: opacity .5s;
}
.fade-enter, .fade-leave-to {
opacity: 0;
}
@前端进阶之旅: 代码已经复制到剪贴板
当我们点击按钮切换显示状态的时候,被 <transition> 包裹的内容会有过渡动画。那么接下来我们从源码的角度来分析它的实现原理。
# 内置组件
<transition> 组件和 <keep-alive> 组件一样,都是 Vue 的内置组件,而 <transition> 的定义在 src/platforms/web/runtime/component/transtion.js 中,之所以在这里定义,是因为 <transition> 组件是 web 平台独有的,先来看一下它的实现:
export default {
name: 'transition',
props: transitionProps,
abstract: true,
render (h: Function) {
let children: any = this.$slots.default
if (!children) {
return
}
// filter out text nodes (possible whitespaces)
children = children.filter((c: VNode) => c.tag || isAsyncPlaceholder(c))
/* istanbul ign