From 99b4e72b7d370e610e2b85f79c21c8c0877df7d2 Mon Sep 17 00:00:00 2001 From: oppiliappan Date: Sun, 12 Apr 2026 04:45:43 +0100 Subject: [PATCH] feat: implement queue snapshotting before queue mutations, store the state of the queue into the queue history manager. Signed-off-by: oppiliappan --- src/js/queue.js | 33 +++++++++++++++++++++++++++++++++ 1 file changed, 33 insertions(+) diff --git a/src/js/queue.js b/src/js/queue.js index b9a76cc..e3766b6 100644 --- a/src/js/queue.js +++ b/src/js/queue.js @@ -1,8 +1,36 @@ // queue management, sorting, virtual scrolling, and track display +class QueueSnapshot { + static create(queue, queueIndex) { + return { + queue: structuredClone(queue), + queueIndex, + timestamp: Date.now(), + }; + } + + static apply(snapshot, state) { + state.queue = structuredClone(snapshot.queue); + state.queueIndex = snapshot.queueIndex; + } +} + +// create snapshot of current queue state +function snapshotQueue() { + return QueueSnapshot.create(state.queue, state.queueIndex); +} + +// restore queue state from snapshot and update UI +function restoreQueue(snapshot) { + if (!snapshot) return; + QueueSnapshot.apply(snapshot, state); + updateQueue(); +} + // sort or shuffle queue, preserving current track position // if items are selected, only sorts selected items, otherwise sorts entire queue function sortQueue(field, ascending) { + history.saveState(snapshotQueue()); const currentTrack = state.queueIndex >= 0 ? state.queue[state.queueIndex] : null; const selectedIndices = queueSelection?.getSelected() ?? []; @@ -144,6 +172,7 @@ function getQueueCallbacks() { // move items within queue function moveQueueItems(queue, selectedIndices, insertPos, callbacks = {}) { + history.saveState(snapshotQueue()); const { onSelectionChange, onQueueChange } = callbacks; const sortedIndices = Array.from(selectedIndices).sort((a, b) => a - b); const movedItems = sortedIndices.map((i) => queue[i]); @@ -221,6 +250,7 @@ const SONG_EXTRACTORS = { // add songs to queue async function addToQueue(fetcher, songExtractor, insertNext = false) { + history.saveState(snapshotQueue()); const songs = await songExtractor(await fetcher()); songs.forEach((song) => { if (song.userRating && song.userRating > 0) { @@ -293,6 +323,7 @@ function updateQueueDisplay() { // clear selected rows function clearSelectedRows() { + history.saveState(snapshotQueue()); const toRemove = queueSelection.getSelected(); if (toRemove.length === 0) return; @@ -328,6 +359,7 @@ function clearSelectedRows() { // remove a song by index, adjusting queue index if necessary function removeFromQueue(idx) { + history.saveState(snapshotQueue()); const isCurrentTrack = idx === state.queueIndex; state.queue.splice(idx, 1); @@ -375,6 +407,7 @@ function handleCurrentTrackDeleted() { // remove all items from queue function clearQueue() { + history.saveState(snapshotQueue()); state.queue = []; state.queueIndex = -1; saveQueue(); -- 2.51.2