Activity生命周期

?????Activity是Android組件中最基本也是最為常見用的四大組件之一,也是我們在開發(fā)過程之中接觸最多的組件,所以了解Activity的生命周期,并正確的理解與應(yīng)用,是必不可少的。下面就來介紹一下Activity生命周期。

生命周期

?????活動在系統(tǒng)中被活動堆棧管理。當一個新的活動開始時,將會強加于堆棧的頂端并成為運行活動狀態(tài)。而之前的活動總是被放置在這個活動下面的堆棧中,并且不會被移動到前臺直到新的活動退出為止。
?????活動從開始到結(jié)束經(jīng)歷各種狀態(tài)。從一個狀態(tài)到另一個狀態(tài)的轉(zhuǎn)變,從無到有再到無,這樣一個過程中所經(jīng)歷的各個狀態(tài)就叫做生命周期。Activity擁有自己的生命周期,而它的意義就在于,當我們對當前的界面進行展示的過程中,本身也會經(jīng)歷各個階段去準備和處理當前的activity,然后展示給用戶,而開發(fā)者為了界面上一些炫酷的效果與功能,做一些特殊處理時,就離不開這些生命周期。

各生命周期狀態(tài)說明

方法 描述 用途(以當前界面播放視頻為例) 下一個方法
onCreate() 當Activity第一次創(chuàng)建時調(diào)用。該方法(如果有)會提供給你一個包含之前活動的凍結(jié)狀態(tài)信息bundle包。 進行一系列初始化操作,如:創(chuàng)建View,加載視頻數(shù)據(jù)等。 onStart()
onRestart() 當Activity被停止后調(diào)用,在重新開始之前 當活動停止后重新啟動該活動時調(diào)用(不常用),針對停止后重啟操作。 onStart()
onStart() 當Activity被展示在用戶眼前時調(diào)用。如果活動出現(xiàn)在前臺緊接著是onResume(),如果活動直接隱藏則緊接著是onStop()。 該方法也不常用。 onResume() or onStop()
onResume() 當Activity將開始與用戶進行交互時調(diào)用。在這個時間點你的活動將會在活動堆棧的頂端,用戶輸入將會訪問它。 暫停后恢復我們會在該方法中進行一些操作,例如視頻繼續(xù)播放。 onPause()
onPause() 當系統(tǒng)將要恢復一個之前的活動。這是一個有代表性的常常用于提交未被存儲的改動信息為持久數(shù)據(jù),停止動畫和消耗CPU的東西等。實現(xiàn)該方法必須要特別的迅速,因為在此方法返回之前,下一個活動將不會恢復。如果活動將返回到前臺則接下來調(diào)用onResume(),如果要隱藏到用戶看不見的地方時,則調(diào)用onStop(); 該方法十分重要,用來做信息持久化存儲操作以及停止消耗CPU資源操作,如記錄視頻播放進度時間,以及暫停視頻播放操作等。 onResume or onStop()
onStop() 當另一個活動被恢復且完全覆蓋該活動,而該Activity將不在展示給用戶時調(diào)用。這種情況將發(fā)生在一個新的活動將被開始,一個退出的活動將被恢復,又或者該活動將要被銷毀。如果該活動將恢復與用戶交互則調(diào)用onRestart(),如果該活動將被銷毀則調(diào)用onDestory()。 界面將會隱藏或銷毀,做一些重要信息或未被存儲的信息的存儲操作。但也不要太耗時。如存儲用戶信息等操作,以及用戶此次觀看的視頻地址以及時間,便于下次打開該界面時繼續(xù)播放。 onRestart() or onResume()
onDestory() Activity被銷毀錢最后一個被調(diào)用的方法。這個方法將會發(fā)生因為活動將會結(jié)束(在活動中調(diào)用finish()方法,或者系統(tǒng)臨時銷毀該實例節(jié)約空間。你可以使用isFinishing()方法區(qū)別這兩種場景)。 界面將要銷毀,釋放一些實例節(jié)約空間,如置空List集合等。

?????下圖中展示了activity的重要的狀態(tài)改變路徑。矩形中的代表你可以在活動在兩種狀態(tài)間改變時你可以實現(xiàn)的回調(diào)方法去執(zhí)行想要的操作。而帶有顏色的橢圓形代表著activity的主要狀態(tài)。


