1. 程式人生 > >ANDROID FRAMENT的切換(解決REPLACE的低效)

ANDROID FRAMENT的切換(解決REPLACE的低效)

原博主:https://www.cnblogs.com/android-joker/p/4414891.html

在專案中切換Fragment,一直都是用replace()方法來替換Fragment。但是這樣做有一個問題,每次切換的時候Fragment都會重新實列化,重新載入一次資料,這樣做會非常消耗效能用使用者的流量。

官方文件解釋說:replace()這個方法只是在上一個Fragment不再需要時採用的簡便方法。

正確的切換方式是add(),切換時hide(),add()另一個Fragment;再次切換時,只需hide()當前,show()另一個。
這樣就能做到多個Fragment切換不重新例項化:

切換方法:

複製程式碼
/**
     * fragment 切換
     * 
     * @param from
     * @param to
     */
    public void switchContent(Fragment from, Fragment to, int position) {
        if (mContent != to) {
            mContent = to;
            FragmentTransaction transaction = fm.beginTransaction();
            if (!to.isAdded()) { //
先判斷是否被add過 transaction.hide(from) .add(R.id.content_frame, to, tags[position]).commit(); // 隱藏當前的fragment,add下一個到Activity中 } else { transaction.hide(from).show(to).commit(); // 隱藏當前的fragment,顯示下一個 } } }
複製程式碼

這樣做好後看似沒問題。但是比較低端的手機記憶體不足的時候會造成fragment重疊的情況。

實是由Activity被回收後重啟所導致的Fragment重複建立和重疊的問題。

在Activity onCreate()中新增Fragment的時候一定不要忘了檢查一下savedInstanceState

多個Fragment重疊則可以這樣處理:通過FragmentManager找到所有的UI Fragment,按需要show()某一個Fragment,hide()其他即可!

為了能準確找出所需的Fragment,所以在add()或者replace() Fragment的時候記得要帶上tag引數,因為一個ViewGroup 容器可以依附add()多個Fragment,它們的id自然是相同的。

複製程式碼
/**
     * 狀態檢測 用於記憶體不足的時候保證fragment不會重疊
     * 
     * @param savedInstanceState
     */
    private void stateCheck(Bundle savedInstanceState) {
        if (savedInstanceState == null) {
            fm = getFragmentManager();
            FragmentTransaction fts = fm.beginTransaction();
            AnimationFragment af = new AnimationFragment();
            mContent = af;
            fts.add(R.id.content_frame, af);
            fts.commit();
        } else {
            AnimationFragment af = (AnimationFragment) getFragmentManager()
                    .findFragmentByTag(tags[0]);
            PlainFragment pf = (PlainFragment) getFragmentManager()
                    .findFragmentByTag(tags[1]);
            RecordFragment rf = (RecordFragment) getFragmentManager()
                    .findFragmentByTag(tags[2]);
            InformationFragment inf = (InformationFragment) getFragmentManager()
                    .findFragmentByTag(tags[3]);
            TestingFragment tf = (TestingFragment) getFragmentManager()
                    .findFragmentByTag(tags[4]);
            getFragmentManager().beginTransaction().show(af).hide(pf).hide(rf)
                    .hide(inf).hide(tf).commit();
        }
    }