Pomodoro Clock speeding up after pausing

I’ve followed the try, search, read, method, and couldn’t find the specific answer I was facing.

Essentially, I’m having what seems like a common problem, which is that each time a user starts my clock after pausing, a new timer is started, effectively doubling the pace at which the countdown initiates.

The solution to this appears to be the clearInterval() method. Here is the basic code for the function that happens when a user presses play:

  start() {
    let x = this.play;
    if (this.state.running === false) {
    clearInterval(x);
    this.toggleRun();
    this.play();  
    } else {
    this.toggleRun()
    this.play()
      }
    };

My logic behind this is that each time the user pauses, the clear interval method would reset my interval, but this is not happening. Any advice on how to handle this challenge, or why the clearInterval() is not working?

here is the full code (warning: it is slightly spaghetti):

There’s a lot to unpack from the start method, but let me know if this helps:

  • x stores a reference to the function setting up the interval, not to the interval itself. To retrieve this value, you’d actually need to update the start function.

    let x = this.play();
    

    But also the play function itself, since it doesn’t return anything at the moment.

    play() {
        return setInterval(this.decrement, 1000)
      }
    
  • you now have a reference to the interval, but unfortunately, this is the interval starting now, not the interval already running. You can work around this by creating another variable in the state. (I call it interval, but you are free to continue using x; it’s just a preference)

    this.state = {
       // previous
       interval: 0,
    }
    

    You then update this value in the play function

    play() {
       const interval = setInterval(this.decrement, 1000)
       this.setState({
          interval: interval
       });
    }
    

    And access the same in the start function.

    const interval = this.state.interval;
    
  • now that you have a reference to the desired interval, a look to the start function.

    start() {
       const interval = this.state.interval;
       if (this.state.running === false) {
          clearInterval(interval);
          this.toggleRun();
          this.play();  
       } 
       else {
          this.toggleRun()
          this.play()
       }
    };
    

    Here’s there are two issue:

    • when running is equal to false, meaning the application is not counting down, you are clearing an interval that is not supposed to exist. clearInterval should actually be called in the else statement.

    • in the else statement, you are calling the play function again. This means the interval is being set up regardless of the comparison in the if statement.


The start function should ultimately look something like the following:

start() {
   const interval = this.state.interval;
   if (this.state.running === false) {
      // start interval
      this.toggleRun();
      this.play();  
   } 
   else {
      // stop interval
      clearInterval(interval);
      this.toggleRun()
    }
};

Again, there’s a lot to unpack, and I hope this wasn’t too overwhelming. Let me know if it helps.

2 Likes

Thanks for this. I have some ideas now.

You know what’s so crazy? I had thought of the solution to set interval in the state, but forgot to try it. I had been working at it for so long haha! Thanks, I’ll put my head down and fix this thing!

1 Like