ExoPlayer: що це таке, можливості та налаштування

Автор: IT Sectr Опубліковано: 2026-05-23 Час читання: 8 хв

ExoPlayer — це відкрита медіаплеєрна бібліотека для Android, розроблена Google як альтернатива вбудованому MediaPlayer. ExoPlayer забезпечує відтворення аудіо та відео в різних форматах, включаючи DASH, HLS, SmoothStreaming та звичайні медіафайли, через єдиний API з підтримкою адаптивного стрімінгу. За даними Google I/O (2024), ExoPlayer використовується більш ніж у 60 000 Android-додатках, включаючи YouTube, Google TV та Netflix.

Головне

  • ExoPlayer — це медіаплеєрна бібліотека з відкритим вихідним кодом для Android від Google.
  • Кроссплатформенні формати — ExoPlayer підтримує DASH, HLS, SmoothStreaming та RTSP через модульну систему розширень.
  • Кастомізація — кожен компонент плеєра (рендерер, джерело даних, DRM) може бути замінений на власну реалізацію.
  • Canvas і Compose — ExoPlayer інтегрується як з традиційним View-підходом (SurfaceView), так і з Jetpack Compose.
  • DRM — підтримка Widevine, PlayReady та ClearKey через модульну DRM-систему.

Що таке ExoPlayer?

ExoPlayer — це бібліотека для відтворення мультимедіа під Android з відкритим вихідним кодом (Apache 2.0), перша версія якої була випущена Google у 2014 році. На відміну від вбудованого MediaPlayer, який є тонкою обгорткою над системним медіа-кодеком (MediaCodec), ExoPlayer реалізований повністю на рівні Java/Kotlin, що дає розробникам повний контроль над кожним етапом відтворення.

Архітектурно ExoPlayer побудований на модульному принципі: кожен аспект відтворення реалізований окремим компонентом. Основний модуль (exoplayer-core) містить плеєр, рендерери, трек-селектори та керування буфером. Додаткові модулі (exoplayer-dash, exoplayer-hls, exoplayer-rtsp, exoplayer-smoothstreaming) додають підтримку відповідних протоколів стрімінгу. Така архітектура дозволяє додаткам підключати тільки необхідні компоненти, мінімізуючи розмір APK.

ExoPlayer 2 (поточна мажорна версія) була випущена у 2018 році та принесла кардинальну переробку API: введення Player Interface, підтримку Compose через AndroidX Media3, покращену обробку помилок та адаптивні алгоритми вибору треків. Починаючи з версії 2.19 (2024), ExoPlayer став частиною бібліотеки AndroidX Media, що спростило інтеграцію та оновлення через стандартний Android-менеджер залежностей.

Архітектура ExoPlayer

В основі ExoPlayer лежить компонент ExoPlayerImpl, який керує життєвим циклом відтворення. Він містить MediaSource (джерело медіа), TrackSelector (вибір доріжок), LoadControl (керування буферизацією) та список Renderer (рендерери для відео, аудіо, субтитрів та метаданих). Кожен компонент може бути замінений власною реалізацією через Builder або фабричні методи.

Для рендерингу відео ExoPlayer використовує SurfaceView, TextureView або SphericalSurfaceView (для 360-градусного відео). Рекомендованим варіантом є SurfaceView, оскільки він забезпечує апаратне прискорення та мінімальне енергоспоживання. Для Jetpack Compose бібліотека AndroidX Media3 надає компонент `AndroidView`, що обертає SurfaceView, та експериментальний `Media3Compose` з нативною Compose-інтеграцією.

Можливості ExoPlayer

ExoPlayer надає широкий набір функцій, що виходять за рамки звичайного медіаплеєра. Основні можливості включають підтримку всіх популярних протоколів стрімінгу, гнучку DRM-систему, адаптивне перемикання бітрейту (ABR) та інструменти аналітики відтворення.

