ViewPager + Fragment套用Fragment的问题

今天遇到一个Fragment内显示ViewPager,ViewPager的view也是Fragment的相关问题,最开始使用的是FragmentStatePagerAdapter。出现第一次进入Fragment时,viewpager正常显示数据,当第二次进来时,就无法显示数据,经过打印信息测试,发现第二次进来时并没有走Viewpager显示的Fragment的oncreateview和onactivitycreated方法。开始以为时viewpager的预加载特性导致的。后来在网上各种查,最开始的解决方案是按照这篇博客的方法点击打开链接,针对FragmentPagerAdapter的解决办法如下代码:

@Override
	public Fragment getItem(int position) {
		MyFragment f = new MyFragment();
		return f;
	}

	@Override
	public Object instantiateItem(ViewGroup container, int position) {
		MyFragment f = (MyFragment) super.instantiateItem(container, position);
		String title = mList.get(position);
		f.setTitle(title);
		return f;
	}

	@Override
	public int getItemPosition(Object object) {
		return PagerAdapter.POSITION_NONE;
	}

发现然并卵,第二次进来依然没有数据,关键的是没有view,因为我在instantiateItem方法内让一个隐藏的图片显示,都没有成功。之后又是各种查资料。终于成功了。因为我的这个问题可能比单纯的不显示数据还要复杂一些。解决方法是:

(要确保是Fragment里面套用Fragment)

①显示ViewPager的Fragment获取FragmentManager时不能用getActivity().getSupportFragmentManager()了,要改用getChildFragmentManager()。

仅仅是这样,会出现异常:java.lang.IllegalStateException: No activity

出现场景:第一次启动程序可以正常运行,随便切换pager也不会有问题,第二次必崩!

是什么引起的bug
If you look at the implementation of Fragment, you'll see that when moving to the detached state, it'll reset its internal state. However, it doesn't reset mChildFragmentManager (this is a bug in the current version of the support library). This causes it to not reattach the child fragment manager when the Fragment is reattached, causing the exception you saw.

②修复Bug,

bug原理:This seems to be a bug in the newly added support for nested fragments. Basically, the child FragmentManager ends up with a broken internal state when it is detached from the activity. A short-term workaround that fixed it for me is to add the following to onDetach() of every Fragment which you call getChildFragmentManager() on

在这个Fragment里重写onDetach方法:(这段代码直接复制,不需要修改,Field的包名是java.lang.reflect.Field)

@Override
	public void onDetach() {
		// TODO Auto-generated method stub
		super.onDetach();
		try {
			Field childFragmentManager = Fragment.class
					.getDeclaredField("mChildFragmentManager");
			childFragmentManager.setAccessible(true);
			childFragmentManager.set(this, null);
		} catch (NoSuchFieldException e) {
			throw new RuntimeException(e);
		} catch (IllegalAccessException e) {
			throw new RuntimeException(e);
		}
	}
如果用的是FragmentStatePagerAdapter这种写法会出现 java.lang.IllegalStateException:Fragement no longer exists for key f0: index 0异常,所以要确保使用的是FragmentPagerAdapter。两种方法都是有用的,看看是要解决哪种问题。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值