PiP-এর জন্য আপনার অ্যাপ সেট-আপ করা

আপনার AndroidManifest.xml ফাইলের অ্যাক্টিভিটি ট্যাগে, নিম্নলিখিত কাজগুলি করুন:

  1. আপনার অ্যাপে 'ছবির-মধ্যে-ছবি' (PiP) ব্যবহার করবেন বলে ঘোষণা করতে, supportsPictureInPicture যোগ করে সেটি true-এ সেট করুন।
  2. আপনার অ্যাক্টিভিটি লেআউট কনফিগারেশন পরিবর্তন ম্যানেজ করে তা নির্দিষ্ট করতে, configChanges যোগ করুন এবং এটি orientation|screenLayout|screenSize|smallestScreenSize-এ সেট করুন। এইভাবে, PiP মোড ট্রানজিশনের সময় লেআউট পরিবর্তন হলে, আপনার অ্যাক্টিভিটি আবার চালু হয় না।
<activity
    android:name=".SnippetsActivity"
    android:exported="true"
    android:supportsPictureInPicture="true"
    android:configChanges="orientation|screenLayout|screenSize|smallestScreenSize"
    android:theme="@style/Theme.Snippets">

আপনার Compose কোডে, নিম্নলিখিত কাজগুলি করুন:

  1. Context-এ এই এক্সটেনশন যোগ করুন। অ্যাক্টিভিটি অ্যাক্সেস করার জন্য আপনি এই এক্সটেনশনটি পুরো গাইড জুড়ে একাধিকবার ব্যবহার করবেন।
    internal fun Context.findActivity(): ComponentActivity {
        var context = this
        while (context is ContextWrapper) {
            if (context is ComponentActivity) return context
            context = context.baseContext
        }
        throw IllegalStateException("Picture in picture should be called in the context of an Activity")
    }

Android 12-এর আগের ভার্সনের জন্য অ্যাপ থেকে বেরিয়ে আসার সময় PiP যোগ করুন

Android 12-এর আগের ভার্সনে PiP যোগ করতে, addOnUserLeaveHintProvider ব্যবহার করুন। Android 12-এর আগের ভার্সনে PiP যোগ করতে এইসব ধাপ অনুসরণ করুন:

  1. একটি ভার্সন গেট যোগ করুন যাতে এই কোডটি শুধুমাত্র O থেকে R পর্যন্ত ভার্সনে অ্যাক্সেস করা যায়।
  2. Context-কে 'কী' হিসেবে ব্যবহার করে DisposableEffect ব্যবহার করুন।
  3. DisposableEffect-এর মধ্যে, ল্যাম্বডা ব্যবহার করে onUserLeaveHintProvider ট্রিগার করা হলে কী আচরণ হবে তা নির্ধারণ করুন। ল্যাম্বডাতে, findActivity()-এ enterPictureInPictureMode() কল করুন এবং PictureInPictureParams.Builder().build()-এ পাস করুন।
  4. findActivity() ব্যবহার করে addOnUserLeaveHintListener যোগ করুন এবং ল্যাম্বডাতে পাস করুন।
  5. onDispose-এ, findActivity() ব্যবহার করে removeOnUserLeaveHintListener যোগ করুন এবং ল্যাম্বডাতে পাস করুন।

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O &&
    Build.VERSION.SDK_INT < Build.VERSION_CODES.S
) {
    val context = LocalContext.current
    DisposableEffect(context) {
        val onUserLeaveBehavior = Runnable {
            context.findActivity()
                .enterPictureInPictureMode(PictureInPictureParams.Builder().build())
        }
        context.findActivity().addOnUserLeaveHintListener(
            onUserLeaveBehavior
        )
        onDispose {
            context.findActivity().removeOnUserLeaveHintListener(
                onUserLeaveBehavior
            )
        }
    }
} else {
    Log.i("PiP info", "API does not support PiP")
}

Android 12-এর পরবর্তী ভার্সনের জন্য অ্যাপ থেকে বেরিয়ে আসার সময় PiP যোগ করুন

