应用框架优化方案

来源:互联网 发布:期货1分钟实时数据 编辑:程序博客网 时间:2024/06/06 16:26

1、问题描述

         使\应用使用越来越慢,主要表现在切换tab bar时,页面切换卡顿明显

2、问题分析

  •        主界面布局
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:layout_width="match_parent"    android:layout_height="match_parent"    android:background="@color/pageBg"    android:orientation="vertical" >    <FrameLayout        android:id="@+id/details"        android:layout_marginBottom="60dp"        android:layout_width="fill_parent"        android:layout_height="fill_parent" />    <fragment        android:id="@+id/table"        android:layout_marginTop="-60dp"        android:layout_width="fill_parent"        android:layout_height="fill_parent"        android:name="com.synnex.neighborhood.ui.TableBarFragment" /></LinearLayout>
  • 底部导航栏TableBarFragment实现页面切换,核心源码如下:
public void changeFragment(int index) {        FragmentTransaction fragmentTransaction = fragmentManager    .beginTransaction();    android.support.v4.app.Fragment otherdesc = getFragmentManager().findFragmentById(    R.id.details);    if (otherdesc != null && otherdesc.isVisible()) {    fragmentTransaction.remove(otherdesc);    fragmentTransaction    .setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);    }        TempData.fragmentNo = index;    tempIndex = index;    switch (index) {    case 0:    cutIndex = 0;               agmentNew newIndex = new IndexFragmentNew();    fragmentTransaction.replace(R.id.details, newIndex);    break;    case 1:    cutIndex = 1;    IntetractsMainFragment searchIntent = new IntetractsMainFragment();    fragmentTransaction.replace(R.id.details, searchIntent);    break;    case 2:    cutIndex = 2;    PropertyMainFragmentNew propertyIntent = new PropertyMainFragmentNew();    fragmentTransaction.replace(R.id.details, propertyIntent);    break;    case 3:    cutIndex = 3;    if(changeLifeAroundVersion){    LifeAroundTypeNewFragment LifeAroundIntent = new LifeAroundTypeNewFragment();    fragmentTransaction.replace(R.id.details, LifeAroundIntent);    }else if(changeLifeAroundVersion20150310){    mLifeAroundTypeListNewFragment = new LifeAroundTypeListNewFragment();    mLifeAroundTypeListNewFragment.mCallback = this;    fragmentTransaction.replace(R.id.details, mLifeAroundTypeListNewFragment);    } else{    LifeAroundTypeFragment LifeAroundIntent = new LifeAroundTypeFragment();    fragmentTransaction.replace(R.id.details, LifeAroundIntent);    }    break;    case 4:    cutIndex = 4;    MineFragment mineFragment = new MineFragment();    fragmentTransaction.replace(R.id.details, mineFragment);    break;    default:    break;    }    fragmentTransaction.commitAllowingStateLoss();}

       我们在处理页面切换的时候会将对应模块的Fragement replace,replace 后会将Fragement彻底删除,下次切换回来的时候,Fragement需要重新创建,Fragement没有重用这种效率特别低,就会导致以上切换卡顿的问题。可能会有同学提出为什么不将Fragement添加到BackStack,我们可以这么做但无法实现我们想要的功能,BackStack适用于我们按back 键的时候将Fragment回退,否则按back键,应用会退出当前activity,

如果我们想在一个activity中放置多个Fragement,且按back键能顺序退出类似于退activity这种类似功能我们可以使用该属性。

   作为底部导航栏,我们希望切换tab时对应的界面能够迅速的加载出来,中间没卡顿而不是退出的时候顺序退出。该如何实现了?

3、解决方案

        其实Fragement的切换除了replace外官方提供了另外的方式。

         show 和 add,当Fragement 已经创建需要显示时调用show方法,其他模块的Fragement 则hide;如果Fragement 没有创建则创建该Fragement并调用add方法添加到需要显示的区域。这种方式的好处是当我们加载过一次Fragement后,以后切换会特别流畅,原因是它不需要重新去创建将所有视图重新初始化。这样即可解决切换问题。

FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();hideFrgement(fragmentTransaction) ;//隐藏其他模块的FragementTempData.fragmentNo = index;tempIndex = index;switch (index) {case 0:cutIndex = 0;if(newIndex!=null){fragmentTransaction.show(newIndex);}else {newIndex = new IndexFragmentNew();fragmentTransaction.add(R.id.details, newIndex);}break;case 1:cutIndex = 1;if(searchIntent!=null){fragmentTransaction.show(searchIntent);}else {searchIntent = new IntetractsMainFragment();fragmentTransaction.add(R.id.details, searchIntent);}break;case 2:cutIndex = 2;if(propertyIntent!=null){fragmentTransaction.show(propertyIntent);}else {propertyIntent = new PropertyMainFragmentNew();fragmentTransaction.add(R.id.details, propertyIntent);}break;case 3:cutIndex = 3;if(mLifeAroundTypeListNewFragment!=null){fragmentTransaction.show(mLifeAroundTypeListNewFragment);}else {mLifeAroundTypeListNewFragment = new LifeAroundTypeListNewFragment();mLifeAroundTypeListNewFragment.mCallback = this;fragmentTransaction.add(R.id.details,mLifeAroundTypeListNewFragment);}break;case 4:cutIndex = 4;if(mineFragment!=null){fragmentTransaction.show(mineFragment);}else {mineFragment = new MineFragment();fragmentTransaction.add(R.id.details, mineFragment);}break;default:break;}fragmentTransaction.commitAllowingStateLoss();

        当然有利必有弊,这种方案其实是典型的空间换时间,将Fragement缓存到内存中,如果我们的模块过多有10多个或者几十个Fragement,这可能会导致oom等类似问题。如果我们的应用没有复杂到这个量级其实是完全没有问题的。当然应用本身也需要做一些内存的优化和管理。

     

0 0
原创粉丝点击