אפליקציות שמשתמשות כרגע בגרסה הנפרדת com.google.android.exoplayer2
הספרייה ו-androidx.media
יועברו אל androidx.media3
. כדאי להשתמש
סקריפט ההעברה כדי להעביר קובצי build מסוג GRid, Java
קובצי מקור של Kotlin וקובצי פריסת XML מ-ExoPlayer
2.19.1
ל-AndroidX Media3 1.1.1
.
סקירה כללית
לפני ההעברה, כדאי לעיין בקטעים הבאים כדי לקבל מידע נוסף על היתרונות של ממשקי ה-API החדשים, ממשקי ה-API להעברה והדרישות המוקדמות שהפרויקט של האפליקציה שלכם צריך לעמוד בהם.
למה כדאי לעבור ל-Jetpack Media3
- זה הבית החדש של ExoPlayer, ואילו
com.google.android.exoplayer2
הופסק. - גישה ל-Player API ברכיבים/תהליכים שונים באמצעות
MediaBrowser
מתוךMediaController
. - להשתמש ביכולות המתקדמות של
MediaSession
MediaController
API. - אפשר לפרסם יכולות הפעלה באמצעות בקרת גישה פרטנית.
- כדי לפשט את האפליקציה, מסירים את
MediaSessionConnector
PlayerNotificationManager
- תאימות לאחור עם ממשקי API בצד הלקוח שתואמים למדיה
(
MediaBrowserCompat
/MediaControllerCompat
/MediaMetadataCompat
)
ממשקי API של מדיה להעברה אל AndroidX Media3
- ExoPlayer והתוספים שלו
זה כולל את כל המודולים של פרויקט ExoPlayer מדור קודם, מלבד המודול mediasession הופסק. אפליקציות או מודולים, בהתאם אפשר להעביר חבילות ב-com.google.android.exoplayer2
עם סקריפט העברה. - MediaSessionConnector (בהתאם ל
androidx.media.*
חבילות שלandroidx.media:media:1.4.3+
)
יש להסיר אתMediaSessionConnector
ולהשתמש בandroidx.media3.session.MediaSession
במקום זאת. - MediaBrowserServiceCompat (בהתאם ל-
androidx.media.*
חבילות שלandroidx.media:media:1.4.3+
)
העברת מחלקות משנה שלandroidx.media.MediaBrowserServiceCompat
אלandroidx.media3.session.MediaLibraryService
וקוד באמצעותMediaBrowserCompat.MediaItem
עדandroidx.media3.common.MediaItem
. - MediaBrowserCompat (בהתאם ל-
android.support.v4.media.*
חבילות שלandroidx.media:media:1.4.3+
)
מעבירים את קוד הלקוח באמצעותMediaBrowserCompat
אוMediaControllerCompat
כדי להשתמש ב-androidx.media3.session.MediaBrowser
עםandroidx.media3.common.MediaItem
.
דרישות מוקדמות
מוודאים שהפרויקט נמצא בבקרת מקור
כדאי לוודא שאפשר לבטל בקלות שינויים שהוחלו על ידי כלי העברה שמכילים סקריפטים. אם עדיין לא הגדרת את הפרויקט שלך לבקרת מקור, עכשיו זה זמן מתאים להתחיל איתו. אם מסיבה כלשהי אינך רוצה לעשות זאת, צור עותק לגיבוי של הפרויקט שלך לפני התחלת ההעברה.
עדכון האפליקציה
מומלץ לעדכן את הפרויקט כדי להשתמש ב- בגרסה העדכנית ביותר של ספריית ExoPlayer ומסירים קריאות ל-methods שהוצאו משימוש. אם בכוונתך להשתמש בסקריפט להעברה, עליכם להתאים לגרסה שאליה מתבצע העדכון, עם הגרסה שהסקריפט מטפל בה.
מעלים את compileSdkVersion של האפליקציה ל-32 לפחות.
שדרוג Gradle ואת הפלאגין של Android Studio Gradle שפועלת עם יחסי התלות המעודכנים שמוזכרים למעלה. עבור מופע:
- גרסה של הפלאגין Android Gradle: 7.1.0
- גרסת Gradle: 7.4
החלפת כל הצהרות הייבוא עם תווים כלליים לחיפוש שמשתמשות בסיומת (*) ושימוש בהצהרות ייבוא מלאות: מחיקת התו הכללי לחיפוש לייבא דפי חשבון ולהשתמש ב-Android Studio כדי לייבא את הצהרות (F2 - Alt/Enter, F2 - Alt/Enter, ...).
העברה מ-
com.google.android.exoplayer2.PlayerView
אלcom.google.android.exoplayer2.StyledPlayerView
. זה הכרחי כי אין ערך מקבילcom.google.android.exoplayer2.PlayerView
ב-AndroidX Media3.
העברת ExoPlayer עם תמיכה בסקריפטים
הסקריפט מאפשר לעבור מ-com.google.android.exoplayer2
לממשק החדש
מבנה החבילה והמודול במסגרת androidx.media3
. הסקריפט מתקיים
מתבצעות בדיקות אימות מסוימות בפרויקט, ואזהרות אם האימות נכשל.
אחרת, היא מחילה את המיפויים של חבילות ומחלקות עם שם חדש ברמה של
של פרויקט Android gradle שנכתב ב-Java או ב-Kotlin.
usage: ./media3-migration.sh [-p|-c|-d|-v]|[-m|-l [-x <path>] [-f] PROJECT_ROOT]
PROJECT_ROOT: path to your project root (location of 'gradlew')
-p: list package mappings and then exit
-c: list class mappings (precedence over package mappings) and then exit
-d: list dependency mappings and then exit
-l: list files that will be considered for rewrite and then exit
-x: exclude the path from the list of file to be changed: 'app/src/test'
-m: migrate packages, classes and dependencies to AndroidX Media3
-f: force the action even when validation fails
-v: print the exoplayer2/media3 version strings of this script
-h, --help: show this help text
שימוש בסקריפט ההעברה
מורידים את סקריפט ההעברה מהתג של פרויקט ExoPlayer שימוש ב-GitHub בהתאם לגרסה שאליה עדכנתם את האפליקציה:
curl -o media3-migration.sh \ "https://raw.githubusercontent.com/google/ExoPlayer/r2.19.1/media3-migration.sh"
יוצרים את קובץ ההפעלה של הסקריפט:
chmod 744 media3-migration.sh
כדי לקבל מידע על האפשרויות, אפשר להריץ את הסקריפט באמצעות
--help
.מריצים את הסקריפט עם
-l
כדי להציג את רשימת הקבצים שנבחרו עבור העברה (יש להשתמש ב--f
כדי לאלץ את דף האפליקציה ללא אזהרות):./media3-migration.sh -l -f /path/to/gradle/project/root
מריצים את הסקריפט באמצעות
-m
כדי למפות חבילות, מחלקות ומודולים אל Media3. הרצת הסקריפט עם האפשרות-m
תחיל את השינויים על הישות שנבחרה .- עצירה בשגיאת אימות בלי לבצע שינויים
./media3-migration.sh -m /path/to/gradle/project/root
- ביצוע באילוץ
אם הסקריפט יגלה הפרה של הדרישות המוקדמות, ניתן לבצע את ההעברה מאולץ עם הדגל
-f
:./media3-migration.sh -m -f /path/to/gradle/project/root
# list files selected for migration when excluding paths
./media3-migration.sh -l -x "app/src/test/" -x "service/" /path/to/project/root
# migrate the selected files
./media3-migration.sh -m -x "app/src/test/" -x "service/" /path/to/project/root
משלימים את השלבים הידניים הבאים אחרי שמריצים את הסקריפט באמצעות האפשרות -m
:
- בודקים איך הסקריפט שינה את הקוד: שימוש בכלי הפרש ותיקון
יכולות להיות בעיות אפשריות (כדאי לדווח על באג אם לדעתכם יש בסקריפט
בעיה כללית שאירעה מבלי להעביר את האפשרות
-f
). - כדי ליצור את הפרויקט: אפשר להשתמש ב-
./gradlew clean build
או ב-Android בוחרים באפשרות File > (קובץ >) סנכרון פרויקט עם קובצי Gradle ואז Build > ניקוי הפרויקט ואז Build > בניית פרויקט מחדש (מעקב אחר ה-build 'Build - Build Output' ב-Android Studio.
פעולות שמומלץ לבצע:
- פתרון בעיות שקשורות להבעת הסכמה לשגיאות בנוגע לשימוש בממשקי API לא יציבים.
- החלפת קריאות ל-API שהוצאו משימוש: השתמשו ב-API החלופי המוצע. מעבירים את הסמן מעל לאזהרה ב-Android Studio ומעיינים ב-JavaDoc של הסמל שהוצא משימוש כדי להבין במה להשתמש במקום בקריאה נתונה.
- מיון הדוחות של הייבוא: פותחים את הפרויקט ב-Android Studio ואז לוחצים לחיצה ימנית על צומת של תיקיית חבילה במציג הפרויקט ובוחרים לבצע אופטימיזציה של ייבוא בחבילות שמכילות את קובצי המקור שהשתנו.
מחליפים את MediaSessionConnector
ב-androidx.media3.session.MediaSession
בעולם הקודם של MediaSessionCompat
, MediaSessionConnector
אחראי לסנכרון מצב הנגן עם מצב הסשן
וקבלת פקודות מנאמני מידע שנדרשים להעניק גישה אל
שיטות לנגן. עם AndroidX Media3, הפעולה הזו מתבצעת ישירות על ידי MediaSession
ללא צורך במחבר.
הסרת כל ההפניות והשימוש ב-MediaSessionConnector: אם השתמשתם הסקריפט האוטומטי להעברת מחלקות וחבילות של ExoPlayer, ואז סביר להניח שהסקריפט השאיר את הקוד שלך במצב לא הידור לגבי את
MediaSessionConnector
שאי אפשר לפענח. פלטפורמת Android Studio להציג את הקוד הפגום כשמנסים לבנות או להפעיל את האפליקציה.בקובץ
build.gradle
שבו שומרים על יחסי התלות, מוסיפים והתלות במודול הסשן של AndroidX Media3, ולהסיר את ליחסי התלות בדור קודם:implementation "androidx.media3:media3-session:1.4.0"
מחליפים את
MediaSessionCompat
ב-androidx.media3.session.MediaSession
.באתר הקוד שבו יצרתם את הגרסה הקודמת של
MediaSessionCompat
, משתמשים ב-androidx.media3.session.MediaSession.Builder
כדי ליצורMediaSession
מעבירים את הנגן כדי ליצור את הכלי ליצירת סשנים.val player = ExoPlayer.Builder(context).build() mediaSession = MediaSession.Builder(context, player) .setSessionCallback(MySessionCallback()) .build()
צריך להטמיע את
MySessionCallback
בהתאם לדרישות האפליקציה. לא חובה לעשות זאת. אם המיקום שרוצים לאפשר לבקרים להוסיף פריטי מדיה לנגן, להטמיעMediaSession.Callback.onAddMediaItems()
היא משתמשת במגוון שיטות שיטות API מדור קודם שמוסיפות פריטי מדיה לנגן לצורך הפעלה שמתאימה לאחור. האיסור הזה כוללMediaController.set/addMediaItems()
methods של בקר Media3, כמו וגםTransportControls.prepareFrom*/playFrom*
ב-API מהדור הקודם. הטמעה לדוגמה שלonAddMediaItems
יכולה אפשר למצוא בPlaybackService
של אפליקציית ההדגמה של הסשן.משחררים את סשן המדיה באתר הקוד שבו השמדתם את הסשן לפני ההעברה:
mediaSession?.run { player.release() release() mediaSession = null }
הפונקציונליות של MediaSessionConnector
ב-Media3
בטבלה הבאה מוצגים ממשקי ה-API של Media3 שמטפלים בפונקציונליות
הוטמעו בעבר ב-MediaSessionConnector
.
MediaSessionConnector | AndroidX Media3 |
---|---|
CustomActionProvider |
MediaSession.Callback.onCustomCommand()/
MediaSession.setCustomLayout() |
PlaybackPreparer |
MediaSession.Callback.onAddMediaItems()
(השם prepare() נקרא באופן פנימי)
|
QueueNavigator |
ForwardingPlayer |
QueueEditor |
MediaSession.Callback.onAddMediaItems() |
RatingCallback |
MediaSession.Callback.onSetRating() |
PlayerNotificationManager |
DefaultMediaNotificationProvider/
MediaNotification.Provider |
העברה של MediaBrowserService
אל MediaLibraryService
AndroidX Media3 מציג את MediaLibraryService
שמחליף את
MediaBrowserServiceCompat
. ה-JavaDoc של MediaLibraryService
וצוות ה-Super שלו
MediaSessionService
מספקים מבוא טוב ל-API,
מודל תכנות אסינכרוני של השירות.
השדה MediaLibraryService
תואם לאחור עם
MediaBrowserService
. אפליקציית לקוח שמשתמשת ב-MediaBrowserCompat
או
MediaControllerCompat
, ממשיך לפעול ללא שינויים בקוד בעת החיבור
אל MediaLibraryService
. מבחינת הלקוחות, לא ברור אם האפליקציה
באמצעות MediaLibraryService
או MediaBrowserServiceCompat
מדור קודם.
![תרשים של רכיב אפליקציה עם שירות, פעילות ואפליקציות חיצוניות.](https://developer.android.com/static/media/images/overview.png?authuser=2&hl=he)
כדי שהתאימות לאחור תעבוד, צריך לרשום את שני השירותים ממשקים עם השירות שלכם ב-
AndroidManifest.xml
. כך הלקוח מוצא את השירות שלכם באמצעות ממשק השירות הנדרש:<service android:name=".MusicService" android:exported="true"> <intent-filter> <action android:name="androidx.media3.session.MediaLibraryService"/> <action android:name="android.media.browse.MediaBrowserService" /> </intent-filter> </service>
בקובץ
build.gradle
שבו שומרים על יחסי התלות, מוסיפים ותלויות בהטמעה של מודול הסשן של AndroidX Media3 להסיר את התלות הקודמת:implementation "androidx.media3:media3-session:1.4.0"
לשנות את השירות כך שיקבל בירושה מ
MediaLibraryService
במקוםMediaBrowserService
כפי שציינו קודם,MediaLibraryService
תואם לגרסה הקודמתMediaBrowserService
בהתאם לכך, ה-API הרחבה יותר של השירות ההצעות ללקוחות נשארות ללא שינוי. לכן, סביר להניח שאפליקציה יכולה לשמור את רוב הלוגיקה שנדרשת כדי להטמיע אתMediaBrowserService
ולהתאים אותו לMediaLibraryService
החדש.ההבדלים העיקריים בהשוואה לדור הקודם
MediaBrowserServiceCompat
הם:להטמיע את השיטות למחזור החיים של השירות: השיטות שצריך ניתנים לשינוי בשירות עצמו
onCreate/onDestroy
, כאשר מקצה/משחררת את הסשן בספרייה, את הנגן במשאבי אנוש. בנוסף לשיטות הרגילות של מחזור החיים של השירות, צריך לשנות את ברירת המחדל שלonGetSession(MediaSession.ControllerInfo)
כדי להחזירMediaLibrarySession
שנבנה ב-onCreate
.הטמעה של MediaLibraryService.MediaLibrarySessionCallback: פיתוח סשן מחייב
MediaLibraryService.MediaLibrarySessionCallback
מוטמע את ה-methods בפועל של ה-API של הדומיין. כך שבמקום לשנות שיטות API של בשירות מהדור הקודם, תבטלו את השיטות יש גם אפשרותMediaLibrarySession.Callback
.לאחר מכן הקריאה החוזרת משמשת ליצירת
MediaLibrarySession
:mediaLibrarySession = MediaLibrarySession.Builder(this, player, MySessionCallback()) .build()
בממשק ה-API ניתן למצוא את ה-API המלא של MediaLibrarySessionCallback התיעוד.
הטמעה
MediaSession.Callback.onAddMediaItems()
: הקריאה החוזרת (callback)onAddMediaItems(MediaSession, ControllerInfo, List<MediaItem>)
מילוי בקשות שיטות שונות של API, עדכניות ומדור קודם, שמוסיפות פריטי מדיה לנגן להפעלה באופן שתואם לאחור. האיסור הזה כוללMediaController.set/addMediaItems()
methods של בקר Media3, וגםTransportControls.prepareFrom*/playFrom*
ב-API מהדור הקודם. הטמעה לדוגמה של הקריאה החוזרת (callback) אפשר למצוא את בPlaybackService
של אפליקציית ההדגמה של הסשן.ב-AndroidX Media3 נעשה שימוש ב-
androidx.media3.common.MediaItem
במקום זאת של MediaBrowserCompat.MediaItem ו-MediaMetadataCompat. חלקים צריך לשנות בהתאם את הקוד שקשור למחלקות הקודמות או למפות אל Media3MediaItem
במקום זאת.מודל התכנות האסינכרוני הכללי השתנה ל-
Futures
ב- בניגוד לגישתResult
שניתן לנתקMediaBrowserServiceCompat
הטמעת השירות שלך יכולה להחזיר אסינכרוניותListenableFuture
במקום לנתק תוצאה או החזרה של 'עתיד מיידי' כדי להחזיר ערך ישירות.
הסרת PlayerNotificationManager
MediaLibraryService
תומך בהתראות מדיה באופן אוטומטי וגם
אפשר להסיר את PlayerNotificationManager
כשמשתמשים ב-MediaLibraryService
או
MediaSessionService
אפליקציה יכולה להתאים אישית את ההתראה על ידי הגדרה של
MediaNotification.Provider
ב-onCreate()
שמחליף את
DefaultMediaNotificationProvider
לאחר מכן MediaLibraryService
יטפל
להפעיל את השירות בחזית לפי הצורך.
כשמבטלים את MediaLibraryService.updateNotification()
, האפליקציה יכולה להימשך עוד יותר
בעלות מלאה על פרסום התראה ועל התחלה/הפסקה של השירות
את קדמת התמונה לפי הצורך.
העברת קוד לקוח באמצעות MediaBrowser
ב-AndroidX Media3, MediaBrowser
מיישם את MediaController/Player
ממשקים וניתן להשתמש בהם כדי לשלוט בהפעלת מדיה בנוסף לעיון במדיה
לספרייה. אם הייתם צריכים ליצור MediaBrowserCompat
MediaControllerCompat
בעולם מהדור הקודם, ניתן לעשות זאת רק באמצעות
MediaBrowser
ב-Media3.
אפשר ליצור MediaBrowser
ולהמתין לחיבור אל
השירות בתהליך הגדרה:
scope.launch {
val sessionToken =
SessionToken(context, ComponentName(context, MusicService::class.java)
browser =
MediaBrowser.Builder(context, sessionToken))
.setListener(BrowserListener())
.buildAsync()
.await()
// Get the library root to start browsing the library.
root = browser.getLibraryRoot(/* params= */ null).await();
// Add a MediaController.Listener to listen to player state events.
browser.addListener(playerListener)
playerView.setPlayer(browser)
}
כדאי לבדוק
שליטה בהפעלה במהלך סשן המדיה
כדי ללמוד איך ליצור MediaController
כדי לשלוט בהפעלה
רקע.
שלבים נוספים ופינוי מקום
שגיאות API לא יציבות
אחרי המעבר ל-Media3, יכול להיות שיופיעו שגיאות איתור שגיאות בקוד לגבי שימוש לא יציב ב-API.
ממשקי ה-API האלה בטוחים לשימוש, ושגיאות השגיאות בקוד הן תוצר לוואי
אחריות לתאימות בינארית. אם לא דורשים קוד בינארי מחמיר
תאימות, ניתן לבטל שגיאות אלה באופן בטוח באמצעות @OptIn
הערה.
רקע
גרסאות v1 או v2 של ExoPlayer לא סיפקו אחריות מחמירה לגבי תאימות בינארית. של הספרייה בין הגרסאות הבאות. הפלטפורמה של ExoPlayer API גדול משלב התכנון, כדי לאפשר לאפליקציות להתאים אישית כמעט כל היבט להפעלה. בגרסאות הבאות של ExoPlayer יופיע מדי פעם הסמל שינויי שמות או שינויי תוכנה אחרים שעלולים לגרום לכשלים (למשל שיטות נדרשות חדשות בממשקים). לחשבון ברוב המקרים אפשר לצמצם את הכשלים האלה על ידי הוספת הסמל החדש לצד הוצאה משימוש של הסמל הישן בכמה גרסאות, כדי לאפשר למפתחים זמן להעביר את השימושים שלהם, אבל זה לא תמיד היה אפשרי.
שינויי התוכנה האלה הובילו לשתי בעיות אצל המשתמשים ב-ExoPlayer v1 ו-v2 ספריות:
- שדרוג מגרסת ExoPlayer עלול לגרום להפסקת ההידור של הקוד.
- אפליקציה שתלויה ב-ExoPlayer גם באופן ישיר וגם דרך ביניים היה צריך לוודא ששני יחסי התלות הם אותה גרסה, אחרת, אי-תאימות בינארית עלולה לגרום לקריסות בזמן הריצה.
שיפורים ב-Media3
Media3 מבטיח תאימות בינארית לקבוצת משנה של פלטפורמת ה-API.
חלקים שלא מבטיחים תאימות בינארית מסומנים
@UnstableApi
. כדי להבהיר את ההבחנה הזו, שימושים לא יציבים
בסמלי API יוצרים שגיאת איתור שגיאות בקוד, אלא אם מוסיפים להם הערות עם @OptIn
.
אחרי המעבר מ-ExpoPlayer v2 ל-Media3, ייתכן שתראו הרבה ממשקי API לא יציבים. שגיאות של איתור שגיאות בקוד. כתוצאה מכך, ייתכן שנראה ש-Media3 היא פחות יציבה. מאשר ExoPlayer גרסה 2. זה לא נכון. 'הבלתי היציב' לחלקים מה-Media3 API יש של היציבות כל פלטפורמת ה-API של ExoPlayer v2, שהפלטפורמה היציבה של Media3 API לא זמינה ב-ExoPlayer v2 הכול. ההבדל הוא פשוט ששגיאה של איתור שגיאות בקוד מתריעה בפניכם רמות היציבות.
טיפול בשגיאות של איתור שגיאות בקוד (lint) לא יציב ב-API
מידע על שגיאות שקשורות לתיקון שגיאות זמין בקטע שעוסק בפתרון בעיות.
להוסיף הערות לשימושים ב-Java וב-Kotlin בממשקי API לא יציבים באמצעות @OptIn
.
ממשקי API שהוצאו משימוש
יכול להיות שיהיו קריאות לממשקי API שהוצאו משימוש ב-Android אולפן. מומלץ להחליף קריאות כאלה בחלופה המתאימה. מעבירים את העכבר מעל הסמל כדי לראות את ה-JavaDoc שמציין באיזה API להשתמש במקום זאת.
![צילום מסך: איך להציג JavaDoc עם חלופה לשיטה שהוצאה משימוש](https://developer.android.com/static/media/media3/exoplayer/images/deprecation.png?authuser=2&hl=he)
דוגמאות קוד ואפליקציות להדגמה
- אפליקציית הדגמה לפעילות של AndroidX Media3 (לנייד ו-WearOS)
- פעולות בהתאמה אישית
- התראה בממשק המשתמש של המערכת, MediaButton/BT
- בקרת ההפעלה של Google Assistant
- UAMP: Android Media Player (branch media3) (נייד, AutomotiveOS)
- התראה בממשק המשתמש של המערכת, MediaButton/BT, המשך הפעלה
- בקרת ההפעלה של Google Assistant או WearOS
- AutomotiveOS: פקודה וכניסה בהתאמה אישית