当前开发的app有许多应用在UI设计上都是仿照微信,在MainActivity中使用ViewPager来展示页面,但是基本上目前所有的应用都需要请求网络来获取数据。而ViewPager的特性是预加载,这样就会造成我不想看其他页面的内容,但是它已经加载完成,造成用户流量的浪费。这样就需要使用懒加载,只有当用户可见时,才去加载数据。在此数据只加载一次,当用户需要刷新数据时可以使用下拉刷新等方式。当然你也可以不做这个设置。只需要稍微修改一下就可以了。 在此先要说下一下几个方法: 1.ViewPager中的setOffscreenPageLimit方法,设置预加载的个数,参数不能小于1,可设为MainActivity下的tab数目。 2.Fragment中的setUserVisibleHint方法,当参数为true时对用户可见,当为false时对用户不可见(注意:此处有坑,后面再说) 下面贴代码:
/** * Created by LiJZ */ public abstract class LazyFragment extends Fragment { protected View view; /** * 是否对用户可见的标志位 */ private boolean isVisible; /** * 判断view是不是已经填充完毕的标记位 */ private boolean isPrepared; /** * 是否已经加载过数据 */ private boolean isAlreadyLoadData = false; @Override public void setUserVisibleHint(boolean isVisibleToUser) { super.setUserVisibleHint(isVisibleToUser); if (isVisibleToUser) { isVisible = true; onVisible(); } else { isVisible = false; onInVisible(); } } /** * setUserVisibleHint为true时调用的方法 */ private void onVisible() { lazyLode(); } /** * setUserVisibleHint为false时调用的方法 */ private void onInVisible() { if (isAlreadyLoadData) { InVisibleEvent(); System.out.println("LazyFragment.onInVisible:InVisibleEvent"); } } private void lazyLode() { //确保View初始化完成 if (!isVisible||!isPrepared) { return; } //加载数据 if (!isAlreadyLoadData) {//如果没有加载过数据 initLazyLodeData(); isAlreadyLoadData = true; } } @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); } @Nullable @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { if (view == null) { view = View.inflate(getActivity(), getLayoutId(), null); } ViewGroup parent = (ViewGroup) view.getParent(); if (parent != null) { parent.removeView(view); } initview(); isPrepared = true; System.out.println("LazyFragment.onCreateView"+"----->"+getClassName()); return view; } @Override public void onViewCreated(View view, @Nullable Bundle savedInstanceState) { super.onViewCreated(view, savedInstanceState); lazyLode(); initData(); initEvent(); } /** * 布局xml文件的id * @return */ public abstract int getLayoutId(); /** * 在onCreateView中调用,可以执行findViewbyId操作 */ public abstract void initview(); /** * 初始化懒加载的数据 */ public abstract void initLazyLodeData(); /** * 初始化数据 */ public abstract void initData(); /** * 初始化事件 */ public abstract void initEvent(); /** * 加载过数据后,fragment变为不可见之后的需要执行的操作 */ public abstract void InVisibleEvent(); public String getClassName() { return getClass().getSimpleName(); } @Override public void onResume() { super.onResume(); System.out.println("onResume"+"----->"+getClassName()); } @Override public void onPause() { super.onPause(); System.out.println("onPause"+"----->"+getClassName()); } @Override public void onDestroyView() { super.onDestroyView(); System.out.println("onDestroyView"+"----->"+getClassName()); } @Override public void onDestroy() { super.onDestroy(); System.out.println("onDestroy"+"----->"+getClassName()); } }注意: 此种方式在ViewPager+Fragment情况下使用没问题,当UI结构为ViewPager+Fragment+Viewpager时,在内层ViewPager中会出现问题。因为setUserVisibleHint不同步。 可以参考这篇文章:http://www.jianshu.com/p/e7449278e33d Android的嵌套很容易出现问题,搭建布局前先考虑好各方面的问题,否则就是给自己找事情做。这是我老大当初给我说的。都是泪啊。
