Остановить вызов setInterval в JavaScript

Я использую setInterval(fname, 10000); для вызова функции каждые 10 секунд в JavaScript. Можно ли перестать звонить по какому-то событию?

Я хочу, чтобы пользователь мог остановить повторное обновление данных.

Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
1 498
0
1 042 954
15
Перейти к ответу Данный вопрос помечен как решенный

Ответы 15

Ответ принят как подходящий

setInterval() возвращает идентификатор интервала, который можно передать clearInterval():

var refreshIntervalId = setInterval(fname, 10000);

/* later */
clearInterval(refreshIntervalId);

См. Документацию для setInterval() и clearInterval().

Как вы можете запустить его снова после остановки с помощью 'clearInterval ()'? Если я попытаюсь перезапустить его, у меня будет работать в 2 раза больше, чем setInterval.

Dan 02.04.2012 19:37

Я тоже Каждый раз, когда я хочу использовать SetInterval (MyFunction, 4000); он становится все быстрее и быстрее, каждый раз в 2 раза быстрее :( как я могу перезапустить заданный интервал ??

Alireza Masali 03.02.2013 17:15

SetInterval () не изменяет скорость, которую вы ему передаете. Если все, что он делает, ускоряется каждый раз, когда вы вызываете SetInterval (), тогда у вас есть несколько таймеров, которые работают одновременно, и должен открываться новый вопрос.

EpicVoyage 12.04.2013 15:14

Убедитесь, что вы действительно его останавливаете. Из-за области действия переменной у вас может не быть правильного идентификатора для вызова clearInterval. Я использовал window.refreshIntervalId вместо локальной переменной, и он отлично работает!

Sergey Orshanskiy 15.10.2013 08:10

нельзя ли использовать this внутри fname?

Jürgen Paul 04.12.2013 14:22

одно и тоже. var interval; внутри Singleton - fn start(){ interval = setInterval(localFnToMethod, 1000) } - fn restart(){ clearInterval(interval); start(); } ... заставляет меня запускать партии одного и того же метода "start" ... ???

Cody 14.01.2015 05:25

@PineappleUndertheSea да, вы можете это сделать, вы можете определить идентификатор, а затем без проблем вызвать clearInternal внутри fname.

carzogliore 03.02.2015 07:56

Я начал прикреплять дескриптор setInterval к ​​связанному с ним элементу (при необходимости): $('foo').data('interval', setInterval(fn, 100));, а затем очищать его с помощью clearInterval($('foo').data('interval'));. Я уверен, что есть способ сделать это и без использования jQuery.

Michael 24.02.2017 20:14

SetInterval существует и работает в глобальной области окна. Когда вы назначаете идентификатор setInterval локальной переменной, локальная переменная перезаписывается при обновлении страницы, а setInterval становится потерянным в глобальной области. У вас больше нет ссылки на его идентификатор, но он продолжает работать. Исправление состоит в том, чтобы поместить переменную, в данном случае «refreshIntervalId», в глобальную область видимости. Это означает, что не используйте var для его объявления.

Dieter Donnert 01.04.2019 00:00

Большое спасибо. Вы помогли мне решить ошибку, возникшую в течение года. Салют и уважение.

Elias Prado 06.08.2020 04:21

Если вы установите возвращаемое значение setInterval для переменной, вы можете использовать clearInterval, чтобы остановить его.

var myTimer = setInterval(...);
clearInterval(myTimer);

Я не вижу разницы между этим и ответом Джона

Andrei 04.04.2020 01:48

поздно, но я думаю, что это скопировано с некоторой разницей в словах не более ясным, чем ответ Джона

Ibnelaiq 18.06.2020 17:59

Вы можете установить новую переменную и увеличивать ее на ++ (считать на единицу) каждый раз, когда она запускается, а затем я использую условный оператор для ее завершения:

var intervalId = null;
var varCounter = 0;
var varName = function(){
     if (varCounter <= 10) {
          varCounter++;
          /* your code goes here */
     } else {
          clearInterval(intervalId);
     }
};

$(document).ready(function(){
     intervalId = setInterval(varName, 10000);
});

Надеюсь, что это поможет, и это правильно.

Я был удивлен, узнав, что это работает clearInterval(varName);. Я ожидал, что clearInterval не будет работать при передаче имени функции, я думал, что для этого требуется идентификатор интервала. Я полагаю, это может работать только в том случае, если у вас есть именованная функция, поскольку вы не можете передать анонимную функцию как переменную внутри себя.

Patrick M 15.08.2012 21:24

На самом деле я думаю, что это не работает. Код перестает выполняться из-за ограничения счетчика, но интервал продолжает запускать varName (). Попробуйте записать что-нибудь после clearInterval () (внутри предложения else), и вы увидите, что это записывается вечно.

Rafael Oliveira 10.04.2013 19:14

Так много голосов за то, что не работает, иногда я не понимаю людей на SO: P

Stranded Kid 20.04.2015 16:30

Рафаэль Оливейра прав: интервал не останавливается, он все еще идет, но условие не выполняется.

Morfidon 30.04.2015 17:13

$(document).ready(function(){ }); - это jQuery, поэтому он не работает. Об этом надо было хотя бы упомянуть.

paddotk 16.06.2015 18:07

@OMGrant, помимо примера, который не работает, у вас есть переменная с именем varName, в которой хранится безымянная функция - что ?? Вам следует изменить или удалить этот ответ, ИМХО.

Dean Radcliffe 26.09.2015 15:58

Если отбросить имена переменных, ответ будет правильным. Сохраните возвращенное значение setInterval, зацикливая и увеличивая счетчик, и когда этот счетчик достигает максимума, вы clearInterval с идентификатором из ранее. Оно работает.

TankorSmash 19.08.2016 02:31

Как очень ясно сообщает MSN, clearInterval ожидает идентификатор, а не функцию: developer.mozilla.org/en-US/docs/Web/API/WindowTimers/…. Из-за того, что этот ответ неверен, а также вводит в заблуждение, я голосую за него.

sidewinderguy 28.09.2016 23:30

Ответ фиксирован (отвечающий принимает предложенное изменение). (@Motes)

user202729 03.10.2019 04:46

В ответах выше уже объяснялось, как setInterval возвращает дескриптор и как этот дескриптор используется для отмены таймера интервала.

Некоторые архитектурные особенности:

Пожалуйста, не используйте переменные без области видимости. Самый безопасный способ - использовать атрибут объекта DOM. Самым простым местом будет «документ». Если обновление запускается кнопкой старт / стоп, вы можете использовать саму кнопку:

<a onclick = "start(this);">Start</a>

<script>
function start(d){
    if (d.interval){
        clearInterval(d.interval);
        d.innerHTML='Start';
    } else {
        d.interval=setInterval(function(){
          //refresh here
        },10000);
        d.innerHTML='Stop';
    }
}
</script>

Поскольку функция определяется внутри обработчика нажатия кнопки, вам не нужно определять ее снова. Таймер можно возобновить, если снова нажать кнопку.

Что лучше поставить на document, чем на window?

icktoofay 19.01.2014 09:52

исправление. Я хотел сказать документ. Тело. В моем примере кода я эффективно использую саму кнопку. У кнопки нет идентификатора, но указатель «this» привязан к параметру «d» в функции. Использование «окна» в качестве области видимости рискованно, потому что функции тоже присутствуют. Например, "function test () {}" доступен через window.test, что равносильно тому, что не использовать область видимости вообще, потому что это сокращение. Надеюсь это поможет.

Schien 19.01.2014 10:05

не терять переменные "без области видимости" -> не использовать "без области видимости" Я бы отредактировал это, но изменение меньше 6 букв, и ошибка сбивает с толку.

Leif Neland 24.07.2014 16:13

Для этого вам не нужна DOM. Просто мы, IIFE, чтобы избежать загрязнения в глобальном масштабе.

Onur Yıldırım 23.08.2016 18:52

хороший момент при использовании IIFE. в зависимости от того, что вам нужно, хранилище DOM может иметь дополнительное преимущество, делая значение доступным для других статических функций. это компромисс между удобством и защитой прицела.

Schien 23.08.2016 22:56

Мне нужно добавить d.interval = undefined после innerhtml = 'start', чтобы он снова заработал. Потому что это работает только один раз.

jocmtb 09.11.2019 19:23

Почему бы не использовать более простой подход? Добавьте класс!

Просто добавьте класс, который сообщает интервалу ничего не делать. Например: при наведении.

var i = 0;
this.setInterval(function() {
  if (!$('#counter').hasClass('pauseInterval')) { //only run if it hasn't got this class 'pauseInterval'
    console.info('Counting...');
    $('#counter').html(i++); //just for explaining and showing
  } else {
    console.info('Stopped counting');
  }
}, 500);

/* In this example, I'm adding a class on mouseover and remove it again on mouseleave. You can of course do pretty much whatever you like */
$('#counter').hover(function() { //mouse enter
    $(this).addClass('pauseInterval');
  },function() { //mouse leave
    $(this).removeClass('pauseInterval');
  }
);

/* Other example */
$('#pauseInterval').click(function() {
  $('#counter').toggleClass('pauseInterval');
});
body {
  background-color: #eee;
  font-family: Calibri, Arial, sans-serif;
}
#counter {
  width: 50%;
  background: #ddd;
  border: 2px solid #009afd;
  border-radius: 5px;
  padding: 5px;
  text-align: center;
  transition: .3s;
  margin: 0 auto;
}
#counter.pauseInterval {
  border-color: red;  
}
<!-- you'll need jQuery for this. If you really want a vanilla version, ask -->
<script src = "https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>


