vue使用优化后的动画级别的定时器 requestAnimationFrame 比setInterval, setTimeout效果要高很多
概述
默认情况下,requestAnimationFrame执行频率是1000/60,大概是16ms多执一次。
本文只是写了一个最简单的例子,您可依据业务要求进行套用。
效果图
完整demo
<template>
<div>
<div class="box">
<div class="elem" :style="{left:left+'px'}"></div>
</div>
<div class="btns">
<button @click="stop" :disabled='!isLoop'>停止动画</button>
<button @click="start" :disabled='isLoop'>重新开始动画</button>
<button @click="add" :disabled='!isLoop'>加速</button>
<button @click="sub" :disabled='!isLoop'>减速</button>
</div>
</div>
</template>
<script>
export default {
data() {
return {
flag: true,
left: 0,
max:200,
step:5,
rid:'',
interval:0,
interval0:1000/60,//动画时间,1s动一下
nowTime:'',
lastTime:'',
isLoop:true,//正在运行
}
},
mounted() {
this.initInterval()
this.animLoop()
},
methods: {
initInterval(){
this.isLoop=false
this.interval=this.interval0
},
animLoop(){
this.isLoop=true
//记录当前时间
this.nowTime = Date.now()
// 当前时间-上次执行时间如果大于diffTime,那么执行动画,并更新上次执行时间
if(this.nowTime-this.lastTime > this.interval){
this.lastTime = this.nowTime
this.render();
}
this.rid=window.requestAnimationFrame(this.animLoop);
},
render() {
if (this.flag == true) {
if (this.left >= this.max-this.step) {
this.flag = false
}
this.left+=this.step
} else {
if (this.left <= 0+this.step) {
this.flag = true
}
this.left-=this.step
}
},
start(){
this.initInterval()
this.animLoop()
},
stop(){
cancelAnimationFrame(this.rid)
this.initInterval()
},
add(){
this.interval=this.interval/2
},
sub(){
this.interval=this.interval*2
}
},
};
</script>
<style scoped>
.box{
border:1px solid #f00;
position: absolute;
width: 300px;
height: 100px;
box-sizing: border-box;
left: 30px;
top:30px;
z-index: 1;
}
.elem {
width: 100px;
height: 100px;
background: lightgreen;
position: absolute;
left: 0;
top: 0;
}
.btns{
position: absolute;
top: 150px;
}
</style>