Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Javascript progress bar not updating 'on the fly', but all-at-once once process finished?

I have a loop which should be updating a progress bar as the loop increments, however it's only colouring the progress bar in one go after the loop has actually finished. I remember having a similar problem, if I used alert statements, the colouring would work, so I think it has to do with the concurrency of threads. To solve my old problem, I used setTimeout. However, this still isn't getting my progress bar coloured in real-time.

Here's what I'm doing:

for (var i = 0; i < numOfRows; i++) {
    setTimeout('ColourBlock(' + i + ')', 0);

    // do_work
}

function ColourBlock (position){
    document.getElementById("block" + position).style.backgroundColor = "orange";
}

Somebody told me it could be due to JavaScript optimization? Can anyone help please?

like image 304
James Avatar asked Apr 21 '11 11:04

James


2 Answers

It's not about threads. It's about the fact that when code makes a rapid sequence of DOM or style changes, the browser does not attempt to update the view between each one. Instead, it waits for things to calm down and then repaints.

If you coded up a sequence as you describe with a non-zero timeout value (say, 100 milliseconds) for each change, then you would see it happen. As you've written it, with a zero millisecond timeout, all the updates are going to happen within a very short period of time - probably well under a millisecond, unless you've got thousands of those blocks.

(Note that your sample code wouldn't give 100 as the timeout to each change; you'd have to put them incrementally farther into the future, adding another 100 for each one. Or you could use an interval timer and cancel it after the last update.)

like image 61
Pointy Avatar answered Oct 28 '22 13:10

Pointy


Browsers will not update UI while executing javascript code. When code finishes and control is returned to UI, the updates will happen all at once.

This is also the reason why it worked with alerts - when alert poped up, the javascript execution was suspended and control was returned to the UI.

like image 43
Luc Avatar answered Oct 28 '22 13:10

Luc