0

How to know which events slow down setTimeout()?

In my code I have a keyframe animation of 2 seconds.

I add a class to animate a div

$('#first').addClass('first-start');

and using setTimeout I add a class to stop the animation only after 1 second.

setTimeout(function() {
    $('#first').addClass('first-pause');
}, 1000);

All animation should be of 2 seconds if I don't block it.

I noticed that setTimeout sometimes not run exactly after 1000 milliseconds. How can I solve this?

How can I know which events slow down setTimeout?

Son Truong
  • 13,661
  • 5
  • 32
  • 58
Borja
  • 3,359
  • 7
  • 33
  • 66

2 Answers2

1

JavaScript timers are very inaccurate and there is nothing you can do about it. The timers only fire up if both of the following are met:

  • The Execution Stack of the currently active queued event is empty
  • The timer has elapsed

The key insight to grasping why is it so is understanding that JavaScript is single-threaded by specification (outside Node.js Cluster and Browser WebWorker APIs)

The first item on my list greatly depends on the code outside the setTimeout call in the current execution context. Depending on the event loop implementation, it can also depend even on other events that might have managed to interject between the current Event Queue item by virtue of arriving into the queue prior to the timer being set or even (in some implementations) by arriving before the timer has elapsed.

As JavaScript is single threaded nothing is interrupted in it's execution, and the items awaiting in the queue, including elapsed timers, are only processed when all the previous items have completely executed.

MDN, as always, gives you more detailed insight into theoretical aspects as well as the SpiderMonkey implementation of these concepts:

https://developer.mozilla.org/en-US/docs/Web/JavaScript/EventLoop

Bojan Markovic
  • 510
  • 7
  • 22
  • Yes but How can i know if queued is empty ? How can i know what there are in queue ? – Borja Sep 07 '18 at 07:17
  • Read the article. YOU put things in the queue by executing your application, but you cannot "know" if the queue is empty. Everything your web page does gets added to the queue. It's executed as it comes, there is no way to really control it. It's very likely, no, it's almost certain that you are looking at the whole problem the wrong way. You cannot control timing in JavaScript precisely so give up on that, timed keyframe animations are generally better done entirely using CSS -- there are dozens of resources about CSS animations online, at least one is very likely to be about your use-case. – Bojan Markovic Sep 07 '18 at 08:06
-1

inside the setTimeout use the removeClass function to remove the 'first-start' class that you added.

setTimeout(function() {
$('#first').removeClass('first-pause');

}, 1000);

sandeep kumar
  • 124
  • 1
  • 4