FragmentManager popBackStack不会删除片段

时间:2014-05-06 15:43:22

标签: android android-fragments android-nested-fragment fragmentmanager

我正在使用Fragments实现菜单导航。所以我从Home开始,然后用户可以导航到每个部分的不同部分和细节。

当用户更改部分时,我会在fragmentmanager backstack上调用pop,直到我到达Home,然后加载新部分。

这一切都按预期工作。但是我遇到了这个问题:

  1. 在onResume()上加载一个调用setHasOptionsMenu(true)的部分
  2. 加载另一个部分(旧部分,它被用来离开堆栈)。我觉得没问题。没有菜单显示
  3. 离开应用程序(例如,转到Android Laucher活动)然后当我返回时,我看到了正确的部分,但它显示了旧片段的菜单。
  4. 我已经迭代了后台并打印了每个片段,并且它不是带有菜单的片段。

    我在onResume()方法上放置了一个调试标记(标记了setHasOptionsMenu(true)),它确实进入了这里,所以碎片它仍然在某处。

    我想知道我是否做错了什么,我怎么能解决它,thx

    更新

    我使用此代码加载新片段

    fm.beginTransaction()
        .add(container, sectionFragment.getFragment())
        .addToBackStack(sectionFragment.getFragmentName())
        .commit();
    

    并删除:

    private void clearStack(){
    int count = fm.getBackStackEntryCount();
        while(count > 1){
            fm.popBackStack();
            count--;
        }
    }
    

    注1:我使用add代替替换,因为当我从详细信息部分导航回来时,我不想丢失片段的状态。当我加载另一个不同的部分,然后我调用clearStack将堆栈弹出到1,然后加载新的片段。最后,我调用executePendingTransactions()来完成从事务中删除片段。

    注意2:我发现它正在我的片段onDestroy()方法中进入,所以它被摧毁了。但是,当主要活动恢复时,我不知道为什么会再次调用它。

6 个答案:

答案 0 :(得分:22)

我发现问题不在于添加和删除堆栈片段的逻辑。

问题是一些片段在其中加载了另一个片段(它有ViewPager组件)。然后我想,当片段被移除后,这些片段也被移除了。

仅在使用getChildFragmentManager()方法时才是这样。在其他碎片中加载碎片时必须使用此方法。如果没有,则片段与片段活性相关联。

答案 1 :(得分:6)

我发现了这个问题,因为在打电话之后

fragmentManager.popBackStack(null, FragmentManager.POP_BACK_STACK_INCLUSIVE);

此代码fragmentManager.getFragments().size()返回堆栈中的最大片段数。我检查了null上的每个片段。我发现一些片段在我的情况下是空的。也许这对某人有帮助)

答案 2 :(得分:5)

popBackStack只会恢复您的上一个FragmentTransaction

如果您使用FragmentTransaction.addpopBackStack只会致电FragmentTransacetion.remove

但如果您致电FragmentTransaction.replacepopBackStack会致电FragmentTransaction.removeFragmentTransaction.add

对于您的“注1”: FragmentTransaction.replace不会更改您的片段状态。

答案 3 :(得分:0)

如果您真的想要立即删除片段,请按照: How to replace Fragments of different types?

否则使用片段替换事务来平滑transitiona和hassel free方法,请参阅https://stackoverflow.com/a/23013075/3176433

同样了解Fragment生命周期, http://developer.android.com/guide/components/fragments.html

答案 4 :(得分:0)

我有一个类似的问题,popBackStack()没有删除我的片段。 但是,我注意到我拨错了FragmentManager,我必须拨打getSupportFragmentMananger()而不是getFragmentManager()

答案 5 :(得分:0)

在具有<fragment><androidx.fragment.app.FragmentContainerView>android:name="androidx.navigation.fragment.NavHostFragment"的活动中可能有app:defaultNavHost="true"app:navGraph="@navigation/nav_graph"

在这种情况下,导航由nav_graph保持。如果您不想使用NavControllerNavHostFragment,也许应该删除导航并清除<fragment>标签。