Fragment & Headers 使用


Fragment

1,簡介

Fragment名為碎片和Activity相似。

Fragment用來描述一些行為或一部分用戶界面在一個Activity中,你可以合並多個fragment在一個單獨的activity中建立多個UI面板,同時重用fragment在多個activity.可以認為fragment作為一個activity中的一節模塊 fragment有自己的生命周期,接收自己的輸入事件,你可以添加或移除從運行中的activity.

Fragment作為Android 3.0的新特性,有些功能還是比較強大的,比如 合並兩個Activity



 可以看到兩個Activity通過兩個Fragment合並到一個Activity的布局方式,對於平板等大屏幕設備來說有着不錯的展示面板。

       如下例子,在一個activity的布局文件中嵌入兩個fragment

<?xml version="1.0" encoding="utf-8"?>

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"

    android:orientation="vertical"

    android:layout_width="fill_parent"

    android:layout_height="fill_parent"  >

    <TextView 

             android:layout_width="fill_parent"

             android:layout_height="wrap_content"

             android:text="@string/hello" />

   

    <fragment android:name="com.aaa.MainActivity$MyFragment"

            android:id="@+id/fg1"

            android:layout_width="match_parent"

            android:layout_height="wrap_content" />

   

    <fragment android:name="com.aaa.MainActivity$MyFragment2"

            android:id="@+id/fg2"

            android:layout_width="match_parent"

            android:layout_height="wrap_content" />

   

</LinearLayout>

       這樣就把兩個fragment嵌入到了使用該布局文件的activity中。 使用很簡單,和普通的Veiw沒有區別。這樣也就有一個好處是,布局文件可以重復使用(類似include)。需要說明的是嵌入的Fragment存在於ActivityViewGroup中。

Settings使用PreferenceActivity

Settings模塊主界面就是繼承自PreferenceActivity,采用headersfragment來顯示。

public class Settings extends PreferenceActivity … {

….

@Override

    public void onBuildHeaders(List<Header> target) {

        loadHeadersFromResource(R.xml.settings_headers, target);

        ….

}

    ….

}

 

顯示界面使用PreferenceFragment

顯示界面都是直接或簡介繼承自Fragment。比如:網絡設置WirelessSettings繼承自PreferenceFragmentPreferenceFragmentFragment子類,我們可以根據不同需求來選擇使用哪個Fragment,就像選擇ActivityListActivity一樣。

Fragment:你可以在onCreate方法中使用res/layout/xxx.xml文件,就像activity一樣。

PreferenceFragment:如果你顯示的為列表,那么你就可以使用PreferenceFragment來實現,它里封裝了ListView用作列表顯示。其使用的布局文件為res/xml/xxx.xml

 由上可知道Settings界面布局和架構。

例子:

使用fragmentview進行布局。

效果圖:

采用相對布局,左邊是一個Fragment,右邊是兩個上下顯示的fragment

 JAVA代碼如下:定義了三個 fragment,分別使用各自的布局文件。

public static class MyFragment extends Fragment {

         @Override

         public View onCreateView(LayoutInflater inflater, ViewGroup container,  Bundle savedInstanceState) {

                   return inflater.inflate(R.layout.myfragment, container, false);

}

    }

public static class MyFragment2 extends Fragment {

                   @Override

                   public View onCreateView(LayoutInflater inflater, ViewGroup container,

                           Bundle savedInstanceState) {

                            return inflater.inflate(R.layout.myfragment2, container, false);

                   }

         }

        

         public static class MyFragment3 extends PreferenceFragment {

        @Override

        public void onCreate(Bundle savedInstanceState) {

            super.onCreate(savedInstanceState);

            // Load the preferences from an XML resource

            addPreferencesFromResource(R.xml.my_fragmented2);

        }

}

 

2,生命周期

一個fragment必須總是嵌入在一個activity中,同時fragment的生命周期受activity而影響。

其生命周期如下圖所示:


 

可看見Framment生命周期比較復雜,如果你熟悉activity的生命周期,那么Fragment的生命周期也是類似的。Activityfragment回調順序如下:

activity.onCreate

  fragment.onAttach

  fragment.onCreate

activity.onStart

  fragment.onActivityCreated

  fragment.onStart

activity.onResume

  fragment.onResume

  fragment.onStop

activity.onStop

  fragment.onDestroyView

  fragment.onDestroy

  fragment.onDetach

activity.onDestroy

       可知道當activity 暫停,那么所有在這個activityfragments將被destroy釋放。 你可以在activity的不同生命周期中,對fragment執行不同操作。

 3Fragment簡單示例

自定義一個fragment,需要繼承(或間接繼承)Fragment類。

public class MyFragment extends Fragment {

        

         @Override

         public View onCreateView(LayoutInflater inflater, ViewGroup container,

                 Bundle savedInstanceState) {

                  

                   return inflater.inflate(R.layout.myfragment, container, false);

         }

 

}

onCreateView()

當系統調用fragment在首次繪制用戶界面時,如果畫一個UI在你的fragment你必須返回一個View當然了你可以返回null代表這個fragment沒有UI.

 myfragment.xml.  和普通的layout定義完全一樣。

