您的位置:首页 > 移动开发 > Android开发

[置顶] Android四大组件之Activity

2015-08-29 19:36 435 查看

一、Activity简介

1.Activity作为安卓四大组件之一,主要用来提供手机屏幕和用户的的交互,比如:打电话、拍照、发邮件、看地图等等。

2.每个Activity都有一个手机窗口用来绘制用户界面。这些窗口可以全屏,也可以小于手机屏幕,还可以浮在其他窗口之上。

3.一个应用(Application)至少有一个Activity,当然,通常一个应用有多个Activity,但只有一个’main’Activity,这个’main’Activity就是在应用启动后第一个Activity。

4.一个Activity可以通过Intent对象来启动另一个Activity,当新的Activity启动时,前一个Activity便会停止,有序地并压入

后台’栈’(stack)中。因此,多个Activity遵循’后进先出’的原则。也就是说,如果当前Activity关闭,那么前一个Activity

便会出‘栈’并显示到当前窗口。

二、Activity的生命周期



Activity生命周期主要有如下7个方法:

1)onCreate():当Activity被创建后执行的第一个方法,这个方法主要用来进行创建视图,绑定数据等,同时,这个方法还会传递一个Bundle对象,这个对象包含Activity之前的状态,如果这个状态被捕获的话。后面只跟随onStart()方法。

2)onRestart():当Activity处于停止(stopped)状态并且将要重新启动该Activity时会调用这个方法。后面只跟随onStart()方法。

3)onStart():当Activity将要被用户可见时会调用这个方法。如果Activity将要进入前台,那么后面跟随onResume()方法;如果Activity将要被隐藏,那么后面跟随onStop()方法。

4)onResume():当Activity将要与用户进行交互时会调用这个方法。此时,这个Activity位于’栈顶’(the top of activity stack)。后面只跟随onPause()方法。

5)onPause():当系统将要resume另一个Activity时将会调用这个方法。这个方法常用来作数据的持久化、停止动画等消耗CPU的操作。只有等这个方法返回,另一个Activity才能被resumed,因此这个方法不应该做耗时操作。如果Activity将要回到前台,后面跟随onResume()方法;如果Activity将要不可见,后面跟随onStop()方法。

6)onStop():当Activity变为不可见时将会调用这个方法。下面两种情况会调用这个方法:

(i)该Activity被销毁(destroyed)。

(ii)该Activity被另一个Activity覆盖,并且完全不可见。

4000
当Activity重新变为可交互状态时,跟随onRestart()方法;当Activity被销毁时,跟随onDestroy()方法。

7)onDestroy():当Activity被销毁时调用该方法。下面两种情况会调用这个方法:

(i)调用finish()方法。

(ii)系统内存不足,临时销毁该实例以节省内存。

注意:在这7个方法中,onPause(),onStop(),onDestroy()这三个方法返回后,系统都有可能杀死该Activity,在可用内存极低的情况下。

附生命周期代码示例:

public class ExampleActivity extends Activity {
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// The activity is being created.
}
@Override
protected void onStart() {
super.onStart();
// The activity is about to become visible.
}
@Override
protected void onResume() {
super.onResume();
// The activity has become visible (it is now "resumed").
}
@Override
protected void onPause() {
super.onPause();
// Another activity is taking focus (this activity is about to be "paused").
}
@Override
protected void onStop() {
super.onStop();
// The activity is no longer visible (it is now "stopped")
}
@Override
protected void onDestroy() {
super.onDestroy();
// The activity is about to be destroyed.
}
}


三、Activity的使用方法

1.创建一个Activity:

(i)创建Activity的子类,重写onCreate()方法。根据需求来选择性重写其他生命周期方法。
(ii)在Manifest.xml文件中注册。


<manifest ... >
<application ... >
<activity android:name=".ExampleActivity" />
...
</application ... >
...
</manifest >


2.使用intent filters

<activity android:name=".ExampleActivity" android:icon="@drawable/app_icon">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>


使用intent filters可以定义如何让其他应用(Application)激活这个Activity。

3.启动一个Activity

(i)无返回参数方式

Intent intent = new Intent(this, SignInActivity.class);
startActivity(intent);


(ii)有返回参数方式

Intent intent = new Intent(Intent.ACTION_SEND);
intent.putExtra(Intent.EXTRA_EMAIL, recipientArray);
startActivity(intent);


private void pickContact() {
// Create an intent to "pick" a contact, as defined by the content provider URI
Intent intent = new Intent(Intent.ACTION_PICK, Contacts.CONTENT_URI);
startActivityForResult(intent, PICK_CONTACT_REQUEST);
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
// If the request went well (OK) and the request was PICK_CONTACT_REQUEST
if (resultCode == Activity.RESULT_OK && requestCode == PICK_CONTACT_REQUEST) {
// Perform a query to the contact's content provider for the contact's name
Cursor cursor = getContentResolver().query(data.getData(),
new String[] {Contacts.DISPLAY_NAME}, null, null, null);
if (cursor.moveToFirst()) { // True if the cursor is not empty
int columnIndex = cursor.getColumnIndex(Contacts.DISPLAY_NAME);
String name = cursor.getString(columnIndex);
// Do something with the selected contact's name...
}
}
}


