简体   繁体   中英

How to update state object within setInterval? [Hooks]

I am wondering if anyone has experience merging a state object within a setInterval() function. After trying a few things, I ended up with the solution below, but would appreciate any additional input / tips on how to do this.


Some context: My codebase started growing, and now I have multiple state variables. I am trying to group the ones that are related into a single object to have more control over the number of renders that occur. One of those state variables is updated within a setInterval() function.


I originally had a single state:

const [seconds, setSeconds] = useState(10)

const start = () => {
  interval = setInterval(() => {
    setSeconds((seconds) => seconds - 1000);
  }, 1000);
}

But I am trying to implement something like:

const [timer, setTimer] = useState({ seconds: 10, status: 'initial', count: 0 })

And I need to update the 'seconds' property of this object. First I attempted something like... setTimer({...timer, seconds: timer.seconds - 1000 }); ... which left the interval running, but the 'seconds' were never updated from the subtraction.

Eventually, I implemented the following, which seems to do the trick so far:

const start = () => {
  interval = setInterval(() => {
    setTimer((timer) => (timer = { ...timer, seconds: timer.seconds - 1000 }));
  }, 1000);
}

For example, you can use Immer , like in this article. And you can set your state more easily.

You need to do like this:

const start = () => {
  interval = setInterval(() => {
    setTimer((timer) => ({ ...timer, seconds: timer.seconds - 1000 }));
  }, 1000);
}

Or better would be this:

const updatedTimer = {...timer,seconds:timer.seconds - 1000};
const start = () => {
  interval = setInterval(() => {
    setTimer(updatedTimer);
  }, 1000);

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM