Rút gọn APK

Giảm thiểu kích thước tệp APK là khía cạnh quan trọng để phát triển một ứng dụng Android tốt. Điều này đặc biệt đúng khi nhắm đến các thị trường đang phát triển cũng như khi phát triển Ứng dụng Android tức thì. Trong những trường hợp như vậy, bạn nên giảm thiểu kích thước của thư viện ExoPlayer có trong tệp APK. Trang này trình bày một số bước đơn giản có thể giúp bạn đạt được mục tiêu này.

Chỉ sử dụng các phần phụ thuộc bắt buộc

Chỉ phụ thuộc vào các mô-đun thư viện mà bạn thực sự cần. Ví dụ: sau đây là các phần phụ thuộc trên các mô-đun thư viện ExoPlayer, DASH và giao diện người dùng, có thể là yêu cầu bắt buộc đối với một ứng dụng chỉ phát nội dung DASH:

Kotlin

implementation("androidx.media3:media3-exoplayer:1.3.1")
implementation("androidx.media3:media3-exoplayer-dash:1.3.1")
implementation("androidx.media3:media3-ui:1.3.1")

Groovy

implementation "androidx.media3:media3-exoplayer:1.3.1"
implementation "androidx.media3:media3-exoplayer-dash:1.3.1"
implementation "androidx.media3:media3-ui:1.3.1"

Bật tính năng rút gọn mã và tài nguyên

Bạn nên bật tính năng rút gọn mã và tài nguyên cho bản dựng phát hành của ứng dụng. ExoPlayer có cấu trúc theo cách cho phép rút gọn mã để xoá một cách hiệu quả chức năng không dùng đến. Ví dụ: đối với một ứng dụng phát nội dung DASH, bạn có thể bật tính năng rút gọn mã để giảm mức đóng góp của ExoPlayer vào kích thước tệp APK.

Đọc bài viết Rút gọn, làm rối mã nguồn và tối ưu hoá ứng dụng để tìm hiểu cách bật tính năng rút gọn mã và tài nguyên.

Chỉ định trình kết xuất mà ứng dụng của bạn cần

Theo mặc định, các trình kết xuất của trình phát sẽ được tạo bằng cách sử dụng DefaultRenderersFactory. DefaultRenderersFactory phụ thuộc vào tất cả các phương thức triển khai Renderer được cung cấp trong thư viện ExoPlayer. Do đó, không có phương thức nào trong số đó bị xoá bằng tính năng rút gọn mã. Nếu biết rằng ứng dụng chỉ cần một tập hợp con trình kết xuất, bạn có thể chỉ định RenderersFactory của riêng mình. Ví dụ: một ứng dụng chỉ phát âm thanh có thể xác định một nhà máy như sau khi tạo thực thể ExoPlayer:

Kotlin

val audioOnlyRenderersFactory =
  RenderersFactory {
    handler: Handler,
    videoListener: VideoRendererEventListener,
    audioListener: AudioRendererEventListener,
    textOutput: TextOutput,
    metadataOutput: MetadataOutput,
    ->
    arrayOf<Renderer>(
      MediaCodecAudioRenderer(context, MediaCodecSelector.DEFAULT, handler, audioListener)
    )
}
val player = ExoPlayer.Builder(context, audioOnlyRenderersFactory).build()

Java

RenderersFactory audioOnlyRenderersFactory =
    (handler, videoListener, audioListener, textOutput, metadataOutput) ->
        new Renderer[] {
            new MediaCodecAudioRenderer(
                context, MediaCodecSelector.DEFAULT, handler, audioListener)
        };
ExoPlayer player = new ExoPlayer.Builder(context, audioOnlyRenderersFactory).build();

Thao tác này sẽ cho phép xoá các phương thức triển khai Renderer khác bằng cách rút gọn mã. Trong ví dụ này, các trình kết xuất văn bản và siêu dữ liệu sẽ bị xoá (tức là mọi phụ đề hoặc siêu dữ liệu trong luồng phát (ví dụ: ICY) sẽ không được người chơi xử lý hoặc phát ra).

