Leonard Ge
Leonard Ge

Reputation: 879

Clear Interval doesn't work in VUE

I am trying to build a Pomodoro Timer using VUE.js, below is the relevant code snippet that I had problems on. So the problem is that the clearInterval Method doesn't seem to work here.

   data: {
        workTimeInMin: 1,
        breakTimeInMin: 1,
        timeRemainInMillisecond: 0,
        timerOn: false,
        rest: false
      },

      methods: {
        startOrStopTheTimer: function() {
          var self = this;
          var interval;
          if (this.timerOn){
            this.timerOn = !this.timerOn;
            window.clearInterval(interval);
            console.log("clearInterval");
          }else {
            this.timerOn = !this.timerOn;
            interval = setInterval(function(){
            console.log("123");
            if (self.timeRemainInMillisecond <= 0) {
              console.log("1");
              self.rest = !self.rest;
              if (self.rest) {
                self.timeRemainInMillisecond = self.restTimeInMin*60*1000;
              }else {
                self.timeRemainInMillisecond = self.workTimeInMin*60*1000;
              }
            }
              this.timeRemainInMillisecond = this.timeRemainInMillisecond-1000
            }, 1000);
          }
        },

You can find a live demo here.

In the page, when I click start an set Interval method is called. Then I clicked the stop, it is supposed to clear the interval, however it doesn't seem to work as I intend it to. You can inspect the console and easily find the "123" keeps popping up which indicates that the interval is not cleared.

After searching a while in the StackOverFlow, I found that if I define the variable interval to in the global context it will work as I intend it. But I wish to know why it is so.

Your help will be highly appreciated. Thanks in advance!

Upvotes: 2

Views: 30448

Answers (4)

Leandro Ferreira
Leandro Ferreira

Reputation: 435

This works like a charm:


data () {
    return {
        polling: null
    }
},
methods: {
    pollData () {
        this.polling = setInterval(() => {
            console.log('fired...')
        }, 3000)
    }
},
beforeDestroy () {
    clearInterval(this.polling)
},
created () {
    this.pollData()
}

Upvotes: 4

bparticle
bparticle

Reputation: 157

I arrived at this page because Vue still seems to handle setInterval in the strange way as described by the OP. I tried all the fixes above and found only two options work:

  • Global scope the interval variable (as mentioned above and less than an ideal workaround)
  • Use Vuex to store the timer and handle it the usual Vuex way.

I was happy to find that using Vuex bypasses the problem, since I'm using Vuex anyway. It doesn't shed light on why this issue exists, but it does give us a way to move forward with little sacrifices made.

So just declare the variable in the Vuex state, use mutations to start and stop the timer and all works as expected.

Upvotes: 4

Rizwan
Rizwan

Reputation: 4433

You can clear setInterval and clearinterval. here is sample code please modify according to your need

if (val && !this.t) {
    this.t = setInterval(() => {
        location.reload()
    }, 10 * 1000)
} else {
    clearInterval(this.t)
}

Upvotes: 6

reinerBa
reinerBa

Reputation: 1660

Your problem is that var interval is a declared new every time the function is called. So the variable that holds a reference to your interval is not accessible.

Just use this.interval and the variable will added to the data-section of your component under the hood.

You can also just use this mixin (plugin) / have a look how it works there: Vue interval mixin

Upvotes: 8

Related Questions