Android ViewPaper使用FragmentPagerAdapter出现的FragmentManagerImpl为空的问题
来源:互联网 发布:长沙理工网络教学平台 编辑:程序博客网 时间:2024/05/20 03:44
问题描述
在使用ViewPaper结合FragmentPagerAdapter实现fragment滑动切换过程中,插入OTG存储设备,进入界面很卡顿,弹出停止运行提示。
问题类型
INT,ANR
堆栈信息
10-22 17:43:10.683 3175 3175 E AndroidRuntime: FATAL EXCEPTION: main10-22 17:43:10.683 3175 3175 E AndroidRuntime: Process: com.xxx.xxxx, PID: 317510-22 17:43:10.683 3175 3175 E AndroidRuntime: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.support.v4.app.FragmentManagerImpl.performPendingDeferredStart(android.support.v4.app.Fragment)' on a null object reference10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.support.v4.app.Fragment.setUserVisibleHint(Fragment.java:879)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.support.v4.app.FragmentPagerAdapter.setPrimaryItem(FragmentPagerAdapter.java:130)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.support.v4.view.ViewPager.populate(ViewPager.java:1104)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.support.v4.view.ViewPager.setCurrentItemInternal(ViewPager.java:552)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.support.v4.view.ViewPager.setCurrentItemInternal(ViewPager.java:514)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.support.v4.view.ViewPager.setCurrentItem(ViewPager.java:506)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at com.xxx.xxxx.ui.MyActivity.setTabSelection(MyActivity.java:477)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at com.xxx.xxxx.ui.MyActivity.access$2100(MyActivity.java:69)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at com.xxx.xxxx.ui.MyActivity$MyTabOnClickListener.onClick(MyActivity.java:301)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.view.View.performClick(View.java:5212)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.view.View$PerformClick.run(View.java:21214)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.os.Handler.handleCallback(Handler.java:739)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.os.Handler.dispatchMessage(Handler.java:95)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.os.Looper.loop(Looper.java:148)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at android.app.ActivityThread.main(ActivityThread.java:5619)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at java.lang.reflect.Method.invoke(Native Method)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:850)10-22 17:43:10.683 3175 3175 E AndroidRuntime: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:734)
原因分析
从堆栈信息分析,只因为FragmentPagerAdapter中的fragmentManager为空导致的,但是排查代码,发现fragmentmanager是来自fragmentActivity的getSupportFragmentManager,而且在onCreate中已经初始化了的,并且在整个Activity中并没有出现置空的语句。那问题就来了,为什么fragment为空呢?
1、多线程问题,在其他地方修改了fragmentManager
根据前面的分析,排查后发现不可能为该问题引起。
2、viewpaper的切换出现在了错误的时机,fragmentmanager已被回收
根据现象的描述,出现问题前界面卡顿,那会不会是响应界面切换的时候,进入了一个错误的时机。确实,这种可能性是很大的,但是所谓的错误的时机又是什么呢?这个时机应该就是,viewpaper的切换响应在了fragmentmanager被回收之后,然而根据Activity的生命周期,资源的回收应该是在onDestroy之中。所以大胆猜想,在viewpaper切换界面的时候,由于系统原因(anr),导致切换时间延后了,当事件被响应的时候已经是Activity销毁之后了。
问题复现
根据原因分析中的第2点,尝试复现问题。首先,在onDestroy中添加代码行mViewPager.setCurrentItem(index, false);运行apk。进入Activity,然后退出Activity。发现应用停止运行,抓取log,发现log一样。
解决办法
该问题属于小概率的问题,一般情况下,viewpaper的界面切换都可以立即响应的。针对该问题,考虑到viewpaper切换界面的过程是无法中断的,所以无法再onDestroy中添加中断操作,阻止错误时机下的切换操作。所以只能对这一现象添加防呆操作,合理性在于,界面的切换出现在onDestroy之后是没有意义的。那在哪里防呆比较合适呢,这就要看我们的代码能够得到那里了。回看log信息,从上往下看,实现过程自定义了一个adapter继承自FragmentPagerAdapter,巧的是,android.support.v4.app.FragmentPagerAdapter.setPrimaryItem(FragmentPagerAdapter.java:130)
,该方法使我们能够到的最底的地方,所以在这里防呆比较合适。防呆方法就是重写该方法,捕获父类该方法的实现。具体如下:
@Override public void setPrimaryItem(ViewGroup container, int position, Object object) { // TODO 自动生成的方法存根 try { super.setPrimaryItem(container, position, object); } catch (Exception e) { // TODO: handle exception LogUtils.e("MyFragAdapter", "", e); } }
相关链接
http://stackoverflow.com/questions/10456077/nullpointerexception-in-fragmentmanager
- Android ViewPaper使用FragmentPagerAdapter出现的FragmentManagerImpl为空的问题
- Android ViewPaper的使用
- FragmentPagerAdapter调用Fragment的空指针问题
- Fragment内嵌套使用FragmentPagerAdapter出现空白页的问题
- 使用ViewPager设置适配器FragmentPagerAdapter出现页面空白的问题
- Android ViewPaper的Demo介绍
- 使用spring的aop实现权限拦截后出现依赖注入为空的问题
- 使用spring的aop实现拦截action后出现依赖注入为空的问题
- FragmentPagerAdapter使用遇到的问题、instantiate
- FragmentPagerAdapter 遇到的问题
- ViewPager + FragmentPagerAdapter的使用
- PagerAdapter、FragmentPagerAdapter的使用
- ViewPager+FragmentPagerAdapter的使用
- 关于java中判断为空出现空指针异常的问题
- 关于Android Studio使用butterknife:8.5.1注解是,控件总是为空的问题
- android 中的inclue标签中出现的空指针问题
- iText使用PdfCopy时出现的空指针问题
- struts中tiles使用中出现空指尖的问题
- 安卓开发工程师必备的后台知识(Jfinal的配置和了解,VisualSVN server的配置,数据库的安装)
- Resolving conflicts between main and test APK
- python3.4实现调用opencv3.1.0显示图像
- yarn LocalResourcesTrackerImpl remove resource Error
- 辨异 —— 有两人生日在同一天、只有两人生日在同一天
- Android ViewPaper使用FragmentPagerAdapter出现的FragmentManagerImpl为空的问题
- github项目链接
- 171.Anagrams-乱序字符串(中等题)
- github上关于iOS的各种开源项目集合
- nginx启动,重启,关闭命令
- KoaHub.JS基于Node.js开发的处理和显示日期代码
- 关于Hive中的复杂数据类型Array,Map,Structs的一些使用案例
- oracle11g rac RMAN备份恢复至单机
- android开发步步为营之113:Gradle错误Unsupported major.minor version 52.0和 finished with non-zero exit value1解决