Javascript将参数传递给循环内的setTimeout函数

Han*_*com 4 javascript loops

我正在尝试在Javascript中的for循环中执行setTimeout()函数,但是我得到错误"shape is undefined",即使它被定义了,我将它作为参数传递给函数内部setTimeout()调用.如果删除setTimeout机箱,该功能可以正常工作.

为什么我会收到此错误,如何解决?

谢谢!

function fadeShapes(layer, movement, opacity, speed) {
    var shapes = layer.getChildren();

    for(var n = 0; n < shapes.length; n++) {
        var shape = layer.getChildren()[n];
        setTimeout(function(shape){
            shape.transitionTo({
                alpha: opacity,
                duration: speed
            }); 
        }, 100);                
    }
}
Run Code Online (Sandbox Code Playgroud)

Den*_*nis 12

JavaScript没有块作用域,因此所有超时函数都指向同一个变量shape,在循环结束后指向数组的未定义索引.您可以使用匿名函数来模拟您正在寻找的范围:

for(var n = 0; n < shapes.length; n++) {
    var shape = shapes[n]; //Use shapes so you aren't invoking the function over and over
    setTimeout((function(s){
        return function() { //rename shape to s in the new scope.
            s.transitionTo({
                alpha: opacity,
                duration: speed
            });
        };
    })(shape), 100);   
}
Run Code Online (Sandbox Code Playgroud)

正如你可以通过我的问题来判断括号是否匹配,这可能有点棘手.这可以通过ES5清理Array.forEach:

layer.getChildren().forEach(function(shape) { //each element of the array gets passed individually to the function
    setTimeout(function(shape){
        shape.transitionTo({
            alpha: opacity,
            duration: speed
        }); 
    }, 100);                
});
Run Code Online (Sandbox Code Playgroud)

forEach内置于现代浏览器中,但可以在Internet Explorer旧版浏览器中进行填充.