編輯:關於Android編程
Android Activity生命周期以及onSaveInstanceState、onRestoreInstanceState要點備忘
一般的,當Android activity的生命周期進入onPause後,Android系統緊接著就要回調:
protected void onSaveInstanceState(Bundle outState);
因此,通常,Android activity保存現場數據至少其中兩個思路和方法是:
(1)可以在onPause保存現場數據;
(2)也可以在onSaveInstanceState中保存現場數據。
然後到了後面,當activity再次onResume時候恢復出過去發生的現場數據。
(注意!Android保存現場數據的方法和思路很多,上面只是給出其中兩個最基本、最簡單的思路和方法。)
需要注意的一點是,有一種情況,Android系統是不會調用activity的onSaveInstanceState方法:當用戶按了返回鍵(back鍵)退出這個activity時。之所以這麼設計,我謹慎估計Android的系統設計思想認為:既然用戶已經選擇完全退出這個activity,那就沒有必要保存現場數據了。
Android的activity既然有onSaveInstanceState(),那麼,與之對應的onRestoreInstanceState(),在Android activity生命周期的什麼時候被Android系統回調呢?答案是:和onSaveInstanceState一樣,onRestoreInstanceState並不是Android activity生命周期中的一部分。兩者只是在Android activity生命周期發生過程中,Android系統參與進來的回調和過程。
如果要恢復activity的現場數據,雖然onRestoreInstanceState的方法名字看上去挺像回事,但實際上onRestoreInstanceState通常並不被開發者用來做“Restore”數據。然而,要明白的是,至少有一種情況發生時候,Android的onRestoreInstanceState將被系統回調:當activity被銷毀(onDestroy)然後又重新加載這個activity時,在onStart之後還沒有onResume時候將調用onRestoreInstanceState。聽上去很奇怪,既然銷毀了,怎麼又加載這個activity呢?這種情況的場景在哪兒?比如,當activity在橫豎屏切換時候,這種情況的場景就要發生,Android在橫豎排切換時候,將主動銷毀activity和重新創建一個新的activity出來,在此過程中,onRestoreInstanceState就要被回調。
這樣的描述有些過於抽象,寫實例代碼檢驗一下就清楚了。
我寫一個最簡單的Android activity,這個activity沒有任何內容,只是重寫了Android activity的各個生命周期中的方法,目的是追蹤activity在生命周期中各個方法的回調動作。保存一個系統時間戳(System.currentTimeMillis)作為標記,測試的Activity全部代碼如下:
package zhangphil.lifecycle; import android.app.Activity; import android.content.res.Configuration; import android.os.Bundle; import android.util.Log; public class MainActivity extends Activity { private final String TAG = zhangphil; private final String SAVED_DATA = saved_data; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // 判斷Android當前屏幕是橫屏還是豎屏。 if (this.getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT) { Log.d(TAG, 豎屏); } else { Log.d(TAG, 橫屏); } Log.d(TAG, onCreate); } @Override protected void onStart() { super.onStart(); Log.d(TAG, onStart); } @Override protected void onRestart() { super.onRestart(); Log.d(TAG, onRestart); } @Override protected void onResume() { super.onResume(); Log.d(TAG, onResume); } @Override protected void onPause() { super.onPause(); Log.d(TAG, onPause); } @Override protected void onStop() { super.onStop(); Log.d(TAG, onStop); } @Override protected void onDestroy() { super.onDestroy(); Log.d(TAG, onDestory); } @Override protected void onSaveInstanceState(Bundle outState) { super.onSaveInstanceState(outState); long time = System.currentTimeMillis(); outState.putLong(SAVED_DATA, time); Log.d(TAG, onSaveInstanceState -> 保存數據: + time); } @Override protected void onRestoreInstanceState(Bundle savedInstanceState) { super.onRestoreInstanceState(savedInstanceState); long time = savedInstanceState.getLong(SAVED_DATA, -1); Log.d(TAG, onRestoreInstanceState -> 恢復數據: + time); } }
運行這個Activity,然後旋轉機身從豎直方向變為水平方向,把這個activity從從標准豎屏切換到橫屏,Logcat追蹤打印的結果輸出說明了一切,如圖:
簡介項目需要...直接展示效果吧:原理使用UGUI提供的ScrollRect和ScrollBar組件實現基本滑動以及自己控制每次移動一頁來達到滑頁的效果。實現過程1.創建
Canvascanvas是一種抽象概念,是2D圖形系統中的重要部分,canvas一系列函數最終都是android 2D圖形庫Skia的一些列封裝,對應在SKCanvas.
ScaleType設置圖解圖文相配很清晰的看出每個屬性的效果,感覺 CENTER_CROP 比較有用,長寬自動適應 ImageView ,整個圖片自動縮略填充整個區域且居
在我們第一次安裝app的時候,有一些app會出現一個覆蓋在我們原來View上面的浮層view,用來做一個app的指示,讓用戶更快的知道app的整體架構和功能點。下面大家看