AndroidX Navigation 2.7.5中setGraph无法覆盖argument默认值的解决办法
在Navigation 2.7.5版本中,直接调用navController.setGraph()传入参数覆盖默认值的行为失效,原因是当NavHostFragment通过XML绑定导航图后,启动目的地的Fragment已提前初始化并使用默认参数,后续调用setGraph无法更新已创建的Fragment参数。以下是几种可行的解决方法:
方法一:初始化NavHostFragment时传入参数
移除布局中NavHostFragment的app:navGraph属性,改为通过代码创建NavHostFragment并传入导航图和参数,确保启动目的地初始化时就使用自定义参数:
// 先移除布局文件里的app:navGraph="@navigation/nav_graph"配置 val navHostFragment = NavHostFragment.create( R.navigation.nav_graph, bundleOf("sslovo" to SkyConstants.skyStartSlovoSearch) ) supportFragmentManager.beginTransaction() .replace(mainBinding.navHostFragment.id, navHostFragment) .commitNow() // 用commitNow确保Fragment立即完成初始化 navController = navHostFragment.navController
方法二:手动更新Fragment参数
如果无法修改NavHostFragment的初始化方式,可以在目标Fragment的onCreate阶段手动替换默认参数:
class SkySearchFragment : Fragment() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) arguments?.let { args -> // 直接用Bundle操作 if (args.getString("sslovo") == "main") { args.putString("sslovo", SkyConstants.skyStartSlovoSearch) } // 或者用Safe Args(推荐) val safeArgs = SkySearchFragmentArgs.fromBundle(args) if (safeArgs.sslovo == "main") { arguments = SkySearchFragmentArgs.Builder(safeArgs) .setSslovo(SkyConstants.skyStartSlovoSearch) .build() .toBundle() } } } }
方法三:通过导航动作跳转至启动目的地
如果允许重新创建启动目的地Fragment,可以调用navigate方法传入参数覆盖默认值:
// 方式1:使用Safe Args生成的导航方向 val directions = SkySearchFragmentDirections.actionSelf( sslovo = SkyConstants.skyStartSlovoSearch ) navController.navigate(directions) // 方式2:直接传入Bundle navController.navigate( R.id.SkySearchFragment, bundleOf("sslovo" to SkyConstants.skyStartSlovoSearch) )
注意:这种方法会重新创建Fragment实例,若需要保留原有状态需额外处理。
内容的提问来源于stack exchange,提问作者ASDzendo
相关产品推荐
相关产品推荐

