Android-Fragmentを切り替えて回収しない

4345 ワード

現在、市販されているアプリケーションは基本的に単一Activity+マルチFragmentで実現されていますが、このようなアプリは互いに切り替えたときに回収されず、元のFragmentに切り替えたときも元の状態であることが実現されています.
ここではFragmentのadd(),show(),hide()を用いて実現し,すなわち表示と隠蔽を行い,従来のFragmentは破棄されない.
一言も言わないで、コードを貼って、コードは最高の先生です.注釈はまだ詳しい.
public class MainActivity extends AppCompatActivity implements View.OnClickListener {

    private ImageView ibOne;
    private ImageView ibTwo;
    private ImageView ibThree;
    
    private FragmentManager mFm;
    private ArrayList mFragmentList = new ArrayList();
    private String[] mFragmentTagList = {"OneFragment", "TwoFragment", "ThreeFragment"};
    private Fragment mCurrentFragmen = null;  //  Fragment

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        initView();
        initData();
        
    }

    private void initData() {
        OneFragment oneFragment = new OneFragment();
        TwoFragment twoFragment = new TwoFragment();
        ThreeFragment threeFragment = new ThreeFragment();
        mFragmentList.add(0, oneFragment);
        mFragmentList.add(1, twoFragment);
        mFragmentList.add(2, threeFragment);

        mCurrentFragmen = mFragmentList.get(0);

        //  Fragment
        mFm = getFragmentManager();
        FragmentTransaction transaction = mFm.beginTransaction();
        transaction.add(R.id.fl_show, mCurrentFragmen, mFragmentTagList[0]);
        transaction.commitAllowingStateLoss();
    }

    // findViewById
    private void initView() {
        ibOne = (ImageView)findViewById(R.id.ib_one);
        ibTwo = (ImageView)findViewById(R.id.ib_two);
        ibThree = (ImageView)findViewById(R.id.ib_three);

        ibOne.setOnClickListener(this);
        ibTwo.setOnClickListener(this);
        ibThree.setOnClickListener(this);
    }

    @Override
    public void onClick(View view) {
        switch (view.getId()){
            case R.id.ib_one:
                switchFragment(mFragmentList.get(0), mFragmentTagList[0]);
                break;
            case R.id.ib_two:
                switchFragment(mFragmentList.get(1), mFragmentTagList[1]);
                break;
            case R.id.ib_three:
                switchFragment(mFragmentList.get(2), mFragmentTagList[2]);
                break;
        }
    }

    //  Fragment
    void switchFragment(Fragment to, String tag){
        if(mCurrentFragmen != to){
            FragmentTransaction transaction = mFm.beginTransaction();
            if(!to.isAdded()){
                //  :
                //  , , 
                transaction.hide(mCurrentFragmen).add(R.id.fl_show, to, tag).show(to);
            }else{
                //  , 
                transaction.hide(mCurrentFragmen).show(to);
            }
            mCurrentFragmen = to;
            transaction.commitAllowingStateLoss();

        }
    }

    //  activity 
    @Override
    public void onSaveInstanceState(Bundle outState, PersistableBundle outPersistentState) {
        super.onSaveInstanceState(outState, outPersistentState);
        //  Fragment, Fragment 
        updateFragment(outState);
    }

    //  Fragment
    private void updateFragment(Bundle outState) {

        mFm = getFragmentManager();
        if(outState == null){
            FragmentTransaction transaction = mFm.beginTransaction();
            OneFragment oneFragment = new OneFragment();
            mCurrentFragmen = oneFragment;
            transaction.add(R.id.fl_show, oneFragment, mFragmentTagList[0]).commitAllowingStateLoss();
        }else{
            //  tag fragment 
            OneFragment oneFragment = (OneFragment) mFm.findFragmentByTag(mFragmentTagList[0]);
            TwoFragment twoFragment = (TwoFragment) mFm.findFragmentByTag(mFragmentTagList[1]);
            ThreeFragment threeFragment = (ThreeFragment) mFm.findFragmentByTag(mFragmentTagList[2]);
            mFm.beginTransaction().show(oneFragment).hide(twoFragment).hide(threeFragment);
        }
    }
}

私は以前このような需要に対して1つのActivityの中でRelativeLayoutを使って、その中に複数のレイアウト(Fragmentのような)を加えて、下のTabをクリックする時にレイアウトのvisibilityを設定して、思想は同じで、しかしこのように実現するのはとても醜くて、だから使用することを提案しません.
もっと良い実装案があれば教えてくださいね~