I’m using setInterval
to iterate through some images on a page and hide/show the next in a list after x seconds have passed. Every 30 seconds, I make a GET
request to check for new images from my server. Because the http
request takes about a second, setInterval begins executing the next iteration of my code which causes things to get a little screwy. What would be the best way to fix this issue? Here is a sample of my code:
function play(){ if(count == 30){ sync(); //while sync is running (because it takes so long) the play function is called again before the sync operation finishes. } //iterate through the photos hiding and showing them each second. } function sync(){ //http request that takes about a second to complete and updates images on the page. } window.setInterval(function(){ play(); currentSeconds++; count++; },1000);
Advertisement
Answer
Something like this.
function play(){ if(count == 30){ sync().then(() => setTimeout(play, 1000)); } else { setTimeout(play, 1000); } currentSeconds++; count++; } function sync(){ // Use a promise here. return new Promise((resolve, reject) => { setTimeout(() => { resolve(); }, 3000); }) //http request that takes about a second to complete and updates images on the page. } play();
OR , use a flag and simply return if sync is busy.
var syncActive = false; var currentSeconds = 0; var count = 0; function play(){ console.log('trying to play'); if(syncActive) return false; if(count == 30){ sync(); count = 0; } console.log(`could play - count: ${count}`); return true; } function sync(){ syncActive = true; console.log('syncing'); // DO LONG TASK sleep(5000).then(() => { // Note this code is in here to siumlate the long run. console.log('completed sync'); syncActive = false; }); } window.setInterval(function(){ if(play()) { console.log('increase counts'); currentSeconds++; count++; } },100); //<-- reduced to 100 for demo. // DUMMY CODE - Just for demo. const sleep = (milliseconds) => { return new Promise(resolve => setTimeout(resolve, milliseconds)) };