前言:这不是一个“完整”的答案,而是我能在合理时间内提出的最佳答案。 不发布我的结果似乎是一种耻辱,即使它们不是一个完美的答案......
它也只涵盖jQuery.animate;我没有研究 CSS 动画。
至少对于 jQuery,这很困难;它不像浏览器“知道”
一个 jQuery 动画。实际上,jQuery 所做的只是安排一个函数以 setTimeout() 运行 n 次
或setInterval(),每个函数调用都会将元素移动几个像素(或稍微更改一些其他内容),从而产生平滑动画的错觉。
您的浏览器必须以某种方式跟踪属于哪个函数调用
到哪个动画。因为这些是匿名函数,所以这不是真的
容易......可以使用某种特殊的调试语句,但AFAIK没有
浏览器实现了这样的功能。
我们可以做的是测量 jQuery.animate 对
step回调:
为每个动画元素的每个动画属性调用的函数。
此函数提供了修改 Tween 对象以更改
设置之前的属性值。
这最多只能给你一个近似值。但也许这很好
足够的;我创建了一个示例(见下文),它在我的
系统:
"a: 52 updates; 26 upd/s"
"b: 27 updates; 54 upd/s"
"c: 1080 updates; 360 upd/s"
您的系统可能会有所不同,但建议:
-
a 是最便宜的;
-
b 稍微贵一点,但实际上也很便宜
-
c 比 a 或 b 贵几倍。
为了检查这是否大致准确,我只启用了一个动画
时间,并检查这是否对应于 Chromium 和 Firefox 开发人员工具报告的内容:
- Chromium:
a 花了 40ms 非空闲; Firefox:2 次调用 n.fx.tick
- Chromium:
b 花了 40ms 非空闲时间; Firefox:4 次调用 n.fx.tick
- Chromium:
c 花了 130 毫秒非空闲; Firefox:36 次调用 n.fx.tick
这确实大致准确,但不完全准确。
这对您的应用程序是否足够有用?我不知道。也许,也许不是……
测试 HTML:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Animations test</title>
<style>
div { width: 200px; height: 100px; position: relative; color: #fff; }
#test_a { background-color: green; }
#test_b { background-color: red; }
#test_c { background-color: blue; }
</style>
</head>
<body>
<div id="test_a"></div>
<div id="test_b"></div>
<div id="test_c"></div>
<script src="http://code.jquery.com/jquery-2.1.1.min.js"></script>
<script src="anim.js"></script>
</body>
</html>
在 CoffeeScript 中测试 JS:
go = ->
a = b = c = 0
log = (n, t) ->
eval "u = #{n}"
str = "#{n}: #{u} updates; #{parseInt u / t, 10} upd/s"
$("#test_#{n}").html str
console.log str
$('#test_a').animate {left: '500px'},
duration: 500
step: -> a += 1
complete: -> log 'a', .5
$('#test_b').animate {top: '100px', left: '100px', opacity: 0.3, width: '500px'},
duration: 200
step: -> b += 1
complete: -> log 'b', 2
$('#test_c').animate {left: '500px', top: '300px', opacity: .75, height: '50px', width: '400px'},
duration: 3000
step: -> c += 1
complete: -> log 'c', 3
$(document).ready -> setTimeout go, 500
为了方便而编译相同的JS:
// Generated by CoffeeScript 1.7.1
(function() {
var go;
go = function() {
var a, b, c, log;
a = b = c = 0;
log = function(n, t) {
var str;
eval("u = " + n);
str = "" + n + ": " + u + " updates; " + (parseInt(u / t, 10)) + " upd/s";
$("#test_" + n).html(str);
return console.log(str);
};
$('#test_a').animate({
left: '500px'
}, {
duration: 500,
step: function() {
return a += 1;
},
complete: function() {
return log('a', .5);
}
});
return;
$('#test_b').animate({
top: '100px',
left: '100px',
opacity: 0.3,
width: '500px'
}, {
duration: 200,
step: function() {
return b += 1;
},
complete: function() {
return log('b', 2);
}
});
return $('#test_c').animate({
left: '500px',
top: '300px',
opacity: .75,
height: '50px',
width: '400px'
}, {
duration: 3000,
step: function() {
return c += 1;
},
complete: function() {
return log('c', 3);
}
});
};
$(document).ready(function() {
return setTimeout(go, 500);
});
}).call(this);