From ee4d297f22a3b6775a13a64cf9a97e229be21f00 Mon Sep 17 00:00:00 2001 From: andrewlewis Date: Fri, 30 Sep 2016 05:46:14 -0700 Subject: [PATCH] Fix seeking in the last period. When reading the last period, the readingPeriodHolder was set to null in updatePeriods if it was the last period. (This would occur almost immediately when playing a single-period source.) seekToPeriodPosition suppresses reusing a loaded/prepared period if the reading period and playing period did not match, which meant that the whole timeline was recreated when seeking in the last period. Leave readingPeriodHolder non-null. This means that at all times either playingPeriodHolder == readingPeriodHolder (and they could be null or non-null), or playingPeriodHolder and readingPeriodHolder differ and are both non-null. Also fix an issue where streams were never forced to be recreated during track reselection when reading ahead. ------------- Created by MOE: https://github.com/google/moe MOE_MIGRATED_REVID=134774238 --- .../exoplayer2/ExoPlayerImplInternal.java | 29 ++++++++----------- 1 file changed, 12 insertions(+), 17 deletions(-) diff --git a/library/src/main/java/com/google/android/exoplayer2/ExoPlayerImplInternal.java b/library/src/main/java/com/google/android/exoplayer2/ExoPlayerImplInternal.java index 84ed37af8b..2a9360337a 100644 --- a/library/src/main/java/com/google/android/exoplayer2/ExoPlayerImplInternal.java +++ b/library/src/main/java/com/google/android/exoplayer2/ExoPlayerImplInternal.java @@ -529,9 +529,9 @@ import java.io.IOException; rebuffering = false; setState(ExoPlayer.STATE_BUFFERING); - if (periodPositionUs == C.TIME_UNSET - || (readingPeriodHolder != playingPeriodHolder && (periodIndex == playingPeriodHolder.index - || (readingPeriodHolder != null && periodIndex == readingPeriodHolder.index)))) { + if (periodPositionUs == C.TIME_UNSET || (readingPeriodHolder != playingPeriodHolder + && (periodIndex == playingPeriodHolder.index + || periodIndex == readingPeriodHolder.index))) { // Clear the timeline because either the seek position is not known, or a renderer is reading // ahead to the next period and the seek is to either the playing or reading period. periodIndex = C.INDEX_UNSET; @@ -690,16 +690,14 @@ import java.io.IOException; } if (selectionsChangedForReadPeriod) { - // Release everything after the playing period because a renderer may have read data from a - // track whose selection has now changed. + // Update streams and rebuffer for the new selection, recreating all streams if reading ahead. + boolean recreateStreams = readingPeriodHolder != playingPeriodHolder; releasePeriodHoldersFrom(playingPeriodHolder.next); playingPeriodHolder.next = null; readingPeriodHolder = playingPeriodHolder; loadingPeriodHolder = playingPeriodHolder; bufferAheadPeriodCount = 0; - // Update streams for the new selection, recreating all streams if reading ahead. - boolean recreateStreams = readingPeriodHolder != playingPeriodHolder; boolean[] streamResetFlags = new boolean[renderers.length]; long periodPositionUs = playingPeriodHolder.updatePeriodTrackSelection( playbackInfo.positionUs, loadControl, recreateStreams, streamResetFlags); @@ -810,11 +808,11 @@ import java.io.IOException; playingPeriodHolder.setIndex(timeline, timeline.getWindow(period.windowIndex, window), index); - MediaPeriodHolder previousPeriod = playingPeriodHolder; + MediaPeriodHolder previousPeriodHolder = playingPeriodHolder; boolean seenReadingPeriod = false; bufferAheadPeriodCount = 0; - while (previousPeriod.next != null) { - MediaPeriodHolder periodHolder = previousPeriod.next; + while (previousPeriodHolder.next != null) { + MediaPeriodHolder periodHolder = previousPeriodHolder.next; index++; timeline.getPeriod(index, period, true); if (!periodHolder.uid.equals(period.uid)) { @@ -835,7 +833,7 @@ import java.io.IOException; } // Update the loading period to be the latest period that is still valid. - loadingPeriodHolder = previousPeriod; + loadingPeriodHolder = previousPeriodHolder; loadingPeriodHolder.next = null; // Release the rest of the timeline. @@ -849,7 +847,7 @@ import java.io.IOException; if (periodHolder == readingPeriodHolder) { seenReadingPeriod = true; } - previousPeriod = periodHolder; + previousPeriodHolder = periodHolder; } } else if (loadingPeriodHolder != null) { Object uid = loadingPeriodHolder.uid; @@ -997,14 +995,11 @@ import java.io.IOException; } updateTimelineState(); - if (readingPeriodHolder != null && readingPeriodHolder.isLast) { - readingPeriodHolder = null; + if (readingPeriodHolder.isLast) { + // The renderers have their final SampleStreams. for (Renderer renderer : enabledRenderers) { renderer.setCurrentStreamIsFinal(); } - } - if (readingPeriodHolder == null) { - // The renderers have their final SampleStreams. return; }