Google se compromete a impulsar la igualdad racial para las comunidades afrodescendientes. Obtén información al respecto.

Compatibilidad con pantalla en pantalla

Android 8.0 (API nivel 26) permite iniciar actividades en modo de pantalla en pantalla (PIP). PIP es un tipo especial de modo de multiventana que se usa principalmente para la reproducción de videos. Permite al usuario ver un video en una ventana pequeña fijada en una esquina de la pantalla mientras navega entre apps o explora contenido en la pantalla principal.

PIP aprovecha las API de multiventana disponibles en Android 7.0 para proporcionar la ventana de video fijada superpuesta. Para agregar PIP a tu app, debes registrar las actividades que admitan PIP, cambiar tu actividad al modo de PIP según sea necesario y asegurarte de que los elementos de la IU estén ocultos y la reproducción de video continúe cuando la actividad esté en modo de PIP.

La ventana de PIP aparece en la capa superior de la pantalla, en una esquina que elige el sistema. Puedes arrastrar la ventana de PIP a otra ubicación. Cuando presionas la ventana, aparecen dos controles especiales: un botón para activar o desactivar la pantalla completa (en el centro de la ventana) y un botón de cierre (una "X" en la esquina superior derecha).

Tu app controla cuándo la actividad actual ingresa en modo de PIP. Estos son algunos ejemplos:

  • Una actividad puede ingresar al modo de PIP cuando el usuario presiona el botón de inicio o el botón de recientes para elegir otra app. (Así es como Google Maps sigue mostrando indicaciones mientras el usuario ejecuta otra actividad al mismo tiempo).
  • Tu app puede mover un video al modo de PIP cuando el usuario navega hacia atrás desde el video para explorar otro contenido.
  • Tu app puede cambiar un video al modo de PIP mientras un usuario mira el final de un episodio de contenido. La pantalla principal muestra información promocional o de resumen sobre el próximo episodio de la serie.
  • Tu app puede proporcionar una manera para que los usuarios pongan en cola contenido adicional mientras miran un video. El video sigue reproduciéndose en modo de PIP mientras la pantalla principal muestra una actividad de selección de contenido.

Declaración de compatibilidad con pantalla en pantalla

De manera predeterminada, el sistema no admite automáticamente PIP para apps. Si deseas admitir PIP en tu app, establece android:supportsPictureInPicture y android:resizeableActivity en true para registrar tu actividad de video en el manifiesto. Además, especifica que tu actividad maneja los cambios de configuración de diseño para que no se reinicie cuando se realicen cambios de diseño durante las transiciones del modo de PIP.

    <activity android:name="VideoActivity"
        android:resizeableActivity="true"
        android:supportsPictureInPicture="true"
        android:configChanges=
            "screenSize|smallestScreenSize|screenLayout|orientation"
        ...
    

Cómo cambiar tu actividad a pantalla en pantalla

Para ingresar al modo de pantalla en pantalla, una actividad debe llamar a enterPictureInPictureMode(). Por ejemplo, en el siguiente código, se cambia una actividad al modo de PIP cuando el usuario hace clic en un botón exclusivo en la IU de la app:

Kotlin

    override fun onActionClicked(action: Action) {
        if (action.id.toInt() == R.id.lb_control_picture_in_picture) {
            activity?.enterPictureInPictureMode()
            return
        }
    }
    

Java

    @Override
    public void onActionClicked(Action action) {
        if (action.getId() == R.id.lb_control_picture_in_picture) {
            getActivity().enterPictureInPictureMode();
            return;
        }
        ...
    }
    

Es posible que desees incluir lógica que cambie una actividad al modo de PIP en lugar de pasar a segundo plano. Por ejemplo, Google Maps cambia al modo de PIP si el usuario presiona el botón de inicio o recientes mientras la app está navegando. Para solucionar este caso, anula onUserLeaveHint():

Kotlin

    override fun onUserLeaveHint() {
        if (iWantToBeInPipModeNow()) {
            enterPictureInPictureMode()
        }
    }
    

Java

    @Override
    public void onUserLeaveHint () {
        if (iWantToBeInPipModeNow()) {
            enterPictureInPictureMode();
        }
    }
    

Cómo administrar la IU durante el modo de pantalla en pantalla

Cuando la actividad ingresa al modo de pantalla en pantalla o sale de este, el sistema llama a Activity.onPictureInPictureModeChanged() o a Fragment.onPictureInPictureModeChanged().

Debes anular estas devoluciones de llamada para volver a dibujar los elementos de la IU de la actividad. Ten en cuenta que en modo de PIP tu actividad se muestra en una ventana pequeña. Los usuarios no pueden interactuar con los elementos de la IU cuando están en modo de PIP y los detalles de los elementos pequeños de la IU pueden ser difíciles de ver. Las actividades de reproducción de video con una IU mínima proporcionan la mejor experiencia del usuario. La actividad solo debe mostrar los controles de reproducción de video. Quita otros elementos de la IU antes de que la actividad ingrese a PIP y restablécelos cuando vuelva a ser de pantalla completa:

Kotlin

    override fun onPictureInPictureModeChanged(isInPictureInPictureMode: Boolean,
                                               newConfig: Configuration) {
        if (isInPictureInPictureMode) {
            // Hide the full-screen UI (controls, etc.) while in picture-in-picture mode.
        } else {
            // Restore the full-screen UI.
        }
    }
    

