为什么不能在数组中定义图像,如下所示。 为什么每次都需要在数组中推送一个新的Image对象?
var canvas = null;
var ctx = null;
var assets = [
'/media/img/gamedev/robowalk/robowalk00.png',
'/media/img/gamedev/robowalk/robowalk01.png',
'/media/img/gamedev/robowalk/robowalk02.png',
'/media/img/gamedev/robowalk/robowalk03.png',
'/media/img/gamedev/robowalk/robowalk04.png',
'/media/img/gamedev/robowalk/robowalk05.png',
'/media/img/gamedev/robowalk/robowalk06.png',
'/media/img/gamedev/robowalk/robowalk07.png',
'/media/img/gamedev/robowalk/robowalk08.png',
'/media/img/gamedev/robowalk/robowalk09.png',
'/media/img/gamedev/robowalk/robowalk10.png',
'/media/img/gamedev/robowalk/robowalk11.png',
'/media/img/gamedev/robowalk/robowalk12.png',
'/media/img/gamedev/robowalk/robowalk13.png',
'/media/img/gamedev/robowalk/robowalk14.png',
'/media/img/gamedev/robowalk/robowalk15.png',
'/media/img/gamedev/robowalk/robowalk16.png',
'/media/img/gamedev/robowalk/robowalk17.png',
'/media/img/gamedev/robowalk/robowalk18.png'
];
var frames = [];
var onImageLoad = function() {
console.log("IMAGE!!!");
};
var setup = function() {
j=0;
body = document.getElementById('body');
canvas = document.createElement('canvas');
ctx = canvas.getContext('2d');
canvas.width = 100;
canvas.height = 100;
body.appendChild(canvas);
for (i = 0; i <= assets.length - 1; ++i) {
frames[i].src = assets[i];
}
setInterval(animate,30);
}
var animate = function() {
ctx.clearRect(0,0,canvas.width,canvas.height);
if (j >= assets.length) {
j=0;
}
var image = new Image();
image.src = frames[j];
ctx.drawImage(image,0,0);
++j;
}
答案 0 :(得分:1)
第一个原因是减少延迟。仅将URL放入数组意味着在动画开始之前尚未预取图像。当从网络中检索每个图像时,第一轮动画将变得缓慢而不稳定。如果重复动画,下一轮将更快。 这种考虑主要适用于替换页面(在DOM中)上的图像元素而不是通过写入画布的动画。
第二个原因是消除开销并提高动画循环的效率。在循环中使用new Image()
意味着每个帧的绘制时间包括创建新Image对象以及在画布上绘制它所花费的时间。 此外图像内容只能在获取后写入画布,因此必须从附加到图像对象的onload
处理程序写入画布。发布的代码不会这样做,并且可能会在某些浏览器中尝试同步将没有数据的图像写入画布时抛出错误。即使否则成功,重复的动画会在每次显示一个帧时产生一个新的Image对象,并搅动内存使用量。
请注意,在将对象推入预加载的图像对象数组之前,原始版本可能使用onImageLoad
来检查图像何时从Web完全加载。这是预取动画图像的首选方法。
在使用之前不要忘记定义j
: - )