Transformaciones

Transcodificación entre formatos

Puedes especificar los formatos de audio y video de salida que deseas producir cuando compilas Transformer. Por ejemplo, el siguiente código muestra cómo configurar Transformer para que genere video H.264/AVC y audio AAC:

Kotlin

Transformer.Builder(context)
    .setVideoMimeType(MimeTypes.VIDEO_H264)
    .setAudioMimeType(MimeTypes.AUDIO_AAC)
    .build()

Java

new Transformer.Builder(context)
    .setVideoMimeType(MimeTypes.VIDEO_H264)
    .setAudioMimeType(MimeTypes.AUDIO_AAC)
    .build();

Si el formato de los medios de entrada ya coincide con la configuración de audio o video, Transformer cambia automáticamente a la transmuxing, es decir, copia las muestras comprimidas del contenedor de entrada al contenedor de salida sin modificaciones. Esto evita el costo de procesamiento y la posible pérdida de calidad de la decodificación y la recodificación en el mismo formato.

Cómo quitar audio o video

Quita audio o video con EditedMediaItem.Builder, por ejemplo:

Kotlin

EditedMediaItem.Builder(inputMediaItem).setRemoveAudio(true).build()

Java

new EditedMediaItem.Builder(inputMediaItem).setRemoveAudio(true).build();

Cómo recortar un clip

Puedes quitar cualquier contenido multimedia que esté fuera de las marcas de tiempo de inicio y finalización especificadas si configuras el recorte en el elemento multimedia de entrada. Por ejemplo, para producir un clip que contenga solo el contenido multimedia entre los 10 y los 20 segundos, haz lo siguiente:

Kotlin

val inputMediaItem = MediaItem.Builder()
    .setUri(uri)
    .setClippingConfiguration(
        ClippingConfiguration.Builder()
            .setStartPositionMs(10_000)
            .setEndPositionMs(20_000)
            .build())
    .build()

Java

MediaItem inputMediaItem =
    new MediaItem.Builder()
        .setUri(uri)
        .setClippingConfiguration(
            new MediaItem.ClippingConfiguration.Builder()
                .setStartPositionMs(10_000)
                .setEndPositionMs(20_000)
                .build())
        .build();

Listas de edición de MP4

Para un recorte más rápido, Transformer admite listas de edición MP4, lo que permite ediciones más eficientes de "solo recorte" sin volver a transcodificar el video completo. Este método utiliza muestras codificadas existentes y un "anuncio previo al video" dentro de la lista de edición, que le indica al reproductor que comience la reproducción en un punto específico, lo que permite omitir de manera eficaz el segmento inicial no deseado.

Para que las ediciones de recorte sean mucho más rápidas, llama a experimentalSetMp4EditListTrimEnabled(true).

Kotlin

Transformer.Builder(context)
    .experimentalSetMp4EditListTrimEnabled(true)
    .build()

Java

new Transformer.Builder(context)
    .experimentalSetMp4EditListTrimEnabled(true)
    .build();

Es importante tener en cuenta que no todos los reproductores multimedia admiten la posición "previo al video". Esto significa que, cuando se usa un reproductor de este tipo, el archivo comenzará a reproducirse desde el principio absoluto de la muestra codificada, independientemente de la información de la lista de edición que pueda especificar un punto de partida diferente.

Cómo optimizar los cortes

Para reducir la latencia del recorte del inicio de un video, habilita la optimización del recorte.

Kotlin

Transformer.Builder(context)
    .experimentalSetTrimOptimizationEnabled(true)
    .build()

Java

new Transformer.Builder(context)
    .experimentalSetTrimOptimizationEnabled(true)
    .build();

Esto acelera la exportación, ya que decodifica y vuelve a codificar la menor cantidad posible del video y, luego, une los datos recodificados con el resto del video original. La optimización se basa en la capacidad de unir parte del archivo de entrada con la salida recién codificada, lo que significa que el formato de salida del codificador y el formato de entrada deben ser compatibles. Por ejemplo, si el archivo se produjo originalmente en un dispositivo con una implementación de codificador diferente, es probable que no sea posible aplicar la optimización. Para que la optimización se realice correctamente, el codificador proporcionado a Transformer a través de EncoderFactory debe tener un nivel y un perfil compatibles con el formato de entrada.

