【布局優(yōu)化】喂传藏!住在xml里的fragment,我要"replace"掉你彤守!

前言

大家應(yīng)該都知道毯侦,F(xiàn)ragment的加載方式有倆種:靜態(tài)加載動(dòng)態(tài)加載
對(duì)于這倆種具垫,不用縮侈离!我猜大家肯定更喜歡用后者吧,畢竟咱都是愛用動(dòng)的boy嘛 嘖嘖嘖~好像跑偏了

哈哈筝蚕,顏歸正傳卦碾!上!代起宽!碼洲胖!

<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/rootview"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:tools="http://schemas.android.com/tools">
   <!--其余代碼省略-->
    <FrameLayout
        android:id="@+id/container"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:layout_behavior="@string/appbar_scrolling_view_behavior"/>

</android.support.design.widget.CoordinatorLayout>

眼熟不?然后配合下面這段代碼


getSupportFragmentManager().beginTransaction().replace(R.id.container,new ProcessDetailFragment()).commit();

就可以實(shí)現(xiàn)fragment的動(dòng)態(tài)加載了坯沪,是不是很開心绿映?

然鵝,當(dāng)我打開Android Studio 的Layout Inspector[1]的時(shí)候,我并不怎么開森

當(dāng)前fragment加載后的布局結(jié)構(gòu)

為毛fragment布局不是直接替換掉container布局而是在它里面2嫦摇Xひ弧!

其實(shí)一般情況也沒啥淹冰,只是如果是這里库车,那!就樱拴!堅(jiān)柠衍!決!不疹鳄!能拧略!忍芦岂!眼神好的童鞋可能發(fā)現(xiàn)了瘪弓,這個(gè)fragment里面是個(gè)典型的ViewPager+Tablayout組合,而ViewPager里面又會(huì)有一堆fragment ,所以布局結(jié)構(gòu)那叫一個(gè)復(fù)雜禽最,這種布局哪怕多一層嵌套都是會(huì)相當(dāng)影響UI加載速度滴啊腺怯,所以,必須干掉它川无!

But How呛占?

聰明的你肯定想到了 哈哈 沒錯(cuò)!靜態(tài)加載fragment懦趋!于是晾虑,代碼我改改改

<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/rootview"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:tools="http://schemas.android.com/tools">
   <!--其余代碼省略-->
   <fragment
        android:id="@+id/fragView"
        android:name="com.xxx.ProcessDetailFragment"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:layout_behavior="@string/appbar_scrolling_view_behavior"/>

</android.support.design.widget.CoordinatorLayout>

運(yùn)行代碼,打開視圖檢查

修改后的布局結(jié)構(gòu)

怎么感覺好像故事快要講完了? 哈哈 仅叫,撇了一眼標(biāo)題帜篇,好像又跑題了 !

當(dāng)然木有跑題诫咱! 啰嗦了這么多笙隙,其實(shí)是在為后文作鋪墊哦

其實(shí)這是在復(fù)現(xiàn)當(dāng)時(shí)項(xiàng)目開發(fā)中一步步遇到問題解決問題的過程,沒有上述問題的粗現(xiàn)坎缭,接下來要講的東東也就不會(huì)發(fā)生了哦 所以算是個(gè)前情概要吧 就像看電影一樣 嘿嘿 大家多擔(dān)待

不呼不喚竟痰,我始出來!

現(xiàn)在視圖層級(jí)已經(jīng)達(dá)到我們的預(yù)期了掏呼,可是坏快!問題又粗線了,這個(gè)項(xiàng)目的viewPager里面是一個(gè)個(gè)fragment憎夷,其代表的是TabLayout中一個(gè)個(gè)菜單的詳情頁面假消,每個(gè)詳情頁面中數(shù)據(jù)會(huì)有操作,然后當(dāng)其中某個(gè)fragment中數(shù)據(jù)變化之后會(huì)影響其它fragment的數(shù)據(jù)和菜單的展示岭接,因此富拗,在每一次數(shù)據(jù)變化的時(shí)候臼予,我們需要刷新整個(gè)ProcessDetailFragment!

