إتاحة استخدام صور متحركة لإيماءة إظهار شاشة الرجوع في "طرق العرض"

يمكنك إنشاء صور متحركة وانتقالات مخصّصة للسمات داخل التطبيق، وصور متحركة مخصّصة للانتقال بين الأنشطة، وصور متحركة مخصّصة للانتقال بين الأجزاء باستخدام إيماءات إظهار شاشة الرجوع باستخدام Views أو Compose. لتجربة طريقة Compose، يُرجى الاطّلاع على مقالة إضافة صور متحركة لإيماءة إظهار شاشة الرجوع.

إضافة انتقالات مخصّصة باستخدام Progress API

باستخدام الإصدار 1.8.0-alpha01 من AndroidX Activity أو الإصدارات الأحدث، يمكنك استخدام واجهات برمجة التطبيقات Predictive Back Progress لتطوير صور متحركة مخصّصة لإيماءة إظهار شاشة الرجوع في تطبيقك. وتكون واجهات برمجة التطبيقات Progress مفيدة في تحريك طرق العرض، ولكنّها تتضمّن قيودًا عند تحريك الانتقالات بين الأجزاء. في OnBackPressedCallback، قدّمنا الطرق handleOnBackProgressed وhandleOnBackCancelled وhandleOnBackStarted لتحريك العناصر أثناء تمرير المستخدم للخلف. استخدِم هذه الطرق إذا كنت بحاجة إلى تخصيص أكثر من الصور المتحركة التلقائية التي يوفّرها النظام أو الصور المتحركة لمكوّنات Material.

نتوقّع أن تستخدم معظم التطبيقات واجهات برمجة تطبيقات AndroidX المتوافقة مع الأنظمة القديمة، ولكن هناك أيضًا واجهات برمجة تطبيقات مماثلة للنظام الأساسي ضمن واجهة OnBackAnimationCallback المتاحة للاختبار في الإصدار 14 من نظام التشغيل Android والإصدارات الأحدث.

استخدام واجهات برمجة التطبيقات Progress API مع AndroidX Transitions

يمكن استخدام واجهات برمجة التطبيقات Progress API مع الإصدار 1.5.0-alpha01 من AndroidX Transitions أو الإصدارات الأحدث على نظام التشغيل Android 14 والإصدارات الأحدث لإنشاء انتقالات "إيماءة إظهار شاشة الرجوع".

  1. استخدِم TransitionManager#controlDelayedTransition بدلاً من beginDelayedTransition لتشغيل الانتقالات أثناء تمرير المستخدم سريعًا للخلف.
  2. أنشئ الانتقال في غضون handleOnBackStarted.
  3. يمكنك تشغيل الانتقال مع حدث الرجوع في "handleOnBackProgressed" من خلال ربط "currentFraction" بـ "BackEvent.progress"، ما يوضّح مدى تمرير المستخدم للخلف.
  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.

موارد إضافية