Activity生命周期.png
方法 描述 用途(以當前界面播放視頻為例) 下一個方法
onCreate() 當Activity第一次創(chuàng)建時調(diào)用。該方法(如果有)會提供給你一個包含之前活動的凍結(jié)狀態(tài)信息bundle包。 進行一系列初始化操作,如:創(chuàng)建View,加載視頻數(shù)據(jù)等。 onStart()
onRestart() 當Activity被停止后調(diào)用,在重新開始之前 當活動停止后重新啟動該活動時調(diào)用(不常用),針對停止后重啟操作。 onStart()
onStart() 當Activity被展示在用戶眼前時調(diào)用。如果活動出現(xiàn)在前臺緊接著是onResume(),如果活動直接隱藏則緊接著是onStop()。 該方法也不常用。 onResume() or onStop()
onResume() 當Activity將開始與用戶進行交互時調(diào)用。在這個時間點你的活動將會在活動堆棧的頂端,用戶輸入將會訪問它。 暫停后恢復我們會在該方法中進行一些操作,例如視頻繼續(xù)播放。 onPause()
onPause() 當系統(tǒng)將要恢復一個之前的活動。這是一個有代表性的常常用于提交未被存儲的改動信息為持久數(shù)據(jù),停止動畫和消耗CPU的東西等。實現(xiàn)該方法必須要特別的迅速,因為在此方法返回之前,下一個活動將不會恢復。如果活動將返回到前臺則接下來調(diào)用onResume(),如果要隱藏到用戶看不見的地方時,則調(diào)用onStop(); 該方法十分重要,用來做信息持久化存儲操作以及停止消耗CPU資源操作,如記錄視頻播放進度時間,以及暫停視頻播放操作等。 onResume or onStop()
onStop() 當另一個活動被恢復且完全覆蓋該活動,而該Activity將不在展示給用戶時調(diào)用。這種情況將發(fā)生在一個新的活動將被開始,一個退出的活動將被恢復,又或者該活動將要被銷毀。如果該活動將恢復與用戶交互則調(diào)用onRestart(),如果該活動將被銷毀則調(diào)用onDestory()。 界面將會隱藏或銷毀,做一些重要信息或未被存儲的信息的存儲操作。但也不要太耗時。如存儲用戶信息等操作,以及用戶此次觀看的視頻地址以及時間,便于下次打開該界面時繼續(xù)播放。 onRestart() or onResume()
onDestory() Activity被銷毀錢最后一個被調(diào)用的方法。這個方法將會發(fā)生因為活動將會結(jié)束(在活動中調(diào)用finish()方法,或者系統(tǒng)臨時銷毀該實例節(jié)約空間。你可以使用isFinishing()方法區(qū)別這兩種場景)。 界面將要銷毀,釋放一些實例節(jié)約空間,如置空List集合等。

階段狀態(tài)

Activity4種主要狀態(tài).png

?????一個Activity從本質(zhì)上講擁有4種狀態(tài):

  • 運行:如果當前的activity在前臺界面上時(堆棧頂端)。
  • 暫停:如果activity被另一個非全屏活動強占焦點并覆蓋時(如彈窗dialog),它將會暫停。一個暫停的活動也是完全活躍的(它的所有的狀態(tài)和成員信息將會保留,但activity本身將不會再依附于WindowsManager了),在內(nèi)存極度缺乏的狀態(tài)會被系統(tǒng)殺死。
  • 停止:如果activity完全被另一個全屏活動遮擋住時,它將會停止。該活動也仍保留全部的狀態(tài)和成員信息,但將會被隱藏起來不再展示給用戶,并且當內(nèi)存在其他地方被需要時該活動就將會被系統(tǒng)殺死。
  • 重啟:如果activity處于暫停或者停止狀態(tài),系統(tǒng)將會在內(nèi)存中終止該活動無論是結(jié)束活動或者殺死進程。當它再一次展示給用戶時,它必須是完全重啟并且恢復到之前的狀態(tài)。

狀態(tài)轉(zhuǎn)換

Activity狀態(tài)轉(zhuǎn)換.png