4.关闭一个Activity

调用finish()方法可以关闭Activity自身。

调用finishActivity()方法关闭之前打开的Activity。

注意:使用这种方式关闭Activity,适合Activity关了之后完全没有必要再回来的情况。

5.Activity之间传递数据

(i)直接发送

Intent intent = new Intent(this,MainActivity2.class);
intent.putExtra("name", "zz");
intent.putExtra("age", 22);
intent.putExtra("sex",'男');
startActivity(intent);


接收代码onCreate()中:

Intent intent = getIntent();
String name2 = intent.getStringExtra("name");
int age2 = intent.getIntExtra("age", 0);
char sex2 = intent.getCharExtra("sex",' ');
tv.setText("name="+name+",age="+age+",sex="+sex);


(ii)传递Bundle对象

Intent intent = new Intent(this,MainActivity2.class);
Bundle bundle = new Bundle();
bundle.putString("name", "Jhon");
bundle.putInt("age", 18);
bundle.putChar("sex", '男');
intent.putExtra("person", bundle);
startActivity(intent);


接收代码onCreate()中:

Intent intent = getIntent();
Bundle bundle = intent.getBundleExtra("person");
String name = bundle.getString("name");
int age = bundle.getInt("age");
char sex = bundle.getChar("sex");


(iii)传递自定义对象

首先,自定义一个类,实现Parcelable(或Serializable)接口。

当然,如果你传递的是一个包含自定义类的集合,那么集合本身和该自定义类都需要实现上述接口之一。

import android.os.Parcel;
import android.os.Parcelable;

public class Cat implements Parcelable {

String name;
String sex;

public Cat(){}

private Cat(Parcel in){
name = in.readString();
sex = in.readString();
}
//使用Parcelable必须带这个方法
public static final Parcelable.Creator<Cat> CREATOR = new Parcelable.Creator<Cat>() {
public Cat createFromParcel(Parcel in) {
return new Cat(in);
}
public Cat[] newArray(int size) {
return new Cat[size];
}
};

@Override
public int describeContents() {
return 0;
}

//重写此方法,封装要传递的参数
@Override
public void writeToParcel(Parcel dest, int flags) {
dest.writeString(name);
dest.writeString(sex);
}

@Override
public String toString() {
return "Cat [name=" + name + ", sex=" + sex + "]";
}
}


然后,发送代码如下:

Intent intent = new Intent(this,MainActivity2.class);
Cat cat = new Cat();
cat.name = "黑猫  ";
cat.sex = "母";
intent.putExtra("cat", cat);
startActivity(intent);


接收代码onCreate()中:

Intent intent = getIntent();
Cat cat = intent.getParcelableExtra("cat");
String name = cat.name;
String sex = cat.sex;
String string = cat.toString();


6.保存Activity状态

1)为什么要保存Activity状态?

当一个Activity进入“Paused”或“Stopped”状态时,Activity的对象任然在内存中,关于它的所有成员信息和当前状态都是活动的。因此,当它回到前台的时候,这个改变任然存在。

但是,当系统为了节省内存而杀死Activity时,Activity的对象被销毁。如果不进行处理,当它回到前台的时候,会重新创建一个新的Activity对象,并且所有之前的状态都将消失。作为一个用户,肯定不希望这种情况发生。



2)那么,如何保存Activity状态呢?

Activity默认会实现onSaveInstanceState()方法,这个方法会自动保存我们的Activity的UI的有用信息,前提是我们为这个View定义了id属性。

即使如此,我们仍然需要实现这个方法,来保存添加的信息。不要忘了super.onSaveInstanceState()。

如果实现了onRestoreInstanceState()方法,也要添加super.onRestoreInstanceState()。

注意:不要在onSaveInstanceState()里面做数据持久化操作。该方法只适合于保存UI状态。如果要做数据持久化应该在onPause()方法中保存(例如数据需要保存到数据库)。

3)如何测试状态保存没有?

通过旋转手机屏幕可以测试。

当手机屏幕旋转,为了适配不同屏幕的资源文件,Activity默认会重新创建。

也正因为如此,我们才需要保存Activity的状态,因为用户经常旋转屏幕。

四.Activity其他常用方法

1.onKeyDown:手机常用按键监听

@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
return super.onKeyDown(keyCode, event);
}


2.onBackPressed:返回按键监听

@Override
public void onBackPressed() {
super.onBackPressed();

}


3.moveTaskToBack(boolean nonRoot):类似Home键按下效果

当nonRoot=false时,仅当启动Activity生效。

当nonRoot=true时,无限制。

应用场景:

如果用户在按返回键的时候你并不希望退出(默认就finish了),而是只希望置后台,就可以调这个方法。

@Override
public boolean moveTaskToBack(boolean nonRoot) {
return super.moveTaskToBack(nonRoot);
}


@Override
public void onBackPressed() {
super.onBackPressed();
moveTaskToBack(false);
}


五.相关Framework层的类

1.ActivityThread类

这个类作用:

根据Activity Manager的要求,

①管理一个应用进程的主线程的执行。

②安排并启动活动,广播,和其他操作。

以上就是Activity的基本介绍,如有错误,还请指正。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: