Изображения

ExoPlayer поддерживает следующие графические форматы. Информацию о том, как интегрировать внешние библиотеки, которые могут поддерживать другие форматы, вы найдете в разделе Библиотеки загрузки изображений.

Формат изображения Поддерживается Примечания
BMP ДА
GIF НЕТ Нет поддержки Extractor
JPEG ДА
Фото с движением в формате JPEG ДА Поддерживаются статичные изображения и видео.
JPEG Ultra HDR ДА На устройствах с версиями ОС до Android 14 или экранами без поддержки HDR используется SDR.
PNG ДА
WebP ДА
HEIF/HEIC ДА
Фото с движением в формате HEIC ДА
AVIF (базовый) ДА Декодирование только на Android 14 и более поздних версиях

Как воспроизвести изображения в плейлисте

Чтобы воспроизвести изображение в составе плейлиста, создайте MediaItem с URI изображения и передайте его проигрывателю. Для элемента MediaItem необходимо задать атрибут imageDurationMs, чтобы указать, как долго должно показываться изображение.

Kotlin

// Create a player instance.
val player = ExoPlayer.Builder(context).build()
// Set the media item to be played with the desired duration.
player.setMediaItem(MediaItem.Builder().setUri(imageUri).setImageDurationMs(2000).build())
// Prepare the player.
player.prepare()

Java

// Create a player instance.
ExoPlayer player = new ExoPlayer.Builder(context).build();
// Set the media item to be played with the desired duration.
player.setMediaItem(new MediaItem.Builder().setUri(imageUri).setImageDurationMs(2000).build());
// Prepare the player.
player.prepare();

Как воспроизвести фото с движением

Фото с движением – это файлы, в которых статичное изображение объединено с коротким видео.

  • Если длительность показа изображения задана с помощью свойства setImageDuration, фото с движением показывается в течение заданного времени как статичное изображение.
  • Если длительность изображения не задана, фото с движением воспроизводится как видео.

Настройка загрузки изображений с помощью источника медиаконтента

Чтобы получить доступ к дополнительным настройкам, создайте объект ProgressiveMediaSource и передайте его непосредственно проигрывателю вместо MediaItem.

Kotlin

// Create a data source factory.
val dataSourceFactory: DataSource.Factory = DefaultHttpDataSource.Factory()
// Create a media item with the image URI and the desired duration.
val mediaItem = MediaItem.Builder().setUri(imageUri).setImageDurationMs(2000).build()
// Create a progressive media source for this media item.
val mediaSource = ProgressiveMediaSource.Factory(dataSourceFactory).createMediaSource(mediaItem)
// Create a player instance.
val player = ExoPlayer.Builder(context).build()
// Set the media source to be played.
player.setMediaSource(mediaSource)
// Prepare the player.
player.prepare()

Java

// Create a data source factory.
DataSource.Factory dataSourceFactory = new DefaultHttpDataSource.Factory();
// Create a media item with the image URI and the desired duration.
MediaItem mediaItem = new MediaItem.Builder().setUri(imageUri).setImageDurationMs(2000).build();
// Create a progressive media source for this media item.
MediaSource mediaSource =
    new ProgressiveMediaSource.Factory(dataSourceFactory).createMediaSource(mediaItem);
// Create a player instance.
ExoPlayer player = new ExoPlayer.Builder(context).build();
// Set the media source to be played.
player.setMediaSource(mediaSource);
// Prepare the player.
player.prepare();

Настроить воспроизведение

ExoPlayer предлагает несколько способов настроить воспроизведение в соответствии с потребностями вашего приложения. Примеры приведены на странице настройки.

Интеграция сторонних библиотек для загрузки изображений

Изображениями часто управляют внешние библиотеки загрузки изображений, например Glide или Coil.

Чтобы интегрировать эти библиотеки в конвейер воспроизведения, выполните следующие действия:

  1. Определите MediaItem с MIME-типом APPLICATION_EXTERNALLY_LOADED_IMAGE.
  2. Предоставьте декодер изображений, чтобы получить Bitmap из библиотеки загрузки изображений.
  3. Предоставьте внешний загрузчик, чтобы активировать кеширование и предварительную загрузку.