?????上圖中我們可以看到Activity在生命周期狀態(tài)進行轉(zhuǎn)換的過程中,activity本身是在什么時候調(diào)用的onSaveInstanceState()方法與onRestoreInstanceState()方法來進行重要信息的存儲與恢復的。因為在蜂巢版本之前onSaveInstanceState()方法只有在activity異常退出時才會調(diào)用,所以我們應(yīng)該在onPause()方法中進行信息持久化存儲的操作,在蜂巢之后的版本,生命周期就可以正常的調(diào)用onSaveInstanceState()方法來進行信息持久化存儲的操作了。

部分實例列舉

?????上面說了一堆Activity生命周期的定義,在實際應(yīng)用中,我們更傾向于實踐運用,所以我會列舉部分實例。Github傳送門,大家可以給我點個小星星。

  • 打開activity關(guān)閉activity生命周期如下(啟動與銷毀)
// activity啟動
05-24 11:16:44.124 16259-16259/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onCreate
05-24 11:16:44.125 16259-16259/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onStart
05-24 11:16:44.125 16259-16259/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onResume
// activity關(guān)閉
05-24 11:16:46.691 16259-16259/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onPause
05-24 11:16:47.038 16259-16259/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onStop
05-24 11:16:47.038 16259-16259/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onDestroy

?????可以看到正常的啟動與關(guān)閉Activity不會調(diào)用onSaveInstanceState(Bundle)方法與onRestoreInstanceState(Bundle)方法,所以如果要離開該界面時,該界面的重要信息,我們要在onPause()或onStop()方法中進行存儲。

  • 彈窗(dialog、popupwindow)
[空]

?????沒錯,你沒看錯。是空!因為dialog與popupwindow實際上是一個存在于這個activity上的控件,所以它并不會影響activity本身的生命周期!試想如果你每次彈窗你的activity都要走onPause方法的話,那你的一些存儲持久化操作是不是會不停地無更新的存儲呢?所以,不要被一些說法誤導,如果你不知道,那么就去動手實踐。

  • 打開Dialog樣式的Activity(暫停狀態(tài))
// 在Manifest文件中首先設(shè)置dialog樣式
<activity android:name=".TranslateActivity"
        android:theme="@style/Theme.AppCompat.Dialog">
</activity>
// 然后你懂得,我們來打開這個dialog樣式的Activity
05-24 16:27:24.964 26913-26913/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onPause
05-24 16:27:25.206 26913-26913/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onSaveInstanceState
// 最后我們關(guān)閉這個Activity
05-24 16:27:28.227 26913-26913/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onResume
  • 屏幕旋轉(zhuǎn)
05-24 11:24:47.377 16724-16724/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onPause
05-24 11:24:47.378 16724-16724/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onSaveInstanceState
05-24 11:24:47.378 16724-16724/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onStop
05-24 11:24:47.378 16724-16724/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onDestroy
05-24 11:24:47.451 16724-16724/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onCreate
05-24 11:24:47.454 16724-16724/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onStart
05-24 11:24:47.454 16724-16724/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onRestoreInstanceState
05-24 11:24:47.454 16724-16724/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onResume

?????此處的onSaveInstanceState(Bundle)方法與onRestoreInstanceState(Bundle)方法具體執(zhí)行時機,當targetSdkVersion小于3時onSaveInstanceState是在onPause方法中調(diào)用的,而大于3時是在onStop方法中調(diào)用的。而onRestoreInstanceState是在onStart之后、onResume之前調(diào)用的。

  • 按Home鍵后再開啟app(停止狀態(tài))
// 點擊home鍵(菜單鍵)
05-24 11:50:25.097 17817-17817/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onPause
05-24 11:50:25.407 17817-17817/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onSaveInstanceState
05-24 11:50:25.407 17817-17817/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onStop
// 打開App
05-24 11:51:05.471 17817-17817/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onRestart
05-24 11:51:05.476 17817-17817/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onStart
05-24 11:51:05.476 17817-17817/com.perry.activitylifecycle E/TAG lifecycle:  ------>>> onResume

小結(jié)

?????文章中我們具體的了解了Activity的7大生命周期與4種本質(zhì)狀態(tài),還有onSaveInstanceState(Bundle)方法與onRestoreInstanceState(Bundle)具體執(zhí)行時機。便于我們更好的了解與利用Activity中的每一種生命周期方法。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

推薦閱讀更多精彩內(nèi)容