Android 12-এর পরে, PictureInPictureParams.Builder একটি মডিফায়ারের মাধ্যমে যোগ করা হয় যা অ্যাপের ভিডিও প্লেয়ারে পাস করা হয়।

  1. modifier তৈরি করে তাতে onGloballyPositioned-কে কল করুন। লেআউট কোঅর্ডিনেট পরবর্তী ধাপে ব্যবহার করা হবে।
  2. PictureInPictureParams.Builder()-এর জন্য ভেরিয়েবেল তৈরি করুন।
  3. SDK-টি S বা তার পরবর্তী ভার্সন কিনা তা চেক করতে একটি if স্টেটমেন্ট যোগ করুন। যদি তাই হয়, তাহলে বিল্ডারে setAutoEnterEnabled যোগ করুন এবং সোয়াইপ করার সময় PiP মোডে প্রবেশ করার জন্য এটি true-এ সেট করুন। এটি enterPictureInPictureMode-এর মাধ্যমে যাওয়ার চেয়ে আরও স্মুথ অ্যানিমেশন প্রদান করে।
  4. setPictureInPictureParams()-কে কল করতে findActivity() ব্যবহার করুন। builder-এ build()-কে কল করুন এবং পাস করুন।

val pipModifier = modifier.onGloballyPositioned { layoutCoordinates ->
    val builder = PictureInPictureParams.Builder()

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
        builder.setAutoEnterEnabled(true)
    }
    context.findActivity().setPictureInPictureParams(builder.build())
}
VideoPlayer(pipModifier)

PiP উইন্ডোর অ্যাস্পেক্ট রেশিও সেট করতে setAspectRatio ব্যবহার করুন

PiP উইন্ডোর অ্যাস্পেক্ট রেশিও সেট করতে, আপনি নির্দিষ্ট কোনও অ্যাস্পেক্ট রেশিও বেছে নিতে পারেন অথবা প্লেয়ারের ভিডিও সাইজের প্রস্থ ও উচ্চতা ব্যবহার করতে পারেন। আপনি media3 প্লেয়ার ব্যবহার করলে, অ্যাস্পেক্ট রেশিও সেট করার আগে প্লেয়ারটি নাল নয় এবং প্লেয়ারের ভিডিও সাইজ VideoSize.UNKNOWN-এর সমান নয় তা চেক করে নিন।

val context = LocalContext.current

val pipModifier = modifier.onGloballyPositioned { layoutCoordinates ->
    val builder = PictureInPictureParams.Builder()
    if (shouldEnterPipMode && player != null && player.videoSize != VideoSize.UNKNOWN) {
        val sourceRect = layoutCoordinates.boundsInWindow().toAndroidRectF().toRect()
        builder.setSourceRectHint(sourceRect)
        builder.setAspectRatio(
            Rational(player.videoSize.width, player.videoSize.height)
        )
    }

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
        builder.setAutoEnterEnabled(shouldEnterPipMode)
    }
    context.findActivity().setPictureInPictureParams(builder.build())
}

VideoPlayer(pipModifier)

আপনি কাস্টম প্লেয়ার ব্যবহার করলে, প্লেয়ারের উচ্চতা ও প্রস্থের উপর অ্যাস্পেক্ট রেশিও সেট করুন। এর জন্য আপনার প্লেয়ারের নির্দিষ্ট সিনট্যাক্স ব্যবহার করুন। মনে রাখবেন, শুরু করার সময় আপনার প্লেয়ারের সাইজ পরিবর্তন করা হলে, অ্যাস্পেক্ট রেশিওর বৈধ সীমার বাইরে চলে গেলে, আপনার অ্যাপ ক্র্যাশ করবে। অ্যাস্পেক্ট রেশিও কখন গণনা করা যেতে পারে, সেই বিষয়ে আপনাকে চেক যোগ করতে হতে পারে, যেমনটি media3 প্লেয়ারের জন্য করা হয়।