attempt to fix mpv autoNext behavior (#1768)

This commit is contained in:
jeffvli
2026-02-27 00:28:03 -08:00
parent b62f62671d
commit afca396654
2 changed files with 66 additions and 15 deletions
+5 -1
View File
@@ -116,11 +116,15 @@ const createMpv = async (data: {
mpv.on('status', (status) => { mpv.on('status', (status) => {
if (status.property === 'playlist-pos') { if (status.property === 'playlist-pos') {
// mpv uses playlist-pos = -1 when nothing is playing (ended, cleared, load failure, etc).
if (status.value === -1) { if (status.value === -1) {
mpv?.pause(); mpv?.pause();
return;
} }
if (status.value !== 0) { // In our 2-item queue model, playlist-pos should normally be 0.
// When mpv auto-advances to the next track it becomes > 0 (typically 1).
if (typeof status.value === 'number' && status.value > 0) {
getMainWindow()?.webContents.send('renderer-player-auto-next'); getMainWindow()?.webContents.send('renderer-player-auto-next');
} }
} }
+61 -14
View File
@@ -865,42 +865,89 @@ export const usePlayerStoreBase = createWithEqualityFn<PlayerState>()(
return currentIndex === queue.items.length - 1; return currentIndex === queue.items.length - 1;
}, },
mediaAutoNext: () => { mediaAutoNext: () => {
const currentIndex = get().player.index; const stateSnapshot = get();
const player = get().player; const currentIndex = stateSnapshot.player.index;
const player = stateSnapshot.player;
const repeat = player.repeat; const repeat = player.repeat;
const queue = get().getQueueOrder(); const queue = stateSnapshot.getQueueOrder();
const isShuffle = isShuffleEnabled(stateSnapshot);
const playbackLength = isShuffle
? stateSnapshot.queue.shuffled.length
: queue.items.length;
const newPlayerNum = player.playerNum === 1 ? 2 : 1; const newPlayerNum = player.playerNum === 1 ? 2 : 1;
const { nextIndex, shouldPause } = calculateNextIndex( const { nextIndex: nextPlaybackIndex, shouldPause } = calculateNextIndex(
currentIndex, currentIndex,
queue.items.length, playbackLength,
repeat, repeat,
); );
const newStatus = shouldPause ? PlayerStatus.PAUSED : PlayerStatus.PLAYING; const newStatus = shouldPause ? PlayerStatus.PAUSED : PlayerStatus.PLAYING;
set((state) => { set((state) => {
state.player.index = nextIndex; state.player.index = nextPlaybackIndex;
state.player.playerNum = newPlayerNum; state.player.playerNum = newPlayerNum;
setTimestampStore(0); setTimestampStore(0);
state.player.status = newStatus; state.player.status = newStatus;
}); });
if (repeat === PlayerRepeat.ONE && nextIndex === currentIndex) { if (repeat === PlayerRepeat.ONE && nextPlaybackIndex === currentIndex) {
eventEmitter.emit('PLAYER_REPEATED', { eventEmitter.emit('PLAYER_REPEATED', {
index: nextIndex, index: nextPlaybackIndex,
}); });
} }
const nextSong = calculateNextSong(nextIndex, queue.items, repeat); // Compute current/next/previous using the same shuffle-aware mapping as getPlayerData().
let currentQueueIndex = nextPlaybackIndex;
if (isShuffle) {
currentQueueIndex = mapShuffledToQueueIndex(
nextPlaybackIndex,
stateSnapshot.queue.shuffled,
);
}
const currentSong = queue.items[currentQueueIndex];
let nextSong: QueueSong | undefined;
if (isShuffle) {
const nextShuffledIndex = nextPlaybackIndex + 1;
if (nextShuffledIndex < stateSnapshot.queue.shuffled.length) {
const nextQueueIndex = stateSnapshot.queue.shuffled[nextShuffledIndex];
nextSong = queue.items[nextQueueIndex];
} else if (repeat === PlayerRepeat.ALL) {
const firstQueueIndex = stateSnapshot.queue.shuffled[0];
nextSong = queue.items[firstQueueIndex];
} else if (repeat === PlayerRepeat.ONE) {
nextSong = currentSong;
}
} else {
nextSong = calculateNextSong(currentQueueIndex, queue.items, repeat);
}
let previousSong: QueueSong | undefined;
if (isShuffle) {
const prevShuffledIndex = nextPlaybackIndex - 1;
if (prevShuffledIndex >= 0) {
const prevQueueIndex = stateSnapshot.queue.shuffled[prevShuffledIndex];
previousSong = queue.items[prevQueueIndex];
} else if (repeat === PlayerRepeat.ALL) {
const lastShuffledIndex = stateSnapshot.queue.shuffled.length - 1;
const lastQueueIndex = stateSnapshot.queue.shuffled[lastShuffledIndex];
previousSong = queue.items[lastQueueIndex];
}
} else {
previousSong =
currentQueueIndex > 0 ? queue.items[currentQueueIndex - 1] : undefined;
}
return { return {
currentSong: queue.items[nextIndex], currentSong,
index: nextIndex, index: currentQueueIndex,
nextSong, nextSong,
num: newPlayerNum, num: newPlayerNum,
player1: newPlayerNum === 1 ? queue.items[nextIndex] : nextSong, player1: newPlayerNum === 1 ? currentSong : nextSong,
player2: newPlayerNum === 2 ? queue.items[nextIndex] : nextSong, player2: newPlayerNum === 2 ? currentSong : nextSong,
previousSong: queue.items[nextIndex - 1], previousSong,
queueLength: queue.items.length, queueLength: queue.items.length,
status: newStatus, status: newStatus,
}; };