Java

    @Override
    public void onPictureInPictureModeChanged (boolean isInPictureInPictureMode, Configuration newConfig) {
        if (isInPictureInPictureMode) {
            // Hide the full-screen UI (controls, etc.) while in picture-in-picture mode.
        } else {
            // Restore the full-screen UI.
            ...
        }
    }
    

Cómo agregar controles

La ventana de PIP puede mostrar controles cuando el usuario abre el menú de la ventana (tocando la ventana en un dispositivo móvil o seleccionando el menú desde el control remoto del televisor).

Si una app tiene una sesión multimedia activa, aparecerán los controles de reproducción, pausa, siguiente y anterior.

También puedes especificar acciones personalizadas de manera explícita. Para ello, compila PictureInPictureParams con PictureInPictureParams.Builder.setActions() antes de ingresar al modo de PIP y pasa los parámetros cuando ingreses al modo de PIP con enterPictureInPictureMode(android.app.PictureInPictureParams) o setPictureInPictureParams(android.app.PictureInPictureParams). Cuidado. Si intentas agregar más de getMaxNumPictureInPictureActions(), solo obtendrás el número máximo.

Cómo continuar con la reproducción de video en modo de pantalla en pantalla

Cuando tu actividad cambia a PIP, el sistema coloca la actividad en estado pausado y llama al método onPause() de la actividad. La reproducción de video no debe pausarse y debe seguir reproduciéndose si la actividad está pausada en modo de PIP.

En Android 7.0 y versiones posteriores, debes pausar y reanudar la reproducción de video cuando el sistema llame a onStop() y onStart() de tu actividad. De esa forma, puedes evitar tener que verificar si la app está en modo de PIP en onPause() y continuar explícitamente la reproducción.

Si tienes que pausar la reproducción en la implementación de onPause(), verifica el modo de PIP llamando a isInPictureInPictureMode() y maneja la reproducción de manera adecuada, por ejemplo:

Kotlin

    override fun onPause() {
        super.onPause()
        // If called while in PIP mode, do not pause playback
        if (isInPictureInPictureMode) {
            // Continue playback
        } else {
            // Use existing playback logic for paused Activity behavior.
        }
    }
    

Java

    @Override
    public void onPause() {
        // If called while in PIP mode, do not pause playback
        if (isInPictureInPictureMode()) {
            // Continue playback
            ...
        } else {
            // Use existing playback logic for paused Activity behavior.
            ...
        }
    }
    

Cuando tu actividad vuelve al modo de pantalla completa, el sistema reanuda la actividad y llama al método onResume().

Cómo usar una sola actividad de reproducción para pantalla en pantalla

En tu app, un usuario puede seleccionar un video nuevo cuando busca contenido en la pantalla principal, mientras una actividad de reproducción de video está en modo de PIP. Reproduce el video nuevo en la actividad de reproducción existente en modo de pantalla completa, en lugar de iniciar una actividad nueva que podría confundir al usuario.

A fin de asegurarte de que se use una sola actividad para las solicitudes de reproducción de video y se pase al modo de PIP o se saque de él según sea necesario, configura android:launchMode en singleTask en tu manifiesto:

    <activity android:name="VideoActivity"
        ...
        android:supportsPictureInPicture="true"
        android:launchMode="singleTask"
        ...
    

En la actividad, anula onNewIntent() y maneja el video nuevo, lo que detiene cualquier reproducción de video existente si es necesario.

Prácticas recomendadas

PIP puede estar inhabilitado en dispositivos que tienen poca RAM. Antes de que tu app use PIP, verifica que esté disponible llamando a hasSystemFeature(PackageManager.FEATURE_PICTURE_IN_PICTURE).

El modo de PIP está destinado a actividades que reproducen video en pantalla completa. Cuando cambies tu actividad al modo de PIP, evita mostrar algo que no sea contenido de video. Realiza un seguimiento de cuándo tu actividad ingresa al modo de PIP y oculta los elementos de la IU, como se describe en Cómo administrar la IU durante el modo de pantalla en pantalla.

Dado que la ventana de PIP se muestra como una ventana flotante en la esquina de la pantalla, debes evitar mostrar información importante en la pantalla principal en cualquier área que pueda ocultar la ventana de PIP.

Cuando una actividad está en modo de PIP, de manera predeterminada, no recibe el foco de entrada. Para recibir eventos de entrada mientras está en modo de PIP, usa MediaSession.setCallback(). Para obtener más información sobre el uso de setCallback(), consulta Cómo mostrar una tarjeta de Está sonando.

Cuando tu app está en modo de PIP, la reproducción de video en la ventana de PIP puede causar interferencia de audio con otra app, como una app de reproductor de música o de búsqueda por voz. Para evitarlo, solicita el foco de audio cuando comiences a reproducir el video y maneja las notificaciones de cambio de foco de audio, como se describe en Cómo administrar el foco de audio. Si recibes una notificación de pérdida de foco de audio cuando se usa el modo de PIP, pausa o detén la reproducción de video.

Código de ejemplo adicional

Para descargar una app de muestra escrita en Android, consulta Muestra de pantalla en pantalla. Para descargar una app de muestra escrita en Kotlin, consulta Muestra de Android PictureInPicture (Kotlin).