Categories
React

How to Fix a State That is Not Updating When Using React State Hook in setInterval

Spread the love

The setInterval function lets us run a function periodically in our JavaScript code by creating a timer.

We may also use setInterval in our React apps.

Sometimes, we may find that our React component states aren’t updating when we have state updating code in our setInterval callbacks.

In this article, we’ll look at how to make sure that our states are getting updated when we run state updating code in our setInterval callback.

Why is the State Not Updating in the setInterval?

If we have code like the following:

import { useEffect, useState } from "react";

export default function App() {
  const [time, setTime] = useState(0);

  useEffect(() => {
    const timer = setInterval(() => {
      setTime(time + 1);
    }, 1000);
    return () => {
      clearInterval(timer);
    };
  }, []);

  return <div className="App">{time}</div>;
}

Then we may see the value of time isn’t updating every second.

Instead, it only updates once when the component first mounts.

This is because we passed in an empty array as the value of the 2nd argument in the useEffect hook.

This means the useEffect callback runs when the component mounts.

And since time is 0, time + 1 is 1.

The useEffect callback doesn’t have access to the latest time value since it never runs again after it mounts.

Therefore, we can’t just pass in time + 1 to update the value of time .

To fix this, we need to pass in a callback to setTime with the current time value as the parameter and returns the new time value we want.

To do this, we write:

import { useEffect, useState } from "react";

export default function App() {
  const [time, setTime] = useState(0);

  useEffect(() => {
    const timer = setInterval(() => {
      setTime((time) => time + 1);
    }, 1000);
    return () => {
      clearInterval(timer);
    };
  }, []);

  return <div className="App">{time}</div>;
}

We pass in a callback to setTime .

The callback takes the current time value as the parameter.

And it returns time + 1 so that time is updated to time + 1 .

Now we should see the time display updated every second as we expect.

Conclusion

To fix a state that’s not updating in the setInterval callback, we should pass in a callback to the state setter function to update the state.

This is because the useEffect callback has to run in order to have access to the latest state values.

By John Au-Yeung

Web developer specializing in React, Vue, and front end development.

One reply on “How to Fix a State That is Not Updating When Using React State Hook in setInterval”

Leave a Reply

Your email address will not be published. Required fields are marked *