ایجاد و پیکربندی DefaultPreloadManager

این صفحه نحوه ایجاد DefaultPreloadManager را توضیح می‌دهد که براساس استراتژی انتخابی شما، محتوای رسانه‌ای را برای برنامه شما ازقبل بار می‌کند.

مدیران پیش‌بارگذاری براساس کلاس انتزاعی BasePreloadManager به شما امکان می‌دهند محتوا را براساس معیارهای انتخابی‌تان رتبه‌بندی کنید. این سند توضیح می‌دهد که چگونه از کلاس مشتق‌شده DefaultPreloadManager استفاده کنید، که در آن هر عنصر رسانه‌ای با یک عدد صحیح که نشان‌دهنده مکان آن در یک فهرست است رتبه‌بندی می‌شود (برای مثال، موقعیت آن در یک گردونه ویدیویی). مدیر پیش‌بارگذاری براساس میزان نزدیکی به محصولی که کاربر درحال پخش آن است، بارگذاری محصولات را اولویت‌بندی می‌کند. به این ترتیب، اگر کاربر به مورد دیگری برود، مورد جدید می‌تواند بلافاصله شروع به پخش کند.

ایجاد نمونه DefaultPreloadManager سه مرحله دارد:

  • TargetPreloadStatusControl را تعریف کنید که مدیر پیش‌بارگیری بتواند با پُرسمان کردن آن متوجه شود که آیا عنصر رسانه‌ای آماده بار شدن است یا نه و چه مقدار از آن باید بار شود.
  • سازنده‌ای ایجاد کنید که از آن برای ایجاد مدیر پیش‌بارگذاری و ایجاد اشیاء ExoPlayer برنامه‌تان استفاده خواهید کرد.
  • با فراخوانی روش سازنده build()، از سازنده برای ایجاد مدیر پیش‌بارگذاری استفاده کنید.

ایجاد کنترل وضعیت پیش‌بار کردن هدف

وقتی DefaultPreloadManager.Builder را ایجاد می‌کنید، هدف کنترل وضعیت پیش‌بارگذاری را به آن منتقل می‌کنید که خودتان تعریف کرده‌اید. این شیء رابط TargetPreloadStatusControl را پیاده‌سازی می‌کند. وقتی مدیر پیش‌بارگذاری درحال آماده شدن برای پیش‌بارگذاری رسانه است، روش getTargetPreloadStatus() کنترل وضعیت شما را فرا می‌خواند تا تعیین کند که آیا محتوا را برای یک عنصر رسانه‌ای آماده، بار، یا ذخیره کند. بار کردن پیش‌فرض داده‌های رسانه را مستقیماً در بافر درون حافظه پخش‌کننده بار می‌کند و آن را برای بازپخش فوری آماده می‌کند، درحالی‌که ذخیره در حافظه نهان داده‌های رسانه را در حافظه نهان دیسک ماندگار ذخیره می‌کند تا حافظه پخش‌کننده را ذخیره کند. کنترل وضعیت می‌تواند با یکی از این کدهای وضعیت پاسخ دهد:

  • STAGE_SPECIFIED_RANGE_LOADED: مدیر پیش‌بارگذاری باید محتوا را از موقعیت شروع مشخص‌شده و برای مدت مشخص‌شده (به میلی‌ثانیه) در بافر درون حافظه پخش‌کننده بار کند.
  • STAGE_SPECIFIED_RANGE_CACHED: مدیر پیش‌بارگذاری باید محتوا را از موقعیت شروع مشخص‌شده و برای مدت مشخص‌شده (به میلی‌ثانیه) در حافظه نهان دیسک ذخیره کند.
  • STAGE_TRACKS_SELECTED: مدیر پیش‌بارگذاری باید اطلاعات قطعه محتوا را بارگذاری و پردازش کند و قطعه‌ها را انتخاب کند. مدیر پیش‌بارگذاری نباید هنوز شروع به بار کردن محتوا کند.
  • STAGE_SOURCE_PREPARED: مدیر پیش‌بارگذاری باید منبع محتوا را آماده کند. برای مثال، اگر فراداده محتوا در فایل مانیفست جداگانه‌ای باشد، مدیر پیش‌بارگذاری ممکن است آن مانیفست را واکشی و تجزیه کند.
  • null: مدیر پیش‌بار نباید هیچ محتوا یا فراداده‌ای را برای آن مورد رسانه‌ای بار کند.

