React useEffect仅应用实例触发一次,抽屉导航页面跳转后未重新执行
根因分析
你使用的5.x版本Drawer导航默认会缓存所有已加载的子页面,页面切换到其他路由时当前Drawer子页面不会被卸载,仅会处于失焦状态。因此空数组依赖的useEffect只会在页面首次加载、组件挂载时触发一次,后续再次进入该页面时组件没有重新走挂载流程,自然不会输出新的日志,组件内部的state也会保留上次离开时的状态。
你首次进入页面的两次日志输出属于正常逻辑:第一次是组件初始化时someState默认值false触发第二个监听someState的useEffect,第二次是空依赖useEffect执行翻转state为true后再次触发第二个useEffect。
解决方案
提供两种常用处理方案,可根据业务场景选择:
方案1:使用
useFocusEffect监听页面聚焦事件(优先推荐)
React Navigation 内置的useFocusEffect钩子会在每次页面获得焦点时执行,不需要销毁重建组件,性能开销更低,适用于仅需要每次进入页面执行特定逻辑的场景:import { useFocusEffect } from '@react-navigation/native'; import { useCallback, useState, useEffect } from 'react'; // 组件内部代码 const [someState, setSomeState] = useState(false); useFocusEffect( useCallback(() => { // 每次进入页面都会执行的逻辑 setSomeState((prevState) => !prevState); // 可选:返回清理函数,页面失焦时执行 return () => { // 清理逻辑 }; }, []) ); useEffect(() => { console.log('useEffect'); console.log(someState); }, [someState]);方案2:配置页面失焦时自动卸载
如果需要每次进入页面都重置所有组件状态、完全重新走组件挂载流程,可以给对应的Drawer页面配置unmountOnBlur属性:<Drawer.Screen name="目标页面路由名" component={你的页面组件} options={{ unmountOnBlur: true }} />配置后页面每次失焦就会自动卸载,下次进入会重新挂载,空数组依赖的useEffect也会重新触发。
内容的提问来源于stack exchange,提问作者Waleed
相关产品推荐
相关产品推荐

