Aplikacja nie powinna przechodzić w tryb obrazu w obrazie w tych sytuacjach:
- Jeśli film zostanie zatrzymany lub wstrzymany.
- Jeśli jesteś na innej stronie aplikacji niż odtwarzacz.
Aby kontrolować, kiedy aplikacja przechodzi w tryb obrazu w obrazie, dodaj zmienną, która śledzi stan odtwarzacza, używając mutableStateOf.
Przełącz stan w zależności od tego, czy film jest odtwarzany
Aby przełączać stan w zależności od tego, czy odtwarzacz odtwarza film, dodaj detektor do odtwarzacza. Przełącz stan zmiennej stanu w zależności od tego, czy odtwarzacz odtwarza treści:
player.addListener(object : Player.Listener { override fun onIsPlayingChanged(isPlaying: Boolean) { shouldEnterPipMode = isPlaying } })
Przełącz stan w zależności od tego, czy odtwarzacz został zwolniony
Gdy odtwarzacz zostanie zwolniony, ustaw zmienną stanu na false:
fun releasePlayer() { shouldEnterPipMode = false }
Używanie stanu do określania, czy tryb obrazu w obrazie jest włączony (Android 11 i starsze)
- Ponieważ dodanie PiP przed wersją 12 wymaga użycia
DisposableEffect, musisz utworzyć nową zmienną,rememberUpdatedState, ze zmienną stanu ustawioną nanewValue. Dzięki temu zaktualizowana wersja będzie używana wDisposableEffect. W wyrażeniu lambda, które definiuje zachowanie po aktywowaniu
OnUserLeaveHintListener, dodaj instrukcjęifze zmienną stanu wokół wywołaniaenterPictureInPictureMode():val currentShouldEnterPipMode by rememberUpdatedState(newValue = shouldEnterPipMode) 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 { if (currentShouldEnterPipMode) { 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") }
Używanie stanu do określania, czy tryb obrazu w obrazie jest włączony (Android 12 i nowsze)
Przekaż zmienną stanu do setAutoEnterEnabled, aby aplikacja przechodziła w tryb obrazu w obrazie tylko w odpowiednim momencie:
val pipModifier = modifier.onGloballyPositioned { layoutCoordinates -> val builder = PictureInPictureParams.Builder() // Add autoEnterEnabled for versions S and up if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) { builder.setAutoEnterEnabled(shouldEnterPipMode) } context.findActivity().setPictureInPictureParams(builder.build()) } VideoPlayer(pipModifier)
Aby uzyskać płynną animację, użyj setSourceRectHint
Interfejs API setSourceRectHint tworzy płynniejszą animację podczas przechodzenia do trybu obrazu w obrazie. W Androidzie 12 i nowszych wersjach zapewnia też płynniejszą animację podczas wychodzenia z trybu obrazu w obrazie.
Dodaj ten interfejs API do kreatora obrazu w obrazie, aby wskazać obszar aktywności, który jest widoczny po przejściu do trybu obrazu w obrazie.
- Dodaj
setSourceRectHint()dobuildertylko wtedy, gdy stan określa, że aplikacja powinna przejść w tryb obrazu w obrazie. Dzięki temu nie trzeba obliczaćsourceRect, gdy aplikacja nie musi przechodzić w tryb obrazu w obrazie. - Aby ustawić wartość
sourceRect, użyj wartościlayoutCoordinatespodanych przez funkcjęonGloballyPositionedw modyfikatorze. - Wywołaj
setSourceRectHint()nabuilderi przekaż zmiennąsourceRect.
val context = LocalContext.current val pipModifier = modifier.onGloballyPositioned { layoutCoordinates -> val builder = PictureInPictureParams.Builder() if (shouldEnterPipMode) { val sourceRect = layoutCoordinates.boundsInWindow().toAndroidRectF().toRect() builder.setSourceRectHint(sourceRect) } if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) { builder.setAutoEnterEnabled(shouldEnterPipMode) } context.findActivity().setPictureInPictureParams(builder.build()) } VideoPlayer(pipModifier)