HOW 2 ?

最簡單的辦法啃沪,就是用新創(chuàng)建的ProcessDetailFragment替換掉目前的ProcessDetailFragment粘拾,然后新的ProcessDetailFragment會(huì)重新加載更新后的數(shù)據(jù)并展示,So Easy?

于是创千,按照這個(gè)想法缰雇,順便回想一下動(dòng)態(tài)加載fragment的代碼,fragment動(dòng)態(tài)加載的時(shí)候追驴,是需要指定容器布局id的械哟,代碼執(zhí)行后新fragment的布局會(huì)加入到這個(gè)容器布局中,所以如果我們要用新的ProcessDetailFragment替換掉原有的ProcessDetailFragment其實(shí)是不可行的殿雪!

什么暇咆,你不信,那我們用代碼來說話丙曙!

按照動(dòng)態(tài)加載fragment的方式爸业,用新的ProcessDetailFragment替換掉原來布局中的ProcessDetailFragment,注意下面代碼容器id為R.id.fragView亏镰,也就是fragment在xml中聲明的id

  public void refresh() {
          getSupportFragmentManager().beginTransaction()
         .replace(R.id.fragView, new ProcessDetailFragment())
         .commit();
}

然后看看新的視圖結(jié)果:


直接替換后的布局結(jié)構(gòu)

也許有些童鞋會(huì)說扯旷,先remove掉原來的ProcessDetailFragment在用新的fragment執(zhí)行replace就好啊,但其實(shí)如果用過靜態(tài)加載fragment的童鞋肯定知道索抓,F(xiàn)ragmentTransaction的remove針對(duì)靜態(tài)加載的fragment是無效的钧忽,而且本人也在此親測,在執(zhí)行remove后布局結(jié)構(gòu)依然和上圖一致

我有個(gè)大膽的想法

既然replace會(huì)將fragment加入到指定容器id布局之下逼肯,那么我們將這個(gè)容器id設(shè)置為原ProcessDetailFragment的父容器CoordinatorLayout的id,藍(lán)后在父容器中remove掉舊的ProcessDetailFragment布局視圖不就好了耸黑?

OL, 開干汉矿!

新的代碼:

//processDetailFragment 為目前布局中加載的fragment的引用
    public void refresh() {
        if (processDetailFragment != null) {
            //新的ProcessDetailFragment
            ProcessDetailFragment fragment = new ProcessDetailFragment();
            //和老fragment中的布局參數(shù)保持一致 該方法需要自定義實(shí)現(xiàn)
            //該方法可保證新的fragment布局和原fragment大小,行為一致
            fragment.setLayoutParams((CoordinatorLayout.LayoutParams)         
            processDetailFragment.getView().getLayoutParams());
            //將原fragment布局視圖從其父容器中刪除
            ((CoordinatorLayout) findViewById(R.id.rootview))
            .removeView(processDetailFragment.getView());
            //加載新的fragment
            getSupportFragmentManager().beginTransaction()
            .replace(R.id.rootview, fragment).commit();
            //用新fragment替換原fragment的引用
            processDetailFragment = fragment;
        }
    }

代碼運(yùn)行崎坊,新的視圖布局結(jié)構(gòu):

替換后的布局結(jié)構(gòu)圖

后記

嚴(yán)格來講,這算個(gè)偽替代洲拇,但奈揍,條條大路通羅馬!我們最終還是實(shí)現(xiàn)了我們所想所需的效果赋续,不是嗎男翰? 也因此文章標(biāo)題中的替換帶了倆引號(hào) "replace"

本文可轉(zhuǎn)載,轉(zhuǎn)載請(qǐng)注明出處

