說來慚愧,從工作到現在,學習Android已有一年,但面對activity這個最常用的組件仍然許多疑問,遂決定好好看一遍關於activity的官方api,把遺落的知識再次整理一遍。
首先當然是貼出最經典的活動狀態圖,直接從API上截的
其中每個狀態的改變引發的生命週期方法調用就不提了。其實,這篇文章主要想要討論一下圖片左邊這一條path 。
一般情況下,當我們的activity失去焦點但還可見時,onPause方法就會被調用,這時acitity是一個什麼狀態呢?
當然它已經不在棧頂了,而且當系統內存很少時它有可能被回收,但它確實保留了自己的所有狀態和數據,這時:
❀如果將它重新置於棧頂,那麼它的數據將得以保留。
❀ 如果不幸被系統kill掉了,那麼再次可見時onCreate將被調用,這也意味着它將失去一些原本的數據(注意是一些,而不是所有,因爲頁面控件的信息系統會幫我們自動保存,後面會提到)。
這倒沒什麼玄妙,相信很多人已經瞭解了,但是這個問題卻往往被大部分人有意無意的忽略。比如下面一個常見的業務邏輯,一個註冊過程需要分很多頁完成,中間的頁可以跳到下一頁繼續填寫,也可以返回上一頁做出修改,這意味着我們的"上一頁"必須保存當前的數據以備用戶返回時使用,一般的做法時跳轉頁面時不finish當前頁面,這當然可以而且絕大部分時候是不會出錯的,這是因爲即使activity處於不可見狀態也不是那麼容易就被系統回收,但作爲一個嚴謹的業務邏輯還是希望能夠避免這種情況出現的。
解決的方式就是調用onSaveInstanceState()
在上述的情形下,實際的activity實例已經被銷燬,但是系統仍然記得它的存在,當用戶返回到它的時候,系統會創建出一個新的實例來代替它,這裏需要利用舊實例被銷燬時候存下來的數據。這些數據被稱爲“instance state”,是一個存在Bundle對象中的鍵值對集合。
缺省狀態下,系統會把每一個View對象保存起來(比如EditText對象中的文本,ListView中的滾動條位置等),即如果activity實例被銷燬和重建,那麼不需要你編碼,layot狀態會恢復到前次狀態。
但如果要存儲額外的數據的話,就需要調用這個函數,這個函數的使用非常簡單
這裏要注意,onSaveInstanceState()中的super.onSaveInstanceState(outState);不能刪除
系統會在用戶離開activity的時候調用這個函數,並且傳遞給它一個Bundle object,如果系統稍後需要重建這個activity實例,它會傳遞同一個Bundle object到onRestoreInstanceState() 和 onCreate() 方法中去