该框架通过妙味课堂学习视频时候跟着封装的。如下所示
function startMove(obj,json,endFn){
clearInterval(obj.timer);
obj.timer = setInterval(function(){
var bBtn = true;
for(var attr in json){
var iCur = 0;
if(attr == 'opacity'){
if(Math.round(parseFloat(getStyle(obj,attr))*100)==0){
iCur = Math.round(parseFloat(getStyle(obj,attr))*100);
}
else{
iCur = Math.round(parseFloat(getStyle(obj,attr))*100) || 100;
}
}
else{
iCur = parseInt(getStyle(obj,attr)) || 0;
}
var iSpeed = (json[attr] - iCur)/8;
iSpeed = iSpeed >0 ? Math.ceil(iSpeed) : Math.floor(iSpeed);
if(iCur!=json[attr]){
bBtn = false;
}
if(attr == 'opacity'){
obj.style.filter = 'alpha(opacity=' +(iCur + iSpeed)+ ')';
obj.style.opacity = (iCur + iSpeed)/100;
}
else{
obj.style[attr] = iCur + iSpeed + 'px';
}
}
if(bBtn){
clearInterval(obj.timer);
if(endFn){
endFn.call(obj);
}
}
},30);
}
function getStyle(obj,attr){
if(obj.currentStyle){
return obj.currentStyle[attr];
}
else{
return getComputedStyle(obj,false)[attr];
}
}
下面的实现方法是依据tween.js插件实现的方案。通过时间计算偏移量,这样即使定时器执行时间被浏览器篡改,也能通过时间进行补偿,最终运动到目标位置
//运动对象,属性,持续时间,运动方式,回调函数
function startMove(obj, attrs, duration, fx, callback) {
clearInterval(obj.timer);
var startTime = new Date();
var j = {};
for (var attr in attrs) {
j[attr] = {};
//计算初始值
if (attr == 'opacity') {
j[attr].b = Math.round(getStyle(obj, attr) * 100);
} else {
j[attr].b = parseInt(getStyle(obj, attr));
}
//计算初始值与目标值的差值
j[attr].c = attrs[attr] - j[attr].b;
}
var d = duration;
obj.timer = setInterval(function() {
var t = new Date() - startTime;
//当第一进入方法的时间与当前时间差值大于动画的执行时间,停止定时器。
if (t >= d) {
t = d;
clearInterval(obj.timer);
}
for (var attr in attrs) {
var curValue = Tween[fx](t, j[attr].b, j[attr].c, d);
if (attr == 'opacity') {
obj.style.opacity = curValue / 100;
obj.style.filter = 'alpha(opacity=' + curValue + ')';
} else {
obj.style[attr] = curValue + 'px';
}
}
if (t == d) {
callback && callback();
}
}, 15);
}
function getStyle(obj, attr) {
if (obj.currentStyle) {
return obj.currentStyle[attr];
} else {
return getComputedStyle(obj, false)[attr];
}
}
针对运动中用到的tween.js中的easeOut减速曲线做简单分析。由于fraction是一个时间差跟运动时间的比值,所以范围就是从0-1,时间t进行归一化处理也是从0-1
1、黑线部分公式fraction = - t * t
2、粉红色部分公式fraction = - t * t + 1;
3、红色部分公式fraction = - (t - 1) * (t - 1) + 1=- t * t + 2t
对于运动时间为d的过程讲,那么公式就是 - (t / d) * (t / d) + 2t = -(t/=d) * t + 2t = - (t/=d)(t-2);
所以最终的公式就是 -c(t/=d)(t-2) + b; 其中c就是从初始位置到结束位置的变化量。b就是初始位置。纵观整个公式的意思就是根据实际运动时间与计划运动时间的比值,然后乘上初始位置到结束为止的差值,在加上初始位置的值,就是要运动到的位置。由于fraction最大值为1,所以始终可以运动到结束位置,而不会出现小数造成的误差。
如果想要实现更多的运动效果,跟我公式计算即可。要注意曲线纵坐标的值最后一定为1,因为曲线得总体趋势一定是上升的!
这个是我的推导过程,如果有更好的方法,请指导!