<p id = "counter">&nbsp;</p>
<button id = "pauseInterval">Pause</button></p>

Я давно искал этот быстрый и простой подход, поэтому я публикую несколько версий, чтобы познакомить с ним как можно больше людей.

Мне это не кажется проще ... Я также считаю, что лучше удалить интервалы вместо того, чтобы сохранять вызовы функций, которые ничего не делают.

Romain Braun 27.04.2015 21:06

Я не согласен. this.setInterval(function() { if (!$('#counter').hasClass('pauseInterval')) { //do something } }, 500); - это все, что у вас есть для кода. Более того, проверка - это первое, что вы делаете, поэтому при зависании он очень легкий. Вот для чего этот: временная приостановка функции. Если вы хотите прекратить его на неопределенный срок: конечно, вы удаляете интервал.

Aart den Braber 30.04.2015 10:49

Это равносильно опросу и обычно не приветствуется. Он выведет ЦП из состояния низкого энергопотребления, чтобы выполнить (вероятно) бесполезную проверку. Он также задерживает обратную связь от немедленной до от 0 до 500 мс в этом примере.

Charlie 20.04.2017 10:58

Я совершенно не согласен с вами, хотя я писал код 2 года назад. Счетчик все равно должен быть там, потому что ОП попросил его. Конечно, если вы используете это, чтобы остановить счетчик, например, после нажатия кнопки, это было бы неоптимальным решением, но просто для паузы при наведении курсора это одно из самых простых доступных решений.

Aart den Braber 30.04.2017 21:19

@cnu,

Вы можете остановить интервал, когда попробуйте запустить код перед просмотром браузера консоли ur (F12) ... попробуйте комментарий clearInterval (trigger) снова посмотрите консоль, а не красивее? :П

Проверить пример источника:

var trigger = setInterval(function() { 
  if (document.getElementById('sandroalvares') != null) {
    document.write('<div id = "sandroalvares" style = "background: yellow; width:200px;">SandroAlvares</div>');
    clearInterval(trigger);
    console.info('Success');
  } else {
    console.info('Trigger!!');
  }
}, 1000);
<div id = "sandroalvares" style = "background: gold; width:200px;">Author</div>

Уже ответил ... Но если вам нужен специальный таймер с возможностью повторного использования, который также поддерживает несколько задач с разными интервалами, вы можете использовать мой TaskTimer (для узла и браузера).

// Timer with 1000ms (1 second) base interval resolution.
const timer = new TaskTimer(1000);

// Add task(s) based on tick intervals.
timer.add({
    id: 'job1',         // unique id of the task
    tickInterval: 5,    // run every 5 ticks (5 x interval = 5000 ms)
    totalRuns: 10,      // run 10 times only. (omit for unlimited times)
    callback(task) {
        // code to be executed on each run
        console.info(task.name + ' task has run ' + task.currentRuns + ' times.');
        // stop the timer anytime you like
        if (someCondition()) timer.stop();
        // or simply remove this task if you have others
        if (someCondition()) timer.remove(task.id);
    }
});

// Start the timer
timer.start();

В вашем случае, когда пользователи нажимают, чтобы нарушить обновление данных; вы также можете вызвать в timer.pause(), а затем в timer.resume(), если их нужно снова включить.

См. подробнее здесь.

Объявить переменную для присвоения значения, возвращаемого из setInterval (...) и передать назначенную переменную в clearInterval ();

например

var timer, intervalInSec = 2;

timer = setInterval(func, intervalInSec*1000, 30 ); // third parameter is argument to called function 'func'

function func(param){
   console.info(param);
}

// Везде, где у вас есть доступ к объявленному выше таймер, вызовите clearInterval

$('.htmlelement').click( function(){  // any event you want

       clearInterval(timer);// Stops or does the work
});

Метод clearInterval () может использоваться для очистки таймера, установленного с помощью метода setInterval ().

setInterval всегда возвращает значение идентификатора. Это значение можно передать в clearInterval (), чтобы остановить таймер. Вот пример таймера, который начинается с 30 и останавливается, когда становится 0.

  let time = 30;
  const timeValue = setInterval((interval) => {
  time = this.time - 1;
  if (time <= 0) {
    clearInterval(timeValue);
  }
}, 1000);

Вот как я использовал метод clearInterval (), чтобы остановить таймер через 10 секунд.

function startCountDown() {
  var countdownNumberEl = document.getElementById('countdown-number');
  var countdown = 10;
  const interval = setInterval(() => {
    countdown = --countdown <= 0 ? 10 : countdown;
    countdownNumberEl.textContent = countdown;
    if (countdown == 1) {
      clearInterval(interval);
    }
  }, 1000)
}
<head>
  <body>
    <button id = "countdown-number" onclick = "startCountDown();">Show Time </button>
  </body>
</head>

Используйте setTimeOut, чтобы остановить интервал через некоторое время.

var interVal = setInterval(function(){console.info("Running")  }, 1000);
 setTimeout(function (argument) {
    clearInterval(interVal);
 },10000);

Думаю, поможет следующий код:

var refreshIntervalId = setInterval(fname, 10000);

clearInterval(refreshIntervalId);

Вы правильно сделали код на 100% ... Итак ... В чем проблема? Или это учебник ...

Пытаться

let refresch = ()=>  document.body.style= 'background: #'
  +Math.random().toString(16).slice(-6);

let intId = setInterval(refresch, 1000);

let stop = ()=> clearInterval(intId);
body {transition: 1s}
<button onclick = "stop()">Stop</button>

В nodeJS вы можете использовать специальное ключевое слово «это» в функции setInterval.

Вы можете использовать это ключевое слово это для clearInterval, и вот пример:

setInterval(
    function clear() {
            clearInterval(this) 
       return clear;
    }()
, 1000)

Когда вы печатаете значение специального ключевого слова это внутри функции, вы выводите объект тайм-аута Timeout {...}

clearInterval ()

Обратите внимание: с помощью этой возможности вы можете запускать и приостанавливать код. Название немного обманчиво, так как написано CLEAR, но ничего не проясняет. Это действительно пауза.

Протестируйте с этим кодом:

HTML:

<div id='count'>100</div>
<button id='start' onclick='start()'>Start</button>
<button id='stop' onclick='stop()'>Stop</button>

JavaScript:

let count;

function start(){
 count = setInterval(timer,100)  /// HERE WE RUN setInterval()
}

function timer(){
  document.getElementById('count').innerText--;
}


function stop(){
  clearInterval(count)   /// here we PAUSE  setInterval()  with clearInterval() code
}

Другие вопросы по теме