Skip to content

Commit 3a8dfe8

Browse files
committed
Atomically set shuffle/repeat/etc as well
1 parent 8a04ff6 commit 3a8dfe8

4 files changed

Lines changed: 48 additions & 51 deletions

File tree

app/src/main/java/org/akanework/gramophone/logic/GramophonePlaybackService.kt

Lines changed: 7 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -561,25 +561,22 @@ class GramophonePlaybackService : MediaLibraryService(), MediaSessionService.Lis
561561
}
562562
}
563563
scope.launch {
564-
lastPlayedManager.restore { items, factory ->
564+
lastPlayedManager.restore { items ->
565565
if (mediaSession == null) return@restore
566566
if (items != null) {
567567
if (lastPlayedManager.allowSavingState)
568568
return@restore // media items were already applied to player
569-
val extras = Bundle()
570-
extras.putString("nextTitle", "LastPlayedManager") // TODO(MQ)
571-
extras.putParcelable("nextShuffleOrder", factory)
572569
val list = runBlocking { mapMediaItemsForFavorites(items.mediaItems) }
573570
try {
574571
endedWorkaroundPlayer?.setMediaItems(
575572
list,
576573
items.startIndex,
577574
items.startPositionMs,
578-
extras
575+
items.extras
579576
)
580577
} catch (e: IllegalSeekPositionException) {
581578
try {
582-
endedWorkaroundPlayer?.setMediaItems(list, extras)
579+
endedWorkaroundPlayer?.setMediaItems(list, items.extras)
583580
Log.w(TAG, "failed to restore index", e)
584581
} catch (_: IllegalSeekPositionException) {
585582
Log.e(TAG, "failed to restore", e)
@@ -959,7 +956,8 @@ class GramophonePlaybackService : MediaLibraryService(), MediaSessionService.Lis
959956
} else {
960957
endedWorkaroundPlayer!!.setMediaItems(songList, startIndex = position,
961958
startPositionMs = C.TIME_UNSET, title, pinned = false, original = true,
962-
newShuffleOrder = null)
959+
newShuffleOrder = null, ended = false, repeatMode = null,
960+
shuffleModeEnabled = null, playbackParameters = null)
963961
}
964962
SessionResult(SessionResult.RESULT_SUCCESS)
965963
},
@@ -1130,7 +1128,7 @@ class GramophonePlaybackService : MediaLibraryService(), MediaSessionService.Lis
11301128
): ListenableFuture<MediaItemsWithStartPosition> {
11311129
val settable = SettableFuture.create<MediaItemsWithStartPosition>()
11321130
val job = scope.launch {
1133-
lastPlayedManager.restore { items, factory ->
1131+
lastPlayedManager.restore { items ->
11341132
if (items == null) {
11351133
settable.setException(
11361134
NullPointerException(
@@ -1141,10 +1139,7 @@ class GramophonePlaybackService : MediaLibraryService(), MediaSessionService.Lis
11411139
if (isForPlayback && items.mediaItems.isNotEmpty()) {
11421140
val list = runBlocking { mapMediaItemsForFavorites(items.mediaItems) }
11431141
settable.set(MediaItemsWithStartPosition(list, items.startIndex,
1144-
items.startPositionMs, Bundle().apply {
1145-
putString("nextTitle", "LastPlayedManager") // TODO(MQ)
1146-
putParcelable("nextShuffleOrder", factory)
1147-
}))
1142+
items.startPositionMs, items.extras))
11481143
} else if (items.mediaItems.isNotEmpty()) {
11491144
var theItem = items.mediaItems[items.startIndex]
11501145
if (theItem.mediaMetadata.durationMs != null &&

app/src/main/java/org/akanework/gramophone/logic/QueueBoard.kt

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -296,14 +296,11 @@ class QueueBoard(
296296
TAG,
297297
"Setting current queue; $mq; ids: ${plr.currentMediaItem?.mediaId}, ${mq.queue[mq.startIndex].mediaId}"
298298
)
299-
val seed = mq.shuffleOrder
300-
plr.shuffleModeEnabled = mq.shuffleModeEnabled
301-
plr.repeatMode = mq.repeatMode
302-
plr.isEnded = mq.ended
303299
plr.setMediaItems(
304300
mq.queue, mq.startIndex,
305301
mq.startPositionMs,
306-
mq.title, mq.expiry.value == null, mq.isOriginal, seed
302+
mq.title, mq.expiry.value == null, mq.isOriginal, mq.shuffleOrder, mq.ended,
303+
mq.repeatMode, mq.shuffleModeEnabled, null
307304
)
308305
}
309306

app/src/main/java/org/akanework/gramophone/logic/utils/LastPlayedManager.kt

Lines changed: 14 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -166,7 +166,7 @@ class LastPlayedManager(
166166
}
167167
}
168168

169-
suspend fun restore(callback: (MediaItemsWithStartPosition?, CircularShuffleOrder.Persistent) -> Unit) {
169+
suspend fun restore(callback: (MediaItemsWithStartPosition?) -> Unit) {
170170
if (BuildConfig.DEBUG) {
171171
Log.d(TAG, "decoding playlist...")
172172
}
@@ -188,7 +188,7 @@ class LastPlayedManager(
188188
val lastPlayedIdx = prefs.getInt("last_played_idx", 0)
189189
val lastPlayedPos = prefs.getLong("last_played_pos", 0)
190190
if (lastPlayedGrp == null || lastPlayedLst == null) {
191-
runCallback(callback, seed) { null }
191+
withContext(Dispatchers.Main) { callback(null) }
192192
return@withContext
193193
}
194194
val repeatMode = prefs.getInt("repeat_mode", Player.REPEAT_MODE_OFF)
@@ -313,21 +313,25 @@ class LastPlayedManager(
313313
.build()
314314
},
315315
lastPlayedIdx,
316-
lastPlayedPos
316+
lastPlayedPos,
317+
Bundle().apply {
318+
putString("nextTitle", "LastPlayedManager") // TODO(MQ)
319+
putParcelable("nextShuffleOrder", seed)
320+
putBoolean("isEnded", ended)
321+
putInt("repeatMode", repeatMode)
322+
putBoolean("shuffleModeEnabled", shuffleModeEnabled)
323+
putParcelable("playbackParameters", playbackParameters.toBundle())
324+
}
317325
)
318-
runCallback(callback, seed) {
326+
withContext(Dispatchers.Main) {
319327
if (BuildConfig.DEBUG) {
320328
Log.d(
321329
TAG,
322330
"restoring playlist (${data.mediaItems.size} items, repeat $repeatMode, " +
323331
"shuffle $shuffleModeEnabled, ended $ended)..."
324332
)
325333
}
326-
controller.isEnded = ended
327-
controller.repeatMode = repeatMode
328-
controller.shuffleModeEnabled = shuffleModeEnabled
329-
controller.playbackParameters = playbackParameters
330-
data
334+
callback(data)
331335
}
332336
return@withContext
333337
} catch (e: Exception) {
@@ -336,24 +340,13 @@ class LastPlayedManager(
336340
} catch (_: Exception) {
337341
}
338342
Log.e(TAG, Log.getThrowableString(e)!!)
339-
runCallback(callback, seed) { null }
343+
withContext(Dispatchers.Main) { callback(null) }
340344
return@withContext
341345
}
342346
}
343347
}
344348
}
345349

346-
private suspend inline fun runCallback(
347-
crossinline callback: (
348-
MediaItemsWithStartPosition?,
349-
CircularShuffleOrder.Persistent
350-
) -> Unit,
351-
seed: CircularShuffleOrder.Persistent,
352-
noinline parameter: () -> MediaItemsWithStartPosition?
353-
) {
354-
withContext(Dispatchers.Main) { callback(parameter(), seed) }
355-
}
356-
357350
private class SafeDelimitedStringConcat(private val delimiter: String) {
358351
private val b = StringBuilder()
359352
private var hadFirst = false

app/src/main/java/org/akanework/gramophone/logic/utils/exoplayer/EndedWorkaroundPlayer.kt

Lines changed: 25 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@ import androidx.media3.common.C
2323
import androidx.media3.common.DeviceInfo
2424
import androidx.media3.common.ForwardingSimpleBasePlayer
2525
import androidx.media3.common.MediaItem
26+
import androidx.media3.common.PlaybackParameters
2627
import androidx.media3.common.Player
2728
import androidx.media3.common.util.Log
2829
import androidx.media3.exoplayer.ExoPlayer
@@ -72,7 +73,7 @@ class EndedWorkaroundPlayer(
7273
var currentTitle: String? = null
7374
var currentIsPinned = false
7475
var currentIsOriginal = false
75-
var isEnded = false
76+
private var isEnded = false
7677
set(value) {
7778
if (BuildConfig.DEBUG) {
7879
Log.d(TAG, "isEnded set to $value (was $field)")
@@ -161,15 +162,24 @@ class EndedWorkaroundPlayer(
161162
title: String,
162163
pinned: Boolean,
163164
original: Boolean,
164-
newShuffleOrder: CircularShuffleOrder.Persistent?
165-
) {
165+
newShuffleOrder: CircularShuffleOrder.Persistent?,
166+
ended: Boolean,
167+
repeatMode: Int?,
168+
shuffleModeEnabled: Boolean?,
169+
playbackParameters: PlaybackParameters?
170+
): ListenableFuture<*> {
166171
cloneQueue(title, pinned, original)
167172
if (nextShuffleOrder != null)
168173
throw IllegalStateException("shuffleFactory was found orphaned")
169174
nextShuffleOrder = newShuffleOrder?.toFactory()
170-
super.handleSetMediaItems(mediaItems, startIndex, startPositionMs)
175+
isEnded = ended
176+
if (repeatMode != null) super.handleSetRepeatMode(repeatMode)
177+
if (shuffleModeEnabled != null) super.handleSetShuffleModeEnabled(shuffleModeEnabled)
178+
if (playbackParameters != null) super.handleSetPlaybackParameters(playbackParameters)
179+
val ret = super.handleSetMediaItems(mediaItems, startIndex, startPositionMs)
171180
if (nextShuffleOrder != null)
172181
throw IllegalStateException("shuffleFactory was not consumed during set")
182+
return ret
173183
}
174184

175185
override fun handleAddMediaItems(index: Int, mediaItems: List<MediaItem>): ListenableFuture<*> {
@@ -234,16 +244,18 @@ class EndedWorkaroundPlayer(
234244
startPositionMs: Long,
235245
extras: Bundle?
236246
): ListenableFuture<*> {
237-
if (nextShuffleOrder != null)
238-
throw IllegalStateException("shuffleFactory was found orphaned")
239247
val nextTitle = extras?.getString("nextTitle")
240248
?: throw IllegalArgumentException("setMediaItems called but nextTitle is null, logic bug")
241-
nextShuffleOrder = BundleCompat.getParcelable(extras, "nextShuffleOrder",
242-
CircularShuffleOrder.Persistent::class.java)?.toFactory()
243-
cloneQueue(nextTitle, newIsPinned = false, original = true)
244-
val ret = super.handleSetMediaItems(mediaItems, startIndex, startPositionMs)
245-
if (nextShuffleOrder != null)
246-
throw IllegalStateException("shuffleFactory was not consumed during set")
247-
return ret
249+
val seed = BundleCompat.getParcelable(extras, "nextShuffleOrder",
250+
CircularShuffleOrder.Persistent::class.java)
251+
val isEnded = extras.getBoolean("isEnded")
252+
val repeatMode = if (extras.containsKey("repeatMode")) extras.getInt("repeatMode") else null
253+
val shuffleModeEnabled = if (extras.containsKey("shuffleModeEnabled"))
254+
extras.getBoolean("shuffleModeEnabled") else null
255+
val playbackParameters = if (extras.containsKey("playbackParameters"))
256+
PlaybackParameters.fromBundle(extras.getBundle("playbackParameters")!!) else null
257+
return setMediaItems(mediaItems, startIndex, startPositionMs, nextTitle, false,
258+
true, seed, isEnded, repeatMode, shuffleModeEnabled,
259+
playbackParameters)
248260
}
249261
}

0 commit comments

Comments
 (0)