Android四大组件之Activity

一、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生命周期

  1. 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覆盖,并且完全不可见。
    当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的基本介绍,如有错误,还请指正。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值