I have created functions that call other functions like
function abc()
{
def();
}
function def()
{
xyz();
}
Lets say def() is called and at any moment I have a button
<button>STOP</button>
if I press it the execution terminates that means if the execution is run again it should run again from start.
I have seen other solutions in SO but they show how to pause a loop. Can anyone help me out?
You could use a variable to determine whether your code runs or terminates:
var abort = false;
function abc()
{
if (abort) {
return;
}
def();
}
function def()
{
if (abort) {
return;
}
xyz();
}
<button onclick="abort = true">STOP</button>
The only thing you'd have to add is to reset abort back to false whenever you're triggering the main functionality.
Related
I have two onclick functions on page:
function fn_name_1() {
//do buch of stuff
}
function fn_name_2() {
//do buch of stuff
}
When user clicks on fn_name_1() it starts executing which is take a while (about 4 seconds to complete).
If user clicks on fn_name_2() while fn_name_1() is in process it messes fn_name_1().
I had tried to setTimeOut for several second for fn_name_2() but it an awful user experience because when they hit the button they expect immediate result on their actions.
Basically I want to:
Scenario 1
User hit fn_name_2() button, its check if fn_name_1() is running and if it is not - proceed with executing fn_name_2() as normal.
Scenario 2
User hit fn_name_2() button, its check if fn_name_1() is running and if it dit, wait for completion and start executing automatically right after fn_name_1() is completed.
How it can be solved?
The simplest way is to have a variable which is accessible to both functions:
let runningTestOne = false;
function testOne(callback) {
console.log('Starting testOne');
runningTestOne = true;
setTimeout(() => {
runningTestOne = false;
console.log('done with testOne');
if (callback) {
callback();
}
}, 5000);
};
function testTwo() {
if (runningTestOne) {
console.log('cannot run');
return;
} else {
console.log('can run test two');
}
};
function runWithCallback() {
testOne(testTwo);
}
<button onclick="testOne()">Test One</button>
<button onclick="testTwo()">Test Two</button>
<button onclick="runWithCallback()">With callback</button>
Make fn_name_1 asynchronous, and let it return a promise, then you can store that promise, and only execute the second task when the promise resolved:
function fn_name_1() {
//do buch of stuff
return new Promise(resolve => {
setTimeout(resolve, 1000);
});
}
let isDone = fn_name_1();
function fn_name_2() {
isDone.then(() => {
//do buch of stuff
});
}
something like this?
var wait=false;
function fn_name_1() {
wait=true;
//do bunch of stuff
wait=false;
}
function fn_name_2() {
while(wait){/*do nothing*/}
//do bunch of stuff
}
I am executing setTimeout function in a page which loads via ajax call. but if i click the link to load the page again, i afraid the last setTimeout call still continues and the number of intervals of the calls set by setTimeout executes multiple times.
tried this is the remote page:
var RefreshInterval = null;
clearTimeout(RefreshInterval);
function someFunction()
{
....
setNextRefresh();
}
function setNextRefresh() {
console.log(wifiRadarRefreshInterval);
RefreshInterval = null;
clearTimeout(RefreshInterval);
RefreshInterval = setTimeout('someFunction();', 20*1000);
}
declare var RefreshInterval = null; outside of page loaded by ajax and use this code on the page:
clearTimeout(RefreshInterval);
function someFunction()
{
....
setNextRefresh();
}
function setNextRefresh() {
console.log(wifiRadarRefreshInterval);
clearTimeout(RefreshInterval);
RefreshInterval = setTimeout('someFunction();', 20*1000);
}
if i don't want to declare it in parent page, here is the solution i found:
//Clear previously loaded calls if exists
try{ clearTimeout(wifiRadarRefreshInterval); }catch(e){}
var wifiRadarRefreshInterval = null;
function somefunction(){
....
setNextRefresh();
}
function setNextRefresh() {
try{
clearTimeout(wifiRadarRefreshInterval);
wifiRadarRefreshInterval = null;
wifiRadarRefreshInterval = setTimeout('somefunction();', 20*1000);
}
catch(e){
console.log(e.message + e.stack);
}
}
Do not use this
var RefreshInterval = null;
clearTimeout(RefreshInterval);
You are actually assigning a null and then trying to clear it. Which will not work, The timeout must be cleared by using the clearTimeout and by passing the variable which was assigned to the setTimeout. Here you will end up passing a null so the timer is never cleared.
Here is a small sample which will demonstrate a fix to your problem JS Fiddle
So insted of setting the variable to null and then trying to clear it, Just check if the variable is not defined and if it is defined clear it, else move on. Use the code below, Also you must remove the top two lines as mentioned
function setNextRefresh() {
console.log(wifiRadarRefreshInterval);
if (typeof RefreshInterval !== 'undefined') {
clearTimeout(RefreshInterval);
}
RefreshInterval = setTimeout('someFunction();', 20*1000);
}
Click on the button say like 4 times, The output should be printed only once. That is if the ajax call is made 4 times the set time out must execute only once. Check below snippet for demo
var clickCount= 0; // just to maintain the ajax calls count
function NewPageSimilator(clicksTillNow) { // this acts as a new page. Let load this entire thing on ajaX call
if (typeof RefreshInterval !== 'undefined') {
clearTimeout(RefreshInterval);
}
function setNextRefresh() {
window.RefreshInterval = setTimeout(printTime, 3000); //20*1000
}
function printTime() {// dumy function to print time
document.getElementById("output").innerHTML += "I was created at click number " + clicksTillNow + '<br/>';
}
setNextRefresh();
}
document.getElementById("ajaxCall").addEventListener("click", function() { // this will act as a ajax call by loading the scripts again
clickCount++;
NewPageSimilator(clickCount);
});
document.getElementById("clear").addEventListener("click", function() { //reset demo
clickCount = 0;
document.getElementById("output").innerHTML = "";
});
<p id="output">
</p>
<button id="ajaxCall">
AJAX CALL
</button>
<button id="clear">
Clear
</button>
I am trying to block the back button in certain cases.
However as soon as I add the eventlistener it always blocks the back button.
document.addEventListener("deviceready", onDeviceReady, false);
function onDeviceReady() {
document.addEventListener("backbutton", onBackKey, false);
}
function onBackKey() {
if($scope.quicksetup)
{
alert("1");
return false;
}
else
{
alert("2");
return true;
}
}
It comes in the else structure but when it returns true it doesn't execute the back action anymore.
There are no errors whatsoever in logcat.
I have no idea what is causing this...
Once you set the listener you overwrite the backbutton behaviour no matter if you return true or false it will not execute the normal way anymore.
You need to use navigator.app.backHistory() and navigator.app.exitApp(); to handle going back and exiting the app.
The onbackbutton callback does not expect anything to be returned, it is not a boolean callback function.
function onBackKey() {
if($scope.quicksetup)
{
alert("1");
return;
}
else
{
alert("2");
navigator.app.exitApp(); //I guess you want to exit the app here
}
}
I want a js function executed once in my code.Either in resize or load handler
.I have a function which is executed if one statement is true and another in the window resize.So when my statement is true then the function is executed and i do not want the function executed again if the window is resized.
My js codes are
if(vertical){
vertical();
}
And
$(window).resize(function(){
vertical();
}
And
var vertical = function(){
..........
}
i also prevent execution if window is resized multiple times
You have to use some kind of flags for that:
var flag = false;
function vertical() {
if (!flag) {
flag = true;
// do your job
}
}
You could solve this via a semaphore.
So you set a flag to false and before you call the function you only want to call once check if(flag) , execute the code and set flag to true
Add a variable to check if the function is fired
var execute = true;
if(vertical){
if (execute) {
vertical();
execute = false;
}
}
$(window).resize(function(){
if (execute) {
vertical();
execute = false;
}
}
Just use unbind function at the end of vertical() function so when it will execute at first it will unbind the event for next window resize.
I'm using the $(window).scroll(); to specify a function to be call for when the user scrolls too close to the top or bottom.
The function takes a second to execute, and if they continue scrolling, it executes multiple times before the first one has even finished.
Is there any way I can let the function start executing and then tell the $(window).scroll() function that it needs to wait before executing that function again?
You could set a boolean that you're already checking scroll position:
checkingPosition = false;
$window.scroll(function() {
if(checkingPosition) return;
checkingPosition = true;
//do stuff
checkingPosition = false;
});
I'd do something like this to avoid scope issues/confusion by encapsulating the data into an object... in this case, the jQuery object (on the window element):
$(function() {
$(window).data('checking_scroll',false);
$(window).scroll(function() {
if($(this).scrollTop() >= 200 /* or whatever... */) {
if($(this).data('checking_scroll') === true) {
return false;
} else {
whatever_function();
}
}
});
});
function whatever_function() {
$(window).data('checking_scroll',true);
// do all your stuff...
$(window).data('checking_scroll',false);
}
... but that's just me.