在 Android 8.0 中,用戶可以使用 Quicksettings 磁貼或顯示設置在自動旋轉和縱向旋轉模式之間切換。在 Android 9 中,我們更新了縱向旋轉模式,以通過固定當前屏幕旋轉來消除意外旋轉,即使設備位置發生變化也是如此。用戶可以在需要時通過按下導航欄中的新按鈕手動觸發旋轉。我們將縱向模式重命名為旋轉鎖定,並在自動旋轉關閉時激活。自動旋轉模式沒有變化。
當設備處於旋轉鎖定模式時,用戶可以將屏幕鎖定到頂部可見 Activity 支持的任何旋轉(給定當前系統約束)。如果頂部 Activity 可以在自動旋轉模式下多次旋轉呈現,則在旋轉鎖定模式下應該可以使用相同的選項,但基於 Activity 的screenOrientation
設置的一些例外情況。
旋轉鎖定模式通過在導航欄中顯示設備旋轉更改的按鈕來工作。為此,即使自動旋轉關閉,設備的方向傳感器也必須保持激活狀態。點擊此按鈕可有效設置用戶旋轉首選項( Settings.System.USER_ROTATION
)。 WindowManager 使用此首選項以及有關頂級活動和系統狀態的其他詳細信息來更改系統的旋轉。 WindowManager 在決定移動到另一個 Activity 時以何種旋轉方式呈現系統時,會繼續使用用戶旋轉首選項。
在活動之間移動時應保持用戶輪換偏好。但是,由於大多數手機用戶只想在短時間內處於橫向狀態,因此我們添加了自然方向偏差。只要係統旋轉更改為設備的自然方向,用戶旋轉首選項就會重置為設備的自然方向。對於大多數手機,設備的自然方向是縱向 (0º)。在使用僅縱向應用、鎖定手機或返回啟動器工作區時,通常會重置用戶旋轉偏好。
在過去十年中,用戶的輪換交互並沒有太大變化。鑑於他們之前在導航欄中的旋轉和按鈕定位歷史,用戶可能會發現很難發現此功能。出於這個原因,我們為旋轉按鈕添加了一個介紹模式,當它出現時會突出顯示它。介紹模式行為僅發生在前幾個按鈕交互中,之後介紹模式被禁用。
資源
Android 9 添加了對旋轉建議的支持。大多數更改都包含在以下文件中。
-
services/.../server/policy/PhoneWindowManager.java
:- 消耗
WindowOrientationListener
輸出的鉤子(MyOrientationListener
,負責監控傳感器以確定設備是否已旋轉) - 即使禁用自動旋轉,也保持
WindowOrientationListener
處於活動狀態(請參閱needSensorRunningLp()
) - 在給定用戶旋轉偏好、頂部 Activity
screenOrientation
設置和系統狀態的情況下計算系統旋轉(請參閱rotationForOrientationLw()
) - 確定頂部 Activity 是否可以旋轉到給定的旋轉(參見
isRotationChoicePossible()
)
- 消耗
-
SystemUI/.../statusbar/phone/NavigationBarFragment
:- 確定導航欄按鈕是否應顯示在來自
PhoneWindowManager
的旋轉建議回調中(請參閱onRotationProposal()
) - 處理何時隱藏旋轉導航欄按鈕(請參閱
setRotateSuggestionButtonState(false)
的調用) - 處理按鈕超時,包括隱藏導航欄時的特殊情況(通常全屏)
- 返回設備的自然方向時重置用戶偏好(
mRotationWatcher
) - 為導航欄按鈕動畫選擇適當的樣式,在
NavigationBarView
中應用(請參閱onRotationProposal()
) - 添加介紹模式邏輯,包括專門的動畫(參見
Settings.Secure.NUM_ROTATION_SUGGESTIONS_ACCEPTED
的參考) - 實現 disable2 旋轉標誌(參見
disable()
)
- 確定導航欄按鈕是否應顯示在來自
-
SystemUI/.../statusbar/phone/NavigationBarView.java
:- 樣式按鈕圖標動畫以匹配待定旋轉(請參閱
updateRotateSuggestionButtonStyle()
) - 處理按鈕可見性更改(請參閱
setRotateButtonVisibility()
),包括在某些輔助功能服務處於活動狀態時隱藏旋轉按鈕的邏輯(考慮最右側的導航欄按鈕堆棧排名)
- 樣式按鈕圖標動畫以匹配待定旋轉(請參閱
-
SystemUI/res/layout/menu_ime.xml
:- 包括用於旋轉按鈕的新
KeyButtonView
,堆疊在菜單和 IME/鍵盤選擇器上方但在輔助功能按鈕下方
- 包括用於旋轉按鈕的新
SystemUI/res/drawable/ic_sysbar_rotate_button.xml
:- 用於為旋轉導航欄按鈕設置動畫的複雜
AnimatedVectorDrawable
- 樣式(在
SystemUI/res/values/styles.xml
)用於設置旋轉的開始和結束角度,因此可以使用相同的可繪製對象為各種開始和結束旋轉設置動畫 - 圖標著色通過
TintedKeyButtonDrawable
設置
- 用於為旋轉導航欄按鈕設置動畫的複雜
執行
Android 9 包含所有必要的更改,以使旋轉建議適用於使用軟件導航鍵(返回、主頁等)的設備。
使用希望實現此功能的硬件導航鍵創建設備的設備製造商將需要設計和實現自己的系統 UI 功能或禁用該功能。建議當設備與當前系統旋轉成 90º 或 180º 並可以快速訪問時,任何引入的表面都易於使用。由於這些原因,不建議使用通知(如 IME/鍵盤選擇器所做的那樣)。
使用此功能的硬件要求與使用自動旋轉的要求相同。
當自動旋轉關閉時,系統出於任何原因更改為設備的自然旋轉時,用戶旋轉首選項 ( Settings.System.USER_ROTATION
) 必須重置為設備的自然旋轉,以實現實現一致性。提供的實現會執行此操作(請參閱NavigationBarFragment.mRotationWatcher
)。
StatusBarManager.disable2
中有一個新標誌可以暫時阻止輪換建議的出現。請參閱StatusBarManager.DISABLE2_ROTATE_SUGGESTIONS
。在所有實現中都必須遵守此標誌,因為它由關鍵系統應用程序使用,包括設置嚮導。提供的實現支持這一點(參見NavigationBarFragment.disable()
)。
如果可能,我們強烈建議啟用該功能並遵循 AOSP 實施。我們的目標是保持設備之間的旋轉體驗相似,反映當今大多數手機在自動旋轉和縱向鎖定之間的體驗一致性。
定制
由於輪換建議僅在輪換鎖定模式(自動輪換關閉)中出現,因此可以通過選擇默認自動輪換關閉來選擇該功能是否對新安裝默認開啟。請參閱SettingsProvider/res/values/defaults.xml
中的def_accelerometer_rotation
以進行默認更改。
用戶可以通過快速設置或顯示設置中的旋轉圖塊輕鬆更改自動旋轉是否處於活動狀態(無論默認情況如何)。
驗證
對於測試,可以通過更改門控Settings.Secure
值來關閉和打開該功能。這可以通過從特權 adb 實例運行以下命令來輕鬆完成:
adb shell settings put secure show_rotation_suggestions <x>
將 x 設置為0
表示關閉, 1
表示打開。
對於測試,可以通過更改關聯的Settings.Secure
值來重置引入模式。這可以通過從特權 adb 實例運行以下命令來輕鬆完成:
adb shell settings put secure num_rotation_suggestions_accepted 0