您的位置:首页 > 产品设计 > UI/UE

前端框架vue.js系列(11):元素动画过渡效果

2017-09-30 10:53 1131 查看
Vue 在插入、更新或者移除 DOM 时,提供多种不同方式的应用过渡效果。它们包括:

(1)在CSS过渡和动画中自动应用 class

(2)配合使用第三方 CSS 动画库,引入animate.css实现效果过渡

(3)配合使用第三方 JavaScript 动画库,引入velocity.js实现效果过渡

(4)引入tween.js数值实现数值过渡

在CSS过渡和动画中自动应用 class

Vue 提供了 transition 的封装组件,在下列情形中,可以给任何元素和组件添加 entering/leaving 过渡。也就是说,使用这种方法实现过渡效果,需要将实现效果的标签放到<transition ></transition>内。当插入或删除包含在 transition 组件中的元素时,Vue 将会做以下处理:

1. 自动嗅探目标元素是否应用了 CSS 过渡或动画,如果是,在恰当的时机添加/删除 CSS 类名。

2. 如果过渡组件提供了 JavaScript 钩子函数,这些钩子函数将在恰当的时机被调用。

3. 如果没有找到 JavaScript 钩子并且也没有检测到 CSS 过渡/动画,DOM 操作 (插入/删除) 在下一帧中立即执行。(注意:此指浏览器逐帧动画机制,和 Vue 的 nextTick 概念不同)

参考Demo:

<style>
.fade-enter-active,
.fade-leave-active {
transition: opacity .5s/*transition用法:属性值  时长。表示某属性值变化过程所需时长*/
}

.fade-enter,
.fade-leave-to {
opacity: 0
}
</style>

<div id="app">
<button v-on:click="show = !show">
Toggle
</button>
<transition name="fade">
<p v-if="show">大家好,这里是过渡动画测试</p>
</transition>
</div>

<script>
var vue = new Vue({
el: "#app",
data: {
show: true
}
});
</script>
点击按钮即可看到过渡效果。
(注)从上面例子可看到<transition name="fade">定义了name为'fade',这个'fade'的作用在于命名过渡动画样式,如上例子中的样式.fade-?-?。这是这种过渡效果的命名规则。在进入/离开的过渡中,会有 6 个 class 切换:

.name-enter:定义进入过渡的开始状态,在元素被插入时生效,在下一个帧移除。
.name-enter-active:定义过渡的状态。在元素整个过渡过程中作用,这个类可以被用来定义过渡的过程时间,延迟和曲线函数。
.name-enter-to: 2.1.8版及以上,定义进入过渡的结束状态。在元素被插入一帧后生效。
.name-leave: 定义离开过渡的开始状态,在离开过渡被触发时生效,在下一个帧移除。
.name-leave-active:定义过渡的状态。在元素整个过渡过程中作用,在离开过渡被触发后立即生效,这个类可以被用来定义过渡的过程时间,延迟和曲线函数。
.name-leave-to: 2.1.8版及以上 定义离开过渡的结束状态。在离开过渡被触发一帧后生效 (于此同时 v-leave 被删除)。
上例中的运行过程如图所示:



引入animate.css实现效果过渡

这种方法需要引用animate.css,百度上搜一下即可下载。它在进入/离开的过渡中,也会有 6 个 状态切换,与上一种类似:

enter-class

enter-active-class

enter-to-class (2.1.8+)

leave-class

leave-active-class

leave-to-class (2.1.8+)

参考Demo:

<link href="https://cdn.jsdelivr.net/npm/animate.css@3.5.1" rel="stylesheet" type="text/css">

<!-- animate.css过渡,地址:https://daneden.github.io/animate.css/ -->
<div id="animatecss">
<button @click="show = !show">
Toggle render
</button>
<transition name="custom-classes-transition" enter-active-class="animated bounceInDown" leave-active-class="animated bounceOutRight">
<p v-if="show">hello</p>
</transition>
</div>

<script>
var animatecss = new Vue({
el: '#animatecss',
data: {
show: true
}
})
</script>
(注)所包含的动画效果可以到animate.css官网查看。

引入velocity.js实现效果过渡

通过使用transition的钩子函数监听,监听状态类别如下:

