這裡,我們將自上而下設計用戶界面,從在平板設備上顯示的用戶界面核心組件Activity類,到在Activity類的實例內創建的Fragment對象。
在使用可視化工具編輯佈局文件把線框轉換成指定用戶界面的XML代碼之前,需要先邁出關鍵的一步:因為Fragment類總是包含子類,在通過Fragment佈局之前需要先創建這些類。
對於前文所提到的線框,我們需要創建三個Fragment子類:
·ContentFragment
·DetailFragment
·QueryResultsListFragment
在Fragment子類中的很多生命週期回調是為了便於日誌記錄,提供簡單的Fragment對像生命週期可視化,並且支持使用代碼骨架方法構建基於應用的代碼。以下是QueryResultsListFragment類的源代碼。
在這段代碼中:
2 包含日誌代碼的生命週期方法。
1 onCreateView的實現,它對佈局進行擴展並調用attachAdapter方法。
3 私有方法attachAdapter,支持該片段的列表顯示一些測試數據。
4 OnItemClickListener接口的實現,它響應用戶交互,在這個例子中,即執行一些簡單的代碼,把一些測試數據發送給屏幕右側欄的Fragment對象,或者如果屏幕太小無法顯示兩個片段,就執行後續的活動。注意這裡沒有給出該判斷的代碼。
package com.finchframework.uiframework; import android.app.Activity; import android.app.Fragment; import android.content.res.Configuration; import android.os.Bundle; import android.util.Log; import android.view.LayoutInflater; import android.view.Menu; import android.view.MenuInflater; import android.view.View; import android.view.ViewGroup; import android.widget.AdapterView; import android.widget.AdapterView.OnItemClickListener; import android.widget.ArrayAdapter; import android.widget.ListView; public class QueryResultsListFragment extends Fragment implements OnItemClickListener{ // String for logging the class name private final String TAG = getClass.getSimpleName; // Turn logging on or off private final boolean L = true; public void onAttach(Activity activity) { super.onAttach(activity); // Notification that the fragment is associated with an Activity if (L) Log.i(TAG, \"onAttach \" + activity.getClass.getSimpleName); } public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Tell the system we have an options menu this.setHasOptionsMenu(true); if (null != savedInstanceState) restoreState(savedInstanceState); // Notification that if (L) Log.i(TAG, \"onCreate\"); } // Factor this out of methods that get saved state private void restoreState(Bundle savedInstanceState) { // TODO Auto-generated method stub } @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { 1 final ListView list = (ListView) inflater.inflate( R.layout.list_frag_list, container, false); if (L) Log.i(TAG, \"onCreateView\"); attachAdapter(list); list.setOnItemClickListener(this); return list; } public void onStart { 2 super.onStart; if (L) Log.i(TAG, \"onStart\"); } public void onresume { super.onResume; if (L) Log.i(TAG, \"onResume\"); } public void onPause { super.onPause; if (L) Log.i(TAG, \"onPause\"); } public void onStop { super.onStop; if (L) Log.i(TAG, \"onStop\"); } public void onDestroyView { super.onDestroyView; if (L) Log.i(TAG, \"onDestroyView\"); } public void onDestroy { super.onDestroy; if (L) Log.i(TAG, \"onDestroy\"); } public void onDetach { super.onDetach; if (L) Log.i(TAG, \"onDetach\"); } // //////////////////////////////////////////////////////////////////// // Minor lifecycle methods // //////////////////////////////////////////////////////////////////// public void onActivityCreated { // Notification that the containing activiy and its View hierarchy exist if (L) Log.i(TAG, \"onActivityCreated\"); } // ////////////////////////////////////////////////////////////////////////// // Overrides of the implementations ComponentCallbacks methods in Fragment // ////////////////////////////////////////////////////////////////////////// @Override public void onConfigurationChanged(Configuration newConfiguration) { super.onConfigurationChanged(newConfiguration); // This won\'t happen unless we declare changes we handle in the manifest if (L) Log.i(TAG, \"onConfigurationChanged\"); } @Override public void onLowMemory { // No guarantee this is called before or after other callbacks if (L) Log.i(TAG, \"onLowMemory\"); } ///////////////////////////////////////////////////////////////////////////// // Menu handling code ///////////////////////////////////////////////////////////////////////////// public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) { inflater.inflate(R.menu.search_menu, menu); } // ////////////////////////////////////////////////////////////////////////// // App-specific code // ////////////////////////////////////////////////////////////////////////// /** * Attach an adapter that loads the data to the specified list * @param list */ private void attachAdapter(final ListView list) { 3 // Make a trivial adapter that loads an array of strings ArrayAdapter<String> numbers = new ArrayAdapter<String>( list.getContext.getApplicationContext, android.R.layout.simple_list_item_1, new String { \"one\", \"two\", \"three\", \"four\", \"five\", \"six\" }); // tell the list to use it list.setAdapter(numbers); // l.setOnItemClickListener(this); } // ////////////////////////////////////////////////////////////////////////// // Implementation of the OnItemClickListener interface // ////////////////////////////////////////////////////////////////////////// @Override public void onItemClick(AdapterView<?> arg0, View view, int position, long id) { 4 // As an example of sending data to our fragments, we will create a bundle // with an int and a string, based on which view was clicked Bundle b = new Bundle; int ordinal = position + 1; b.putInt(\"place\", ordinal); b.putString(\"placeName\", Integer.toString(ordinal)); TabManager.loadTabFragments(getActivity, b); } }
Fragment子類需要做的就是通過onCreateView方法返回一個View對象。因此,我們也會為每個Fragment類定義一個簡單的佈局,可以加載並返回結果View層次。