تحية للجميع.قبل يومين ، كانت هناك مهمة لتبديل ترجمات WebVTT في تدفق HLS.نشغل الفيديو باستخدام ExoPlayer ، وبدا في البداية أنه سيتعين على Google and Co. توفير حل من مربع "أخذها وفعلها". لكن الواقع لم يتزامن مع التوقعات :)لم يؤد Googling و Habring إلى نتيجة ، وكل ذلك جاء لاختيار التطبيق التجريبي الرسمي ExoPlayer.لان نظرًا لأن المقالة تفترض بعض الإلمام ببنية HLS ووجود بعض الخبرة في ExoPlayer ، فإننا نصل إلى هذه النقطة.هذا ما تخبرنا به الوثائق حول تبديل التدفقات (الفيديو والصوت والترجمات). ولا تخبرنا بأي شيء تقريبًا - قم بتهيئة اللاعب باستخدام DefaultTrackSelector واستخدمه. هذا كل شيء ، حسنًا :)يتم تخزين جميع الترجمات من أي نوع (CEA-608 ، WebVtt) مثل أي مسارات أخرى داخل DefaultTrackSelector ويجب أن تكون قادرًا على الوصول إليها. ينقسم كل شيء إلى مجموعات ومجموعات فرعية ، وباختصار ، تبدو البنية الداخلية على النحو التالي:الآن دعنا نحاول الحصول على ترجمات من نوع WebVTT ، يجب تخزينها داخل Renderer بنوع "3" (C.TRACK_TYPE_TEXT - ثابت في Exo):fun getVttSubtitles(): List<String> {
val tracks = mutableListOf<String>()
defaultTrackSelector.currentMappedTrackInfo?.let { mappedTrackInfo ->
val renderCount = mappedTrackInfo.rendererCount
for (renderIndex in 0 until renderCount) {
val renderType = mappedTrackInfo.getRendererType(renderIndex)
if (renderType == C.TRACK_TYPE_TEXT) {
val trackGroupArray = mappedTrackInfo.getTrackGroups(renderIndex)
for (trackGroupArrayIndex in 0 until trackGroupArray.length) {
val trackGroup = trackGroupArray[trackGroupArrayIndex]
for (trackGroupIndex in 0 until trackGroup.length) {
val format = trackGroup.getFormat(trackGroupIndex)
if (format.sampleMimeType == MimeTypes.TEXT_VTT) {
tracks += format.language.orEmpty()
}
}
}
}
}
}
return tracks
}
كما ترون ، لا يتم توفير بعض الطرق المناسبة للتكرار والبحث ويجب عليك القيام بكل الحلقات باستخدام الأقلام.لكننا بحاجة إلى معرفة ليس فقط عن القائمة نفسها ، ولكن أيضًا عن الخيارات المحددة (التي سنختارها في المستقبل). لسبب ما ، لا يمكنك الحصول على المسارات المحددة من DefaultTrackSelector ، ولكن يمكنك استخدام ExoPlayer نفسه. مخطط الحصول هو نفسه تقريبًا ، نتعمق ، ولكن هنا نتخطى الممر من خلال العارضين:fun getSelectedVttSubtitles(): List<String> {
val selectedLangs = mutableListOf<String>()
val currentTrackSelections = exoPlayer.currentTrackSelections
for (selectionIndex in 0 until currentTrackSelections.length) {
val trackSelection = currentTrackSelections[selectionIndex]
if (trackSelection != null) {
val length = trackSelection.length()
for (trackIndex in 0 until length) {
val format = trackSelection.getFormat(trackIndex)
if (format.sampleMimeType == MimeTypes.TEXT_VTT) {
selectedLangs += format.language.orEmpty()
}
}
}
}
return selectedLangs
}
حسنًا ، لدينا قائمة مشتركة وقائمة مختارة. كيفية الجمع والعرض على واجهة المستخدم ليس الغرض من هذه المقالة. هناك عدة طرق. علينا فقط أن نتعلم كيفية ضبط المسار.من أجل الوضوح ، سنقوم بذلك بطريقة جبينية ، بحيث تكون جميع الدورات والمؤشرات واضحة.تركيب مسار برمز لغته ("ru" ، "en" ، ...):fun selectTrackByIsoCodeAndType(langCode: String) {
defaultTrackSelector.currentMappedTrackInfo?.let { mappedTrackInfo ->
val renderCount = mappedTrackInfo.rendererCount
for (renderIndex in 0 until renderCount) {
val renderType = mappedTrackInfo.getRendererType(renderIndex)
if (renderType == C.TRACK_TYPE_TEXT) {
val trackGroupArray = mappedTrackInfo.getTrackGroups(renderIndex)
for (trackGroupArrayIndex in 0 until trackGroupArray.length) {
val trackGroup = trackGroupArray[trackGroupArrayIndex]
for (trackGroupIndex in 0 until trackGroup.length) {
val format = trackGroup.getFormat(trackGroupIndex)
if (format.sampleMimeType == MimeTypes.TEXT_VTT
&& format.language == langCode
) {
val currentParams = defaultTrackSelector.buildUponParameters()
currentParams.clearSelectionOverride(
renderIndex, trackGroupArray
)
val override = DefaultTrackSelector.SelectionOverride(
trackGroupArrayIndex, trackGroupIndex
)
currentParams.setSelectionOverride(
renderIndex,
trackGroupArray,
override
)
defaultTrackSelector.setParameters(currentParams)
return
}
}
}
}
}
}
}
استنتاج
لقد قمنا بتغطية أساسيات كيفية الحصول على ترجمات WebVTT وتبديلها في ExoPlayer.في الواقع ، يمكن أن تعمل الطريقة نفسها بسهولة مع الأنواع الأخرى من الترجمات - يكفي تحديد الأساليب بالنوع. بنفس الطريقة ، لن يكون من الصعب العمل مع المسارات الصوتية. بالطبع ، من الصعب جدًا استخدام الحل في هذا النموذج ويتطلب إحضاره إلى شكل أكثر ملاءمة.شكرا للانتباه.