ФункціяОписМодуль
DASHАдаптивний стрімінг за стандартом MPEGexoplayer-dash
HLSHTTP Live Streaming від Appleexoplayer-hls
SmoothStreamingАдаптивний стрімінг від Microsoftexoplayer-smoothstreaming
RTSPReal-Time Streaming Protocol для liveexoplayer-rtsp
WidevineDRM-захист контентуexoplayer-drm
ConcatenationСклеювання кількох медіафайлівexoplayer-core
AdsIMA SDK інтеграція для рекламиexoplayer-ima

Адаптивне перемикання бітрейту

ABR (Adaptive Bitrate) в ExoPlayer реалізований через інтерфейс AdaptiveTrackSelection. За замовчуванням використовується AdaptiveTrackSelectionFactory, який створює DefaultAdaptiveTrackSelection — збалансований алгоритм, що враховує пропускну здатність мережі та розмір буфера. Для специфічних сценаріїв можна підключити альтернативні реалізації: BOLA (мінімізація перемикань), RandomAdaptiveTrackSelection (тестування) або власну реалізацію через інтерфейс TrackSelection.

BandwidthMeter — ще один ключовий компонент, відповідальний за вимірювання пропускної здатності мережі. За замовчуванням використовується DefaultBandwidthMeter, який збирає статистику по всіх HTTP-запитах плеєра. Розробник може розширити його для врахування додаткових факторів: типу мережі (Wi-Fi, 4G, 5G), сигналу стільникової вежі або вартості трафіку для користувача.

DRM та захист контенту

ExoPlayer підтримує Widevine (L1, L3), PlayReady та ClearKey DRM. Отримання ліцензії налаштовується через DrmSessionManager, який взаємодіє з ліцензійним сервером. Для відео преміум-класу (4K HDR) потрібна апаратна підтримка Widevine L1, що забезпечує захист на рівні чіпа та запобігає захопленню екрану. Вибір DRM-системи залежить від цільової платформи: Widevine використовується на Android та Chromecast, PlayReady — на Xbox та Windows, FairPlay — на iOS та Apple TV. ExoPlayer визначає доступну DRM-систему автоматично на основі MPD-файлу та не вимагає ручної конфігурації для базових сценаріїв.

Як інтегрувати ExoPlayer в Android-проєкт

Підключення ExoPlayer до Android-проєкту виконується через Gradle-залежності. Починаючи з версії 2.19, ExoPlayer входить до складу AndroidX Media (androidx.media3), що забезпечує сумісність з Jetpack Compose та іншими компонентами AndroidX. Розглянемо покрокову інтеграцію на Kotlin.

Підключення залежностей

Додайте модулі ExoPlayer у файл build.gradle (Module). Мінімальний набір включає core, ui та модуль для необхідного протоколу стрімінгу. Для відтворення DASH-контенту знадобиться exoplayer-dash, для HLS — exoplayer-hls.

groovy
dependencies {
    implementation "androidx.media3:media3-exoplayer:1.5.0"
    implementation "androidx.media3:media3-ui:1.5.0"
    implementation "androidx.media3:media3-exoplayer-dash:1.5.0"
    implementation "androidx.media3:media3-exoplayer-hls:1.5.0"
}

Базова інтеграція в Activity

Створення та налаштування плеєра в Activity або Fragment. ExoPlayer використовує PlayerView (або StyledPlayerView для кастомізації) для відображення відео та вбудованих елементів керування. Мінімальна конфігурація включає створення плеєра через ExoPlayer.Builder та передачу MediaItem з URI джерела.

kotlin
class PlayerActivity : AppCompatActivity() {

    private var player: ExoPlayer? = null

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_player)

        player = ExoPlayer.Builder(this).build()
        val playerView = findViewById<StyledPlayerView>(R.id.playerView)
        playerView.player = player

        val mediaItem = MediaItem
            .Builder()
            .setUri("https://example.com/video.mp4")
            .build()
        player?.setMediaItem(mediaItem)
        player?.prepare()
    }

    override fun onDestroy() {
        player?.release()
        super.onDestroy()
    }
}

