I'm encountering a problem with setTimeout, and I can't figure out why.
I'm using cordova, and the setTimeout function leads to curious comportment.
app.displayData = function(device) {
app.readThermometer(device);
app.readAccelerometer(device);
app.readHumidity(device);
app.readMagnetometer(device);
//setTimeout(app.displayData(device), 5000);
};
This is executed once.
app.displayData = function(device) {
app.readThermometer(device);
app.readAccelerometer(device);
app.readHumidity(device);
app.readMagnetometer(device);
setTimeout(app.displayData(device), 5000);
};
This is executed many times, but way faster than once every 5 seconds. It is a problem for me because it prevent jQuery from executing correctly. (Never getting the dom modification expected)
What am I missing? If it is a bug in cordova, do you know other way to delay code execution in javascript?
You're calling the function app.displayData directly
setTimeout(app.displayData(device), 5000);
Try the following instead
setTimeout(function () {
app.displayData(device);
}, 5000);
And another alternative if you prefer Function.bind
setTimeout(app.displayData.bind(app, device), 5000);
Related
I'm writing a "Game of Life" in javascript. I have all the logic done in a function called doGeneration(). I can repeatedly call this from the console and everything goes as planned, however, if I put it in a while loop the execution blocks the UI and I just see the end result (eventually).
while (existence) {
doGeneration();
}
If I add a setTimeout(), even with a generation limit of say 15, the browser actually crashes (Canary, Chrome).
while (existence) {
setTimeout(function() {
doGeneration();
},100);
}
How can I call doGeneration() once every second or so without blocking the DOM/UI?
You want setInterval
var intervalId = setInterval(function() {
doGeneration();
}, 1000);
// call this to stop it
clearInterval(intervalId);
I would use requestAnimationFrame(doGeneration). The idea of this function is to let the browser decide at what interval the game logic or animation is executed. This comes with potential benefits.
https://hacks.mozilla.org/2011/08/animating-with-javascript-from-setinterval-to-requestanimationframe/
Rather than using setINterval or setTimeout and assume some random time interval will be enough for the UI to update you shoul/could make the doGeneration smart enough to call itself after dom was updated and if the condition of existence is satisfied.
I'm trying to make a heartbeat animation with jQuery but it has some behavior I don't understand.
function pulse() {
var target = $('body');
target.animate({
'font-size': '100.2%',
'background-size': '230%'
}, 200).delay(1600)
.animate({
'font-size': '100.1%',
'background-size': '200%'
}, 200, function () {
window.setTimeout(pulse(), 4000);
}).delay(200);
}
Fiddle
It seems to me that the setTimeout(pulse(), 4000); is executed inmediatly, regardless of the timeout I use. Also, when I view it on my mobile phone it crashes after a short while.
I'm not too familiar with jQuery delay method but am I doing something wrong? I'm not sure if I read my own code correctly :)
EDIT:
Updated Fiddle: It's my other code that crashes the mobile device 'click document to mute' code crashes it. Would you mind taking a glance at it and tell me if you see what might crash the phone?
setTimeout(pulse(), 4000); should be setTimeout(pulse, 4000);
Notice there are no parentheses after pulse.
This is because when the parentheses are present, it means the function should be evaluated (which is what causes it's immediate execution). Without them, it is a reference to a function passed as an argument to setTimeout and will only be executed when setTimeout chooses to execute it, which is what you want.
I have an event that I'm firing every 5 seconds to check if a file has finished processing.
I'm doing the following:
if (InSuppArray(item.Id) == false && item.Status() == "Queue") {
var t = setTimeout(function () { checkQueuedSupp(item.OrderId) }, 5000);
suppIds.push({ Id: item.OrderId, TimerId: t });
}
Basically, multiple files can be uploaded so this created an array of timers and kills them as the files completes.
This works great in Firefox and Chrome, but the timer only fires one time in Internet Explorer.
Is there a better way to do this? I searched around and found some issues with IE and setTimeout but most of those were alluding to the fact that it just never works in IE, which mine at least fires once.
1) Is is working for first iteration? Yes your code works fine.
2) If repetitive is your problem then check the following:
setTimeout is not a repetitive method. Instead use setInterval.
if (InSuppArray(item.Id) == false && item.Status() == "Queue") {
var t = setInterval(function () { checkQueuedSupp(item.OrderId) }, 5000);
suppIds.push({ Id: item.OrderId, TimerId: t });
}
To make setTimeout as repetitive, try to make it has recursive.
setTimeout is to delay execute the function, not repeatedly to execute it. What you want is setInterval which will execute your function for every time interval you specified.
I have following code
$('document').ready(function() {
reload();
});
function reload() {
$('div#info').load('http://somesite.ru/script.php');
setInterval(reload(), 10000);
}
but seems like method reload() runs too fast. Firefox shows me message, about jquery.min.js is sems to busy. How can I make part of page refresh one time for each 10 seconds?
You should remove the (), also put the setInterval function outside the context of the reload function.
function reload() {
$('#info').load('http://somesite.ru/script.php');
}
$(document).ready(function() {
setInterval(reload, 10000);
});
Replace:
setInterval(reload(), 10000);
with:
setInterval(reload, 10000);
Use setTimeout() instead it is safe and performance wise good than the setInterval() to fulfill your requirement.
var time= setTimeout(reload,1000);
after checking certain conditions in the reload() method call the setTimeout inside it again
function reload()
{
/// your logic
setTimeout(reload,1000);
}
use the above variable to destroy the interval whenever you don't want to reload anymore
clearTimout(time);
Refer: http://www.w3schools.com/js/tryit.asp?filename=tryjs_setinterval
setInterval(function(){reload();},10000);
Another way is just use
$('document').ready(function() {
setInterval(function() {
$('div#info').load('http://somesite.ru/script.php');
}, 10000);
});
All works fine. Thanks a lot for your answers.
I am using the following code as part of an autocomplete script to avoid hammering the server with every keystroke:
var that = this;
textInput.bind("keyup", function() {
clearTimeout(that.timer);
that.timer = setTimeout (that.doStuff(), 2000);
});
Unfortunately, this does not clear the old timers. They still all execute.
Does anyone know what I'm missing?
Thanks!
You probably want to use:
that.timer = setTimeout (that.doStuff, 2000);
instead of:
that.timer = setTimeout (that.doStuff(), 2000);
Otherwise, doStuff will be called immediately.