باید استراتژی‌ای برای تصمیم‌گیری درباره میزان محتوایی که برای هر عنصر رسانه‌ای بار می‌کنید داشته باشید. در این مثال، محتوای بیشتری برای مواردی که به مورد درحال پخش نزدیک‌تر هستند بار می‌شود. اگر کاربر محتوایی با شاخص n پخش می‌کند، کنترل‌کننده کدهای زیر را برمی‌گرداند:

  • نمایه n+۱ (مورد رسانه‌ای بعدی): بار کردن ۳۰۰۰ میلی‌ثانیه (۳ ثانیه) از جای شروع پیش‌فرض
  • نمایه n-1 (فایل رسانه‌ای قبلی): بار کردن ۱۰۰۰ میلی‌ثانیه (۱ ثانیه) از موقعیت شروع پیش‌فرض
  • فایل‌های رسانه‌ای دیگر در محدوده n-2 تا n+2: برگشت PreloadStatus.TRACKS_SELECTED
  • فایل‌های رسانه‌ای دیگر در محدوده n-4 تا n+4: برگشت PreloadStatus.SOURCE_PREPARED
  • برای همه عناصر رسانه‌ای دیگر، null را برگردانید

class MyTargetPreloadStatusControl(var currentPlayingIndex: Int = 0) :
  TargetPreloadStatusControl<Int, DefaultPreloadManager.PreloadStatus> {

  override fun getTargetPreloadStatus(index: Int): DefaultPreloadManager.PreloadStatus {
    if (index - currentPlayingIndex == 1) { // next track
      // return a PreloadStatus that is labelled by STAGE_SPECIFIED_RANGE_LOADED and
      // suggest loading 3000ms from the default start position
      return DefaultPreloadManager.PreloadStatus.specifiedRangeLoaded(3000L)
    } else if (index - currentPlayingIndex == -1) { // previous track
      // return a PreloadStatus that is labelled by STAGE_SPECIFIED_RANGE_LOADED and
      // suggest loading 3000ms from the default start position
      return DefaultPreloadManager.PreloadStatus.specifiedRangeLoaded(3000L)
    } else if (abs(index - currentPlayingIndex) == 2) {
      // return a PreloadStatus that is labelled by STAGE_TRACKS_SELECTED
      return DefaultPreloadManager.PreloadStatus.PRELOAD_STATUS_TRACKS_SELECTED
    } else if (abs(index - currentPlayingIndex) <= 4) {
      // return a PreloadStatus that is labelled by STAGE_SOURCE_PREPARED
      return DefaultPreloadManager.PreloadStatus.PRELOAD_STATUS_SOURCE_PREPARED
    }
    return DefaultPreloadManager.PreloadStatus.PRELOAD_STATUS_NOT_PRELOADED
  }
}

نکات کلیدی درباره کد

  • وقتی نمونه‌ای از MyTargetPreloadStatusControl را ایجاد می‌کنید، آن را به سازنده مدیر پیش‌بارگذاری منتقل می‌کنید.
  • currentPlayingIndex شاخص هر مورد رسانه‌ای را که درحال پخش است نگه می‌دارد. این وظیفه برنامه است که این مقدار را به‌روز نگه دارد.
  • وقتی مدیر پیش‌بارگذاری آماده بار کردن محتوا باشد، getTargetPreloadStatus را فرا می‌خواند و اطلاعات رتبه‌بندی‌ای را که برای آن عنصر رسانه‌ای مربوطه مشخص کرده‌اید ارسال می‌کند. در مورد DefaultPreloadManager، این اطلاعات رتبه‌بندی یک عدد صحیح است که موقعیت مورد را در گردونه مشخص می‌کند. این روش با مقایسه آن شاخص با شاخص موردی که درحال‌حاضر انتخاب شده است، کد برگشتی را انتخاب می‌کند.