Обробка помилок та станів

Для production-додатків необхідна обробка можливих помилок відтворення: мережеві збої, непідтримувані формати, помилки DRM-ліцензування. ExoPlayer надає інтерфейс Player.Listener з методами onPlayerError, onPlaybackStateChanged та onPlayWhenReadyChanged. Рекомендується показувати користувачеві інформативні повідомлення про помилки з можливістю повтору.

ExoPlayer проти MediaPlayer: порівняння

Вибір між ExoPlayer та вбудованим MediaPlayer — поширене питання при розробці Android-додатків. MediaPlayer є частиною Android SDK з версії 1.0, в той час як ExoPlayer — бібліотека, що вимагає підключення через Gradle. Розглянемо їх відмінності за ключовими критеріями.

КритерійExoPlayerMediaPlayer
АрхітектураМодульна, повністю на Java/KotlinОбгортка над системними C++ компонентами
СтрімінгDASH, HLS, SmoothStreaming, RTSPТільки локальні файли та HLS (Android 9+)
КастомізаціяПовна (будь-який компонент замінний)Мінімальна (тільки параметри)
ОновленняЧерез Google Play або APK (незалежно від ОС)Тільки через оновлення Android (OTA)
Розмір APK+1-3 MB (залежно від модулів)0 (частина ОС)
Min SDKAPI 16+ (Android 4.1)API 1+
DRMWidevine, PlayReady, ClearKeyWidevine (обмежено)

ExoPlayer виграє в сценаріях, що вимагають стрімінгу (DASH, HLS), кастомізації UI, підтримки DRM та незалежності від версії Android. MediaPlayer підходить для простих додатків, що відтворюють локальні медіафайли, де розмір APK критичний і немає вимог до адаптивного стрімінгу. Для сучасних додатків з контентом з мережі ExoPlayer є однозначним вибором.

Виняток — додатки з мінімальним SDK нижче API 16 (Android 4.1), яких практично не залишилося на ринку. Для всіх додатків з targetSdk 33+ та мінімальним SDK 21+ ExoPlayer не тільки бажаніший, але й необхідний для підтримки сучасних форматів, таких як AV1 та Dolby Vision через відповідні розширення.

Просунуте налаштування ExoPlayer

Для production-додатків базова інтеграція ExoPlayer часто вимагає додаткового налаштування: керування кешуванням, оптимізація буферизації для мобільних мереж, інтеграція з аналітикою та кастомізація вибору аудіо-доріжок. Розглянемо просунуті сценарії використання.

Кешування контенту

CacheDataSourceFactory дозволяє кешувати завантажені сегменти на локальному сховищі, що економить трафік при повторному перегляді та забезпечує офлайн-відтворення. ExoPlayer використовує SimpleCache з бібліотеки exoplayer-cas — файлове кешування з підтримкою LRU-евакуації та лімітів розміру.

kotlin
val cache = SimpleCache(
    cacheDir,
    LeastRecentlyUsedCacheEvictor(50 * 1024 * 1024),
    AppDatabaseProvider(this)
)

val cacheDataSourceFactory = CacheDataSource
    .Factory()
    .setCache(cache)

val player = ExoPlayer.Builder(this)
    .setMediaSourceFactory(
        DefaultMediaSourceFactory(cacheDataSourceFactory)
    )
    .build()

Обробка перемикання мережі

У мобільних додатках критична обробка перемикання між Wi-Fi та стільниковою мережею. ExoPlayer надає ConnectivityManager для відстеження стану мережі. При втраті з’єднання рекомендується не зупиняти плеєр, а перевести його в стан PAUSED зі збереженням позиції. Після відновлення з’єднання — відновити відтворення з перезавантаженням сегментів.

Інтеграція з Jetpack Compose

