That guy
That guy

Reputation: 339

How to limit the number of iterations done by setInterval

I display video ads to my users. I don't host these ads by the way; I get them from another company.

When ever an ad is clicked it leaves a cookie in the user's browser. I've created a function that checks the existence of a cookie every 10 seconds.

What I would like to do is to limit the number of times this function can run or the number of seconds it can run for.

Below is the function:

function checkCookie()
{
var cookie=getCookie("PBCBD2A0PBP3D31B");
  if (cookie!=null && cookie!="")
  {
  alert("You clicked on an ad" );
  }

setInterval("checkCookie()", 10000);

So to recap. I want to limit the number of iterations that setInterval("checkCookie()", 10000); can make

Upvotes: 17

Views: 20842

Answers (5)

adi518
adi518

Reputation: 862

Passing a Callback to the Interval Function, which in turn updates a counter in the global scope:

var countIntervals = 0,
    intervalFunc = function(_callback){

        console.log(countIntervals);

        if(countIntervals > 5) {            
            clearInterval(setIntervalVar);
        } else {
            // do stuff
            _callback();
        }
    };

setIntervalVar = setInterval(intervalFunc.bind(null, function(){
    countIntervals++;
}), 500);

Upvotes: 0

Mr. Polywhirl
Mr. Polywhirl

Reputation: 48683

WindowTimers.setInterval(func, delay[, param1, param2, ...])

The 3rd parameter and onward in setInterval are optional parameters to pass to the interval function. Note, these optional arguments are not supported in IE9 and earlier.

We can use this to our advantage by avoiding the use of global or outside-scope. as seen below. The interval function keeps track of the limit and the current increment of the counter through the opts parameter.

The runTask function takes a mandatory fn argument which returns a boolean value to determine if the timer's task has been completed. There are two taks that are run in the example below, with each varying in the rate at which each is run and the condition to be met.

The first two tasks finish, but the last one runs out of attempts before the condition is met.

function writeLine(el, text) {
  el.innerHTML += [].slice.call(arguments, 1).join(' ') + '\n';
}

function runTask(options, interval, limit) {
  var interval = setInterval(function(opts) {
    opts.incr = (opts.incr || 0) + 1;    
    if (opts.fn(opts)) {
      clearInterval(interval);
      writeLine(opts.el, '>> Task finished...');
    } else if (opts.incr > limit) {
      clearInterval(interval);
      writeLine(opts.el, '>> Exceeded limit of ' + limit);
    } else {
      writeLine(opts.el, '>> Attempt: ' + opts.incr + '/' + limit);
    }
  }, interval, options);
}

// 5 atttempts to reach 4 in 250ms.
runTask({
  fn : function(opts) { return opts.incr === 4; },
  el : document.querySelectorAll('div.col')[0]
}, 250, 5);

// 10 atttempts to reach 7 in 100ms.
runTask({
  fn : function(opts) { return opts.incr === 7; },
  el : document.querySelectorAll('div.col')[1]
}, 100, 10);

// 10 atttempts to reach 15 in 50ms.
runTask({
  fn : function(opts) { return opts.incr === 15; },
  el : document.querySelectorAll('div.col')[2]
}, 50, 10);
.col {
  display: inline-block;
  width: 175px;
  font-family: monospace;
  white-space: pre;
  border: thin solid black;
  vertical-align: top;
  padding: 4px;
}
<div class="col"></div>
<div class="col"></div>
<div class="col"></div>

Upvotes: 1

j08691
j08691

Reputation: 207923

This should do it:

function checkCookie() {
    var cookie = getCookie("PBCBD2A0PBP3D31B");
    if (cookie != null && cookie != "") {
        alert("You clicked on an ad");
    }
    if (counter > 10) clearInterval(clr);
    counter++;
    clr = setInterval(function(){checkCookie()}, 10000);​
}
var counter = 0;
checkCookie();

Upvotes: 4

Alex Turpin
Alex Turpin

Reputation: 47776

When you call setInterval, it returns you an interval ID that you can then use to stop it by calling clearInterval. As such, you'll want to count the iterations in a variable, and once they've reached a certain count, use clearInterval with the ID provided by setInterval.

var iterations = 0;
var interval = setInterval(foo, 10000);
function foo() {
    iterations++;
    if (iterations >= 5)
        clearInterval(interval);
}

Live example

Upvotes: 28

mellamokb
mellamokb

Reputation: 56779

You just need some sort of global counter variable to keep track. For instance, the follow code would only run the cookie check a maximum of 20 times per page load.

var numChecks = 0;

function checkCookie()
{
    ...

    numChecks++;
    if (numChecks < 20) setTimeout("checkCookie()", 10000);
}

setTimeout("checkCookie()", 10000);

Upvotes: 0

Related Questions