By Jonah H.


2010-11-08 01:57:36 8 Comments

This is my first real dive into JavaScript. Sure I've used it before, but I've never really written anything from scratch.

Anyway, I'm having a very strange problem that I hope someone can figure out for me.

I'm trying to make the text from a div fade from black to white. Simple, yeah?

The following code works. It will change the color to white, however, the setTimeout time of 500ms is being ignored.

If you use Chrome and look at the JS console, you'll easily see that the doFade() method is being called almost instantaneously, not every 500 milliseconds.

Can anyone explain this?

var started = false;
var newColor;
var div;
var hex = 0;

function fadestart(){
    if (typeof fadestart.storedColor == 'undefined') {
        div = document.getElementById('test');
        fadestart.storedColor = div.style.color;
    }
    if(!started){
        console.log('fadestart');
        newColor = fadestart.storedColor;
        started = true;
        setTimeout(doFade(), 500);
    }
}

function fadestop(){
    console.log('fadestop');
    div.style.color = fadestart.storedColor;
    started = false;
    hex = 0;
}

function doFade(){
    if(hex<=238){
        console.log(hex);
        hex+=17;
        div.style.color="rgb("+hex+","+hex+","+hex+")";
        setTimeout(doFade(), 500);
    }
}

3 comments

@KeatsKelleher 2010-11-08 02:01:47

You need to get rid of the parentheses on doFade().

The parentheses invoke the function instantly.

Just use this in stead: doFade

@Surreal Dreams 2010-11-08 02:03:12

Actually, you want 'dofade()' as a string, in quotes. You got the root cause, though.

@Alex Jasmin 2010-11-08 02:03:46

Yes func evaluates to the function itself while func() call the function and evaluates to its return value.

@KeatsKelleher 2010-11-08 02:04:48

pretty sure you don't need quotes. You should be able to put either doFade or "doFade". I think there might even be slight performance benefits to not converting the string "doFade" to the function handle.

@deceze 2010-11-08 02:05:28

@Surreal Actually, you want to pass the function without parentheses. Quoting it executes the passed code snippet in the global context, which can have vastly different results.

@Angiosperm 2010-11-08 02:09:29

@Surreal Dreams setTimeout accepts function or a string to be eval'd as the callback. Functions in Javascript are first class objects and can be (often are) passed around freely around as such. As Javascript is incredibly dynamic, eval can (and should) almost always be avoided.

@Angiosperm 2010-11-08 02:15:24

@deceze a function passed to setTimeout is still executed in the global context, as setTimeout provides no way to change the receiver of the callback (and trying this with setTimout.call/apply throws in exception). While I agree that you shouldn't pass a quoted string, your reasoning is wrong.

@deceze 2010-11-08 02:20:59

@Angio I mean that if a function is not callable from the global scope, e.g. because it was created non-publically in its own scope, setTimeout("foo()", 500) may not be able to call anything, or it will call the wrong function. I'm not talking about .call context at the moment.

@Angiosperm 2010-11-08 02:29:45

@deceze Ah ok thats much clearer :)

@Surreal Dreams 2010-11-08 02:48:40

@akellehe, @deceze & @Angio: Thanks for correcting me. I felt reasonably confident about my answer, but I knew if I was wrong you guys would be all over me and I'd learn it right. :) So thanks.

@CommaToast 2014-01-27 22:24:47

Why do they have it execute immediately with parens? Is it so that you can have another function return the function to use as the timeout dynamically?

@Doin 2016-05-12 18:29:03

@CommaToast: That is indeed the effect, but the reason is not specifically to enable you to do that. Rather it's a very general matter of syntax. If you write a(b(), c()) in javascript (as in most languages), it means "compute the return values of b() and c(), and then pass those as parameters to a()". This is true even in the case where "a" is "setTimeout".

@CrandellWS 2017-01-05 18:18:43

Anyone got documentation on this?

@Shrikant Dande 2018-05-29 13:33:34

how to pass parameters then?

@KeatsKelleher 2018-05-30 13:41:13

@ShrikantDande you can define your function with a closure. The function defining your function can accept parameters and return your function, which is passed to setTimeout

@Shrikant Dande 2018-05-31 11:13:50

actually I am passing function to dispatch , which is not working setTimeout(() => { dispatch(actions.success(mock_Response, dataKey)); }, 1000);

@PeterWong 2010-11-08 02:04:59

I think you should use setTimeout(doFade, 500); or setTimeout("doFade()", 500);

@ThiefMaster 2010-11-08 02:08:10

The quoted call also works but is awful. See akellehe's answer for details.

@PeterWong 2010-11-08 02:14:55

Yes of course. My habit is passing a function or even an inline function. But quoting it is always another choice (of course not a better choice in most cases).

@asoundmove 2016-10-05 13:08:27

Nice one, the quoted function seems to be the only choice if passing a parameter.

@asoundmove 2016-10-05 13:11:08

Just noticed this one has a better answer: stackoverflow.com/questions/3800512/…

@deceze 2010-11-08 02:04:30

setTimeout(doFade(), 500);

This line says "execute doFade(), then pass whatever value it returns to setTimeout, which will execute this return value after 500 milliseconds." I.e., you're calling doFade() right there on the spot.

Skip the parentheses to pass the function to setTimeout:

setTimeout(doFade, 500);

Related Questions

Sponsored Content

18 Answered Questions

[SOLVED] setTimeout or setInterval?

26 Answered Questions

[SOLVED] How can I pass a parameter to a setTimeout() callback?

12 Answered Questions

[SOLVED] How to dispatch a Redux action with a timeout?

8 Answered Questions

[SOLVED] Combination of async function + await + setTimeout

21 Answered Questions

[SOLVED] Getting the ID of the element that fired an event

  • 2008-09-07 08:09:38
  • Joda
  • 1217174 View
  • 930 Score
  • 21 Answer
  • Tags:   javascript jquery

17 Answered Questions

[SOLVED] Why is setTimeout(fn, 0) sometimes useful?

6 Answered Questions

[SOLVED] Difference between setTimeout with and without quotes and parentheses

16 Answered Questions

[SOLVED] Ajax request returns 200 OK, but an error event is fired instead of success

6 Answered Questions

[SOLVED] how to write setTimeout with params by Coffeescript

Sponsored Content