З виходом AndroidX Media3 бібліотека отримала експериментальну підтримку Jetpack Compose. Компонент `AndroidView` обертає SurfaceView або PlayerView, забезпечуючи сумісність з Compose-ієрархією. Для більш глибокої інтеграції використовується бібліотека `androidx.media3:media3-ui-compose`, що надає Compose-сумісні елементи керування плеєром.

kotlin
@Composable
fun VideoPlayer(uri: String) {
    val context = LocalContext.current
    val player = remember {
        ExoPlayer.Builder(context).build()
            .also { it.setMediaItem(MediaItem.fromUri(uri)) }
    }

    DisposableEffect(key = null) {
        player.prepare()
        onDispose { player.release() }
    }

    AndroidView(
        factory = { StyledPlayerView(context).also { it.player = player } }
    )
}

Часто задавані питання

Яка мінімальна версія Android для ExoPlayer?

ExoPlayer підтримує Android API 16+ (Android 4.1 Jelly Bean). Однак для DASH та HLS з fMP4 сегментами рекомендується API 21+ (Android 5.0 Lollipop). Модулі DRM (Widevine) вимагають API 19+, а апаратне декодування HEVC доступне з API 21.

Чи можна використовувати ExoPlayer для аудіо без відео?

Так, ExoPlayer чудово підходить для аудіо. Для відтворення тільки звуку не потрібен SurfaceView або PlayerView. ExoPlayer автоматично вибере аудіо-рендерер та працюватиме у фоновому режимі. Для фонового відтворення рекомендується використовувати MediaSessionService для інтеграції з системними елементами керування.

Як перемкнутися між аудіо-доріжками в ExoPlayer?

TrackSelector в ExoPlayer керує вибором аудіо-доріжок. Для перемикання використовуйте player.getCurrentTracks().groups та player.setTrackSelectionParameters() із зазначенням бажаної мови аудіо. Для стрімів DASH та HLS з множинними аудіо-доріжками перемикання відбувається без переривання відтворення.

Чи підтримує ExoPlayer субтитри?

Так, ExoPlayer підтримує вбудовані (в контейнері MP4, WebM) та зовнішні субтитри у форматах TTML, SRT, VTT та CEA-608. Для зовнішніх субтитрів використовується SingleSampleMediaSource або MergingMediaSource для об’єднання з відео-потоком. Відображення стилізованих субтитрів налаштовується через CaptionStyleCompat.

Як зменшити затримку при live-стрімінгу в ExoPlayer?

Для Low-Latency стрімінгу налаштуйте LoadControl з меншими цільовими значеннями буфера: використовуйте DefaultLoadControl.Builder().setTargetBufferBytes(1024 * 512).setBufferDurationsMs(500, 2000, 500, 1000) для HLS LL та DASH LL. Також вкажіть minPlaybackSpeed = 1.02 для прискореного заповнення буфера при відставанні від live-трансляції.

Підсумки

  • ExoPlayer — відкрита медіаплеєрна бібліотека від Google з модульною архітектурою та повною кастомізацією.
  • Адаптивний стрімінг — підтримує DASH, HLS, SmoothStreaming та RTSP через модульну систему розширень.
  • DRM — Widevine, PlayReady та ClearKey інтегруються через модуль exoplayer-drm з єдиним API.
  • Кешування — SimpleCache забезпечує офлайн-відтворення та економію трафіку при повторних переглядах.
  • Compose — починаючи з AndroidX Media3, ExoPlayer інтегрується з Jetpack Compose через AndroidView.
  • Кастомізація — кожен компонент (MediaSource, TrackSelector, LoadControl, Renderer) може бути замінений.
  • Рекомендується використовувати ExoPlayer для всіх проєктів, що вимагають стрімінгу, DRM або кастомізації відтворення.

Ми розробимо мобільний застосунок під ключ

IT Sectr створює застосунки для iOS та Android для стартапів і бізнесу з 2017 року. Ми проконсультуємо вас і запропонуємо найкраще рішення.

Обговорити проект

Читайте також