Chỉ định những công cụ trích xuất mà ứng dụng của bạn cần

Theo mặc định, trình phát sẽ tạo các thực thể Extractor để phát nội dung nghe nhìn liên tục bằng DefaultExtractorsFactory. DefaultExtractorsFactory phụ thuộc vào tất cả các phương thức triển khai Extractor được cung cấp trong thư viện ExoPlayer. Do đó, không có phương thức nào trong số đó bị xoá bằng tính năng rút gọn mã. Nếu biết rằng ứng dụng của mình chỉ cần phát một số ít định dạng vùng chứa hoặc không phát nội dung nghe nhìn luỹ tiến, thì bạn có thể chỉ định ExtractorsFactory của riêng mình. Ví dụ: một ứng dụng chỉ cần phát tệp mp4 có thể cung cấp factory như:

Kotlin

val mp4ExtractorFactory = ExtractorsFactory {
  arrayOf<Extractor>(Mp4Extractor(DefaultSubtitleParserFactory()))
}
val player =
  ExoPlayer.Builder(context, DefaultMediaSourceFactory(context, mp4ExtractorFactory)).build()

Java

ExtractorsFactory mp4ExtractorFactory =
    () -> new Extractor[] {new Mp4Extractor(new DefaultSubtitleParserFactory())};
ExoPlayer player =
    new ExoPlayer.Builder(context, new DefaultMediaSourceFactory(context, mp4ExtractorFactory))
        .build();

Điều này sẽ cho phép xoá các phương thức triển khai Extractor khác bằng cách rút gọn mã, nhờ đó có thể làm giảm đáng kể kích thước.

Nếu ứng dụng của bạn không hề phát nội dung tiến bộ, bạn nên truyền ExtractorsFactory.EMPTY đến hàm khởi tạo DefaultMediaSourceFactory, sau đó truyền mediaSourceFactory đó đến hàm khởi tạo ExoPlayer.Builder.

Kotlin

val player =
  ExoPlayer.Builder(context, DefaultMediaSourceFactory(context, ExtractorsFactory.EMPTY)).build()

Java

ExoPlayer player =
    new ExoPlayer.Builder(
            context, new DefaultMediaSourceFactory(context, ExtractorsFactory.EMPTY))
        .build();

Tạo bản sao MediaSource tuỳ chỉnh

Nếu ứng dụng của bạn đang dùng một MediaSource.Factory tuỳ chỉnh và bạn muốn xoá DefaultMediaSourceFactory bằng tính năng loại bỏ mã, thì bạn nên truyền MediaSource.Factory trực tiếp đến hàm khởi tạo ExoPlayer.Builder.

Kotlin

val player = ExoPlayer.Builder(context, customMediaSourceFactory).build()

Java

ExoPlayer player = new ExoPlayer.Builder(context, mediaSourceFactory).build();

Nếu ứng dụng của bạn đang dùng MediaSource trực tiếp thay vì MediaItem, bạn nên truyền MediaSource.Factory.UNSUPPORTED đến hàm khởi tạo ExoPlayer.Builder để đảm bảo có thể loại bỏ DefaultMediaSourceFactoryDefaultExtractorsFactory bằng tính năng rút gọn mã.

Kotlin

val player = ExoPlayer.Builder(context, MediaSource.Factory.UNSUPPORTED).build()
val mediaSource =
  ProgressiveMediaSource.Factory(dataSourceFactory, customExtractorsFactory)
    .createMediaSource(MediaItem.fromUri(uri))

Java

ExoPlayer player = new ExoPlayer.Builder(context, MediaSource.Factory.UNSUPPORTED).build();
ProgressiveMediaSource mediaSource =
    new ProgressiveMediaSource.Factory(dataSourceFactory, customExtractorsFactory)
        .createMediaSource(MediaItem.fromUri(uri));