- 论坛徽章:
- 0
|
Android Fragments 详细使用
Fragments 诞生初衷
自从Android 3.0中引入fragments 的概念,根据词海的翻译可以译为:碎片、片段。其上的是为了解决不同屏幕分辩率的动态和灵活UI设计。大屏幕如平板小屏幕如手机,平板电脑的设计使得其有更多的空间来放更多的UI组件,而多出来的空间存放UI使其会产生更多的交互,从而诞生了fragments 。fragments 的设计不需要你来亲自管理view hierarchy 的复杂变化,通过将Activity 的布局分散到frament 中,可以在运行时修改activity 的外观,并且由activity 管理的back stack 中保存些变化。
Fragments 设计理念
在设计应用时特别是Android 应用 ,有众多的分辨率要去适应,而fragments 可以让你在屏幕不同的屏幕上动态管理UI。例如:通讯应用程序(QQ),用户列表可以在左边,消息窗口在右边的设计。而在手机屏幕用户列表填充屏幕当点击某一用户时,则弹出对话窗口的设计,如下图:
Fragments的生命周期
每一个fragments 都有自己的一套生命周期回调方法和处理自己的用户输入事件。 对应生命周期可参考下图:
其中大多数程序必须使用Fragments 必须实现的三个回调方法分别为:
onCreate
系统创建Fragments 时调用,可做执行初始化工作或者当程序被暂停或停止时用来恢复状态,跟Activity 中的onCreate相当。
onCreateView
用于首次绘制用户界面的回调方法,必须返回要创建的Fragments 视图UI。假如你不希望提供Fragments 用户界面则可以返回NULL。
onPause
当用户离开这个Fragments 的时候调用,这时你要提交任何应该持久的变化,因为用户可能不会回来。更多的事件可以参考上图的生命周期关系图。
Fragments 的类别
系统内置了三种Fragments ,这三种Fragments 分别有不同的应用场景分别为:
DialogFragment
对话框式的Fragments,可以将一个fragments 对话框并到activity 管理的fragments back stack 中,允许用户回到一个前曾摒弃fragments.
ListFragments
类似于ListActivity 的效果,并且还提供了ListActivity 类似的onListItemCLick和setListAdapter等功能。
PreferenceFragments
类似于PreferenceActivity .可以创建类似IPAD的设置界面。
Fragments 的详细使用
首先先来看一张DEMO 效果图:
左边点击时,右边的字符会与左边选中的项的字符相同。与IPAD上的设置界面很相似,这一点是否借鉴了ipad 上的UI呢?
相就的XML文件:- 01.<linearlayout xmlns:android="http://schemas.android.com/apk/res/android"
- 02. android:layout_width="match_parent"
- 03. android:layout_height="match_parent"
- 04. android:orientation="horizontal" >
- 05.
- 06. <fragment class="com.xuzhi.fragment.FragmentDemoActivity$TitlesFragment" android:id="@+id/titles" android:layout_weight="1"
- 07. android:layout_width="0px" android:layout_height="match_parent"
- 08. />
- 09.
- 10. <framelayout android:id="@+id/details" android:layout_weight="1" android:layout_width="0px" android:layout_height="match_parent"
- 11. android:background="?android:attr/detailsElementBackground"
- 12. >
- 复制代码
复制代码 主界面代码(己做注释):- 01.package com.xuzhi.fragment;
- 02.import android.app.Activity;
- 03.import android.app.AlertDialog;
- 04.import android.app.Fragment;
- 05.import android.app.FragmentTransaction;
- 06.import android.app.ListFragment;
- 07.import android.os.Bundle;
- 08.import android.util.TypedValue;
- 09.import android.view.LayoutInflater;
- 10.import android.view.View;
- 11.import android.view.ViewGroup;
- 12.import android.widget.ArrayAdapter;
- 13.import android.widget.ListView;
- 14.import android.widget.ScrollView;
- 15.import android.widget.TextView;
- 16.
- 17.public class FragmentDemoActivity extends Activity {
- 18.
- 19. public static String[] array = { "text1,", "text2", "text3", "text4",
- 20. "text5,", "text6", "text7", "text8" };
- 21.
- 22. /** Called when the activity is first created. */
- 23. @Override
- 24. public void onCreate(Bundle savedInstanceState) {
- 25. super.onCreate(savedInstanceState);
- 26. setContentView(R.layout.main);
- 27. }
- 28.
- 29.
- 30. public static class TitlesFragment extends ListFragment {
- 31.
- 32. boolean mDualPane;
- 33. int mCurCheckPosition = 0;
- 34.
- 35. @Override
- 36. public void onCreate(Bundle savedInstanceState) {
- 37. // TODO Auto-generated method stub
- 38. super.onCreate(savedInstanceState);
- 39. System.out.println("Fragment-->onCreate");
- 40. }
- 41.
- 42. @Override
- 43. public View onCreateView(LayoutInflater inflater, ViewGroup container,
- 44. Bundle savedInstanceState) {
- 45. // TODO Auto-generated method stub
- 46. System.out.println("Fragment-->onCreateView");
- 47. return super.onCreateView(inflater, container, savedInstanceState);
- 48. }
- 49.
- 50. @Override
- 51. public void onPause() {
- 52. // TODO Auto-generated method stub
- 53. super.onPause();
- 54. System.out.println("Fragment-->onPause");
- 55. }
- 56.
- 57.
- 58. @Override
- 59. public void onStop() {
- 60. // TODO Auto-generated method stub
- 61. super.onStop();
- 62.
- 63. System.out.println("Fragment-->onStop");
- 64. }
- 65.
- 66. @Override
- 67. public void onAttach(Activity activity) {
- 68. // TODO Auto-generated method stub
- 69. super.onAttach(activity);
- 70. System.out.println("Fragment-->onAttach");
- 71. }
- 72.
- 73. @Override
- 74. public void onStart() {
- 75. // TODO Auto-generated method stub
- 76. super.onStart();
- 77. System.out.println("Fragment-->onStart");
- 78. }
- 79.
- 80. @Override
- 81. public void onResume() {
- 82. // TODO Auto-generated method stub
- 83. super.onResume();
- 84. System.out.println("Fragment-->onResume");
- 85. }
- 86.
- 87. @Override
- 88. public void onDestroy() {
- 89. // TODO Auto-generated method stub
- 90. super.onDestroy();
- 91. System.out.println("Fragment-->onDestroy");
- 92. }
- 93.
- 94.
- 95.
- 96. @Override
- 97. public void onActivityCreated(Bundle savedInstanceState) {
- 98. // TODO Auto-generated method stub
- 99. super.onActivityCreated(savedInstanceState);
- 100. System.out.println("Fragment-->onActivityCreted");
- 101. setListAdapter(new ArrayAdapter(getActivity(),
- 102. android.R.layout.simple_list_item_1, array));
- 103.
- 104. View detailsFrame = getActivity().findViewById(R.id.details);
- 105.
- 106. mDualPane = detailsFrame != null
- 107. && detailsFrame.getVisibility() == View.VISIBLE;
- 108.
- 109. if (savedInstanceState != null) {
- 110. mCurCheckPosition = savedInstanceState.getInt("curChoice", 0); //从保存的状态中取出数据
- 111. }
- 112.
- 113. if (mDualPane) {
- 114. getListView().setChoiceMode(ListView.CHOICE_MODE_SINGLE);
- 115.
- 116. showDetails(mCurCheckPosition);
- 117. }
- 118. }
- 119.
- 120. @Override
- 121. public void onSaveInstanceState(Bundle outState) {
- 122. // TODO Auto-generated method stub
- 123. super.onSaveInstanceState(outState);
- 124.
- 125. outState.putInt("curChoice", mCurCheckPosition);//保存当前的下标
- 126. }
- 127.
- 128. @Override
- 129. public void onListItemClick(ListView l, View v, int position, long id) {
- 130. // TODO Auto-generated method stub
- 131. super.onListItemClick(l, v, position, id);
- 132. showDetails(position);
- 133. }
- 134.
- 135. void showDetails(int index) {
- 136. mCurCheckPosition = index;
- 137. if (mDualPane) {
- 138. getListView().setItemChecked(index, true);
- 139. DetailsFragment details = (DetailsFragment) getFragmentManager()
- 140. .findFragmentById(R.id.details);
- 141. if (details == null || details.getShownIndex() != index) {
- 142. details = DetailsFragment.newInstance(mCurCheckPosition);
- 143.
- 144. //得到一个fragment 事务(类似sqlite的操作)
- 145. FragmentTransaction ft = getFragmentManager()
- 146. .beginTransaction();
- 147. ft.replace(R.id.details, details);//将得到的fragment 替换当前的viewGroup内容,add则不替换会依次累加
- 148. ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);//设置动画效果
- 149. ft.commit();//提交
- 150. }
- 151. } else {
- 152. new AlertDialog.Builder(getActivity()).setTitle(
- 153. android.R.string.dialog_alert_title).setMessage(
- 154. array[index]).setPositiveButton(android.R.string.ok,
- 155. null).show();
- 156. }
- 157. }
- 158. }
- 159.
- 160. /**
- 161. * 作为界面的一部分,为fragment 提供一个layout
- 162. * @author terry
- 163. *
- 164. */
- 165. public static class DetailsFragment extends Fragment {
- 166.
- 167. public static DetailsFragment newInstance(int index) {
- 168. DetailsFragment details = new DetailsFragment();
- 169. Bundle args = new Bundle();
- 170. args.putInt("index", index);
- 171. details.setArguments(args);
- 172. return details;
- 173. }
- 174.
- 175. public int getShownIndex() {
- 176. return getArguments().getInt("index", 0);
- 177. }
- 178.
- 179. @Override
- 180. public View onCreateView(LayoutInflater inflater, ViewGroup container,
- 181. Bundle savedInstanceState) {
- 182. // TODO Auto-generated method stub
- 183. if (container == null)
- 184. return null;
- 185.
- 186. ScrollView scroller = new ScrollView(getActivity());
- 187. TextView text = new TextView(getActivity());
- 188.
- 189. int padding = (int) TypedValue.applyDimension(
- 190. TypedValue.COMPLEX_UNIT_DIP, 4, getActivity()
- 191. .getResources().getDisplayMetrics());
- 192. text.setPadding(padding, padding, padding, padding);
- 193. scroller.addView(text);
- 194.
- 195. text.setText(array[getShownIndex()]);
- 196. return scroller;
- 197. }
- 198. }
- 199.}
- 复制代码
复制代码 注意:
1.如果你想在Fragment 里面创建menu,则必须在onCreate的时候设置让它可以存在optionMenu才可以创建,代码为:
2.- 01.public static class DetailsFragment extends Fragment {
- 02.
- 03. @Override
- 04. public void onCreate(Bundle savedInstanceState) {
- 05. // TODO Auto-generated method stub
- 06. super.onCreate(savedInstanceState);
- 07. setHasOptionsMenu(true);
- 08. }
- 09.}
- 复制代码
复制代码 之后的操作即可以像平常Android的menu用法一样,代码为:
3.- 01.@Override
- 02. public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
- 03. // TODO Auto-generated method stub
- 04. super.onCreateOptionsMenu(menu, inflater);
- 05. menu.add("Menu 1a").setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM);
- 06. menu.add("Menu 1b").setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM);
- 07. }
- 08.
- 09. @Override
- 10. public boolean onOptionsItemSelected(MenuItem item) {
- 11. // TODO Auto-generated method stub
- 12. Toast.makeText(getActivity(), "index is"+getShownIndex()+" && menu text is "+item.getTitle(), 1000).show();
- 13. return super.onOptionsItemSelected(item);
- 14. }
- 复制代码
复制代码 更多详细的使用方法,请参考SDK和APIDEMO中相关的例子和解释。DEMO下载
FragmentDemo.zip
(61.32 KB, 下载次数: 211)
|
|