Commit 32347362 by aquilescanta Committed by Toni

Select text track matching selected audio language when selecting forced text tracks

PiperOrigin-RevId: 240133676
parent e91eec7c
...@@ -1510,6 +1510,7 @@ public class DefaultTrackSelector extends MappingTrackSelector { ...@@ -1510,6 +1510,7 @@ public class DefaultTrackSelector extends MappingTrackSelector {
} }
AudioTrackScore selectedAudioTrackScore = null; AudioTrackScore selectedAudioTrackScore = null;
String selectedAudioLanguage = null;
int selectedAudioRendererIndex = C.INDEX_UNSET; int selectedAudioRendererIndex = C.INDEX_UNSET;
for (int i = 0; i < rendererCount; i++) { for (int i = 0; i < rendererCount; i++) {
if (C.TRACK_TYPE_AUDIO == mappedTrackInfo.getRendererType(i)) { if (C.TRACK_TYPE_AUDIO == mappedTrackInfo.getRendererType(i)) {
...@@ -1528,7 +1529,10 @@ public class DefaultTrackSelector extends MappingTrackSelector { ...@@ -1528,7 +1529,10 @@ public class DefaultTrackSelector extends MappingTrackSelector {
// score. Clear the selection for that renderer. // score. Clear the selection for that renderer.
definitions[selectedAudioRendererIndex] = null; definitions[selectedAudioRendererIndex] = null;
} }
definitions[i] = audioSelection.first; TrackSelection.Definition definition = audioSelection.first;
definitions[i] = definition;
// We assume that audio tracks in the same group have matching language.
selectedAudioLanguage = definition.group.getFormat(definition.tracks[0]).language;
selectedAudioTrackScore = audioSelection.second; selectedAudioTrackScore = audioSelection.second;
selectedAudioRendererIndex = i; selectedAudioRendererIndex = i;
} }
...@@ -1546,7 +1550,11 @@ public class DefaultTrackSelector extends MappingTrackSelector { ...@@ -1546,7 +1550,11 @@ public class DefaultTrackSelector extends MappingTrackSelector {
break; break;
case C.TRACK_TYPE_TEXT: case C.TRACK_TYPE_TEXT:
Pair<TrackSelection.Definition, Integer> textSelection = Pair<TrackSelection.Definition, Integer> textSelection =
selectTextTrack(mappedTrackInfo.getTrackGroups(i), rendererFormatSupports[i], params); selectTextTrack(
mappedTrackInfo.getTrackGroups(i),
rendererFormatSupports[i],
params,
selectedAudioLanguage);
if (textSelection != null && textSelection.second > selectedTextTrackScore) { if (textSelection != null && textSelection.second > selectedTextTrackScore) {
if (selectedTextRendererIndex != C.INDEX_UNSET) { if (selectedTextRendererIndex != C.INDEX_UNSET) {
// We've already made a selection for another text renderer, but it had a lower score. // We've already made a selection for another text renderer, but it had a lower score.
...@@ -2020,13 +2028,18 @@ public class DefaultTrackSelector extends MappingTrackSelector { ...@@ -2020,13 +2028,18 @@ public class DefaultTrackSelector extends MappingTrackSelector {
* @param formatSupport The result of {@link RendererCapabilities#supportsFormat} for each mapped * @param formatSupport The result of {@link RendererCapabilities#supportsFormat} for each mapped
* track, indexed by track group index and track index (in that order). * track, indexed by track group index and track index (in that order).
* @param params The selector's current constraint parameters. * @param params The selector's current constraint parameters.
* @param selectedAudioLanguage The language of the selected audio track. May be null if the
* selected audio track declares no language or no audio track was selected.
* @return The {@link TrackSelection.Definition} and corresponding track score, or null if no * @return The {@link TrackSelection.Definition} and corresponding track score, or null if no
* selection was made. * selection was made.
* @throws ExoPlaybackException If an error occurs while selecting the tracks. * @throws ExoPlaybackException If an error occurs while selecting the tracks.
*/ */
@Nullable @Nullable
protected Pair<TrackSelection.Definition, Integer> selectTextTrack( protected Pair<TrackSelection.Definition, Integer> selectTextTrack(
TrackGroupArray groups, int[][] formatSupport, Parameters params) TrackGroupArray groups,
int[][] formatSupport,
Parameters params,
@Nullable String selectedAudioLanguage)
throws ExoPlaybackException { throws ExoPlaybackException {
TrackGroup selectedGroup = null; TrackGroup selectedGroup = null;
int selectedTrackIndex = 0; int selectedTrackIndex = 0;
...@@ -2047,20 +2060,26 @@ public class DefaultTrackSelector extends MappingTrackSelector { ...@@ -2047,20 +2060,26 @@ public class DefaultTrackSelector extends MappingTrackSelector {
if (languageScore > 0 if (languageScore > 0
|| (params.selectUndeterminedTextLanguage && formatHasNoLanguage(format))) { || (params.selectUndeterminedTextLanguage && formatHasNoLanguage(format))) {
if (isDefault) { if (isDefault) {
trackScore = 11; trackScore = 13;
} else if (!isForced) { } else if (!isForced) {
// Prefer non-forced to forced if a preferred text language has been specified. Where // Prefer non-forced to forced if a preferred text language has been specified. Where
// both are provided the non-forced track will usually contain the forced subtitles as // both are provided the non-forced track will usually contain the forced subtitles as
// a subset. // a subset.
trackScore = 8; trackScore = 10;
} else { } else {
trackScore = 5; trackScore = 7;
} }
trackScore += languageScore; trackScore += languageScore;
} else if (isDefault) { } else if (isDefault) {
trackScore = 4; trackScore = 6;
} else if (isForced) { } else if (isForced) {
trackScore = 1 + languageScore; int preferredAudioLanguageScore =
getFormatLanguageScore(format, params.preferredAudioLanguage);
if (preferredAudioLanguageScore > 0) {
trackScore = 3 + preferredAudioLanguageScore;
} else {
trackScore = 1 + getFormatLanguageScore(format, selectedAudioLanguage);
}
} else { } else {
// Track should not be selected. // Track should not be selected.
continue; continue;
......
...@@ -888,7 +888,7 @@ public final class DefaultTrackSelectorTest { ...@@ -888,7 +888,7 @@ public final class DefaultTrackSelectorTest {
/** Tests text track selection flags. */ /** Tests text track selection flags. */
@Test @Test
public void testsTextTrackSelectionFlags() throws ExoPlaybackException { public void testTextTrackSelectionFlags() throws ExoPlaybackException {
Format forcedOnly = buildTextFormat("forcedOnly", "eng", C.SELECTION_FLAG_FORCED); Format forcedOnly = buildTextFormat("forcedOnly", "eng", C.SELECTION_FLAG_FORCED);
Format forcedDefault = Format forcedDefault =
buildTextFormat("forcedDefault", "eng", C.SELECTION_FLAG_FORCED | C.SELECTION_FLAG_DEFAULT); buildTextFormat("forcedDefault", "eng", C.SELECTION_FLAG_FORCED | C.SELECTION_FLAG_DEFAULT);
...@@ -968,6 +968,55 @@ public final class DefaultTrackSelectorTest { ...@@ -968,6 +968,55 @@ public final class DefaultTrackSelectorTest {
} }
/** /**
* Tests that the default track selector will select a forced text track matching the selected
* audio language when no text language preferences match.
*/
@Test
public void testSelectingForcedTextTrackMatchesAudioLanguage() throws ExoPlaybackException {
Format forcedEnglish =
buildTextFormat(/* id= */ "forcedEnglish", /* language= */ "eng", C.SELECTION_FLAG_FORCED);
Format forcedGerman =
buildTextFormat(/* id= */ "forcedGerman", /* language= */ "deu", C.SELECTION_FLAG_FORCED);
Format audio = buildAudioFormat(/* id= */ "audio");
Format germanAudio =
buildAudioFormat(
/* id= */ "germanAudio",
MimeTypes.AUDIO_AAC,
/* bitrate= */ Format.NO_VALUE,
"deu",
/* selectionFlags= */ 0,
/* channelCount= */ Format.NO_VALUE,
/* sampleRate= */ Format.NO_VALUE);
RendererCapabilities[] rendererCapabilities =
new RendererCapabilities[] {
ALL_AUDIO_FORMAT_SUPPORTED_RENDERER_CAPABILITIES,
ALL_TEXT_FORMAT_SUPPORTED_RENDERER_CAPABILITIES
};
// The audio declares no language. The first forced text track should be selected.
TrackGroupArray trackGroups = wrapFormats(audio, forcedEnglish, forcedGerman);
TrackSelectorResult result =
trackSelector.selectTracks(rendererCapabilities, trackGroups, periodId, TIMELINE);
assertFixedSelection(result.selections.get(1), trackGroups, forcedEnglish);
// Ditto.
trackGroups = wrapFormats(audio, forcedGerman, forcedEnglish);
result = trackSelector.selectTracks(rendererCapabilities, trackGroups, periodId, TIMELINE);
assertFixedSelection(result.selections.get(1), trackGroups, forcedGerman);
// The audio declares german. The german forced track should be selected.
trackGroups = wrapFormats(germanAudio, forcedGerman, forcedEnglish);
result = trackSelector.selectTracks(rendererCapabilities, trackGroups, periodId, TIMELINE);
assertFixedSelection(result.selections.get(1), trackGroups, forcedGerman);
// Ditto
trackGroups = wrapFormats(germanAudio, forcedEnglish, forcedGerman);
result = trackSelector.selectTracks(rendererCapabilities, trackGroups, periodId, TIMELINE);
assertFixedSelection(result.selections.get(1), trackGroups, forcedGerman);
}
/**
* Tests that the default track selector will select a text track with undetermined language if no * Tests that the default track selector will select a text track with undetermined language if no
* text track with the preferred language is available but * text track with the preferred language is available but
* {@link Parameters#selectUndeterminedTextLanguage} is true. * {@link Parameters#selectUndeterminedTextLanguage} is true.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or sign in to comment