3

I'm trying the following:

var timeout = 300;
var colors = ['aqua', 'limegreen']
for (var i=0; i < 4; ++i) {
    console.log(colors[i % colors.length]);
    setTimeout(function() { changeColor(colors[i % colors.length]) }, i * timeout);
}

function changeColor(color) {
    console.log(color);
}

This doesn't work because the parameter for changeColor is resolved when it get's executed...this means, the color will always be the same. In my chrome it also didn't work to pass the params after the timeout:

var color = colors[i % colors.length];
setTimeout(function() { changeColor() }, i * timeout, color);

Well, I now have a workaround with an interval which works...but since I'm here to learn....how is this done with a timeout?

Cœur
  • 37,241
  • 25
  • 195
  • 267
CYB
  • 421
  • 1
  • 4
  • 12
  • possible duplicate of [Access outside variable in loop from Javascript closure](http://stackoverflow.com/questions/1331769/access-outside-variable-in-loop-from-javascript-closure) – Felix Kling Sep 08 '11 at 15:30

2 Answers2

1

You are suffering from a closure problem; the reference to the value of i has been captured and so all the functions contain the same value. You need to do something like this to capture the reference of i at the moment of invoking:

 for(var i = 0; i < 4; i++)
 {
      (function(index)
      {
          setTimeout(function()
          {
              changeColor(colors[index & colors.length]);
          }, index * timeout);
      })(i)
 }
Tejs
  • 40,736
  • 10
  • 68
  • 86
  • Of course this works also (at least with the modulo instead of the & ;). Thanks to you too. – CYB Sep 08 '11 at 16:31
1

The anonymous function which calls changeColor will be executed when for cycle will be ended already. So it will equal to the last value it gets. To prevent this capture the value you need in closure by wrapping the call to setTimeout with anonymous function:

for (var i=0; i < 4; ++i) {
    console.log(colors[i % colors.length]);
    (function(i){
        setTimeout(function() { changeColor(colors[i % colors.length]) }, i * timeout);
    })(i);    
}
bjornd
  • 22,397
  • 4
  • 57
  • 73