Fragment状态的保存

当我们需要切换fragment的时候,官方给我们提供了两种方式:replace和add.
首先来看看replace方法:
replace方法相当于先移除remove()原来所有已存在的fragments,然后添加add()当前这个fragment。这就导致了一个问题,我们切换一次,然后再切换回来,相当于重新加载了这个fragment,原来的状态不复存在,这显然与我们的日常使用不符。先做个实现说明一下这个现象。

这里写图片描述
这里写图片描述

最下面是两个按钮,用于切换两个Fragment,第一个Fragment中是一个按钮和一个文字,默认显示为你好吗,点击按钮切换文字为我很好,如图所示

这里写图片描述
但是当我们点击第二个按钮切换到第二个Fragment,然后在切换回来的时候,发现文字又变成默认的了,这就说明重新实例化了fragment对象,Fragment的状态没有得到保存。

我们在每个Fragment的生命周期的onCreateView方法中打印一行Log

Log.d("Fragment", "FragmentOne------onCreateView");

每次切换Fragment时我们去看控制台是不是都会打印这句话。
这里写图片描述
可以看到,每次点击按钮切换Fragment时都会调用Fragment的onCreateView生命周期方法。这就说明使用replace方法切换Fragment是无法保存状态的。
代码如下:

public class MainActivity extends FragmentActivity implements OnClickListener {

    private Button bt1;
    private Button bt2;
    private FragmentManager manager;
    private FragmentTransaction transaction;
    FragmentOne fragmentOne;
    FragmentTwo fragmentTwo;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        bt1 = (Button) findViewById(R.id.bt1);
        bt2 = (Button) findViewById(R.id.bt2);
        bt1.setOnClickListener(this);
        bt2.setOnClickListener(this);
        manager = getSupportFragmentManager();
        // 默认选中第一个按钮
        bt1.performClick();
    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
        case R.id.bt1:
            if (fragmentOne == null) {
                fragmentOne = new FragmentOne();
            }
            transaction = manager.beginTransaction();
            transaction.replace(R.id.fl_content, fragmentOne);
            break;
        case R.id.bt2:
            if (fragmentTwo == null) {
                fragmentTwo = new FragmentTwo();
            }
            transaction = manager.beginTransaction();
            transaction.replace(R.id.fl_content, fragmentTwo);
            break;
        }
        transaction.commit();
    }
}

接下来看看add方法:
使用add的时候要和hide和show方法结合起来使用,使用hide隐藏原来的fragment,使用show显示你想要的fragment.
通过实验发现当第一个framgment里面的文字改变之后,在切换回来文字的状态依然是显示为我很好。而且通过控制台我们可以看到两个fragment的onCreateView方法只是在第一次点击按钮的时候会调用,下次切换不在调用。
这里写图片描述
说明采用add方法很好的保存的fragment的状态,避免每次去实例化新的对象。
代码如下:

public class MainActivity extends FragmentActivity implements OnClickListener{

    private Button bt1;
    private Button bt2;
    //代表当前的fragment
    private Fragment content;
    FragmentOne fragmentOne;
    FragmentTwo fragmentTwo;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        bt1 = (Button) findViewById(R.id.bt1);
        bt2 = (Button) findViewById(R.id.bt2);
        bt1.setOnClickListener(this);
        bt2.setOnClickListener(this);
        content = new FragmentOne();
        //默认选中第一个Fragment
        bt1.performClick();
    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
        case R.id.bt1:
            if(fragmentOne == null){
                fragmentOne = new FragmentOne();
            }
            switchContent(content, fragmentOne);
            break;
        case R.id.bt2:
            if(fragmentTwo == null){
                fragmentTwo = new FragmentTwo();
            }
            switchContent(content, fragmentTwo);
            break;
        }
    }
    /**
     * 切换fragment
     * @param from 要隐藏的fragment
     * @param to 要显示的fragment
     */
    public void switchContent(Fragment from, Fragment to){
        if(content!=to){
            content =to;
            FragmentTransaction transaction= getSupportFragmentManager().beginTransaction();
            //此处必须要进行判断,因为同一个fragment只能被add一次,否则会发生异常
            if(!to.isAdded()){
                //未添加
                transaction.hide(from).add(R.id.fl_content, to).commit();
            }else{
                //添加过直接显示
                transaction.hide(from).show(to).commit();
            }
        }
    }
}

但是,在使用add的时候,作为容器的FrameLayout其实有2层,使用replace的话只有一层,多层肯定比一层来的浪费。具体使用什么方法还是看具体的需求吧!

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值