畫中畫

Android手持設備的畫中畫(PIP)功能使用戶可以將具有正在進行中的活動的應用程序的大小調整到一個小窗口中。 PIP對於視頻應用程序特別有用,因為在用戶自由執行其他操作的同時,內容仍會繼續播放。用戶可以通過SystemUI操縱此窗口的位置,並通過(最多三個)應用程序提供的操作與當前畫中畫的應用程序進行交互。

PIP要求支持它的應用程序顯式選擇加入,並在每個活動的基礎上工作。 (一個應用程序可以有多個活動,其中只有一個活動在PIP中。)活動通過調用enterPictureInPictureMode()請求輸入畫中畫,並以onPictureInPictureModeChanged()的形式接收活動回調。

使用setPictureInPictureParams()方法,活動可以在PIP和自定義操作中控制其縱橫比,這使用戶可以與活動進行交互而不必擴展活動。在PIP中,活動處於暫停但處於渲染狀態,並且不直接接收觸摸輸入或窗口焦點。一次只能在PIP中執行一項任務。

有關更多信息,請參閱Android開發者畫中畫文檔。

設備要求

要支持PIP,請在/android/frameworks/base/core/java/android/content/pm/PackageManager.java啟用PackageManager#FEATURE_PICTURE_IN_PICTURE系統功能。支持PIP的設備的最小寬度必須大於220dp。與分屏多窗口類似,PIP允許在屏幕上同時運行多個活動。因此,設備應具有足夠的CPU和RAM來支持此用例。

執行

大多數活動生命週期管理是在ActivityManagerWindowManager之間的系統中完成的。參考UI實現位於SystemUI包中。

對系統的修改不應影響兼容性測試套件(CTS)測試所定義的系統固有行為。 PIP的系統邏輯主要圍繞“固定”堆棧中的任務和活動的管理。這是一個快速的課程概述:

  • ActivityRecord跟踪每個活動的畫中畫狀態。為了防止用戶在某些情況下(例如在鎖定屏幕中或在VR期間)輸入PIP,請在checkEnterPictureInPictureState()添加案例。
  • ActivityManagerService從活動到請求輸入PIP的主要接口,以及從WindowManagerSystemUI調用以更改PIP活動狀態的接口。
  • ActivityStackSupervisor從叫ActivityManagerService或縮小的固定堆棧移動任務,更新WindowManager是必要的。
  • PinnedStackWindowController ActivityManagerWindowManager接口。
  • PinnedStackControllerSystemUI報告系統中的更改,例如顯示/隱藏的IME,更改的寬高比或更改的操作。
  • BoundsAnimationController以一種在調整大小時不會觸發配置更改的方式對PIP活動窗口進行動畫處理。
  • PipSnapAlgorithm在系統和SystemUI中使用的共享類,用於控制PIP窗口在屏幕邊緣附近的捕捉行為。

參考SystemUI提供了PIP的完整實現,該實現支持向用戶呈現自定義操作以及常規操作(例如擴展和解僱)。設備製造商可以基於這些更改,只要它們不影響CDD定義的內在行為即可。這是一個快速的課程概述:

  • PipManagerSystemUI即開始與組件SystemUI
  • PipTouchHandler觸摸處理程序,它控制操縱PIP的手勢。僅在PIP的輸入使用者處於活動狀態時才使用它(請參閱InputConsumerController )。可以在此處添加新手勢。
  • PipMotionHelper一個便利類,可跟踪PIP位置以及屏幕上允許的區域。調用ActivityManagerService來更新或設置PIP的位置和大小並為其設置動畫。
  • PipMenuActivityController啟動一個活動,該活動顯示當前在PIP中的活動提供的動作。此活動是任務覆蓋活動,它刪除覆蓋的輸入使用者以使其具有交互性。
  • PipMenuActivity菜單活動的實現。
  • PipMediaController當媒體會話以可能影響PIP上默認操作的方式更改時,更新SystemUI的偵聽器。
  • PipNotificationController確保在用戶使用PIP功能時激活通知的控制器。
  • PipDismissViewController當用戶開始與PIP交互時向用戶顯示的疊加層,指示可以將其關閉。

默認位置

有多種系統資源可控制PIP的默認位置:

  • config_defaultPictureInPictureGravity重力整數,它控制放置PIP的角,例如BOTTOM|RIGHT
  • config_defaultPictureInPictureScreenEdgeInsets從屏幕側面放置PIP的偏移量。
  • config_pictureInPictureDefaultSizePercentconfig_pictureInPictureDefaultAspectRatio屏幕寬度百分比config_pictureInPictureDefaultAspectRatio的組合控制PIP的大小。計算的默認PIP大小不應小於CTS和CDD定義的@dimen/default_minimal_size_pip_resizable_task
  • config_pictureInPictureSnapMode在規定的搶購行為PipSnapAlgorithm

設備實現不應更改CDD和CTS中定義的最小和最大縱橫比。

權限

AppOpsManagermaster/core/java/android/app/AppOpsManager.java )中的每包“應用程序操作”( OP_PICTURE_IN_PICTURE )使用戶可以通過系統設置在每個應用程序級別上控制PIP。當活動請求進入畫中畫模式時,設備實現需要遵守此檢查。

測驗

要測試PIP實現,請在/cts/hostsidetests/services/activitymanager下的主機端CTS測試中運行所有與畫中畫相關的測試,尤其是在ActivityManagerPinnedStackTests.java