Android活动的生命周期

返回栈

Android是使用任务(Task)来管理活动的,一个任务就是一组存放在栈里的活动的集合,这个栈也被称作返回栈(Back Stack)

可见和不可见的含义
  • 可见:当前活动在主屏能看到,比如当前活动界面打开一个Dialog样式的活动,那么此活动并没有被完全遮挡,仍然是可见状态,
  • 不可见:当前活动被完全遮挡
活动状态
  • 运行状态(当前处于栈顶的活动)
  • 暂停状态(活动不再处于栈顶,但仍然可见)
  • 停止状态(活动不再处于栈顶,并且完全不可见)
  • 销毁状态(活动从返回栈中移除)
活动的生存期

Activity类中定义了7个回调方法,覆盖了活动生命周期的每一个环节

  • onCreate(): 会在活动第一次被创建时调用,完成一些初始化操作,如加载布局、绑定事件
  • onStart(): 在活动由不可见变为可见的时候调用
  • onResume(): 在活动准备好和用户进行交互的时候调用,此时活动一定处于返回栈的栈顶,并处于运行状态
  • onPause(): 在系统准备去启动或者恢复另一个活动的时候用。我们通常会在这个方法中将一些消耗CPU的资源释放掉,以及保存一些关键数据,这个方法的执行速度一定要快,不然会影响到新的栈顶活动的使用
  • onStop(): 在活动完全不可见时调用。如果启动的新活动是一个对话框式的活动,那么只有onPause()会得到执行,而onStop()不会执行,因为对话框式的活动不会完全遮挡住上一个活动
  • onDestroy(): 在活动被销毁之前调用,之后活动的状态将变成销毁状态
  • onRestart(): 在活动由停止状态变为运行状态之前调用,即活动被重新启动

以上7个方法,除了onRestart()方法,其他都是两两相对的,从而将活动分为3中生存期:

  • 完整生存期:活动在onCreate()方法和onDestroy()方法之间所经历的,即从初始化到释放内存
  • 可见生存期:从onStart()到onStop(),活动对于用户来说都是可见的,即使无法进行交互,即从资源加载到资源释放

  • 前台生存期:从onResume()到onPause(),此时的活动都是运行态,可以和用户交互的,我们平时看到和接触最多的就是出于这个状态下的活动

活动生存期图

简单demo

实现从MainActivity分别跳转到activity2和activity3并返回,其中activity3是dialog主题,观察Mainactivity的声明周期

Mainactivity中复写了上面的那些生命周期方法

其中activity3在注册页面配置为对话框主题

1
2
3
4
 <activity
android:name=".activity.ThirdActivity"
android:theme="@style/Theme.AppCompat.Dialog"> <!-- 使用Dialog主题-->
</activity>

主活动布局

主活动启动 log输出:

从主活动跳转到activity2 log输出:

从activity2返回 log输出:

从主活动跳转到activity3 log输出:

  • 可以清楚的看到 ,这里只调用了onPause ,而没有继续调用onStop,与上面圈出来的跳转到activity2的log不同,因为activity3 是对话框式,并没有完全遮挡主活动,所以没有调用onStop

从activity3返回 log打印:

结束主活动,返回桌面 log打印:

活动被回收了咋办?

当活动进入停止态,即执行了onStop(),是可能被系统回收的。回收了之后,如果BACK到之前的活动,系统就会重新onCreate()->onStart()->onResume(),而不是onRestart()->onStart()->onResume()。

如果真的系统真的onCreate()了,那么原活动的临时数据就会丢失!

所以Activity又提供了一个onSaveInstanceState()的回调方法来解决临时数据得不到保存的问题。

onSaveInstanceState()会携带一个Bundle类型的参数,Bundle提供了一系列的方法保存数据,比如putString()和putInt()等,其第一个参数是键值,第二个参数是数据。比如MainActivity要保存数据,可以重写这个:

1
2
3
4
5
6
@Override
public void onSaveInstanceState(@NonNull Bundle outState, @NonNull PersistableBundle outPersistentState) {
super.onSaveInstanceState(outState, outPersistentState);
String tempData = "这里是你刚刚输入的数据";
outState.putString("key", tempData);
}

取值的之后直接从onCreate()中的Bundle取值

1
2
3
4
5
6
7
8
9
10
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);

if (savedInstanceState!=null){
String tempData = savedInstanceState.getString("key");
Log.d(TAG, tempData);
}
...
}
0%