所以我正在使用android导航组件,但遇到了问题(2.2.0-rc04版本)。
我有一个welcomeFragment
(wF)。我想从wF
导航到另一导航图中的loginSellerFragment
(lSF)。我也不想在导航到wF
时从堆栈(popUpTo,popUpToInclusive)中删除lSF
,因为用户可能想返回到它。
<fragment
android:id="@+id/welcomeFragment">
<action
android:id="@+id/action_welcomeFragment_to_nav_onboarding_seller"
app:launchSingleTop="true"
app:destination="@id/nav_onboarding_seller" />
</fragment>
导航到lSF后,堆栈看起来像这样: wF lSF
我们现在在lSF
上,登录后我们想转到feedFragment
(fF),它又在单独的图中,但是这次我们要清除所有的后退堆栈,因为如果用户登录并按回,他希望应用程序退出,而不是让他回到wF
或lSF
,因此我在popUpTo="@id/loginSellerFragment popUpToInclusive='true"
的操作中使用了lSF
到fF
。
<fragment
android:id="@+id/loginSellerFragment">
<action
android:id="@+id/action_login_to_seller"
app:destination="@+id/seller" . //this is the graph that has as firstDestination, feedFragment
app:launchSingleTop="true"
app:popUpTo="@id/loginSellerFragment"
app:popUpToInclusive="true" />
</fragment>
因此,此时在后退堆栈中的值应该仅为 fF ,因为我们删除了lSF
(包括lSF
在内的所有内容)
问题
当我在fF
上并按回去时,该应用程序不会关闭,而是将我带到wF
(wF
应该已经从后堆栈中弹出了)< / p>
我尝试过的事情
我尝试使用popUpTo="@id/loginSellerFragment popUpToInclusive='true"
来代替popUpTo="@id/welcomeFragment popUpToInclusive='true"
,但效果很好,但是我很确定这不是应该这样做的方法。我在这里想念什么?我在构建堆栈时错了吗?
我也尝试从popUpTo="@id/welcomeFragment popUpToInclusive='true"
导航到wF
后添加lSF
,但这会破坏我的用户体验,因为我不希望应用程序在我退出时退出m仍在登录过程中。
请注意,所有这些片段都在单独的图中。
要导航,我使用FragmentDirections
例如:findNavController.navigate(WelcomeFramgentDirections.actionXtoY())
答案 0 :(得分:8)
在使用popUpTo
选项时,要掌握导航组件如何操纵后退堆栈并不容易。
您在问题中提到的解决方案是正确的:
您确实应该使用popUpTo="@id/welcomeFragment" popUpToInclusive="true"
而不是popUpTo="@id/loginSellerFragment" popUpToInclusive="true"
。
我将尝试解释原因。
启动应用程序时,堆栈将为空,并显示welcomeFragment
。
从welcomeFragment
导航到loginSellerFragment
时,您的后栈中将有welcomeFragment
。
与登录相比,您将从loginSellerFragment
导航到feedFragment
,在后退堆栈中,您将拥有loginSellerFragment
和welcomeFragment
。
自从您使用popUpTo="@id/welcomeFragment"
以来,应用程序就会开始从后退栈中弹出(删除)片段,直到达到welcomeFragment
。由于我们使用了welcomeFragment
,因此popUpToInclusive="true"
也将被删除。
Backstack的行为应类似于FIFO(先进先出)堆栈,因此,如果要以这种方式删除片段,则:
首先将删除顶部的片段,即loginSellerFragment
。
接下来,welcomeFragment
将是最上面的片段。由于我们需要弹出片段,直到到达welcomeFragment
,这才是我们停止的地方,但是welcomeFragment
也将由于popUpToInclusive="true"
而被删除,并且您的后退栈将为空。
如果您尝试从welcomeFragment
向后导航,则由于后栈为空,因此将退出应用程序。
我希望这会有所帮助。您还可以阅读有关堆栈数据结构的更多信息。
答案 1 :(得分:0)
对我来说设置 XML 代码并没有真正解决问题,不得不使用额外的代码行
findNavController()
.navigate(R.id.navigationFragment,
null,
NavOptions.Builder()
.setPopUpTo(R.id.splashFragment,
true).build()
)