先看图:
Android中的activity通过onSaveInstanceState()方法保存activity的状态,在onCreate或者onRestoreInstanceState方法恢复状态,如果是通过onRestart方法前端运行的话,只会执行onSaveinstanceState方法。直接看代码:
- package com.hebaijun.savestate;
- import android.app.Activity;
- import android.os.Bundle;
- import android.util.Log;
- public class SaveStateActivity extends Activity {
- public static final String TAG = "SaveStateActivity";
- @Override
- public void onCreate(Bundle savedInstanceState) {
- if (savedInstanceState!=null) {
- Log.v(TAG, savedInstanceState.getString("data"));
- }
- super.onCreate(savedInstanceState);
- setContentView(R.layout.main);
- Log.v(TAG, "onCreate");
- }
- @Override
- protected void onRestoreInstanceState(Bundle savedInstanceState) {
- Log.v(TAG, savedInstanceState.getString("data"));
- super.onRestoreInstanceState(savedInstanceState);
- Log.v(TAG, "onRestoreInstanceState");
- }
- @Override
- protected void onSaveInstanceState(Bundle outState) {
- outState.putString("data", "example");
- super.onSaveInstanceState(outState);
- Log.v(TAG, "onSaveInstanceState");
- }
- @Override
- protected void onPause() {
- super.onPause();
- Log.v(TAG, "onPause");
- }
- @Override
- protected void onResume() {
- super.onResume();
- Log.v(TAG, "onResume");
- }
- @Override
- protected void onStart() {
- super.onStart();
- Log.v(TAG, "onStart");
- }
- @Override
- protected void onRestart() {
- super.onRestart();
- Log.v(TAG, "onRestart");
- }
- }
main.xml
- <?xml version="1.0" encoding="utf-8"?>
- <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="fill_parent"
- android:layout_height="fill_parent"
- android:orientation="vertical" >
- <EditText
- android:id="@+id/editText1"
- android:layout_width="match_parent"
- android:layout_height="wrap_content" >
- </EditText>
- </LinearLayout>
![](https://img-my.csdn.net/uploads/201205/14/1336983822_5983.png)
- 我们可以看出onSaveInstanceState方法在onPause方法前执行。Android 3.0之后,onSaveInstanceState在onPause之后,onStop之前调用。
- 程序恢复执行的时候调用了onRestart方法,并没有调用 onRestoreInstanceState方法。
![](https://img-my.csdn.net/uploads/201205/14/1336983859_8101.png)
- 程序并没有调用onSaveInstanceState方法,因为按BACK键表明用户已经明确退出,所以不会执行保存状态的操作。就是说 onSaveInstanceState能不能被执行到是不确定的,要保存永久的数据话还是在onPause方法中用其他方式保存。
- 如果在edittext中输入字符的话,重新执行也不会重新出现。
onRestoreInstanceState的执行时机
private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
activity.mCalled = false;
if (r.isPersistable()) {
mInstrumentation.callActivityOnCreate(activity,r.state, r.persistentState);
} else {
mInstrumentation.callActivityOnCreate(activity,r.state);
}
r.activity = activity;
r.stopped = true;
if (!r.activity.mFinished) {
activity.performStart();
r.stopped = false;
}
if (!r.activity.mFinished) {
if (r.isPersistable()) {
if (r.state != null || r.persistentState != null) {
mInstrumentation.callActivityOnRestoreInstanceState(activity,r.state, r.persistentState);
}
} else if (r.state != null) {
mInstrumentation.callActivityOnRestoreInstanceState(activity,r.state);
}
}
if (!r.activity.mFinished) {
activity.mCalled = false;
if (r.isPersistable()) {
mInstrumentation.callActivityOnPostCreate(activity,r.state, r.persistentState);
} else {
mInstrumentation.callActivityOnPostCreate(activity,r.state);
}
}
从代码的逻辑看出,OnRestoreInstanceState在performStart之后,OnPostCreate之前调用,调用的条件是r.state != null 。r.state是AMS传过来的,也就是说OnRestoreInstanceState的调用取决于AMS是否想恢复activity。
除此之外,r.state也会被传入onCreate函数,所以,对activity状态恢复的工作,可以在onCreate中进行,也可以在OnRestoreInstanceState中进行。
从Activity中onCreate函数和OnRestoreInstanceState函数设计初衷看,onCreate函数用于恢复activity本身的状态信息,也包括其中的fragment信息;OnRestoreInstanceState函数用于恢复Activity中window和DecorView的状态。
protected void onCreate(@Nullable Bundle savedInstanceState) {
if (savedInstanceState != null) {
Parcelable p = savedInstanceState.getParcelable(FRAGMENTS_TAG);
mFragments.restoreAllState(p, mLastNonConfigurationInstances != null
? mLastNonConfigurationInstances.fragments : null);
}
mFragments.dispatchCreate();
getApplication().dispatchActivityCreated(this, savedInstanceState);
}
protected void onRestoreInstanceState(Bundle savedInstanceState) {
if (mWindow != null) {
Bundle windowState = savedInstanceState.getBundle(WINDOW_HIERARCHY_TAG);
if (windowState != null) {
mWindow.restoreHierarchyState(windowState);
}
}
}