如何清理在useEffect之外的函数?



我有一个重发代码按钮,按下后将禁用它30秒。下面是我的函数。

const time = useRef(30);
function disableResendBtn() {
time.current = 30;
setsendCodeBtnDisabled(true);
const interval = setInterval(() => {
(time.current = time.current - 1),
setsendCodeBtnText(i18n.t('RESEND') + '(' + time.current + ')'),
console.log(time.current);
}, 1000);
setTimeout(() => {
setsendCodeBtnDisabled(false);
setsendCodeBtnText(i18n.t('RESEND'));
clearInterval(interval);
}, 30000);
}

当我移动到下一页时,我得到了Can't perform a React state update on an unmounted component. This is a no-op, but it indicates a memory leak in your application. To fix, cancel all subscriptions and asynchronous tasks in %s.%s, a useEffect cleanup function的错误。这个错误不是每次都显示。所以我很困惑setInterval/setTimeout函数是否是原因。

无论如何,我如何使用useEffect来清除它呢?该函数不在useEffect中。

您可以将setIntervalsetTimeout的返回值存储在ref中,然后创建一个空的useEffect,然后为您清理这些。

我能想到一个更简单的方法。而不是跟踪这些间隔和超时,然后使用空的useEffect进行清理,您可以创建一个useEffect,它每秒更新当前时间。并且,为了跟踪禁用状态,您可以创建另一个状态来跟踪"直到按钮应该被禁用"。

export default function App() {
const [currentTime, setCurrentTime] = React.useState(Date.now());
const [disabledUntil, setDisabledUntil] = React.useState(0);
React.useEffect(() => {
const interval = setInterval(() => {
setCurrentTime(Date.now());
}, 1000);
return () => clearInterval(interval);
}, []);
const onClick = () => {
// disable button for 30 seconds
setDisabledUntil(Date.now() + 30 * 1000);
};
const buttonDisabledSeconds = Math.floor(
(disabledUntil - currentTime) / 1000
);
return (
<div>
<button onClick={onClick} disabled={currentTime < disabledUntil}>
Send
</button>
<p>
{buttonDisabledSeconds >= 0 &&
`Button disabled for ${buttonDisabledSeconds} seconds`}
</p>
</div>
);
}

这样,cleanup非常接近实际的间隔定义。

相关内容

  • 没有找到相关文章

最新更新