【问题标题】:Calling getSupportFragmentManager() after getChildFragmentManager() causes IllegalStateException: Recursive entry to executePendingTransactions在 getChildFragmentManager() 之后调用 getSupportFragmentManager() 会导致 IllegalStateException: Recursive entry to executePendingTransactions
【发布时间】:2015-01-16 14:00:45
【问题描述】:

我正在使用 FrameLayout 来显示片段

 <FrameLayout
        android:id="@+id/fragment_content"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:layout_above="@+id/bottom_layout"
        android:background="@android:color/white" >
    </FrameLayout>

并打开我正在使用的片段

ft.add(R.id.fragment_content, frag);
ft.commit();
fm.beginTransaction();

一个片段包含地图,所以我在布局文件中使用这些行

<fragment
        android:id="@+id/trafic_Alarm_main_mapView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        class="com.Utilities.MySupportMapFragment"
        android:layout_alignParentTop="true" />

这是我的 Java 代码

try{
mMap=(MySupportMapFragment)TabsActivity.fm.findFragmentById(R.id.trafic_Alarm_main_mapView)).getMap();
}catch (Exception e){
mMap=((MySupportMapFragment)getChildFragmentManager().findFragmentById(R.id.trafic_Alarm_main_mapView)).getMap();
}

现在,如果调用 getChildFragmentManager() 并且我切换到另一个使用 getSupportFragmentManager 开始事务的片段会导致崩溃。提供日志

01-16 18:36:15.690    7294-7294/com.TrafikAlarm E/AndroidRuntime﹕ FATAL EXCEPTION: main
    Process: com.TrafikAlarm, PID: 7294
    java.lang.IllegalStateException: Recursive entry to executePendingTransactions
            at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1461)
            at android.support.v4.app.FragmentManagerImpl$1.run(FragmentManager.java:454)
            at android.os.Handler.handleCallback(Handler.java:739)
            at android.os.Handler.dispatchMessage(Handler.java:95)
            at android.os.Looper.loop(Looper.java:135)
            at android.app.ActivityThread.main(ActivityThread.java:5221)
            at java.lang.reflect.Method.invoke(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:372)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:899)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:694)

我正在使用 android studio 并编译这些库,

compile 'com.google.android.gms:play-services:6.5.87'
compile 'com.android.support:appcompat-v7:21.0.3'

当我使用 eclipse 时,我不需要使用 getChildFragmentManager 并且一切正常。

提前致谢。

【问题讨论】:

  • 那个 Java 代码的上下文是什么?它位于何处。在我假设的父片段中?
  • 可能您正试图使用​​嵌套在其他片段中的片段。参考这个链接stackoverflow.com/questions/22150950/…
  • 安迪,上下文是片段活动类。
  • 你为什么第二次打电话给fm.beginTransaction();?
  • Matish 只接一个电话

标签: android android-fragments google-maps-android-api-2 android-nested-fragment


【解决方案1】:

【讨论】:

  • 我尝试使用这个,我得到同样的错误 mMap=((MySupportMapFragment)getParentFragment().getFragmentManager().findFragmentById(R.id.trafic_Alarm_main_mapView)).getMap(); java.lang.NullPointerException:尝试在空对象引用上调用虚拟方法 'android.support.v4.app.FragmentManager android.support.v4.app.Fragment.getFragmentManager()'
【解决方案2】:

由于您的上下文是一个片段,您是否尝试过在使用子片段管理器之前调用 super ?

super(fragment.getChildFragmentManager());

【讨论】:

  • 我应该在哪里称呼它?
  • this 所在方法的第一行:try{ mMap=(MySupportMapFragment)TabsActivity.fm.findFragmentById(R.id.trafic_Alarm_main_mapView)).getMap(); }catch (Exception e){ mMap=((MySupportMapFragment)getChildFragmentManager().findFragmentById(R.id.trafic_Alarm_main_mapView)).getMap(); }
  • 我没有在任何被覆盖的方法中使用它。父级覆盖方法是 onCreateView 并且不支持 super(fragment.getChildFragmentManager());
【解决方案3】:

您好,您似乎遇到了递归问题Recursive entry to executePendingTransactions,因为您不止一次重复调用,并且在异常处理中,实际上捕获异常错误并尝试“做某事()”是错误的

try{

mMap=(MySupportMapFragment)TabsActivity.fm.findFragmentById(R.id.trafic_Alarm_main_mapView)).getMap();

}catch (Exception e){

mMap=((MySupportMapFragment)getChildFragmentManager().findFragmentById(R.id.trafic_Alarm_main_mapView)).getMap();

}

删除catch区域的不必要的调用,如果出现新错误,请务必阅读日志猫,并在正确的@override中添加/删除片段,例如@onCreate 与fragment 合作的活动。

希望对你有帮助。

【讨论】:

    【解决方案4】:

    布局片段一次性很棒,添加和忘记一种用法。除此之外,您必须使用 java 代码管理片段。

    在添加、替换片段时只需遵守一些规则:

    Int frameId = // id of host view
    Fragment manager = // fragment manager, of Activity or a Fragment
    String tag = // unique tag for the fragment
    String clazz = // class name of the fragment
    Bundle args = // initial data to be supplied to fragment instance
    
    Fragment frg = manager.findFragmentbyTag(tag);
    
    if(frg == null){
      frg = Fragment.instantiate(context,clazz,args);
    }
    
    if(!frg.isAdded()){
       manager.beginTransaction().add(frameId, frg, tag).commit();
    }
    

    如果 Fragment 还必须在开始时显示嵌套的 Fragment,您可以在其 onViewCreated() 中使用上述代码。

    FragmentManager 本质上是异步的,在commit() 之后,它不会立即应用片段更改。提交计划在未来某个时间发生。 executePendingTransactions() 可用,但使用时应格外小心。它使所有计划的事务立即运行,并且当它们运行时,您不能再次调用它。

    【讨论】:

      【解决方案5】:

      我找到了错误。我正在使用 FragmentActivity 管理器返回地图对象以删除导致问题的地图片段而日志没有。所以,我改变了

      TabsActivity.fm.beginTransaction().remove((MySupportMapFragment) TabsActivity.fm.findFragmentById(R.id.trafic_Alarm_main_mapView)).commit();
      

      到

      TabsActivity.fm.beginTransaction().remove((MySupportMapFragment) getChildFragmentManager().findFragmentById(R.id.trafic_Alarm_main_mapView)).commit();
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-01-25
        • 2015-09-30
        • 1970-01-01
        • 2015-03-25
        • 1970-01-01
        相关资源
        最近更新 更多