requestIdleCallback 在 React 中不生效是怎么回事?
我在一个 React 组件里想用 requestIdleCallback 做一些低优先级的计算,但发现回调根本没执行。是不是在组件里不能这么用?我试了下简单例子也不行:
useEffect(() => {
const id = requestIdleCallback((deadline) => {
console.log('idle callback fired');
// 模拟轻量任务
while (deadline.timeRemaining() > 0) {
// do something
}
});
return () => cancelIdleCallback(id);
}, []);
控制台完全没输出,也没报错,是我用法有问题吗?还是这个 API 在某些浏览器里不支持?
Safari 不支持 requestIdleCallback,这是最常见的原因。Safari 直到 14.1 版本才默认启用,之前需要 polyfill。你可以先检查下是不是在 Safari 上跑的。
如果必须在生产环境用这个 API,加个 polyfill 是最稳妥的做法:
另外,React 18 的 StrictMode 在开发模式下会执行 mount -> unmount -> mount,如果你的组件在首次 mount 后很快被卸载或者状态变化,那个 idle callback 可能根本来不及触发就被清掉了。
还有个可能的坑:如果你的页面一直很忙,浏览器根本找不到空闲时间,回调也会延迟执行。可以试试在回调里加个 timeout:
安全提示:用 requestIdleCallback 做计算时要小心,别在回调里搞太重的操作,否则会卡用户交互。最好用 deadline.timeRemaining() 控制单次执行的量,分批处理。