Как настроить внешнюю загрузку мультимедийных объектов

Чтобы использовать пути выполнения библиотеки загрузки изображений, в элементе MediaItem, добавленном в Player, должен быть явно определен MIME-тип APPLICATION_EXTERNALLY_LOADED_IMAGE:

Kotlin

val mediaItem =
  MediaItem.Builder()
    .setUri(imageUri)
    .setMimeType(MimeTypes.APPLICATION_EXTERNALLY_LOADED_IMAGE)
    .build()

Java

MediaItem mediaItem =
    new MediaItem.Builder()
        .setUri(imageUri)
        .setMimeType(MimeTypes.APPLICATION_EXTERNALLY_LOADED_IMAGE)
        .build();

Декодирование изображений с помощью внешней библиотеки

Для получения Bitmap из Uri средству визуализации изображений требуется ExternallyLoadedImageDecoder. Этот декодер можно предоставить, переопределив DefaultRenderersFactory.getImageDecoderFactory.

В примере ниже Glide используется для загрузки изображения, размер которого ограничен размером экрана, чтобы избежать создания слишком больших объектов Bitmap:

Kotlin

val glideImageDecoderFactory: ImageDecoder.Factory =
  ExternallyLoadedImageDecoder.Factory { request: ExternalImageRequest ->
    val displaySize = Util.getCurrentDisplayModeSize(context)
    GlideFutures.submit(
      Glide.with(context)
        .asBitmap()
        .load(request.uri)
        .override(max(displaySize.x, displaySize.y))
    )
  }
val player: Player =
  ExoPlayer.Builder(context)
    .setRenderersFactory(
      object : DefaultRenderersFactory(context) {
        override fun getImageDecoderFactory(context: Context): ImageDecoder.Factory {
          return glideImageDecoderFactory
        }
      }
    )
    .build()

Java

ImageDecoder.Factory glideImageDecoderFactory =
    new ExternallyLoadedImageDecoder.Factory(
        request -> {
          Point displaySize = Util.getCurrentDisplayModeSize(context);
          return GlideFutures.submit(
              Glide.with(context)
                  .asBitmap()
                  .load(request.uri)
                  .override(max(displaySize.x, displaySize.y)));
        });
Player player =
    new ExoPlayer.Builder(context)
        .setRenderersFactory(
            new DefaultRenderersFactory(context) {
              @Override
              protected ImageDecoder.Factory getImageDecoderFactory(Context context) {
                return glideImageDecoderFactory;
              }
            })
        .build();

Предварительная загрузка изображений с помощью внешней библиотеки

Во время воспроизведения проигрыватель запрашивает предварительную загрузку следующего изображения, как только предыдущий элемент в плейлисте будет полностью загружен. Если вы используете внешнюю библиотеку загрузки изображений, то для запуска предварительной загрузки необходимо указать ExternalLoader. Если предварительная загрузка невозможна или не требуется, загрузчик все равно нужно предоставить, но он может ничего не делать.

В примере ниже используется библиотека Glide, которая обеспечивает предварительную загрузку запрошенного изображения на диск.

Kotlin

val glidePreloader = ExternalLoader { request: LoadRequest ->
  GlideFutures.submit(
    Glide.with(context)
      .asFile()
      .apply(
        RequestOptions.diskCacheStrategyOf(DiskCacheStrategy.DATA)
          .priority(Priority.HIGH)
          .skipMemoryCache(true)
      )
      .load(request.uri)
  )
}
val player: Player =
  ExoPlayer.Builder(context)
    .setMediaSourceFactory(
      DefaultMediaSourceFactory(context).setExternalImageLoader(glidePreloader)
    )
    .build()

Java

ExternalLoader glidePreloader =
    request ->
        GlideFutures.submit(
            Glide.with(context)
                .asFile()
                .apply(
                    diskCacheStrategyOf(DiskCacheStrategy.DATA)
                        .priority(Priority.HIGH)
                        .skipMemoryCache(true))
                .load(request.uri));
Player player =
    new ExoPlayer.Builder(context)
        .setMediaSourceFactory(
            new DefaultMediaSourceFactory(context).setExternalImageLoader(glidePreloader))
        .build();