Функции settimeout, setinterval и clearinterval

Notes

The function is commonly used to set a delay for functions that are executed again and again, such as animations.


Ensure that execution duration is shorter than interval frequency

In these cases, a recursive pattern is preferred:

(function loop(){
   setTimeout(function() {
      // Your logic here

      loop();
  }, delay);
})();

In the above snippet, a named function is declared and is immediately executed. is recursively called inside after the logic has completed executing. While this pattern does not guarantee execution on a fixed interval, it does guarantee that the previous interval has completed before recursing.

Usage of JavaScript setInterval

JavaScript interval to be set use function. It could be defined simply as a method which allows you to invoke functions in set intervals.

The JS function is similar to the setTimeout method. How are they different? Well, calls functions once. However, with the set interval method you can invoke them multiple times.

Let’s say you need to display a message to your website visitors every 3 seconds. By applying the JavaScript function, you will be able to perform this task and incorporate a new feature on your website.

However, we would recommend not to overuse this function as it might disrupt the overall user experience. The following code example shows the way the message is set to be displayed every 3 seconds:

Example Copy

Как остановить выполнение?

Метод clearInterval () останавливает выполнение функции, указанной в методе setInterval ().

window.clearInterval(timerVariable)

window.clearInterval() метод может быть написан без префикса окна.

Метод clearInterval () использует переменную, возвращаемую из setInterval ():

myVar = setInterval(function, milliseconds);clearInterval(myVar);

Пример


Тот же пример, что и выше, но мы добавили кнопку «остановить время»:

<p id=»demo»></p><button onclick=»clearInterval(myVar)»>Stop time</button><script>var myVar = setInterval(myTimer, 1000); function myTimer() {    var d = new Date();    document.getElementById(«demo»).innerHTML = d.toLocaleTimeString();}</script>

❮ Назад Дальше ❯

Syntax to Follow

See the code snippet below. This is the syntax of the function that you should keep in mind:

As you can see, the JavaScript can contain three parameters. The first one identifies which function is going to be applied in the set time intervals. As you might expect, you also should include the milliseconds to set the frequency of your function. Additionally, you can specify parameters for the function to be applied.

Parameter Description
function Required. Defines the function to run.
milliseconds Required. Defines how often the function will be executed (in millisecond intervals).
param_one, param_two, … Not required. Defines any additional function parameters.

Совместимость с браузерами

Update compatibility data on GitHub

Chrome Edge Firefox Internet Explorer Opera Safari Android webview Chrome для Android Firefox для Android Opera для Android Safari on iOS Samsung Internet
Chrome Полная поддержка 30 Edge Полная поддержка 12 Firefox Полная поддержка 1 IE Полная поддержка 4 Opera Полная поддержка 4 Safari Полная поддержка 1 WebView Android Полная поддержка 4.4 Chrome Android Полная поддержка 30 Firefox Android Полная поддержка 4 Opera Android Полная поддержка 10.1 Safari iOS Полная поддержка 1 Samsung Internet Android Полная поддержка 3.0
Supports parameters for callback Chrome Полная поддержка Да Edge Полная поддержка 12 Firefox Полная поддержка Да IE Полная поддержка 10 Opera Полная поддержка Да Safari ? WebView Android Полная поддержка Да Chrome Android Полная поддержка Да Firefox Android ? Opera Android ? Safari iOS ? Samsung Internet Android Полная поддержка Да
Throttling of tracking timeout scripts Chrome ? Edge ? Firefox Полная поддержка 55 IE ? Opera ? Safari ? WebView Android ? Chrome Android ? Firefox Android Полная поддержка 55 Opera Android ? Safari iOS ? Samsung Internet Android ?

Методы setTimeout() и clearTimeout()

Метод предназначен для вызова кода на языке JavaScript после указанного количества миллисекунд.

Метод имеет два обязательных параметра:

  • — строка, содержащая код на языке JavaScript, который будет вызван в момент срабатывания таймера;
  • — указывается количество миллисекунд через которые данный таймер сработает.

