FFmpeg開發筆記(五十六)使用Media3的Exoplayer播放網路影片

aqi00發表於2024-10-13
Android早期的MediaPlayer控制元件對於網路影片的相容性很差,所以後來單獨推出了Exoplayer庫增強支援網路影片,在《Android Studio開發實戰:從零基礎到App上線(第3版)》一書第14章的“14.3.3 新型播放器ExoPlayer”就詳細介紹了Exoplayer庫的詳細用法。

現在Android官方再次升級Exoplayer,並將其納入了Jetpack的Media3第三代媒體庫,作為音影片相關操作的統一處理引擎。升級後的Exoplayer就成為Media3的統一媒體播放引擎,提供了音訊和影片播放的應用級元件,意欲在音影片渲染方向上一統江湖。
根據Android官網的介紹,ExoPlayer還擺脫裝置和作業系統碎片化問題,讓App程式碼以一致的方式執行於整個Android生態系統中。因為Media3是個很新很新的Jetpack庫,所以它對開發環境要求比較高,需滿足下列條件才能正常引入Media3。
1、開發工具要選用Android Studio Jellyfish(小水母版本)或更高版本。
2、Gradle版本不低於8.6。
3、App模組的build.gradle裡面compileSdk和targetSdk要升級到34或者更高版本。
根據上述條件準備好了開發環境,再按照以下描述引入Media3的ExoPlayer庫,詳細步驟說明如下。

一、修改模組的build.gradle

在build.gradle的dependencies節點內部補充下面的導包語句,把ExoPlayer用到的相關庫都加進來。

implementation "androidx.media3:media3-exoplayer:1.4.0"
implementation "androidx.media3:media3-exoplayer-hls:1.4.0"
implementation "androidx.media3:media3-exoplayer-rtsp:1.4.0"
implementation "androidx.media3:media3-ui:1.4.0"
implementation "androidx.media3:media3-common:1.4.0"
implementation "androidx.media3:media3-session:1.4.0"
implementation "androidx.media3:media3-datasource:1.4.0"
implementation "androidx.media3:media3-datasource-rtmp:1.4.0"

二、編輯播放介面的佈局檔案

開啟播放介面的XML佈局檔案,給根佈局新增如下的屬性配置:

xmlns:app="http://schemas.android.com/apk/res-auto"

接著在佈局內部新增來自ExoPlayer庫的PlayerView控制元件節點,舉例如下:

<!-- use_controller是否顯示控制欄,show_timeout控制欄的消失間隔,show_buffering是否顯示緩衝區,resize_mode大小調整模式 -->
<androidx.media3.ui.PlayerView
    android:id="@+id/pv_content"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    app:show_buffering="always"
    app:show_timeout="5000"
    app:use_controller="true"
    app:resize_mode="fit"/>

三、活動頁面程式碼增加ExoPlayer的處理程式碼

首先補充下面一行程式碼宣告PlayerView物件:

private ExoPlayer mPlayer; // 宣告一個新型播放器物件

接著在onCreate方法裡面補充以下程式碼,獲取PlayerView物件,並對其設定ExoPlayer的播放器物件:

    PlayerView pv_content = findViewById(R.id.pv_content);
    mPlayer = new ExoPlayer.Builder(this).build();
    pv_content.setPlayer(mPlayer); // 設定播放器檢視的播放器物件

然後新增下面的播放方法,開始播放指定連結的網路影片。

// 播放影片
private void playVideo(Uri uri) {
    DataSource.Factory factory = new DefaultDataSource.Factory(this);
    // 建立指定地址的媒體物件
    MediaItem videoItem = new MediaItem.Builder().setUri(uri).build();
    // 基於工廠物件和媒體物件建立媒體來源
    MediaSource videoSource;
    if (uri.getPath().endsWith("m3u8")) { // hls連結
        videoSource = new HlsMediaSource.Factory(factory)
                .createMediaSource(videoItem);
    } else if (uri.getPath().startsWith("rtsp")) { // rtsp連結
        videoSource = new RtspMediaSource.Factory()
                .createMediaSource(videoItem);
    } else if (uri.getPath().startsWith("rtmp")) { // rtmp連結
        videoSource = new ProgressiveMediaSource.Factory(new RtmpDataSource.Factory())
                .createMediaSource(videoItem);
    } else { // 其他連結(http開頭或https開頭的普通影片連結)
        videoSource = new ProgressiveMediaSource.Factory(factory)
                .createMediaSource(videoItem);
    }
    mPlayer.setMediaSource(videoSource); // 設定播放器的媒體來源
    mPlayer.prepare(); // 播放器準備就緒
    mPlayer.play(); // 播放器開始播放
}

從上述的播放程式碼可知,這裡用到了ExoPlayer的四種播放形式,分別為:播放HLS連結、播放RTMP連結、播放RTSP連結、播放普通網路影片。

四、給AndroidManifest.xml補充網際網路訪問許可權

開啟AndroidManifest.xml,新增下面的網際網路許可權配置:

<uses-permission android:name="android.permission.INTERNET" />

最後編譯執行App,在真機上看到的播放器效果如下圖所示。

可見成功把Media3的ExoPlayer庫跑了起來,並且正常播放網路影片。

更多詳細的FFmpeg開發知識參見《FFmpeg開發實戰:從零基礎到短影片上線》一書。

相關文章