切換需注意資料儲存和恢複
在Android學習筆記(三六):橫屏豎屏的切換中,我們配置了兩個layout,一個使用者普通的portrait,一個使用者landsapce方式。如果只有一個layout,我們沿用上一個例子,刪除了在layout-land/中的xml檔案,則在螢幕切換時,會按照原來的排版,適配新的螢幕。程式我進行了簡化,每按一次pick,就加一,用此來跟蹤是否需要進行資料儲存和恢複,如下:
public class Chapter19Test3 extends Activity{private Button pickButton = null;private int count = 0; protected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setupViews();}private void setupViews(){setContentView(R.layout.chapter_19_test1);pickButton = (Button)findViewById(R.id.c19_pick);pickButton.setText("Pick " + count);pickButton.setOnClickListener(new View.OnClickListener() {public void onClick(View v) {count ++;pickButton.setText("Pick " + count);}});}}
這是一個很簡單的例子。我們發現在轉屏的時候,是重新賦值。也就是也同樣經過了destroy和create的階段,同樣需要進行儲存和恢複。我們點擊Pick按鈕4次,通過模擬器Ctrl+F12進行切換,count重新歸0。右邊是另外兩個例子,widget是一個輸入框,我們可以看到如果我們修改了輸入況中的值,旋轉之後是不改變的,因為widget的內容,系統會幫我們處理,而widget外的我們需要處理。如果我們在例子中跟蹤onCreate和onDestroy會發現,每次轉動螢幕的時候,都會調用destroy,然後create。而且每次切換,destroy-create-destroy-create,但是我不確定是否只是模擬器,在實際target裝置上是否也如此,可以看到切換後有一個明顯UI的變更,可以解釋為什麼重新create兩次。
關於如何資料儲存和恢複,見Android學習筆記(三六):橫屏豎屏的切換 。
不進行螢幕切換
由於某些原因,例如遊戲,在切換畫面的過程中,由於動作慢導致遊戲失敗,我們希望不觸發螢幕切換。我們在AndroidManifest.xml中在activity進行設定:
<activity android:name=".xxxxx" ...... android:screenOrientation="portrait" />
即使我們在layout-land/補充了相關的layout的xml,也不會觸發橫屏和豎屏的布局的轉換。
需要注意的是,我們跟蹤發現,切換也同樣會導致destroy->re-create,也就是需要進行資料的儲存和恢複。由於Android的硬體裝置類型很多,有些是通過smartkey,有些是通過物理鍵盤的開啟,而在模擬器中就是“CTRL+F12”來強制進行螢幕切換。如果我們需要和iPhone那樣有定位陀螺儀來觸發螢幕的切換,我們只需在AndroidManifest.xml中<activity android:name=".xxxxx"
...... android:screenOrientation="sensor" />即可。
自己控制旋轉
我們如果希望自己控制螢幕選擇,在收到相關的旋轉螢幕的事件後,由程式自行控制處理,而不是系統自動處理。可以通過以下步驟:
一、在AndroidManifest.xml中的activity,增加android:configChanges屬性,表示我們需要自行控制這些處理
<activity android:name=".xxx" ... android:configChanges="keyboardHidden|orientation" />
有一點比較奇特的就是,如果我們只設定orientation或者keyboardHidden,會有一些奇怪的現象,可能只出現在模擬器,因為CTRL+F12是模擬器的鍵盤操作。不確定實際裝置會否如此。模擬器切換觸發了key和orientation兩個事件,我們現預設這種情況。
二、在程式中通過onConfigurationChanged()獲得相關的事件並進行處理。
在切換的時候,系統,通過onConfigurationChanged()包括事件,系統將不會自行去處理介面,也就是不會因為重新描繪畫面而對activity進行destroy和re-create,也就是最重要的,不會導致資料的重初始化而導致需對資料進行儲存和恢複,僅此也是一種比較便捷的處理方式。
public void onConfigurationChanged(Configuration newConfig) {super.onConfigurationChanged(newConfig);setupViews();}
一般而且,我們可以通過newConfig來排斷但前的狀態,例如用switch(newConfig.orientation)來判斷當前方向,而判斷如何處理,在這個例子中,簡單地重繪UI就可以了。
相關連結:
我的Android開發相關文章