瞿 蘇
(江蘇旅游職業(yè)學(xué)院, 江蘇 揚(yáng)州 225000)
程序在手機(jī)和平板都能運(yùn)行,是開發(fā)人員必需實現(xiàn)的技術(shù)。同時,界面也能正常地展示,Android 3.0版本以上,引入了碎片(Fragment)的概念,碎片是能夠讓程序更加合理和充分地利用大屏幕的空間。
碎片通常都是在平板開發(fā)中使用的,首先要做的就是創(chuàng)建一個平板模擬器,創(chuàng)建完成后啟動平板模擬器。
在一個活動當(dāng)中添加兩個碎片,并讓這兩個碎片平分活動空間。這個布局非常簡單,只放置了一個按鈕,并讓它水平居中顯示。左右兩側(cè)碎片布局分別為 left-fragment.xml和 right-fragment.xml??梢允褂?fragment>標(biāo)簽在布局中添加碎片,碎片的類名通過android:name屬性加上,并加上包名。兩個碎片平分了整個活動的布局,在真正的項目中很難有什么實際的作用。
設(shè)計程序時,分別新建another_left-fragment.xml和another_right-fragment.xml。通過碎片動態(tài)地添加活動中,可以將程序界面更加多樣。在MainActivity中,向FrameLayout添加內(nèi)容,以此實現(xiàn)動態(tài)添加碎片的功能。代碼如圖1所示:
圖1 動態(tài)添加碎片代碼
結(jié)合replaceFragment()方法中的代碼可以看出,動態(tài)添加碎片主要分為5步,分別是:創(chuàng)建碎片實例;獲取 FragmentManager,調(diào)用 getSupportFragment Manager()方法;開啟一個事務(wù),調(diào)用 beginTransaction()方法;replace()方法,向容器內(nèi)添加或替換碎片;提交事務(wù),調(diào)用 commit()方法。
FragmentTransaction 中調(diào)用 addToBackStack()方法,可以將事務(wù)添加到返回棧中。相關(guān)代碼如圖2所示:
圖2 添加事務(wù)到返回棧
碎片和活動之間的通信,F(xiàn)ragmentManager提供了findFragmentById()的方法,可以從布局文件中獲取碎片,代碼為:RightFragment rightFragment=(RightFragment) getSupportfragmentManager ().findFragmentById(R.id.right_fragment);
獲取碎片后,然后在每個碎片中可以調(diào)用getActivity()方法來得到和當(dāng)前碎片相關(guān)聯(lián)的活動實例,代碼為:MainActivity activity= (MainActivity)getActivity ();也可以通過 getActivity ()方法獲取Context對象。同樣,碎片與碎片之間的通信,可以在碎片中獲取與碎片相關(guān)聯(lián)的活動,再通過活動獲取另外一個碎片的實例。
碎片和活動一樣,也有自己的生命周期,碎片的生命周期,如表1所示。
表1 碎片的生命周期
在使用碎片時,會遇到當(dāng)系統(tǒng)內(nèi)存不足時,進(jìn)入停止?fàn)顟B(tài)的碎片,有可能被回收。所以可以通過調(diào)用onSaveInstanceState()方法保存數(shù)據(jù),保存的數(shù)據(jù)可以通過3個方法獲取,3個方法分別是onCreate().onCreateView()和 onActivityCreated()。
在程序設(shè)計時,在布局文件中通過可以添加碎片和替換碎片,解決了一些問題。但在程序運(yùn)行時,是否可以通過判斷設(shè)備的分辨率或設(shè)備屏幕的寬度來決定加載哪個布局呢?答案是肯定的!Android中,程序運(yùn)行時動態(tài)加載布局有幾個技巧。
平板電腦的屏幕寬度足夠大,程序運(yùn)行時,頁面顯示都是采用雙頁模式,包含子項列表顯示在左側(cè)面板上,列表所選中子項的內(nèi)容則顯示在右側(cè)列表中。但是當(dāng)使用手機(jī)時,程序運(yùn)行,有兩個頁面時,程序運(yùn)行時,怎么判斷是單頁模式還是雙頁模式呢。此時就需要使用限定符(Qualifiers)來完成了。
圖3代碼是使用限定符的例子,是activity main.xml布局文件代碼,該布局文件只有左側(cè)碎片文件并且該左側(cè)碎片文件充滿整個父布局文件,即單頁模式。
圖3 activity-main.xml布局文件代碼
圖4代碼是activiy_main.xml布局文件修改后的代碼,activiy_main.xml是 res目錄下新建的layout-large文件夾中的布局文件。該布局文件中,包含2個碎片文件,分別是left_fragment和right_fragment,即雙頁模式。
圖4 修改后的activity-main.xml文件代碼
圖4布局文件是基于圖3布局文件的改進(jìn),其中l(wèi)arge就是一個限定符,大屏幕設(shè)備會自動加載layout-large文件夾中的布局(圖4布局文件),而小屏幕設(shè)備則加載layout文件中的布局(圖3布局文件)。接著可以將 MainActivity 中 replaceFragment()方法里的代碼注釋掉,并在平板模擬器上重新運(yùn)行程序。再啟動一個手機(jī)模擬器,并在這個模擬器上重新運(yùn)行程序,這樣就實現(xiàn)了在程序運(yùn)行時動態(tài)加載布局的功能。
通過以上表述,large限定符可以判斷單頁或雙頁的問題。但是很多學(xué)習(xí)者會提出這樣的問題:其中的large值怎么確定?多大的值呢?有具體的范圍嗎?不同的設(shè)備加載布局時,都可以通過使用最小寬度限定符(Smallest-widthQualifier)來設(shè)定屏幕寬度,最小寬度限定符指地是屏幕寬度的最小值(單位dp),是設(shè)備是否加載布局的臨界點,當(dāng)屏幕寬度大于臨界點時,就加載一個布局;當(dāng)屏幕寬度小于臨界點時,就加載另一個布局。比如最小寬度限定符為600dp時,當(dāng)程序運(yùn)行時,如果設(shè)備屏幕寬度大于600dp時,程序會自動加載新建的布局;如果設(shè)備屏幕寬度小于600dp時,程序仍然加載原來默認(rèn)的布局。
使用碎片的最典型實例是新聞應(yīng)用,新聞英語等等,設(shè)計的目的就是要求同時兼容手機(jī)和平板電腦。
對于新聞應(yīng)用程序,目錄結(jié)構(gòu)如圖5所示。
圖5 新聞應(yīng)用程序目錄結(jié)構(gòu)
首先新建類News,新建作為新聞內(nèi)容的布局文件news_content_fr-ag.xml,并創(chuàng)建繼承自Fragment的NewsContent-Fragment類。
新聞應(yīng)用程序設(shè)計中,layout-sw600dp文件夾下,創(chuàng)建activity.xml布局文件,該布局文件中,引入了兩個碎片,值得一提地是,activity.xml布局文件的id是news_content_layout。程序運(yùn)行時,如果找到id,則是雙頁模式;找不到id,則是單頁模式。接著在NewsTitleFragment中新建RecyclerView內(nèi)部類NewsAdapter的適配器。其中,判斷單雙頁模式的代碼如下圖6所示。
圖6 判斷單雙反模式的代碼
RecyclerView內(nèi)部類可以是直接訪問NewsTitleFragment,比如 isTwoPane,以此判斷單頁模式還是雙頁模式。最后再在RecyclerView中填充數(shù)據(jù),以便雙頁模式時,右側(cè)新聞內(nèi)容里的碎片數(shù)據(jù)。
本文主要介紹了碎片的基本概念以及使用場景,碎片的常見用法、碎片生命周期的相關(guān)內(nèi)容以及動態(tài)加載布局的技巧,以及碎片的實踐應(yīng)用。