弹出整个FragmentManager BackStack

时间:2017-03-02 22:07:23

标签: android android-fragments fragment-backstack

实际问题/ TL; DR:除了使用一种方法我认为是hack之外,我无法弹出活动的整个backstack以返回到我的初始状态,在onCreate()期间添加了一个片段。片段存在于“活动状态管理器”转储中,但不可见,只留下空屏幕。

我今天遇到过这个问题,主要是试图了解这是由错误还是由于我对FragmentManager的BackStack的误解造成的。我想确保我不会滥用碎片或在不稳定的API基础上构建。

我有一个活动本质上提供了一个降序“树”导航作为按钮网格,其中每个按钮打开一个子网格(例如,具有更多按钮的子类别)或一些自定义形式。表格的内容是无关紧要的,但用户应该以各种顺序重复填写。

我使用支持库中的Fragments(support-v4:25.1.1),每当需要一个新的“屏幕”时(对于表单或子网格),它将使用活动的FragmentManager上的事务添加类似于:

/* adding a new screen, going further down our nav tree */
fragmentManager
            .beginTransaction()
            .addToBackStack("...")
            .replace(R.id.container, newFragment)
            .commit();

除了设置我的活动的初始状态之外,每个事务都是这样的,它会添加初始的“根网格”片段,而不会将事务添加到后台。

/* adding the initial fragment during the first execution of activity's onCreate(). */
fragmentManager
            .beginTransaction()
            .replace(R.id.container, rootFragment)
            .commit();

我在这里发帖的原因是我在尝试弹出整个BackStack时遇到了一个非常奇怪的行为,它应该将用户带回到具有根网格的活动的初始状态(添加了一个在上面的代码中)。我尝试的几乎所有技术都有效地清除了后台堆栈,但是留下了一个空屏幕,而不是我最初的主菜单网格。在查看了这里的多个问题和文档之后,我尝试了多种解决方案,只有这个看起来很黑的问题才有效:

int remainingEntries = fragmentManager.getBackStackEntryCount();
while (remainingEntries-- > 0) {
    fragmentManager.popBackStackImmediate();
}

我说这看起来像是一个黑客,因为它要求我立即(同步)弹出任意数量的backstack条目以到达根目录,而根据我的理解,应该可以这样做单个异步方法调用:

fragmentManager.popBackStackImmediate(null, FragmentManager.POP_BACK_STACK_INCLUSIVE);

或者我也看到过这里张贴的内容:

int id = fragmentManager.getBackStackEntryAt(0).getId();
fragmentManager.popBackStack(id, FragmentManager.POP_BACK_STACK_INCLUSIVE);

这只是根片段的问题,可能是因为将其添加到视图的事务没有添加到backstack,因为当用户按下后退按钮关闭时会导致显示额外的空屏幕活动。

更多详情:

  • 根据活动状态管理器转储,我的片段仍然有其视图,但mFragmentId和mContainerId都设置为#0。
  • 我确实添加了另一个我没有在这里讨论的片段,它保留了它的实例,但它只用于保存一些数据并且没有任何视图。

1 个答案:

答案 0 :(得分:1)

支持库版本 25.1.0及更高版本中有PopBackStackImmediate bug 由于已报告此问题,您必须等待解决方案,或者您可以将支持库版本降级到25.0.1 并获得预期的行为。

<强>更新

在支持库版本 25.3.1 中,似乎已解决此错误。将您的库更新到版本25.3.1。