Для прекращения работы таймера, т.е. для предотвращения вызова кода на языке JavaScript, хранящегося в первом параметре метода , используйте метод . Данный метод () содержит один обязательный параметр — это уникальный идентификатор () таймера, который можно получить как результат выполнения метода . Также таймер прекращает свою работу при закрытии окна.

//запустим таймер и получим его идентификатор, который будет храниться в переменной myTimer
//данный таймер выведет сообщение через 4 секунды после выполнения этой строчки
var myTimer = window.setTimeout("alert('Сообщение');",4000);
//после установления таймера его можно остановить с помощью метода clearInterval().
//Для этого необходимо в качестве параметра данному методу передать идентификатор таймера, хранящийся в переменной myTimer.
clearTimeout(myTimer);

Например, создадим на странице 2 кнопки. При нажатии на первую кнопку на экране будет отображаться количество секунд, прошедших с момента её нажатия. При нажатии на вторую кнопку будем останавливать выполнение данного процесса.

<script>
  // глобальная переменная, хранящая количество секунд, прошедших с момента нажатия ссылки
  var count=0;
  // глобальная переменная, хранящая идентификатор таймера
  var timer;
  //функция, выполняет следующее:
  //1 - выводит значения переменной count в элемент с id="clock"
  //2 - увеличивает значения переменной на 1
  //3 - запускает таймер, который вызовет функцию timeCount() через 1 секунду
  function timeCount() {
    document.getElementById("countTime").innerHTML = count.toString();
    count++;
    timer = window.setTimeout(function(){ timeCount() },1000);
  }
  //функция проверяет выражение !timer по правилу лжи, если оно истинно, 
  //то вызывает функцию timeCount()
  function startCount() {
    if (!timer)
      timeCount();
  }
    //функция проверяет выражение timer по правилу лжи
	//Если оно истинно, то она вызывает метод clearTimeOut() для прекращения работы таймера
	//и присваивает переменной timer значение null
	function stopCount() {
      if (timer) {
        clearTimeout(timer);
        timer=null;
      }
    }
</script>
...
Счётчик: <span id="countTime"></span>
<br />
<a href="javascript:startCount()">3anycтить процесс</a>
<br />
<a href="javascript:stopCount()">Остановить процесс</a>

Пример из реального мира

На прошлой неделе я опубликовал статью о том, как создать бота в Twitter в 38 строчек кода. Единственной причиной, по которой код в этой статье работал, был API от Twitter. Когда вы делаете запросы по API, вам нужно подождать ответа, перед тем как вы сможете как-то с ним работать и соответственно на него воздействовать. Вот то, как выглядит сам запрос.

