React中使用setInterval的组件未随Context状态变更更新倒计时
问题根因
useCountdownhook的useEffect依赖数组为空,只会在组件首次挂载时执行一次,之后即使传入的date参数(也就是Context里更新的startDate)发生变化,也不会重置定时器,会一直用最初传入的日期计算倒计时- 切换Context中选中的对象时,
SidePanel组件拿到了新的startDate,但传给useCountdown之后,hook内部没有响应这个参数变化,因此倒计时不会同步更新
修复方案
给useEffect添加date作为依赖,同时每次依赖变更时先立即执行一次倒计时计算,避免1秒的更新延迟:
export function useCountdown(date: Date) { const [countdown, setCountdown] = useState<number>(0) const formatCountdown = () => { const diffInSeconds = dateFns.differenceInSeconds(date, new Date()) setCountdown(diffInSeconds <= 1 ? 0 : diffInSeconds) } useEffect(() => { // 立即计算一次,避免切换后延迟1秒才更新 formatCountdown() const interval = setInterval(() => { formatCountdown() }, 1000) return () => clearInterval(interval) }, [date]) // 把date加入依赖,日期变化时自动重置定时器 return countdown }
修改后只要Context中的active.startDate发生变化,传入useCountdown的新日期就会触发Effect重新执行,自动清空旧定时器、用新日期计算倒计时,即可和其它数据同步更新。
内容的提问来源于stack exchange,提问作者Jason McFarlane
相关产品推荐
相关产品推荐

