Android基础查漏补缺之Fragment(1)

这两天看了些关于Fragment的知识点,不过内容比较多,可能要分成几篇写。要说我之前对Fragment的认识只停留在“听过”上,显然那时学的是够糙的=.=

一、什么是Fragment

当年只听说这货是Android3.0为平板开发准备的,但其实它现在用的挺广。按指南上说的,“可重复使用的、模块化的Activity组件”显然更合理嘛!定义这种东西,接着引用指南的说法,一个Activity中可以有多个Fragment,同一个Fragment也可以被用在多个不同的Activity中。每个Fragment有自己的生命周期,也可以响应自己的事件,甚至可以在Activity运行时动态地更改,但Fragment必须依附于Activity,自然其生命周期也就受Activity影响了。

二、创建和使用Fragment

以前创建Activity就继承android.app.Activity类,创建Service就继承android.app.Service类,很容易地联想到,创建Fragment就继承android.app.Fragment类!注意android.support.v4.app包下也有一个Fragment类,那是用来保证API4以后历史版本的兼容性的,而现在的MinSDK几乎已经API15+了,因而也就不再需要继承它了。

Fragment作为可以带有UI的组件,自然也是可以用XML来配置布局的,顺便建个XML布局吧!那XML又该在什么地方被加载呢?Fragment里有一个onCreateView()方法,一看参数列表里有个LayoutInflater,返回类型又是View,一定就是它了!覆写这个方法把布局填充起来。

public class ExampleFragment extends Fragment {

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        return inflater.inflate(R.layout.fragment_example, null);
    }

}

Fragment有了,接下来当然是使用它咯~基本的方法有两种,第一种是把Fragment当作Activity中的UI控件一样使用,就像这样。

<fragment
    android:id="@+id/fragment"
    android:name="com.example.test3.ExampleFragment"
    android:layout_width="match_parent"
    android:layout_height="match_parent" />

唯一有点区别的就是android:name这个属性,指定下Fragment具体的类名就是了。另外,android:id这个属性是一定要有的,否则在填充这个布局时就会抛出异常,也可以使用android:tag属性,以后再说,先运行看下效果


前面说过Fragment是可以在Activity运行过程中动态更改的,那么就来试一下“点击一个按钮以添加Fragment”如何?以下代码就是这个按钮的点击事件

public void addFragment(View v) {
    ExampleFragment exampleFragment = new ExampleFragment();
    FragmentManager fragmentManager = getFragmentManager();
    FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
    fragmentTransaction.add(R.id.container, exampleFragment, null);
    fragmentTransaction.addToBackStack(null);
   fragmentTransaction.commit();
}

运行效果是这样的,每点击一次上半部的“添加Fragment”按钮,下半部就出现添加一个里边是一行“Hello, Example Fragment!”文本的Fragment。这里用到了Fragment事务,初步看起来和数据库事务,或者SharedPreference事务很像,都是先begin,做一些事,最后记得commit这样的三个步骤。这里的add()方法有3个参数,第2个参数是要添加的Fragment实例,其他2个则是可选的,含义分别是这个Fragment要放进哪个父布局中和给这个Fragment打个TAG,而addToBackStack()方法用来把我们当前执行的这个事务添加到Activity的回退栈中,这样一来当用户按下返回键时就可以“回滚这个事务”,相当于返回到添加这个Fragment前Activity的状态,而不是退出整个Activity,方法的参数是事务的名称,同样是可选的。


三、Fragment的生命周期

直接看张开发指南里的图吧。


哇,足足11个方法,比Activity的区区6个生命周期方法复杂很多耶,不过只要像学习Activity的生命周期方法那样,先把每个方法的调用时机弄明白(其实就是调用时打一行日志呗),也挺容易的说。对了,别忘了Fragment依附于Activity,所以两者的生命周期方法在被调用时要要一并打印噢,首先是Fragment配置在Activity布局文件内的情形,结果会像这样。

