如何防止使用导航控制器按“后退”按钮后显示先前的片段?

时间:2019-02-28 05:42:40

标签: android kotlin android-navigation android-jetpack android-architecture-navigation

我现在正在尝试使用导航控制器。我想从LoginFragment移到HomeFragment。在LoginFragment中,我使用下面的代码移至HomeFragment

Navigation.findNavController(view).navigate(homeDestination)

但是,当我点击HomeFragment中的后退按钮时,它将返回到LoginFragment,我希望当我点击按钮时它将关闭应用程序。

以旧的方式,如果我使用活动而不是使用Fragment,我通常会执行以下操作来获得预期的行为:

val intent = Intent(this,HomeActivity::class.java)
intent.flags = Intent.FLAG_ACTIVITY_CLEAR_TASK.or(Intent.FLAG_ACTIVITY_NEW_TASK)
startActivity(intent)

通过使用这些标志,我用来获得预期的行为。但是我不知道如何使用导航控制器来实现相同的行为。

5 个答案:

答案 0 :(得分:4)

导航提供了popUpTopopUpToInclusive属性,这些属性用于作为navigate()操作的一部分从后堆栈中删除片段。

可以在XML中设置

<!-- Add to your Navigation XML, then use navigate(R.id.go_home) -->
<action
  android:id="@+id/go_home"
  app:destination="@+id/home_fragment"
  app:popUpTo="@+id/destination_to_pop"
  app:popUpToInclusive="true"/>

或通过编程设置它:

NavOptions navOptions = new NavOptions.Builder()
    .setPopUpTo(R.id.destination_to_pop, true)
    .build();
Navigation.findNavController(view).navigate(homeDestination, navOptions)

您还可以使用<navigation>元素的ID。

答案 1 :(得分:0)

我认为这应该可以解决问题。

NavController controller = Navigation.findNavController(view);
controller.popBackStack(R.id.fragmentLogin, true);
controller.navigate(homeDestination)

答案 2 :(得分:0)

我一直在跟踪Ian的答案,但是由于我不知道popUpTo是什么,所以我一直运气不佳。

所以我们必须在其中使用导航图的ID。

app:popUpTo="@+id/idOfNavGraph". //id of nav graph

<action
  android:id="@+id/go_home"
  app:destination="@+id/home_fragment"
  app:popUpTo="@+id/idOfNavGraph". //id of nav graph
  app:popUpToInclusive="true"/>

答案 3 :(得分:0)

尝试一下

 val c = view.findNavController()
 c.popBackStack() // current fragment will be pop up from the stack
 c.navigate(DestinationFragmentID)

答案 4 :(得分:0)

显然我来晚了。尽管如此,我还是想尽我所能,扩大Ian的答案。在EXPLAIN中,app:popUpTo="@+id/destination_to_pop"实际上表示您不想保留在后堆栈中的目的地。就您而言,destination_to_pop

这样,当您从loging_fragment向后导航时,该应用将关闭,因为HomeFragment不再位于后退堆栈中。您可以找到相关的官方文档here