JS里面的两种运动函数

最新学了一个新的运动函数,与最初学习的有所不同,第一个运动是根据运动速度完成运动 ,第二个则是根据运动的时间来完成运动,而且把之前的函数都进行了一些兼容处理,在这里列出了看一下:

第一种animate1

复制代码
 1 function animate1(obj,data,rate,fn){//运动对象,运动数据,[运动速度],[回调函数]
 2     //遍历获取样式属性
 3     for(var key in data){ 
 4         //通过闭包将key私有化
 5         (function(k){
 6             /*  
 7                 获得样式宽高等会带有单位px需要处理掉,
 8                 如果使用parseInt,当传入opacity为小数时会变为0,所以使用parseFloat
 9             */
10             var cur = parseFloat( (obj.currentStyle || getComputedStyle(obj,null) )[k]);
11             
12             //对特殊值进行处理
13             if(k == "opacity"){
14                 //透明度当前值和目标值放大100倍,防止小数被舍去
15                 cur *= 100;
16                 data[k] *= 100;
17             }
18             
19             //当前值和目标值相等,直接返回
20             if(cur == data[k]){ return; }
21             
22             //通过自身名字定义定时器,解决每个运动共用一个定时器,造成清除其他运动定时器的问题
23             clearInterval(obj[k +'timer']);
24             
25             obj[k+'timer'] = setInterval(function(){
26                 
27                 //当前 += (目标-当前)*比率  比率不传则默认0.2
28                 cur += (data[k] - cur) * (rate || 0.2);
29                 
30                 if(Math.round(cur) == data[k]){ 
31                     //如果到达目标值清除定时器,同步数据
32                     clearInterval(obj[k+'timer']);
33                     cur=data[k];
34                     
35                     //回调,将定时器赋值为0,遍历每个定时器的值相加,如果所有定时器相加都为0,说明运动已经全部完成,执行回调函数
36                     obj[k + "timer"] = 0;
37                     var bl = 0;
38                     for(var key in data){
39                         bl += obj[key + "timer"];
40                     }
41                     if(bl == 0){
42                         //判断是否传入回调函数
43                         fn && fn.call(obj);
44                     }
45                 }
46                 
47                 //使用数据时判断特殊值
48                 if(k == "opacity"){
49                     //opacity具有兼容问题,ie8以下使用filter:alpha(opacity:100)
50                     obj.style.opacity = cur / 100;
51                     obj.style.filter = "alpha(opacity="+ cur +")";
52                 }else{  
53                     obj.style[k] = cur + "px";
54                 }
55             },30)
56         })(key);
57     }
58 }
复制代码

第二种animate2

复制代码
function animate2(obj,data,time,fn){//运动对象,运动数据,[运动时间],[回调函数]
    //保存初始值和变化值
    var start = {};
    var dis = {};
    
    for(var name in data){
        //获取样式,根据属性名保存在json中,{200,height:200}
        start[name] = parseFloat( (obj.currentStyle || getComputedStyle(obj,null) )[name]);
        //变化值 = 目标值 - 初始值  ----> {500,height:300}
        dis[name] = json[name] - start[name];
    } 
    
    //根据完成的时间获得运动次数,30为定时器频率
    var count = Math.round((time || 700)/30);
    
    //记录已经运动次数
    var n = 0;
    //将定时器绑定在对象身上,如果不同对象调用不会清除之前的运动
    clearInterval(obj.timer);
    obj.timer = setInterval(function(){
        
        n++;        
        for(var name in data){
            //位置:起点 + 距离/次数*n        
            var cur = start[name] + dis[name] / count * n;
            
            //对特殊属性进行判断
            if(name == "opacity"){
                obj.style.opacity = cur;
                obj.style.filter = "alpha(opacity:"+cur*100+")";
            } else {
                obj.style[name] = cur + "px";
            }
        }
            
        //如果已经运动次数和总次数相等,则完成运动,清除定时器,执行回调函数
        if(n == count){
            clearInterval(obj.timer);
            fn && fn.call(obj);
        }
        
    },30);  
}
复制代码

总结:

  animate1中各种运动完成的时间是不一致的,而animate2都是在同一时间内完成,

  因此,在调用回调函数的时候animate1需要判断对象中的所有的运动都已经完成,而animate2只要到达运动次数就可以了。

  两个运动函数都能解决正常的动画效果,并不能说哪个就一定比较好,而且都还有改善的地方,以后学到再继续完善

原文地址:https://www.cnblogs.com/LiuWeiLong/p/6084028.html