<!-- 启动App -->
06-09 09:26:11.183 22157-22157/com.example.test3 D/MainActivity: -->onCreate
06-09 09:26:11.286 22157-22157/com.example.test3 D/ExampleFragment: -->onAttach
06-09 09:26:11.286 22157-22157/com.example.test3 D/ExampleFragment: -->onCreate
06-09 09:26:11.287 22157-22157/com.example.test3 D/ExampleFragment: -->onCreateView
06-09 09:26:11.290 22157-22157/com.example.test3 D/ExampleFragment: -->onActivityCreated
06-09 09:26:11.291 22157-22157/com.example.test3 D/MainActivity: -->onStart
06-09 09:26:11.291 22157-22157/com.example.test3 D/ExampleFragment: -->onStart
06-09 09:26:11.291 22157-22157/com.example.test3 D/MainActivity: -->onResume
06-09 09:26:11.291 22157-22157/com.example.test3 D/ExampleFragment: -->onResume
<!-- 点击多任务键 -->
06-09 09:26:35.691 22157-22157/com.example.test3 D/ExampleFragment: -->onPause
06-09 09:26:35.691 22157-22157/com.example.test3 D/MainActivity: -->onPause
06-09 09:26:35.708 22157-22157/com.example.test3 D/ExampleFragment: -->onStop
06-09 09:26:35.708 22157-22157/com.example.test3 D/MainActivity: -->onStop
<!-- 点击返回键 -->
06-09 09:26:41.675 22157-22157/com.example.test3 D/MainActivity: -->onStart
06-09 09:26:41.675 22157-22157/com.example.test3 D/ExampleFragment: -->onStart
06-09 09:26:41.675 22157-22157/com.example.test3 D/MainActivity: -->onResume
06-09 09:26:41.675 22157-22157/com.example.test3 D/ExampleFragment: -->onResume
<!-- 退出App -->
06-09 09:26:49.358 22157-22157/com.example.test3 D/ExampleFragment: -->onPause
06-09 09:26:49.358 22157-22157/com.example.test3 D/MainActivity: -->onPause
06-09 09:26:49.788 22157-22157/com.example.test3 D/ExampleFragment: -->onStop
06-09 09:26:49.788 22157-22157/com.example.test3 D/MainActivity: -->onStop
06-09 09:26:49.788 22157-22157/com.example.test3 D/ExampleFragment: -->onDestroyView
06-09 09:26:49.788 22157-22157/com.example.test3 D/ExampleFragment: -->onDestroy
06-09 09:26:49.788 22157-22157/com.example.test3 D/ExampleFragment: -->onDetach
06-09 09:26:49.788 22157-22157/com.example.test3 D/MainActivity: -->onDestroy

显而易见地,当App启动时,先是要创建Fragment所依附的Activity,而后Fragment才会依次执行onAttach()、onCreate()、onCreateView()和onActivityCreated()四个方法。而当App退出时,相反地,先由Fragment执行onDestoryView()、onDestory()和onDetach()三个方法,而后才能销毁相应的Activity。至于剩下的4个方法,更明显了,和Activity中同名的方法是一一对应的呀,执行的顺序也很容易理解,不是么?

还有就是在Activity运行过程中添加和移除Fragment的情形。添加Fragment的生命周期和上面肯定是一样的,但注意移除的时候,如下,只走了onPause()、onStop()和onDestoryView()三个方法,而没有走onDestory()和onDetach()方法,那么,在按下返回键恢复事务时,也就只会执行对应的onCreateView()、onActivityCreated()、onStart()、onResume()这几个方法了。

06-10 08:27:09.802 5168-5168/com.example.test3 D/ExampleFragment: -->onPause
06-10 08:27:09.802 5168-5168/com.example.test3 D/ExampleFragment: -->onStop
06-10 08:27:09.802 5168-5168/com.example.test3 D/ExampleFragment: -->onDestroyView
06-10 08:27:12.386 5168-5168/com.example.test3 D/ExampleFragment: -->onCreateView
06-10 08:27:12.387 5168-5168/com.example.test3 D/ExampleFragment: -->onActivityCreated
06-10 08:27:12.387 5168-5168/com.example.test3 D/ExampleFragment: -->onStart
06-10 08:27:12.387 5168-5168/com.example.test3 D/ExampleFragment: -->onResume

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值