<?xml version="1.0" encoding="utf-8"?>

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"

    android:orientation="vertical"

    android:layout_width="fill_parent"

    android:layout_height="fill_parent"

    >

         <Button 

            android:id="@+id/btn"

             android:layout_width="fill_parent"

             android:layout_height="wrap_content"

             android:text="@string/hello"

             />

</LinearLayout>

 FragmentManager

可以使用FragmentManager來管理Fragment。在Activity中通getFragmentManagerFragmentManager 一些主要的方法有通findFragmentById()取一個Activity中有Fragment布局。當然findFragmentByTag()方法,以及Fragment中出popBackStack()可以注冊 addOnBackStackChangedListener()管理具體的可以在android.app.FragmentManager中了解

      可以使用FragmentManager進行事物處理。

//通過begintransaction方法獲取一個事物處理實例。

FragmentTransaction transaction = fragmentManager.beginTransaction();

在這期間可以使用 add(), remove()replace()。最終需要改變時執行 commit()即可。

如下例子:替換activity的布局為,MyFragment

public void onCreate(Bundle savedInstanceState) {

         super.onCreate(savedInstanceState);

         Log.i(TAG, "onCreate");

        

         FragmentManager fragmentManager = this.getFragmentManager();

         FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();

         fragmentTransaction.replace(android.R.id.content, new MyFragment());

         fragmentTransaction.commit();

}

 

我們可以使用FragmentManager來獲取嵌入到activityfragment

<fragment android:name="com.aaa.MainActivity$MyFragment"

            android:id="@+id/myFg"

            android:tag="myFragment"

            android:layout_width="match_parent"

            android:layout_height="wrap_content" />

getFragmentManager().findFragmentById(R.id.myFg);

getFragmentManager().findFragmentByTag(“myFragment”);

Headers及其使用

Headers在平板上和Fragment合使用的比多。如Settings

使用就承自PreferenceActivity,然后重寫onBuildHeaders方法,調用loadHeadersFromResource方法加載headers.xml

 my_headers.xml

<?xml version="1.0" encoding="utf-8"?>

<preference-headers xmlns:android="http://schemas.android.com/apk/res/android">

 

    <header android:fragment="com.aaa.MyHeadersPreferenceActivity$MyFragmentTest1"

            android:icon="@drawable/ic_1"

            android:title="Prefs Test 1"

            android:summary="An example of some preferences." />

           

    <header android:fragment="com.aaa.MyHeadersPreferenceActivity$MyFragmentTest2"

            android:icon="@drawable/ic_2"

            android:title="Prefs Test 2"

            android:summary="Some other preferences you can see.">

        <!-- Arbitrary key/value pairs can be included with a header as

             arguments to its fragment. -->

        <extra android:name="someKey" android:value="someHeaderValue" />

    </header>

 

    <header android:icon="@drawable/ic_3"

            android:title="Test Intent"

            android:summary="Launches an Intent.">

        <intent android:action="android.intent.action.VIEW"

                android:data="http://www.baidu.com/" />

    </header>

   

</preference-headers>

可看見1,在header中能夠直接配置一個Fragment2,能夠使用extra標簽來,傳遞參數;3,可直接配置一個Intent  具體其它參數也不用多說了。

 MyHeadersPreferenceActivity

public class MyHeadersPreferenceActivity extends PreferenceActivity {

        

         @Override

         public void onBuildHeaders(List<Header> target) {

                   Log.i(TAG, "onBuildHeaders");

                   loadHeadersFromResource(R.xml.my_headers, target);

         }

        

         public static class MyFragmentTest1 extends PreferenceFragment {

            @Override

                  public void onCreate(Bundle savedInstanceState) {

                       super.onCreate(savedInstanceState);

           

                       // Load the preferences from an XML resource

                       addPreferencesFromResource(R.xml.my_fragmented1);

                  }

               }

        

         public static class MyFragmentTest2 extends PreferenceFragment {

                   @Override

                  public void onCreate(Bundle savedInstanceState) {

                       super.onCreate(savedInstanceState);

 

                       // Can retrieve arguments from headers XML.

                       Log.i(this.getClass().getSimpleName(), "Arguments: " + getArguments());

           

                       // Load the preferences from an XML resource

                       addPreferencesFromResource(R.xml.my_fragmented2);

                  }

              }

}

類比較簡單,繼承自Preferencectivity,重寫onBuildHeaders方法,在此方法中加載headers。還有2Fragment類前邊已經說過了,此處不表。

 

my_fragment1ed1.xml

<?xml version="1.0" encoding="utf-8"?>

<PreferenceScreen

        xmlns:android="http://schemas.android.com/apk/res/android">

    <CheckBoxPreference

            android:key="checkbox_preference_"

            android:title="Checkbox Test title"

            android:summary="Checkbox Test summary." />

</PreferenceScreen>

很簡單,挺眼熟吧。

 從例子中,可以看出,Headers使用也比較簡單。用它結合FragmentPreference來進行界面布局和用戶交互操作很方便。

具體例子API Demo中有。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM