新增對預測返回動畫的支援

使用系統返回 API 時,您可以選擇接收應用程式內動畫,並支援自訂轉場效果。

影片 1: 預測返回動畫

啟用這項功能後,應用程式會顯示返回首頁、跨活動和跨工作的動畫。

您也可以將 Material 元件的依附元件升級至 MDC Android 1.10.0 版,接收下列 Material 元件的動畫:

詳情請參閱 GitHub 上的 Material 元件開發人員指南

這部影片中的簡短範例是使用 Android「設定」應用程式,呈現跨活動和返回首頁的預測返回動畫。

  1. 在動畫中,使用者往回滑動,藉此返回上一個設定畫面。這是跨活動動畫的範例。
  2. 接著在上一個畫面中,使用者再次往回滑動,藉此預覽主畫面和桌布。這是返回首頁動畫的範例。
  3. 使用者持續向右滑動,出現視窗縮小為主畫面上圖示的動畫。
  4. 現在使用者已完全返回主畫面。

進一步瞭解如何新增預測返回手勢支援功能

新增自訂應用程式內轉場效果和動畫

您可以使用預測返回手勢,建立自訂應用程式內屬性動畫和轉場效果、自訂跨活動動畫,以及自訂跨元件動畫。

使用 Progress API 新增自訂轉場效果

在 AndroidX Activity 1.8.0-alpha01 以上版本中,您可以使用 Predictive Back Progress API,為應用程式的預測返回手勢開發自訂動畫。Progress API 可用於為檢視畫面建立動畫,但在 Fragments 之間建立動畫轉場時,會有限制。在 OnBackPressedCallback 中,我們已導入 handleOnBackProgressedhandleOnBackCancelledhandleOnBackStarted 方法,可在使用者滑動返回時為物件建立動畫。如果除了系統提供的預設動畫或 Material 元件動畫,您還需要其他自訂動畫,請使用這些方法。

我們預期大部分應用程式都會使用回溯相容的 AndroidX API,但 OnBackAnimationCallback 介面也提供類似的平台 API,方便您在 Android 14 開發人員預覽版 1 以上版本中進行測試。

搭配使用 AndroidX 轉場效果與 Progress API

在 Android 14 以上版本,Progress API 可搭配使用 AndroidX Transitions 1.5.0-alpha01 以上版本,建立預測返回轉場效果。

  1. 使用 TransitionManager#controlDelayedTransition (而非 beginDelayedTransition),在使用者滑動返回時顯示轉場效果。
  2. handleOnBackStarted 中建立轉場效果。
  3. currentFractionBackEvent.progress 建立關聯,公開使用者已滑動返回的距離,藉此在 handleOnBackProgressed 中的返回事件顯示轉場效果。
  4. 在使用者於 handleOnBackPressed 中採取返回手勢後完成轉場效果。
  5. 最後在 handleOnBackCancelled 內重設轉場效果的狀態。

以下影片、Kotlin 程式碼和 XML 示範如何使用 OnBackPressedCallback,在兩個方塊之間實作自訂轉場效果:

    class MyFragment : Fragment() {

    val transitionSet = TransitionSet().apply {
        addTransition(Fade(Fade.MODE_OUT))
        addTransition(ChangeBounds())
        addTransition(Fade(Fade.MODE_IN))
    }
    ...
    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)

        val callback = object : OnBackPressedCallback(enabled = false) {

            var controller: TransitionSeekController? = null

            @RequiresApi(34)
            override fun handleOnBackStarted(backEvent: BackEvent) {
                // Create the transition
                controller = TransitionManager.controlDelayedTransition(
                    binding.card,
                    transitionSet
                )
                changeTextVisibility(ShowText.SHORT)
            }

            @RequiresApi(34)
            override fun handleOnBackProgressed(backEvent: BackEvent) {
                // Play the transition as the user swipes back
                if (controller?.isReady == true) {
                    controller?.currentFraction = backEvent.progress
                }
            }

            override fun handleOnBackPressed() {
                // Finish playing the transition when the user commits back
                controller?.animateToEnd()
                this.isEnabled = false
            }

            @RequiresApi(34)
            override fun handleOnBackCancelled() {
                // If the user cancels the back gesture, reset the state
                transition(ShowText.LONG)
            }
        }

        binding.shortText.setOnClickListener {
            transition(ShowText.LONG)
            callback.isEnabled = true
        }

        this.requireActivity().onBackPressedDispatcher.addCallback(callback)
    }

    private fun transition(showText: ShowText) {
        TransitionManager.beginDelayedTransition(
            binding.card,
            transitionSet
        )
        changeTextVisibility(showText)
    }

    enum class ShowText { SHORT, LONG }
    private fun changeTextVisibility(showText: ShowText) {
        when (showText) {
            ShowText.SHORT -> {
                binding.shortText.isVisible = true
                binding.longText.isVisible = false
            }
            ShowText.LONG -> {
                binding.shortText.isVisible = false
                binding.longText.isVisible = true
            }
        }
    }
}
  
<?xml version="1.0" encoding="utf-8"?>
...
    <androidx.constraintlayout.widget.ConstraintLayout
        android:id="@+id/card"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        ...>

        <TextView
            android:id="@+id/short_text"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            ... />

        <TextView
            android:id="@+id/long_text"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:visibility="gone"
            .../>

    </androidx.constraintlayout.widget.ConstraintLayout>

