Blog

<基本> setIntervalとclearInterval

この二つはたまにしか使わないので、一発でうまくいくことがあまりない…。

今回反省してちゃんと書き留めておくことにしました。

まずは結果から

デモ

開くと、itemにis-moveというクラスが付いて動きます。2秒ごとにクラスが付いたり消えたり(Toggle)するので、行ったり来たりを繰り返します。

Stopボタンを押すと止まり、Startボタンを押すと再スタートするという仕様にしたいとします。

NGパターン

const item = document.querySelector('.item');
const slideFunc = () => {
  item.classList.toggle('is-move');
}

const startBtn = document.querySelector('.startBtn');
const stopBtn = document.querySelector('.stopBtn');

// NG Timerの設定とsetInterval
const timer = setInterval(slideFunc,2000)
setTimeout(slideFunc,0)//最初の待ちを発生させない

startBtn.addEventListener('click',function(){
  setInterval(timer)
})

// Stopボタン
stopBtn.addEventListener('click',function(){
  clearInterval(timer);
})

これだと、Stopボタンは動作しますがその後Startボタンを押しても再スタートしません。

なぜ動かないのかというと、

  1. setInterval()はインターバルを一意に識別する interval ID を返す。
  2. clearInterval() を呼び出して、インターバルを削除する

からです。つまり、setInterval()で繰り返し命令を作り、clearInterval()でそれが削除されるので、上記のように、最初に作ったtimerを再スタートの時に使いまわそうとしてもできないのです。

OKパターン


const item = document.querySelector('.item');
const slideFunc = () => {
  item.classList.toggle('is-current');
}

const startBtn = document.querySelector('.startBtn');
const stopBtn = document.querySelector('.stopBtn');

// NG Timerの設定とsetInterval
// const timer = setInterval(slideFunc,2000)
// setTimeout(slideFunc,0)//最初の待ちを発生させない

// startBtn.addEventListener('click',function(){
//   setInterval(timer)
// })

// OK Timerの設定とsetInterval
let timer = setInterval(slideFunc,2000);
setTimeout(slideFunc,0)//最初の待ちを発生させない

startBtn.addEventListener('click',function(){
  clearInterval(timer);//タイマーをリセット
  timer = setInterval(slideFunc,2000)
  setTimeout(slideFunc,0)//最初の待ちを発生させない
})

// Stopボタン
stopBtn.addEventListener('click',function(){
  clearInterval(timer);
})

timerをletで入れ替え可能にして、startBtnを押した時に新たに作った繰り返し処理をtimerにセットすることによって、再スタートが可能になります。

ちなみに、再スタート前にclearInterval(timer);(タイマーリセット)を入れておかないと、動いてる時にさらにStartを押した場合に2重にタイマーができて変な動きになります。
timerを上書きしても、clearIntervalで止めない限りは動き続けるということのようです。

おすすめの記事 recommend blog

新着 new blog

github