ExoPlayer: ما هو، الميزات والإعداد

المؤلف: IT Sectr نُشر: 2026-05-23 وقت القراءة: 8 دق

ExoPlayer هي مكتبة مشغل وسائط مفتوحة المصدر لأندرويد طورتها Google كبديل لـ MediaPlayer المدمج. يوفر ExoPlayer تشغيل الصوت والفيديو بتنسيقات متعددة، بما في ذلك DASH وHLS وSmoothStreaming وملفات الوسائط العادية، من خلال واجهة برمجة تطبيقات واحدة مع دعم البث التكيفي. وفقاً لـ Google I/O (2024)، يُستخدم ExoPlayer في أكثر من 60,000 تطبيق أندرويد، بما في ذلك YouTube وGoogle TV وNetflix.

الملامح الرئيسية

  • ExoPlayer — مكتبة مشغل وسائط مفتوحة المصدر لأندرويد من Google.
  • تنسيقات متعددة المنصات — يدعم ExoPlayer DASH وHLS وSmoothStreaming وRTSP من خلال نظام إضافات معياري.
  • التخصيص — يمكن استبدال كل مكون من مكونات المشغل (العارض، مصدر البيانات، DRM) بتطبيق مخصص.
  • Canvas و Compose — يتكامل ExoPlayer مع نهج View التقليدي (SurfaceView) و Jetpack Compose.
  • DRM — دعم Widevine وPlayReady وClearKey من خلال نظام DRM معياري.

ما هو ExoPlayer؟

ExoPlayer هي مكتبة تشغيل وسائط متعددة مفتوحة المصدر (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، دعم Compose عبر AndroidX Media3، تحسين معالجة الأخطاء وخوارزميات اختيار المسار التكيفي. بدءاً من الإصدار 2.19 (2024)، أصبح ExoPlayer جزءاً من مكتبة AndroidX Media، مما يبسط التكامل والتحديثات عبر مدير التبعيات القياسي لأندرويد.

بنية 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
HLSبث مباشر HTTP من Appleexoplayer-hls
SmoothStreamingبث تكيفي من Microsoftexoplayer-smoothstreaming
RTSPبروتوكول البث في الوقت الفعلي للمباشرexoplayer-rtsp
Widevineحماية المحتوى بإدارة الحقوق الرقميةexoplayer-drm
Concatenationدمج ملفات وسائط متعددةexoplayer-core
Adsتكامل IMA 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 في مشروع أندرويد

يتم توصيل ExoPlayer بمشروع أندرويد من خلال تبعيات 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()
    }
}

معالجة الأخطاء والحالات

لتطبيقات الإنتاج، من الضروري معالجة أخطاء التشغيل المحتملة: أعطال الشبكة، التنسيقات غير المدعومة، أخطاء ترخيص DRM. يوفر ExoPlayer واجهة Player.Listener مع طرق onPlayerError وonPlaybackStateChanged وonPlayWhenReadyChanged. يُنصح بعرض رسائل خطأ إعلامية للمستخدم مع خيار إعادة المحاولة.

ExoPlayer ضد MediaPlayer: مقارنة

الاختيار بين ExoPlayer و MediaPlayer المدمج هو سؤال شائع عند تطوير تطبيقات أندرويد. 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 ميغابايت (حسب الوحدات)0 (جزء من نظام التشغيل)
الحد الأدنى SDKAPI 16+ (Android 4.1)API 1+
DRMWidevine, PlayReady, ClearKeyWidevine (محدود)

ExoPlayer يفوز في السيناريوهات التي تتطلب البث (DASH, HLS)، تخصيص واجهة المستخدم، دعم DRM والاستقلال عن إصدار Android. MediaPlayer مناسب للتطبيقات البسيطة التي تشغل ملفات وسائط محلية حيث يكون حجم APK مهماً ولا توجد متطلبات للبث التكيفي. للتطبيقات الحديثة التي تحتوي على محتوى من الشبكة، ExoPlayer هو الخيار الواضح.

استثناء — التطبيقات ذات SDK الأدنى أقل من API 16 (Android 4.1)، والتي لا توجد تقريباً في السوق. لجميع التطبيقات ذات targetSdk 33+ والحد الأدنى SDK 21+، ExoPlayer ليس فقط مفضلاً بل ضرورياً لدعم التنسيقات الحديثة مثل AV1 و Dolby Vision من خلال الإضافات المناسبة.

الإعداد المتقدم لـ ExoPlayer

لتطبيقات الإنتاج، غالباً ما يتطلب التكامل الأساسي لـ 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.

كيفية تقليل زمن الوصول في البث المباشر باستخدام ExoPlayer؟

للبث منخفض زمن الوصول، قم بتكوين LoadControl بقيم مخزن مؤقت مستهدفة أصغر: استخدم DefaultLoadControl.Builder().setTargetBufferBytes(1024 * 512).setBufferDurationsMs(500, 2000, 500, 1000) لـ HLS LL و DASH LL. أيضاً، حدد minPlaybackSpeed = 1.02 لتسريع ملء المخزن المؤقت عند التأخر عن البث المباشر.

الخلاصة

  • 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. سوف نقدم لك النصح ونقترح أفضل حل.

مناقشة المشروع

اقرأ أيضًا