使用預測返回轉場效果時,請注意下列事項:

  • 使用 isSeekingSupported,檢查轉場效果是否支援預測返回手勢。
  • 覆寫 isSeekingSupported,針對自訂轉場效果傳回 true。
  • 為每個動畫建立一個控制器。
  • AndroidX 轉換支援預測返回轉場效果,但架構轉換不支援。移除架構轉場效果,改用 Animator 和 AndroidX 轉場效果。
  • 預測返回轉場效果適用於搭載 Android 14 以上版本的裝置,且無法回溯相容。
  • 系統也支援使用 XML 場景建立的轉場效果。在 handleOnBackStarted 中,請將 TransitionSeekController 設為 TransitionManager.createSeekController 的結果,而非 controlDelayedTransition 的結果。

在 Android 14 以上版本新增自訂活動轉場效果

如要在 Android 14 以上版本中,確保自訂活動轉場效果可支援預測返回手勢,您可以使用 overrideActivityTransition,而不使用 overridePendingTransition。這表示使用者滑動返回時,系統會播放轉場效果動畫。

以下舉例說明這項機制的運作方式。假設在返回堆疊中,活動 B 位於活動 A 上方。您會採取下列做法處理自訂活動動畫:

  • 在活動 B 的 onCreate 方法中,呼叫開始或結束的轉場效果。
  • 在使用者前往活動 B 時,使用 OVERRIDE_TRANSITION_OPEN。在使用者滑動返回活動 A 時,則使用 OVERRIDE_TRANSITION_CLOSE
  • 如果指定 OVERRIDE_TRANSITION_CLOSEenterAnim 是活動 A 的進入動畫,exitAnim 則是活動 B 的結束動畫。

新支援:片段的預測返回功能

使用片段實作預測返回手勢時,有兩種方法。

使用現有的 API

建議您使用現有 API。這些 API 可讓您從螢幕邊緣滑動,透過手勢操控 Animator 或 Androidx 轉場效果。移動手勢是否超過門檻,會決定手勢是否完成,您會返回上一個片段,或者如果取消,您會留在目前的片段。詳情請參閱「使用動畫瀏覽各個片段」。

請注意以下因素:

  • 匯入 Transition 1.5.0 以上版本和 Fragment 1.7.0 以上版本。「Fragment」中大部分的預測返回手勢支援功能,都必須仰賴「Transition」的尋找動畫功能,而只有 Transition 1.5.0 以上版本才提供這項功能。
  • 使用 Fragment 搭配 FragmentManagerNavigation 元件 來處理返回堆疊。如果您自行管理返回堆疊,系統將不支援預測返回手勢。從 FragmentManager 不認識的回溯堆疊中遷移。
  • 部分程式庫提供預測返回手勢支援功能,請參閱說明文件瞭解詳情。
  • 支援 Animator 類別和 AndroidX Transition 程式庫。
  • 不支援 Animation 類別和架構 Transition 程式庫。
  • 預測動畫僅適用於搭載 Android 14 以上版本的裝置。

請在下列情況使用預測返回跨片段:

1.12.02-alpha02 以上版本起,部分 Material 動畫支援預測返回功能,包括 MaterialFadeThroughMaterialSharedAxisMaterialFade。注意:「MaterialContainerTransform」不支援預測返回。

使用回呼

您可以使用回呼建立跨片段轉場效果,但使用回呼時有已知的限制,使用者在滑動返回時無法看到先前的片段。如要建立與預測返回設計指南相對應的跨片段共用元素轉換,請執行下列步驟:

建立 OnBackPressedCallback。在 handleOnBackProgressed 中,縮放及移動程式碼片段。然後從返回堆疊彈出。接著,在回呼外使用 setSharedElementReturnTransition 執行共用元素轉換。

詳情請參閱 GitHub 上的程式碼範例

需求條件

請參閱下表,瞭解 targetSdkVersioncompileSdkVersion、裝置版本、依附元件、資訊清單旗標和片段旗標控管的項目。這份表格列出程式碼需求條件。

類別 動畫 compileSdk targetSdk 裝置版本 android:enableOnBackInvokedCallback 依附元件
系統動畫 返回首頁 33 不限 35 TRUE
跨活動 34 不限 35 TRUE
跨工作 34 不限 35 TRUE
平台 自訂跨活動 34 不限 35 TRUE
Progress API 平台 34 不限 34 TRUE
Material Design 元件 底部功能表 34 不限 34 TRUE Material 元件 1.10.0
側邊功能表 34 不限 34 TRUE Material 元件 1.10.0
導覽匣 34 不限 34 TRUE Material 元件 1.10.0
搜尋 34 不限 34 TRUE Material 元件 1.10.0
Jetpack 動畫 自訂 AndroidX 跨片段 34 不限 34 TRUE AndroidX 片段 1.7
自訂 AndroidX 轉場效果 34 不限 34 TRUE AndroidX 轉場效果 1.5
Progress API Jetpack 34 不限 34 TRUE AndroidX 活動 1.8

其他資源