I am Following along in a course and I do not understand the logical reason for the different behavior in the two code examples. I start with the working example then I highlight what breaks the code. There are solutions for this problem in similar questions but I haven't found a description or term for what is happening.
Below the setInterval works correctly and the timer function counts down per second as it should. There is a secs useState hook to keep track of seconds, and an inProgress useState.
React.useEffect(() => {
if (!inProgress) {
clearInterval(interval.current)
} else {
interval.current = setInterval(() => {
setSecs((secs) => {
const timeLeft = secs - 1;
return timeLeft
})
}, 1000)
}
return () => clearInterval(interval.current);
}, [inProgress])
Below is the code excerpt that varies and breaks the code.
interval.current = setInterval(() => {
setSecs(secs - 1)
console.log('interval fires')
console.log(secs)
}, 1000)
This code does not work, it counts down for one second and then nothing happens. When using the console.logs as seen above, 'interval fires' prints every second as does 'secs', however the secs state is not counting down its stays the same number.
React.useEffect(() => {
if (!inProgress) {
clearInterval(interval.current)
} else {
interval.current = setInterval(() => {
setSecs(secs - 1)
}, 1000)
}
return () => clearInterval(interval.current);
}, [inProgress])
This seems like important behavior to commit to memory, yet I don't know how to categorize it. I'm looking for terms that describe this behavior or a good visual explanation of it.
The last setSec state ran 1000ms ago, and even If I setInterval to 10 seconds the problem persists. So this is not a render, mount, update issue based in time. I don't believe this can be described by closures either. I currently cannot logically understand this behavior.