diff --git a/src/renderer/store/player.store.ts b/src/renderer/store/player.store.ts index 85cca9e7b..a186b3ae8 100644 --- a/src/renderer/store/player.store.ts +++ b/src/renderer/store/player.store.ts @@ -1055,6 +1055,8 @@ export const usePlayerStoreBase = createWithEqualityFn()( ? state.queue.shuffled.length : queue.items.length; + const isStopped = state.player.status === PlayerStatus.STOPPED; + if (repeat === PlayerRepeat.ONE) { // Manual next while repeat-one is active should still advance in the queue. const nextIndex = Math.min(playbackLength - 1, currentIndex + 1); @@ -1063,6 +1065,10 @@ export const usePlayerStoreBase = createWithEqualityFn()( state.player.index = nextIndex; state.player.playerNum = 1; setTimestampStore(0); + + if (isStopped) { + state.player.status = PlayerStatus.PLAYING; + } }); eventEmitter.emit('MEDIA_NEXT', { @@ -1112,6 +1118,10 @@ export const usePlayerStoreBase = createWithEqualityFn()( state.player.index = nextIndex; state.player.playerNum = 1; setTimestampStore(0); + + if (isStopped) { + state.player.status = PlayerStatus.PLAYING; + } }); eventEmitter.emit('MEDIA_NEXT', { @@ -1246,10 +1256,17 @@ export const usePlayerStoreBase = createWithEqualityFn()( previousIndex = Math.max(0, currentIndex - 1); } + // Same Chromium Media Session pitfall as mediaNext: a STOPPED→new-src + // transition without PLAYING drops OS media-key routing. + const resumeFromStopped = get().player.status === PlayerStatus.STOPPED; + set((state) => { state.player.index = previousIndex; state.player.playerNum = 1; setTimestampStore(0); + if (resumeFromStopped) { + state.player.status = PlayerStatus.PLAYING; + } }); eventEmitter.emit('MEDIA_PREV', {