T.get('search/tweets', params, function(err, data, response) {if(!err){// This is where the magic will happen} else {console.log(err);}})

просто означает то, что мы делаем get запрос к Twitter.

У этого запроса есть три параметра: , которые служит маршрутом для нашего запроса, которые являются параметрами поиска и дальше идёт анонимная функция, которая и является колбэком.

Колбэк тут крайне важен, так как нам нужно подождать ответа сервера, перед тем как идти дальше в выполнении кода. Мы понятия не имеем, будет ли наш API запрос успешным или нет, так что после отправки наших параметров к через запрос — мы ждём. Как только Twitter ответит, вызовется наша callback-функция. Twitter либо отправит объект (т.е. ошибку) или объект . В нашем колбэке мы можем применить , чтобы определить был ли наш запрос проведен успешно или нет, а за тем уже соответственно работать с новыми данными.

Таймеры setTimeout и setInterval

Каждый блок JavaScript кода, как правило, выполняется синхронно. Но в коробке у JavaScript уже есть нативные функции (таймеры), которые позволяют задерживать выполнение какого-либо кода.


Это и . Они позволят вам запустить кусок JavaScript кода в определенный момент в будущем. Такой подход называется “отложенным вызовом”. Далее вы узнаете как работают эти два метода и увидите несколько практических примеров.

Правка только для IE

If you want a completely unobtrusive hack for every other mobile or desktop browser, including IE 9 and below, you can either use JavaScript conditional comments:

/*@cc_on
  // conditional IE < 9 only fix
  @if (@_jscript_version <= 6)
  (function(f){
     window.setTimeout =f(window.setTimeout);
     window.setInterval =f(window.setInterval);
  })(function(f){return function(c,t){var a=[].slice.call(arguments,2);return f(function(){c.apply(this,a)},t)}});
  @end
@*/

Or go for a very clean approach based on the IE HTML conditional feature:

<!--><script>
(function(f){
window.setTimeout =f(window.setTimeout);
window.setInterval =f(window.setInterval);
})(function(f){return function(c,t){
var a=[].slice.call(arguments,2);return f(function(){c.apply(this,a)},t)}
});
</script><!-->

Another possibility is to use an anonymous function to call your callback, but this solution is a bit more expensive. Example:

var intervalID = setTimeout(function() { myFunc("one", "two", "three"); }, 1000);

Yet another possibility is to use function’s bind. Example:

setTimeout(function(arg1){}.bind(undefined, 10));

Проблема «this»

Коли ви передаєте до  метод або будь-яку іншу функцію, ймовірно вона буде викликана не з тим значенням , на яке ви очікуєте. Ця проблема детально описана у .

Пояснення

Код, що виконується всередині , викликається із  іншого контекста виконання (execution context), ніж у функції, яка викликала . До функції, яку викликають всередині  застосовуються звичайні правила призначення . І, якщо ви не встановили  під час виклику або за допомогою , його значенням за замовчуванням буде об’єкт   (або ) у нестрогому режимі, або у строгому режимі. Значення  буде іншим, аніж у функції, яка викликала . Розгляньте наступний приклад:

myArray = ;
myArray.myMethod = function (sProperty) {
    alert(arguments.length > 0 ? this : this);
};

myArray.myMethod(); // prints "zero,one,two"
myArray.myMethod(1); // prints "one"

Приклад вище працює тому, що  викликано, як метод масиву . Тому його  дорівнює , а значення  всередині метода дорівнює . Тим не менше, у наступному прикладі:

setTimeout(myArray.myMethod, 1000); // prints "" after 1 second
setTimeout(myArray.myMethod, 1500, "1"); // prints "undefined" after 1.5 seconds

Метод  передано до , як звичайну функцію, якій не задано значення . І коли вона викликається, її  за замовчуванням дорівнює об’єкту . У   неможливо передати  аргументом, як, наприклад, у методи Array (forEach, reduce, тощо), або через використання  , як показано у прикладі нижче:

setTimeout.call(myArray, myArray.myMethod, 2000); // error: "NS_ERROR_XPC_BAD_OP_ON_WN_PROTO: Illegal operation on WrappedNative prototype object"
setTimeout.call(myArray, myArray.myMethod, 2500, 2); // same error

Можливі рішення

Типовий спосіб вирішення цієї проблеми — використання функції обгортки, яка встановлює  із необхідним значенням: 

setTimeout(function(){myArray.myMethod()}, 2000); // prints "zero,one,two" after 2 seconds
setTimeout(function(){myArray.myMethod('1')}, 2500); // prints "one" after 2.5 seconds

Стрілочна функція також є прийнятною альтернативою:

setTimeout(() => {myArray.myMethod()}, 2000); // prints "zero,one,two" after 2 seconds
setTimeout(() => {myArray.myMethod('1')}, 2500); // prints "one" after 2.5 seconds

Ще одне можливе рішення проблеми  — замінити нативні глобальні функції  та  кастомними функціями, які можуть приймати об’єкт  і застосовувати його у колбек функції, використовуючи  . Наприклад: 

// Enable setting 'this' in JavaScript timers
 
var __nativeST__ = window.setTimeout, 
    __nativeSI__ = window.setInterval;
 
window.setTimeout = function (vCallback, nDelay /*, argumentToPass1, argumentToPass2, etc. */) {
  var oThis = this, 
      aArgs = Array.prototype.slice.call(arguments, 2);
  return __nativeST__(vCallback instanceof Function ? function () {
    vCallback.apply(oThis, aArgs);
  } : vCallback, nDelay);
};
 
window.setInterval = function (vCallback, nDelay /*, argumentToPass1, argumentToPass2, etc. */) {
  var oThis = this,
      aArgs = Array.prototype.slice.call(arguments, 2);
  return __nativeSI__(vCallback instanceof Function ? function () {
    vCallback.apply(oThis, aArgs);
  } : vCallback, nDelay);
};

Зверніть увагу:  Подібний підхід дозволяє передавати будь-яку кількість аргументів у колбек функцію таймерів навіть для IE. Таким чином, цей спосіб може також бути використаний як поліфіл. Перегляньте параграф  .

Випробування нового підхода:

myArray = ;
myArray.myMethod = function (sProperty) {
    alert(arguments.length > 0 ? this : this);
};

setTimeout(alert, 1500, "Hello world!"); // the standard use of setTimeout and setInterval is preserved, but...
setTimeout.call(myArray, myArray.myMethod, 2000); // prints "zero,one,two" after 2 seconds
setTimeout.call(myArray, myArray.myMethod, 2500, 2); // prints "two" after 2.5 seconds

Зверніть увагу:  JavaScript 1.8.5 впровадив метод   , який встановлює значення  для кожного виклику вказаної функції. Це допомагає уникнути використання функції обгортки для призначення  колбека.


Приклад використання :

myArray = ;
myBoundMethod = (function (sProperty) {
    console.log(arguments.length > 0 ? this : this);
}).bind(myArray);

myBoundMethod(); // prints "zero,one,two" because 'this' is bound to myArray in the function
myBoundMethod(1); // prints "one"
setTimeout(myBoundMethod, 1000); // still prints "zero,one,two" after 1 second because of the binding
setTimeout(myBoundMethod, 1500, "1"); // prints "one" after 1.5 seconds

JS Tutorial

JS HOMEJS IntroductionJS Where ToJS OutputJS StatementsJS SyntaxJS CommentsJS VariablesJS OperatorsJS ArithmeticJS AssignmentJS Data TypesJS FunctionsJS ObjectsJS EventsJS StringsJS String MethodsJS NumbersJS Number MethodsJS ArraysJS Array MethodsJS Array SortJS Array IterationJS DatesJS Date FormatsJS Date Get MethodsJS Date Set MethodsJS MathJS RandomJS BooleansJS ComparisonsJS ConditionsJS SwitchJS Loop ForJS Loop WhileJS BreakJS Type ConversionJS BitwiseJS RegExpJS ErrorsJS ScopeJS HoistingJS Strict ModeJS this KeywordJS LetJS ConstJS Arrow FunctionJS DebuggingJS Style GuideJS Best PracticesJS MistakesJS PerformanceJS Reserved WordsJS VersionsJS Version ES5JS Version ES6JS JSON

Аргументы функции обратного вызова

If you need to pass an argument to your callback function, but need it to work in Internet Explorer 9 and below, which doesn’t support sending additional parameters (neither with or ) you can include this IE-specific compatibility code which will enable the HTML5 standard parameters passage functionality in that browser for both timers just by inserting it at the beginning of your scripts.

/*\
|*|
|*|  IE-specific polyfill which enables the passage of arbitrary arguments to the
|*|  callback functions of JavaScript timers (HTML5 standard syntax).
|*|
|*|  https://developer.mozilla.org/en-US/docs/DOM/window.setInterval
|*|
|*|  Syntax:
|*|  var timeoutID = window.setTimeout(func, delay, );
|*|  var timeoutID = window.setTimeout(code, delay);
|*|  var intervalID = window.setInterval(func, delay);
|*|  var intervalID = window.setInterval(code, delay);
|*|
\*/

if (document.all && !window.setTimeout.isPolyfill) {
  var __nativeST__ = window.setTimeout;
  window.setTimeout = function (vCallback, nDelay /*, argumentToPass1, argumentToPass2, etc. */) {
    var aArgs = Array.prototype.slice.call(arguments, 2);
    return __nativeST__(vCallback instanceof Function ? function () {
      vCallback.apply(null, aArgs);
    } : vCallback, nDelay);
  };
  window.setTimeout.isPolyfill = true;
}

if (document.all && !window.setInterval.isPolyfill) {
  var __nativeSI__ = window.setInterval;
  window.setInterval = function (vCallback, nDelay /*, argumentToPass1, argumentToPass2, etc. */) {
    var aArgs = Array.prototype.slice.call(arguments, 2);
    return __nativeSI__(vCallback instanceof Function ? function () {
      vCallback.apply(null, aArgs);
    } : vCallback, nDelay);
  };
  window.setInterval.isPolyfill = true;
}

More Examples

Example

Toggle between two background colors once every 300 milliseconds, until it is stopped by clearInterval():

var myVar = setInterval(setColor, 300);function setColor() {  var x = document.body;  x.style.backgroundColor = x.style.backgroundColor == «yellow» ? «pink» : «yellow»;} function stopColor() {  clearInterval(myVar);}

Example

Using setInterval() and clearInterval() to create a dynamic progress bar:

function move() {  var elem = document.getElementById(«myBar»);   var width = 0;  var id = setInterval(frame, 100);  function frame() {    if (width == 100) {      clearInterval(id);    } else {      width++;       elem.style.width = width + ‘%’;     }  }}

Главный поток

В каждом окне выполняется только один главный поток, который занимается выполнением JavaScript, отрисовкой и работой с DOM.

Он выполняет команды последовательно, может делать только одно дело одновременно и блокируется при выводе модальных окон, таких как .

Дополнительные потоки тоже есть

Есть и другие, служебные потоки, например, для сетевых коммуникаций.

Поэтому скачивание файлов может продолжаться пока главный поток ждёт реакции на . Но управлять служебными потоками мы не можем.

Web Workers

Существует спецификация Web Workers, которая позволяет запускать дополнительные JavaScript-процессы(workers).

Они могут обмениваться сообщениями с главным процессом, но у них свои переменные, и работают они также сами по себе.

Такие дополнительные процессы не имеют доступа к DOM, поэтому они полезны, преимущественно, при вычислениях, чтобы загрузить несколько ядер/процессоров одновременно.

JavaScript

JS Array concat() constructor copyWithin() entries() every() fill() filter() find() findIndex() forEach() from() includes() indexOf() isArray() join() keys() length lastIndexOf() map() pop() prototype push() reduce() reduceRight() reverse() shift() slice() some() sort() splice() toString() unshift() valueOf()

JS Boolean constructor prototype toString() valueOf()

JS Classes constructor() extends static super

JS Date constructor getDate() getDay() getFullYear() getHours() getMilliseconds() getMinutes() getMonth() getSeconds() getTime() getTimezoneOffset() getUTCDate() getUTCDay() getUTCFullYear() getUTCHours() getUTCMilliseconds() getUTCMinutes() getUTCMonth() getUTCSeconds() now() parse() prototype setDate() setFullYear() setHours() setMilliseconds() setMinutes() setMonth() setSeconds() setTime() setUTCDate() setUTCFullYear() setUTCHours() setUTCMilliseconds() setUTCMinutes() setUTCMonth() setUTCSeconds() toDateString() toISOString() toJSON() toLocaleDateString() toLocaleTimeString() toLocaleString() toString() toTimeString() toUTCString() UTC() valueOf()

JS Error name message

JS Global decodeURI() decodeURIComponent() encodeURI() encodeURIComponent() escape() eval() Infinity isFinite() isNaN() NaN Number() parseFloat() parseInt() String() undefined unescape()

JS JSON parse() stringify()

JS Math abs() acos() acosh() asin() asinh() atan() atan2() atanh() cbrt() ceil() cos() cosh() E exp() floor() LN2 LN10 log() LOG2E LOG10E max() min() PI pow() random() round() sin() sqrt() SQRT1_2 SQRT2 tan() tanh() trunc()

JS Number constructor isFinite() isInteger() isNaN() isSafeInteger() MAX_VALUE MIN_VALUE NEGATIVE_INFINITY NaN POSITIVE_INFINITY prototype toExponential() toFixed() toLocaleString() toPrecision() toString() valueOf()

JS OperatorsJS RegExp constructor compile() exec() g global i ignoreCase lastIndex m multiline n+ n* n? n{X} n{X,Y} n{X,} n$ ^n ?=n ?!n source test() toString() (x|y) . \w \W \d \D \s \S \b \B \0 \n \f \r \t \v \xxx \xdd \uxxxx

JS Statements break class continue debugger do…while for for…in for…of function if…else return switch throw try…catch var while

JS String charAt() charCodeAt() concat() constructor endsWith() fromCharCode() includes() indexOf() lastIndexOf() length localeCompare() match() prototype repeat() replace() search() slice() split() startsWith() substr() substring() toLocaleLowerCase() toLocaleUpperCase() toLowerCase() toString() toUpperCase() trim() valueOf()

JavaScript

JS Array concat() constructor copyWithin() entries() every() fill() filter() find() findIndex() forEach() from() includes() indexOf() isArray() join() keys() length lastIndexOf() map() pop() prototype push() reduce() reduceRight() reverse() shift() slice() some() sort() splice() toString() unshift() valueOf()

JS Boolean constructor prototype toString() valueOf()

JS Classes constructor() extends static super

JS Date constructor getDate() getDay() getFullYear() getHours() getMilliseconds() getMinutes() getMonth() getSeconds() getTime() getTimezoneOffset() getUTCDate() getUTCDay() getUTCFullYear() getUTCHours() getUTCMilliseconds() getUTCMinutes() getUTCMonth() getUTCSeconds() now() parse() prototype setDate() setFullYear() setHours() setMilliseconds() setMinutes() setMonth() setSeconds() setTime() setUTCDate() setUTCFullYear() setUTCHours() setUTCMilliseconds() setUTCMinutes() setUTCMonth() setUTCSeconds() toDateString() toISOString() toJSON() toLocaleDateString() toLocaleTimeString() toLocaleString() toString() toTimeString() toUTCString() UTC() valueOf()

JS Error name message

JS Global decodeURI() decodeURIComponent() encodeURI() encodeURIComponent() escape() eval() Infinity isFinite() isNaN() NaN Number() parseFloat() parseInt() String() undefined unescape()

JS JSON parse() stringify()

JS Math abs() acos() acosh() asin() asinh() atan() atan2() atanh() cbrt() ceil() cos() cosh() E exp() floor() LN2 LN10 log() LOG2E LOG10E max() min() PI pow() random() round() sin() sqrt() SQRT1_2 SQRT2 tan() tanh() trunc()

JS Number constructor isFinite() isInteger() isNaN() isSafeInteger() MAX_VALUE MIN_VALUE NEGATIVE_INFINITY NaN POSITIVE_INFINITY prototype toExponential() toFixed() toLocaleString() toPrecision() toString() valueOf()

JS OperatorsJS RegExp constructor compile() exec() g global i ignoreCase lastIndex m multiline n+ n* n? n{X} n{X,Y} n{X,} n$ ^n ?=n ?!n source test() toString() (x|y) . \w \W \d \D \s \S \b \B \0 \n \f \r \t \v \xxx \xdd \uxxxx

JS Statements break class continue debugger do…while for for…in for…of function if…else return switch throw try…catch var while

JS String charAt() charCodeAt() concat() constructor endsWith() fromCharCode() includes() indexOf() lastIndexOf() length localeCompare() match() prototype repeat() replace() search() slice() split() startsWith() substr() substring() toLocaleLowerCase() toLocaleUpperCase() toLowerCase() toString() toUpperCase() trim() valueOf()


С этим читают