如果這篇文章對(duì)親有所幫助纽乱,希望親可以可以給我一個(gè)小心心??蛾绎!這是對(duì)我最大的鼓勵(lì)!多謝^^


  1. Windows -> Tools -> Android ->Layout Inspector 即可打開布局檢查,可以查看視圖的布局結(jié)構(gòu) ?

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末租冠,一起剝皮案震驚了整個(gè)濱河市鹏倘,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌顽爹,老刑警劉巖纤泵,帶你破解...
    沈念sama閱讀 216,744評(píng)論 6 502
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異镜粤,居然都是意外死亡捏题,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,505評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門肉渴,熙熙樓的掌柜王于貴愁眉苦臉地迎上來公荧,“玉大人,你說我怎么就攤上這事同规⊙” “怎么了?”我有些...
    開封第一講書人閱讀 163,105評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵捻浦,是天一觀的道長晤揣。 經(jīng)常有香客問我桥爽,道長朱灿,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,242評(píng)論 1 292
  • 正文 為了忘掉前任钠四,我火速辦了婚禮盗扒,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘缀去。我一直安慰自己侣灶,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,269評(píng)論 6 389
  • 文/花漫 我一把揭開白布缕碎。 她就那樣靜靜地躺著褥影,像睡著了一般。 火紅的嫁衣襯著肌膚如雪咏雌。 梳的紋絲不亂的頭發(fā)上凡怎,一...
    開封第一講書人閱讀 51,215評(píng)論 1 299
  • 那天,我揣著相機(jī)與錄音赊抖,去河邊找鬼统倒。 笑死,一個(gè)胖子當(dāng)著我的面吹牛氛雪,可吹牛的內(nèi)容都是我干的房匆。 我是一名探鬼主播,決...
    沈念sama閱讀 40,096評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼浴鸿!你這毒婦竟也來了井氢?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 38,939評(píng)論 0 274
  • 序言:老撾萬榮一對(duì)情侶失蹤岳链,失蹤者是張志新(化名)和其女友劉穎毙沾,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體宠页,經(jīng)...
    沈念sama閱讀 45,354評(píng)論 1 311
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡左胞,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,573評(píng)論 2 333
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了举户。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片烤宙。...
    茶點(diǎn)故事閱讀 39,745評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖俭嘁,靈堂內(nèi)的尸體忽然破棺而出躺枕,到底是詐尸還是另有隱情,我是刑警寧澤供填,帶...
    沈念sama閱讀 35,448評(píng)論 5 344
  • 正文 年R本政府宣布拐云,位于F島的核電站,受9級(jí)特大地震影響近她,放射性物質(zhì)發(fā)生泄漏叉瘩。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,048評(píng)論 3 327
  • 文/蒙蒙 一粘捎、第九天 我趴在偏房一處隱蔽的房頂上張望薇缅。 院中可真熱鬧,春花似錦攒磨、人聲如沸泳桦。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,683評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽灸撰。三九已至,卻和暖如春拼坎,著一層夾襖步出監(jiān)牢的瞬間浮毯,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,838評(píng)論 1 269
  • 我被黑心中介騙來泰國打工演痒, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留亲轨,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 47,776評(píng)論 2 369
  • 正文 我出身青樓鸟顺,卻偏偏與公主長得像惦蚊,于是被迫代替她去往敵國和親器虾。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,652評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容

  • Android 自定義View的各種姿勢1 Activity的顯示之ViewRootImpl詳解 Activity...
    passiontim閱讀 172,085評(píng)論 25 707
  • 在各種Android項(xiàng)目中,我們不可避免要使用到Fragment莉掂,但很多地方其實(shí)我們只是習(xí)慣性或copy代碼來使用...
    HolenZhou閱讀 2,085評(píng)論 1 15
  • 青春總是伴隨著各種各樣的問題葛圃,最近有很多同學(xué)問我問題,今天我就答一答嘍憎妙! 語文是國語固然重要库正,可為什么好多重點(diǎn)高中...
    藍(lán)竹閱讀 351評(píng)論 0 0
  • 1、下載sdk厘唾,導(dǎo)入sdk(libWeChatSDK.a褥符,WXApi.h,WXApiObject.h 三個(gè)文件添加...
    火星的蟈蟈閱讀 1,008評(píng)論 0 2
  • 哈哈哈哈哈太搞笑了好喜歡鄧超歐弟祖藍(lán)哈哈哈哈哈
    AAAAmmmyyy閱讀 283評(píng)論 0 1