ایجاد مدیر پیش‌بارگذاری

برای ایجاد مدیر پیش‌بارگذاری، به DefaultPreloadManager.Builder نیاز دارید. این سازنده با بافت کنونی و کنترل وضعیت پیش‌بار هدف برنامه پیکربندی شده است. می‌توانید مدیر پیش‌بارگذاری را با همه پیکربندی‌های پیش‌فرض ایجاد کنید.

val targetPreloadStatusControl = MyTargetPreloadStatusControl()
val preloadManagerBuilder = DefaultPreloadManager.Builder(context, targetPreloadStatusControl)
val preloadManager = preloadManagerBuilder.build()

سازنده همچنین روش‌های تنظیم‌کننده‌ای ارائه می‌دهد که می‌توانید از آن‌ها برای تنظیم کردن عناصر سفارشی مدیر پیش‌بارگذاری استفاده کنید.

برای مثال، می‌توانید بایت‌های بافر کل هدف را برای همه منابع رسانه‌ای پیش‌بارگذاری در DefaultPreloadManager سفارشی‌سازی کنید، به‌طوری که داده‌های پیش‌بارگذاری‌شده از این حد فراتر نرود. می‌توانید این محدودیت را بااستفاده از setPlayerTargetBufferBytes(String, int) در DefaultLoadControl.Builder سفارشی با نام پخش‌کننده "preload" پیکربندی کنید و آن نمونه را به سازنده مدیر پیش‌بارگیری منتقل کنید:

val targetPreloadStatusControl = MyTargetPreloadStatusControl()
val preloadManagerBuilder = DefaultPreloadManager.Builder(context, targetPreloadStatusControl)

preloadManagerBuilder.setLoadControl(
  DefaultLoadControl.Builder()
    .setPlayerTargetBufferBytes("preload", 128 * 1024 * 1024) // 128 MiB
    .build()
)
val preloadManager = preloadManagerBuilder.build()

اگرچه روش‌های تنظیم‌کننده سازنده اساساً برای سفارشی‌سازی اختیاری هستند، اگر می‌خواهید هریک از عناصر رسانه‌ای را در دیسک ذخیره کنید، باید سازنده را با Cache ازطریق فراخوانی setCache() پیکربندی کنید. اگر حافظه نهان پیکربندی نشده باشد، تلاش برای ذخیره کردن موارد رسانه‌ای منجر به IllegalStateException خواهد شد.

‫ExoPlayer را برای پخش کردن فایل رسانه‌ای پیش‌بارگذاری‌شده ایجاد کنید

علاوه‌بر استفاده از سازنده برای ایجاد مدیر پیش‌بارگذاری، از آن برای ایجاد اشیای ExoPlayer که برنامه‌تان برای پخش محتوا استفاده می‌کند نیز استفاده خواهید کرد، تا ExoPlayer مؤلفه‌ها را به‌درستی با مدیر پیش‌بارگذاری هم‌رسانی کند. همچنان می‌توانید پیکربندی‌های خاص بازپخش را برای ExoPlayer با ارسال نمونه ExoPlayer.Builder با پیکربندی‌های تنظیم‌شده تعیین کنید.

// Direct creation
val exoPlayer = preloadManagerBuilder.buildExoPlayer()

// Creation with custom playback specific configurations
val skipSilenceExoPlayerBuilder = ExoPlayer.Builder(context).setSkipSilenceEnabled(true)
val skipSilenceExoPlayer = preloadManagerBuilder.buildExoPlayer(skipSilenceExoPlayerBuilder)