0

This would be in a javascript function; with an onclick event handler or something. Then onclick it would fadeout what ever the id for box is using the document.getElementsById() object so why won't it fadeout? Like I have seen quite a lot of effects do? Also note I'm trying to do this with out jquery or any of the plugins as I'm trying to learn and master javascript.

setTimeout(function() {
        for(var i = 1; i< 9; i++) {
            setTimeout(function() {
            box.style.opacity = '0.'+i; 
            }, 100);
        }
        }, 1000);
Aaron
  • 11,239
  • 18
  • 58
  • 73
  • can you give more details as to the browser version and agent?? – Neeraj May 09 '11 at 13:46
  • possible duplicate of [Javascript: closure of loop?](http://stackoverflow.com/questions/5555464/javascript-closure-of-loop) and [many others](http://stackoverflow.com/search?q=closure+in+loop+%5Bjavascript%5D) – Matt Ball May 09 '11 at 13:55

3 Answers3

2

You should be calling that function recursively, like this:

    var box = document.getElementById('box');
    var i = 10;
    function fadeOut() {
        if (i>0) {
            i--;
            box.style.opacity = '0.'+i; 
            setTimeout(fadeOut, 100);
        }
    }
    setTimeout(fadeOut, 1000);
Matic
  • 484
  • 2
  • 7
  • that works exactly as I wanted can you please go into more detail of how everything works as I want to be able to understand exactly whats going on – Aaron May 09 '11 at 13:58
  • 1
    You scheduled all the timeouts almost at the same time (in that loop), so they all get triggered at almost the same time. What i've changed here is that first 'i' is set to 10, then 'fadeOut' gets called and decreases i (changes to 9), so the opacity is now set to 0.9, after that it schedules the next update in 100ms ('setTimeout(fadeOut, 100)') and the same function repeats until 'i' is 0 (and opacity is 0.0). Check recursion on wikipedia: http://en.wikipedia.org/wiki/Recursion – Matic May 09 '11 at 14:05
1

A few things:

1) You're actually fading the box in by increasing the opacity rather than fading it out by decreasing the opacity.

2) You're setting all the setTimeout functions at the same time, in the inner call you probably want to call a setInterval and have that increment i. Or, you could pile up the setTimeouts by setting the timing at 100*i rather than just 100.

ADW
  • 4,030
  • 17
  • 13
  • +1, I focused too much on the i being 9, but this is also a good answer, because even after that fix, your fade will wait 100s and then all the timeouts will be called. Probably not what he's looking for. – Robert May 09 '11 at 13:54
1

It wasn't really clear in your question but probably seeing it at 0.9 opacity instantly. The reasoning is that the for loop doesn't actually give you the value of i within the loop, only the address in which to access it. That's fine if you actually use it within the body of the for loop, but you're not doing that. When you set the timeout, by the time the timeout is called it's already finished iterating through the for loop and i is 9. Because of this, each timeout is only going to be setting the opacity to 0.9.

To fix this, you can wrap it in an automatically executed anonymous function, which passes in the value of i. Doing so will cause the anonymous function to scope i, and allow it to be accessed by the timeout when it's called.

setTimeout(function() {
    for (var i = 1; i < 9; i++) (function(i) {
        setTimeout(function() {
            box.style.opacity = '0.' + i;
        }, 100);
    }(i) // (i) at the end automatically executes, with the argument of i
}, 1000);
Robert
  • 21,110
  • 9
  • 55
  • 65