צמצום הגודל של קובץ ה-APK הוא היבט חשוב בפיתוח אפליקציית Android טובה. זה נכון במיוחד כשמטרגטים שווקים מתפתחים, וגם כשמפתחים אפליקציה ללא התקנה ל-Android. במקרים כאלה, כדאי לצמצם את הגודל של ספריית ExoPlayer שנכללת בקובץ ה-APK. בדף הזה מפורטות כמה פעולות פשוטות שיעזרו לכם לעשות את זה.
שימוש רק בתלות הנדרשת
להסתמך רק על מודולי הספרייה שבאמת נחוצים. לדוגמה, הקוד הבא יוסיף יחסי תלות במודולים של ספריות ExoPlayer, DASH ו-UI, כפי שנדרש באפליקציה שמפעילה רק תוכן DASH:
Kotlin
implementation("androidx.media3:media3-exoplayer:1.7.1") implementation("androidx.media3:media3-exoplayer-dash:1.7.1") implementation("androidx.media3:media3-ui:1.7.1")
מגניב
implementation "androidx.media3:media3-exoplayer:1.7.1" implementation "androidx.media3:media3-exoplayer-dash:1.7.1" implementation "androidx.media3:media3-ui:1.7.1"
הפעלה של כיווץ קוד ומשאבים
מומלץ להפעיל כיווץ של קוד ומשאבים בגרסאות ה-build של האפליקציה שמוכנות להפצה. המבנה של ExoPlayer מאפשר כיווץ קוד כדי להסיר ביעילות פונקציונליות שלא נמצאת בשימוש. לדוגמה, באפליקציה שמפעילה תוכן DASH, אפשר להקטין את התרומה של ExoPlayer לגודל ה-APK בכ-40% על ידי הפעלת צמצום קוד.
במאמר כיווץ, ערפול ואופטימיזציה של האפליקציה מוסבר איך להפעיל כיווץ של קוד ומשאבים.
מציינים אילו רכיבי עיבוד נדרשים לאפליקציה
כברירת מחדל, מעבדי הנתונים של הנגן ייווצרו באמצעות DefaultRenderersFactory
. DefaultRenderersFactory
תלוי בכל ההטמעות של Renderer
שמופיעות בספריית ExoPlayer, ולכן אף אחת מהן לא תוסר על ידי צמצום הקוד. אם אתם יודעים שהאפליקציה שלכם צריכה רק קבוצת משנה של רכיבי עיבוד, אתם יכולים לציין במקום זאת את RenderersFactory
. לדוגמה, אפליקציה שמפעילה רק אודיו יכולה להגדיר מפעל באופן הבא כשיוצרים מופעים של 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();
כך אפשר יהיה להסיר הטמעות אחרות של Renderer
באמצעות צמצום קוד. בדוגמה הספציפית הזו של סרטון, רכיבי העיבוד של הטקסט והמטא-נתונים מוסרים (מה שאומר שהנגן לא יעבד או ישדר כתוביות או מטא-נתונים בתוך הסטרימינג (למשל, ICY)).
ציון המחלצים שהאפליקציה צריכה
כברירת מחדל, הנגן יוצר מופעים של Extractor
כדי להפעיל מדיה מתקדמת באמצעות DefaultExtractorsFactory
. DefaultExtractorsFactory
תלוי בכל ההטמעות של Extractor
שמופיעות בספריית ExoPlayer, ולכן אף אחת מהן לא תוסר על ידי צמצום הקוד. אם אתם יודעים שהאפליקציה שלכם צריכה להפעיל רק מספר קטן של פורמטים של קונטיינרים, או שהיא לא מפעילה מדיה מתקדמת בכלל, אתם יכולים לציין במקום זאת ExtractorsFactory
משלכם. לדוגמה,
אפליקציה שצריכה רק להפעיל קובצי mp4 יכולה לספק מפעל כמו:
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();
כך אפשר להסיר הטמעות אחרות של Extractor
באמצעות צמצום קוד, מה שיכול להוביל לצמצום משמעותי בגודל.
אם האפליקציה לא מציגה תוכן מתקדם בכלל, צריך להעביר את הערך
ExtractorsFactory.EMPTY
אל בנאי DefaultMediaSourceFactory
, ואז להעביר את הערך mediaSourceFactory
אל בנאי 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();
יצירת מופע של MediaSource בהתאמה אישית
אם האפליקציה משתמשת ב-MediaSource.Factory
מותאם אישית ואתם רוצים להסיר את DefaultMediaSourceFactory
באמצעות הסרת קוד, אתם צריכים להעביר את MediaSource.Factory
ישירות אל ה-constructor של ExoPlayer.Builder
.
Kotlin
val player = ExoPlayer.Builder(context, customMediaSourceFactory).build()
Java
ExoPlayer player = new ExoPlayer.Builder(context, mediaSourceFactory).build();
אם האפליקציה שלכם משתמשת ישירות ב-MediaSource
במקום ב-MediaItem
, אתם צריכים להעביר את MediaSource.Factory.UNSUPPORTED
אל הבונה ExoPlayer.Builder
כדי לוודא שניתן להסיר את DefaultMediaSourceFactory
ואת DefaultExtractorsFactory
באמצעות צמצום קוד.
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));