Esta optimización solo funciona con entradas MP4 de un solo recurso sin efectos, excepto los efectos de video sin operación y las rotaciones divisibles por 90 grados. Si la optimización falla, Transformer vuelve automáticamente a la exportación normal y registra el resultado de la optimización en ExportResult.OptimizationResult.

Estamos validando esta funcionalidad y esperamos que deje de ser experimental en una versión posterior.

Ediciones de video

EditedMediaItems tienen listas de procesadores de audio y efectos de video para aplicar en orden. La biblioteca incluye implementaciones de efectos de video para casos de uso comunes, o bien puedes escribir efectos personalizados y pasarlos cuando compiles elementos multimedia editados.

Puedes cambiar la escala de los medios, lo que puede ser útil para ahorrar recursos de procesamiento o ancho de banda cuando se trabaja con entradas de muy alta resolución, como videos en 4K u 8K. Por ejemplo, para escalar proporcionalmente a 480 píxeles de alto, haz lo siguiente:

Kotlin

EditedMediaItem.Builder(MediaItem.fromUri(uri))
    .setEffects(Effects(
        /* audioProcessors= */ listOf(),
        /* videoEffects= */ listOf(Presentation.createForHeight(480))
    )).build()

Java

new EditedMediaItem.Builder(MediaItem.fromUri(uri))
    .setEffects(new Effects(
        /* audioProcessors= */ ImmutableList.of(),
        /* videoEffects= */ ImmutableList.of(Presentation.createForHeight(480))))
    .build();

Como alternativa, puedes ajustar el tamaño según un factor determinado, por ejemplo, para reducirlo a la mitad:

Kotlin

val editedMediaItem = EditedMediaItem.Builder(MediaItem.fromUri(uri))
    .setEffects(Effects(
        /* audioProcessors= */ listOf(),
        /* videoEffects= */ listOf(
            ScaleAndRotateTransformation.Builder().setScale(.5f, .5f).build())
    )).build()

Java

new EditedMediaItem.Builder(MediaItem.fromUri(uri))
    .setEffects(new Effects(
        /* audioProcessors= */ ImmutableList.of(),
        /* videoEffects= */ ImmutableList.of(
            new ScaleAndRotateTransformation.Builder().setScale(.5f, .5f).build())))
    .build();

Puedes configurar la rotación de la misma manera:

Kotlin

EditedMediaItem.Builder(MediaItem.fromUri(uri))
    .setEffects(Effects(
        /* audioProcessors= */ listOf(),
        /* videoEffects= */ listOf(
            ScaleAndRotateTransformation.Builder()
                .setRotationDegrees(90f)
                .build())
    )).build()

Java

new EditedMediaItem.Builder(MediaItem.fromUri(uri))
    .setEffects(new Effects(
        /* audioProcessors= */ ImmutableList.of(),
        /* videoEffects= */ ImmutableList.of(
            new ScaleAndRotateTransformation.Builder().setRotationDegrees(90f).build())))
    .build();

Efectos de video personalizados

El constructor Effects acepta una lista de efectos de audio y video para aplicar. Internamente, el framework de efectos de Transformer convierte la lista de efectos de video en una secuencia de programas de sombreadores de GL que se aplican en orden. En algunos casos, el framework de efectos puede aplicar varios efectos con un programa de sombreador. Por ejemplo, un programa de sombreadores puede aplicar varias transformaciones de matriz consecutivas, lo que mejora la eficiencia y la calidad.

Los efectos de video también se admiten para la vista previa en ExoPlayer, con ExoPlayer.setVideoEffects. Para ver un ejemplo de cómo usar esta API, consulta la app de demostración de efectos.

La app de demostración incluye ejemplos de efectos de video personalizados.

Ediciones de audio

Los efectos de audio se implementan aplicando una secuencia de instancias de AudioProcessor al audio sin procesar (PCM). ExoPlayer admite el paso de procesadores de audio a DefaultAudioSink.Builder, lo que permite obtener una vista previa de las ediciones de audio.