mirror of
https://github.com/androidx/media.git
synced 2025-04-30 06:46:50 +08:00
Avoid clipping live offset override to min/max offsets
The live offset override is used to replace the media-defined
live offset after user seeks to ensure the live adjustment adjusts
to the new user-provided live offset and doesn't go back to the
original one.
However, the code currently clips the override to the min/max
live offsets defined in LiveConfiguration. This is useful to
clip the default value (in case of inconsistent values in the media),
but the clipping shouldn't be applied to user overrides as
the player will then adjust the position back to the min/max
and doesn't stay at the desired user position.
See 2416d99857 (r132871601)
PiperOrigin-RevId: 584311004
(cherry picked from commit af0282b9db62a8c5de1dbcc49794872d0157c1ab)
This commit is contained in:
parent
ea642a41e9
commit
c9f6ad0398
@ -4,6 +4,9 @@
|
||||
|
||||
* Common Library:
|
||||
* ExoPlayer:
|
||||
* Fix issue where manual seeks outside of the
|
||||
`LiveConfiguration.min/maxOffset` range keep adjusting the offset back
|
||||
to `min/maxOffset`.
|
||||
* Transformer:
|
||||
* Track Selection:
|
||||
* Extractors:
|
||||
|
@ -379,15 +379,16 @@ public final class DefaultLivePlaybackSpeedControl implements LivePlaybackSpeedC
|
||||
private void maybeResetTargetLiveOffsetUs() {
|
||||
long idealOffsetUs = C.TIME_UNSET;
|
||||
if (mediaConfigurationTargetLiveOffsetUs != C.TIME_UNSET) {
|
||||
idealOffsetUs =
|
||||
targetLiveOffsetOverrideUs != C.TIME_UNSET
|
||||
? targetLiveOffsetOverrideUs
|
||||
: mediaConfigurationTargetLiveOffsetUs;
|
||||
if (minTargetLiveOffsetUs != C.TIME_UNSET && idealOffsetUs < minTargetLiveOffsetUs) {
|
||||
idealOffsetUs = minTargetLiveOffsetUs;
|
||||
}
|
||||
if (maxTargetLiveOffsetUs != C.TIME_UNSET && idealOffsetUs > maxTargetLiveOffsetUs) {
|
||||
idealOffsetUs = maxTargetLiveOffsetUs;
|
||||
if (targetLiveOffsetOverrideUs != C.TIME_UNSET) {
|
||||
idealOffsetUs = targetLiveOffsetOverrideUs;
|
||||
} else {
|
||||
idealOffsetUs = mediaConfigurationTargetLiveOffsetUs;
|
||||
if (minTargetLiveOffsetUs != C.TIME_UNSET && idealOffsetUs < minTargetLiveOffsetUs) {
|
||||
idealOffsetUs = minTargetLiveOffsetUs;
|
||||
}
|
||||
if (maxTargetLiveOffsetUs != C.TIME_UNSET && idealOffsetUs > maxTargetLiveOffsetUs) {
|
||||
idealOffsetUs = maxTargetLiveOffsetUs;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (idealTargetLiveOffsetUs == idealOffsetUs) {
|
||||
|
@ -112,7 +112,7 @@ public class DefaultLivePlaybackSpeedControlTest {
|
||||
|
||||
@Test
|
||||
public void
|
||||
getTargetLiveOffsetUs_afterSetTargetLiveOffsetOverrideUsGreaterThanMax_returnsMaxLiveOffset() {
|
||||
getTargetLiveOffsetUs_afterSetTargetLiveOffsetOverrideUsGreaterThanMax_returnsOverride() {
|
||||
DefaultLivePlaybackSpeedControl defaultLivePlaybackSpeedControl =
|
||||
new DefaultLivePlaybackSpeedControl.Builder().build();
|
||||
|
||||
@ -128,12 +128,12 @@ public class DefaultLivePlaybackSpeedControlTest {
|
||||
|
||||
long targetLiveOffsetUs = defaultLivePlaybackSpeedControl.getTargetLiveOffsetUs();
|
||||
|
||||
assertThat(targetLiveOffsetUs).isEqualTo(400_000);
|
||||
assertThat(targetLiveOffsetUs).isEqualTo(123_456_789);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void
|
||||
getTargetLiveOffsetUs_afterSetTargetLiveOffsetOverrideUsLessThanMin_returnsMinLiveOffset() {
|
||||
getTargetLiveOffsetUs_afterSetTargetLiveOffsetOverrideUsLessThanMin_returnsOverride() {
|
||||
DefaultLivePlaybackSpeedControl defaultLivePlaybackSpeedControl =
|
||||
new DefaultLivePlaybackSpeedControl.Builder().build();
|
||||
|
||||
@ -149,7 +149,7 @@ public class DefaultLivePlaybackSpeedControlTest {
|
||||
|
||||
long targetLiveOffsetUs = defaultLivePlaybackSpeedControl.getTargetLiveOffsetUs();
|
||||
|
||||
assertThat(targetLiveOffsetUs).isEqualTo(5_000);
|
||||
assertThat(targetLiveOffsetUs).isEqualTo(3_141);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -10594,6 +10594,57 @@ public final class ExoPlayerTest {
|
||||
assertThat(liveOffsetAtEnd).isIn(Range.closed(1_900L, 2_100L));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void targetLiveOffsetInMedia_withUserSeekOutsideMaxLivOffset_adjustsLiveOffsetToSeek()
|
||||
throws Exception {
|
||||
long windowStartUnixTimeMs = 987_654_321_000L;
|
||||
long nowUnixTimeMs = windowStartUnixTimeMs + 20_000;
|
||||
ExoPlayer player =
|
||||
new TestExoPlayerBuilder(context)
|
||||
.setClock(
|
||||
new FakeClock(/* initialTimeMs= */ nowUnixTimeMs, /* isAutoAdvancing= */ true))
|
||||
.build();
|
||||
Timeline timeline =
|
||||
new FakeTimeline(
|
||||
new TimelineWindowDefinition(
|
||||
/* periodCount= */ 1,
|
||||
/* id= */ 0,
|
||||
/* isSeekable= */ true,
|
||||
/* isDynamic= */ true,
|
||||
/* isLive= */ true,
|
||||
/* isPlaceholder= */ false,
|
||||
/* durationUs= */ 1000 * C.MICROS_PER_SECOND,
|
||||
/* defaultPositionUs= */ 8 * C.MICROS_PER_SECOND,
|
||||
/* windowOffsetInFirstPeriodUs= */ Util.msToUs(windowStartUnixTimeMs),
|
||||
ImmutableList.of(AdPlaybackState.NONE),
|
||||
new MediaItem.Builder()
|
||||
.setUri(Uri.EMPTY)
|
||||
.setLiveConfiguration(
|
||||
new MediaItem.LiveConfiguration.Builder()
|
||||
.setTargetOffsetMs(9_000)
|
||||
.setMaxOffsetMs(10_000)
|
||||
.build())
|
||||
.build()));
|
||||
player.pause();
|
||||
player.setMediaSource(new FakeMediaSource(timeline));
|
||||
player.prepare();
|
||||
TestPlayerRunHelper.runUntilPlaybackState(player, Player.STATE_READY);
|
||||
long liveOffsetAtStart = player.getCurrentLiveOffset();
|
||||
// Verify test setup (now = 20 seconds in live window, default start position = 8 seconds).
|
||||
assertThat(liveOffsetAtStart).isIn(Range.closed(11_900L, 12_100L));
|
||||
|
||||
// Seek to a live offset of 15 seconds (outside of declared max offset of 10 seconds).
|
||||
player.seekTo(5_000);
|
||||
// Play until close to the end of the available live window.
|
||||
TestPlayerRunHelper.playUntilPosition(
|
||||
player, /* mediaItemIndex= */ 0, /* positionMs= */ 999_000);
|
||||
long liveOffsetAtEnd = player.getCurrentLiveOffset();
|
||||
player.release();
|
||||
|
||||
// Assert the live offset adjustment was permanent.
|
||||
assertThat(liveOffsetAtEnd).isIn(Range.closed(14_100L, 15_900L));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void targetLiveOffsetInMedia_withTimelineUpdate_adjustsLiveOffsetToLatestTimeline()
|
||||
throws Exception {
|
||||
|
Loading…
x
Reference in New Issue
Block a user