honour shuffle order when publishing queue to media session
Issue #5360 PiperOrigin-RevId: 235196177
This commit is contained in:
parent
eea1ce3e0a
commit
e8077fb3f4
@ -60,6 +60,8 @@
|
|||||||
`TrackSelectionDialogBuilder` and add option to select multiple overrides.
|
`TrackSelectionDialogBuilder` and add option to select multiple overrides.
|
||||||
* MediaSessionConnector: Let apps intercept media button events
|
* MediaSessionConnector: Let apps intercept media button events
|
||||||
([#5179](https://github.com/google/ExoPlayer/issues/5179)).
|
([#5179](https://github.com/google/ExoPlayer/issues/5179)).
|
||||||
|
* Fix issue with `TimelineQueueNavigator` not publishing the queue in shuffled
|
||||||
|
order when in shuffle mode.
|
||||||
|
|
||||||
### 2.9.6 ###
|
### 2.9.6 ###
|
||||||
|
|
||||||
|
@ -971,6 +971,7 @@ public final class MediaSessionConnector {
|
|||||||
? PlaybackStateCompat.SHUFFLE_MODE_ALL
|
? PlaybackStateCompat.SHUFFLE_MODE_ALL
|
||||||
: PlaybackStateCompat.SHUFFLE_MODE_NONE);
|
: PlaybackStateCompat.SHUFFLE_MODE_NONE);
|
||||||
invalidateMediaSessionPlaybackState();
|
invalidateMediaSessionPlaybackState();
|
||||||
|
invalidateMediaSessionQueue();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -25,10 +25,10 @@ import com.google.android.exoplayer2.C;
|
|||||||
import com.google.android.exoplayer2.ControlDispatcher;
|
import com.google.android.exoplayer2.ControlDispatcher;
|
||||||
import com.google.android.exoplayer2.Player;
|
import com.google.android.exoplayer2.Player;
|
||||||
import com.google.android.exoplayer2.Timeline;
|
import com.google.android.exoplayer2.Timeline;
|
||||||
import com.google.android.exoplayer2.util.Util;
|
import com.google.android.exoplayer2.util.Assertions;
|
||||||
|
import java.util.ArrayDeque;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An abstract implementation of the {@link MediaSessionConnector.QueueNavigator} that maps the
|
* An abstract implementation of the {@link MediaSessionConnector.QueueNavigator} that maps the
|
||||||
@ -67,6 +67,7 @@ public abstract class TimelineQueueNavigator implements MediaSessionConnector.Qu
|
|||||||
* @param maxQueueSize The maximum queue size.
|
* @param maxQueueSize The maximum queue size.
|
||||||
*/
|
*/
|
||||||
public TimelineQueueNavigator(MediaSessionCompat mediaSession, int maxQueueSize) {
|
public TimelineQueueNavigator(MediaSessionCompat mediaSession, int maxQueueSize) {
|
||||||
|
Assertions.checkState(maxQueueSize > 0);
|
||||||
this.mediaSession = mediaSession;
|
this.mediaSession = mediaSession;
|
||||||
this.maxQueueSize = maxQueueSize;
|
this.maxQueueSize = maxQueueSize;
|
||||||
activeQueueItemId = MediaSessionCompat.QueueItem.UNKNOWN_ID;
|
activeQueueItemId = MediaSessionCompat.QueueItem.UNKNOWN_ID;
|
||||||
@ -193,22 +194,50 @@ public abstract class TimelineQueueNavigator implements MediaSessionConnector.Qu
|
|||||||
// Helper methods.
|
// Helper methods.
|
||||||
|
|
||||||
private void publishFloatingQueueWindow(Player player) {
|
private void publishFloatingQueueWindow(Player player) {
|
||||||
if (player.getCurrentTimeline().isEmpty()) {
|
Timeline timeline = player.getCurrentTimeline();
|
||||||
|
if (timeline.isEmpty()) {
|
||||||
mediaSession.setQueue(Collections.emptyList());
|
mediaSession.setQueue(Collections.emptyList());
|
||||||
activeQueueItemId = MediaSessionCompat.QueueItem.UNKNOWN_ID;
|
activeQueueItemId = MediaSessionCompat.QueueItem.UNKNOWN_ID;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
int windowCount = player.getCurrentTimeline().getWindowCount();
|
ArrayDeque<MediaSessionCompat.QueueItem> queue = new ArrayDeque<>();
|
||||||
|
int queueSize = Math.min(maxQueueSize, timeline.getWindowCount());
|
||||||
|
|
||||||
|
// Add the active queue item.
|
||||||
int currentWindowIndex = player.getCurrentWindowIndex();
|
int currentWindowIndex = player.getCurrentWindowIndex();
|
||||||
int queueSize = Math.min(maxQueueSize, windowCount);
|
queue.add(
|
||||||
int startIndex = Util.constrainValue(currentWindowIndex - ((queueSize - 1) / 2), 0,
|
new MediaSessionCompat.QueueItem(
|
||||||
windowCount - queueSize);
|
getMediaDescription(player, currentWindowIndex), currentWindowIndex));
|
||||||
List<MediaSessionCompat.QueueItem> queue = new ArrayList<>();
|
|
||||||
for (int i = startIndex; i < startIndex + queueSize; i++) {
|
// Fill queue alternating with next and/or previous queue items.
|
||||||
queue.add(new MediaSessionCompat.QueueItem(getMediaDescription(player, i), i));
|
int firstWindowIndex = currentWindowIndex;
|
||||||
|
int lastWindowIndex = currentWindowIndex;
|
||||||
|
boolean shuffleModeEnabled = player.getShuffleModeEnabled();
|
||||||
|
while ((firstWindowIndex != C.INDEX_UNSET || lastWindowIndex != C.INDEX_UNSET)
|
||||||
|
&& queue.size() < queueSize) {
|
||||||
|
// Begin with next to have a longer tail than head if an even sized queue needs to be trimmed.
|
||||||
|
if (lastWindowIndex != C.INDEX_UNSET) {
|
||||||
|
lastWindowIndex =
|
||||||
|
timeline.getNextWindowIndex(
|
||||||
|
lastWindowIndex, Player.REPEAT_MODE_OFF, shuffleModeEnabled);
|
||||||
|
if (lastWindowIndex != C.INDEX_UNSET) {
|
||||||
|
queue.add(
|
||||||
|
new MediaSessionCompat.QueueItem(
|
||||||
|
getMediaDescription(player, lastWindowIndex), lastWindowIndex));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (firstWindowIndex != C.INDEX_UNSET && queue.size() < queueSize) {
|
||||||
|
firstWindowIndex =
|
||||||
|
timeline.getPreviousWindowIndex(
|
||||||
|
firstWindowIndex, Player.REPEAT_MODE_OFF, shuffleModeEnabled);
|
||||||
|
if (firstWindowIndex != C.INDEX_UNSET) {
|
||||||
|
queue.addFirst(
|
||||||
|
new MediaSessionCompat.QueueItem(
|
||||||
|
getMediaDescription(player, firstWindowIndex), firstWindowIndex));
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
mediaSession.setQueue(queue);
|
mediaSession.setQueue(new ArrayList<>(queue));
|
||||||
activeQueueItemId = currentWindowIndex;
|
activeQueueItemId = currentWindowIndex;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user