<transition

  v-on:before-enter="beforeEnter"

  v-on:enter="enter"

  v-on:after-enter="afterEnter"

  v-on:enter-cancelled="enterCancelled"

  v-on:before-leave="beforeLeave"

  v-on:leave="leave"

  v-on:after-leave="afterLeave"

  v-on:leave-cancelled="leaveCancelled"

></transition>

参考Demo:

<script src="https://cdnjs.cloudflare.com/ajax/libs/velocity/1.2.3/velocity.min.js"></script>

<!-- velocity过渡 -->
<div id="velocityjs">
<button @click="show = !show">
Toggle
</button>
<transition v-on:before-enter="beforeEnter" v-on:enter="enter" v-on:leave="leave" v-bind:css="false">
<p v-if="show">
Demo
</p>
</transition>
</div>

<br />
<!-- velocity数组过渡 -->
<div id="staggered-list-demo">
<input v-model="query">
<transition-group name="staggered-fade" tag="ul" v-bind:css="false" v-on:before-enter="beforeEnter" v-on:enter="enter" v-on:leave="leave">
<li v-for="(item, index) in computedList" v-bind:key="item.msg" v-bind:data-index="index">{{ item.msg }}</li>
</transition-group>
</div>

<script>
var velocity = new Vue({
el: '#velocityjs',
data: {
show: false
},
methods: {
beforeEnter: function(el) {
el.style.opacity = 0
el.style.transformOrigin = 'left'
},
enter: function(el, done) {
Velocity(el, {
opacity: 1,
fontSize: '1.4em'
}, {
duration: 300
})
Velocity(el, {
fontSize: '1em'
}, {
complete: done
})
},
leave: function(el, done) {
Velocity(el, {
translateX: '15px',
rotateZ: '50deg'
}, {
duration: 600
})
Velocity(el, {
rotateZ: '100deg'
}, {
loop: 2
})
Velocity(el, {
rotateZ: '45deg',
translateY: '30px',
translateX: '30px',
opacity: 0
}, {
complete: done
})
}
}
})

var velocity2 = new Vue({
el: '#staggered-list-demo',
data: {
query: '',
list: [{
msg: 'Bruce Lee'
},

4000
{
msg: 'Jackie Chan'
},
{
msg: 'Chuck Norris'
},
{
msg: 'Jet Li'
},
{
msg: 'Kung Fury'
}
]
},
computed: {
computedList: function() {
var vm = this
return this.list.filter(function(item) {
return item.msg.toLowerCase().indexOf(vm.query.toLowerCase()) !== -1
})
}
},
methods: {
beforeEnter: function(el) {
el.style.opacity = 0
el.style.height = 0
},
enter: function(el, done) {
var delay = el.dataset.index * 150;
setTimeout(function() {
Velocity(
el, {
opacity: 1,
height: '1.6em'
}, {
complete: done
}
)
}, delay)
},
leave: function(el, done) {
var delay = el.dataset.index * 150
setTimeout(function() {
Velocity(
el, {
opacity: 0,
height: 0
}, {
complete: done
}
)
}, delay)
}
}
});
</script>

引入tween.js数值实现数值过渡
这种过渡效果是:当数字变化时,有一个动态的数字滚动效果。

参考Demo:

<script src="https://cdn.jsdelivr.net/npm/tween.js@16.3.4"></script>

<!-- tween.js数值过渡 -->
<div id="numDemo">
<label>{{animatedNumber}}</label>
<button @click="numChange">改变数值</button>
</div>

<script>
var num = new Vue({
el: '#numDemo',
data: {
animatedNumber: 0
},
methods: {
numChange: function() {
var vm = this;
var oldValue = parseInt(this.animatedNumber);
var newValue = parseInt(this.animatedNumber) + 999;

function animate() {
if(TWEEN.update()) {
requestAnimationFrame(animate)
}
}
new TWEEN.Tween({
tweeningNumber: oldValue
})
.easing(TWEEN.Easing.Quadratic.Out)
.to({
tweeningNumber: newValue
}, 500)
.onUpdate(function() {
vm.animatedNumber = this.tweeningNumber.toFixed(0)
})
.start();
animate();
}
}
});
</script>
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  vue 前端框架