1: Activity的生命周期
Activity有如下3种生命周期:
整体生命周期:onCreate-onStart-onResume-onPause-onStop-onRestart-onDestroy
可视生命周期:onStart-onResume-onPause-onStop
焦点生命周期:onResume-onPause
2:onCreate
为什么重写onCreate方法时,必须调用Activity类的onCreate方法,也就是super.onCreate(savedInstanceState)?
这是因为Activity类没有不带参数的onCreate方法,如果不显示调用super.onCreate(savedInstanceState),
系统将会试图调用super.onCreate()方法,但Activity类中并没有这个方法。
3:setContentView
在Activity中,初始化控件一般在onCreate方法中完成,当然也可以在其它的方法中来完成,但是不能在Activity的
构造方法中来初始化控件或者装载View,因为在构造方法中有很多初始化的工作没有完成,无法调用setContentView
来装载控件,更不能初始化控件。
另外尽量不要在Activity中添加带参数的构造方法,如果非要添加的话,请把无参的构造方法也加上。
因为Activity的创建,一般不是由开发人员来完成的,而是通过Intent对象和startActivity方法在系统内部创建的。
4:配置Activity
创建完成的Activity并不能马上使用,还需要在AndroidManifest.xml文件中进行配置。
每一个Activity都对应上叙文件的<activity>标签,在其标签上有一个必选属性-android:name ,该属性对应我们要想配置的Activity类名。
指定android:name又有以下3种方式:
指定完整的类名:packagename+classname;
只指定类名:如果在manifest标签中指定了packagename,并且要配置的Activity的类文件就在这个package下的话,可以直接写类名,或者在前面加上" . ";
指定相对类名:这种方式类似于第二种,如果要配置的Activity的类文件在这个包下的下一个包中,
例如在manifest中的packagename是mobile.android,需要配置的Activity是mobile.android.test.Main,
那我们可指定一个相对的类名.test.Main。
如果想给我们的Activity设置得漂亮一些,可以为它设置一个图标。android:icon。它指向一个图像资源的ID,这个资源ID所指定的
图像将会作为应用程序列表中的程序图标。如果我们配置时未指定这个属性的话,系统会使用application标签中的android:icon来代替,
这样的方式在后面配置时经常都会用到,不过不是你去配置的,是系统自动写好的。这点很类似写网页中的样式表。
在activity标签中还有一个intent-filter标签,从单词上理解就是意图过滤器,它的作用是对Activity进行分类,其中还包含action和category。
action标签表示Activity可以接收到的动作,category标签表示Activity所属的种类。
5:Intent
任何一个稍微复杂一些的程序都不太可能只有一个界面,在Android中,如果程序包含多个Activity的话,我们就需要使用到Intent作为中间代理来调用。
显式调用:Intent intent=new Intent(Context cont,Class cls);
隐式调用:Intent intent=new Intent("actionName");
然后startActivity(intent);
在不同的Activity之间传值的方式有很多种,这里使用最常用的一种:通过Intent传值。
传值:intent.putExtra(String key,Object value);
接收:getIntent().getExtras().get(key); 但这样返回的是Object类型。
如果知道自己接收的是什么类型的话(假设为String),可以直接getIntent().getStringExtra().get(key),这样可以不再作类型转换。
如果传递的数据是一个对象的话,这个对象的类必须是可序列化的。
之外还可以通过 静态变量、剪切板(不推荐)、全局对象 来传递数据。
我觉得有必要再写一下我对全局变量传递数据的理解。
使用过Java EE的朋友应该对Java Web的4个作用域都非常熟悉了,它们从小到大分别是Page,Request,Session,Application,
其中Application在应用程序内的任何地方都可以访问得到,而Android中的全局对象就非常类似这个Application。
全局对象所对应的类,必须继承自android.app.Application。该类必须要有一个无参的构造函数,类中无需定义静态变量,定义成员变量就行了。
如同Activity一样,单单写一个全局对象的类也是不行的,我们要在AndroidManifest.xml中对它进行配置。
通过<application>标签的android:name属性指定这个类,在程序运行后,这个类的对象就会自动创建,而且一直会在内存中驻留,直到程序被退出。
假定我们定义了一个全局对象 MyApp。可以这样使用它:MyApp myApp=(MyApp)getApplicationContext();然后可以对该对象的变量进行读写。
6:返回数据到前一个Activity
有时候我们不仅需要向Activity传递数据,还要从Activity中返回数据。返回数据也可以像上面介绍的4种方式,但一般建议采用Intent对象方式。
传递数据:Intent intent=new Intent(this,newActivity.class);
startActivityForResult(intent,1);//后一个参数是一个int类型的请求码,可以是任意的整数,只是为了区分请求的来源,以便处理返回结果。
返回数据:Intent intent=new Intent();
intent.putExtra('value",value);
setResult(2,intent);//通过Intent返回结果,第一个参数是响应码,与请求码类似。
finish();//关闭当前的Activity.
接收数据:在接收数据的Activity中,重写onActivityResult方法。
@Override protected void onActivityResult(int requestCode, int resultCode, Intent data) { super.onActivityResult(requestCode, resultCode, data); switch (requestCode) { case 1:// 请求码 switch (resultCode) { case 2: // 响应码 String str = data.getStringExtra("value");// 取值 break; default: break; } break; default: break; } }
这里补充一下关于onNewIntent的介绍:
说到onNewIntent,我们需要先了解一下关于Android的任务栈。
任务栈中包含了activity组件的对象,且任务栈中可以包含有某一个activity组件类型的多个实例对象。在任务栈中的activity组件不能被重排序,只能被压栈和弹栈。
从用户的角度看,一个任务栈就代表了“一个应用程序”。它实际上是一个栈,里面放着一组被排列好的相关的activity组件。位于栈底的activity(根activity)就是开启这个任务栈的activity组件,一般情况下,就是应用程序的主界面。而位于栈顶的activity组件即代表当前被激活的activity组件(可接收用户行为的activity)。 当我们startActivity的时候,
如果新的意图想要打开的Activity就在当前任务栈的栈顶,那么系统将不会去再去创建这个Activity而是通过onNewIntent来调用这个Activity,前提是一定要在当前任务栈的栈顶。
在写测试项目过程中,总结了一下:
一个activity标签里可以有多个intent-filter,然后程序可以通过Intent来指定intent-filter中的action来进行调用,
(但每个intent-filter必须指定它的category,一般就是android.intent.category.DEFAULT就行了)
如果在AndroidManifest.xml中配置了重名的action的话,在调用的时候会列出这些同名的Activity来给用户选择。