From b90c270d54dd67b073bc26139147b0217f203536 Mon Sep 17 00:00:00 2001 From: Broque Thomas <26755000+Nezreka@users.noreply.github.com> Date: Sat, 7 Mar 2026 00:11:15 -0800 Subject: [PATCH] Add Download Now button to wishlist modal and library page download bubbles --- webui/index.html | 4 ++ webui/static/script.js | 103 +++++++++++++++++++++++++++++++++++++++++ webui/static/style.css | 18 ++++++- 3 files changed, 124 insertions(+), 1 deletion(-) diff --git a/webui/index.html b/webui/index.html index 806a954c..c564b839 100644 --- a/webui/index.html +++ b/webui/index.html @@ -4144,6 +4144,10 @@ onclick="closeAddToWishlistModal()"> Close + diff --git a/webui/static/script.js b/webui/static/script.js index 463ad745..c7e82a13 100644 --- a/webui/static/script.js +++ b/webui/static/script.js @@ -13440,6 +13440,46 @@ function closeAddToWishlistModal() { } } +/** + * Handle "Download Now" button click from the Add to Wishlist modal. + * Captures modal data, closes the wishlist modal, then opens the download missing tracks modal. + */ +async function handleWishlistDownloadNow() { + if (!currentWishlistModalData) { + showToast('No album data available', 'error'); + return; + } + + // Capture data before closeAddToWishlistModal clears it + const { album, artist, tracks, albumType } = currentWishlistModalData; + + // Close the wishlist modal + closeAddToWishlistModal(); + + // Build virtual playlist ID and name (same pattern as createArtistAlbumVirtualPlaylist) + const virtualPlaylistId = `artist_album_${artist.id}_${album.id}`; + const playlistName = `[${artist.name}] ${album.name}`; + + // If a download process already exists for this album, just show the existing modal + if (activeDownloadProcesses[virtualPlaylistId]) { + const process = activeDownloadProcesses[virtualPlaylistId]; + if (process.modalElement) { + process.modalElement.style.display = 'flex'; + } + return; + } + + // Open download missing modal (reuses existing function) + showLoadingOverlay('Loading album...'); + await openDownloadMissingModalForArtistAlbum( + virtualPlaylistId, playlistName, tracks, album, artist, false + ); + hideLoadingOverlay(); + + // Register download bubble (reuses existing artist bubble system) + registerArtistDownload(artist, album, virtualPlaylistId, albumType); +} + /** * Add all tracks from any download modal to the wishlist * Universal handler for all modal types (artist albums, playlists, YouTube, Tidal, etc.) @@ -13644,6 +13684,7 @@ window.downloadSelectedCategory = downloadSelectedCategory; window.openAddToWishlistModal = openAddToWishlistModal; window.closeAddToWishlistModal = closeAddToWishlistModal; window.handleAddToWishlist = handleAddToWishlist; +window.handleWishlistDownloadNow = handleWishlistDownloadNow; window.addModalTracksToWishlist = addModalTracksToWishlist; // Helper functions @@ -26165,6 +26206,7 @@ function updateArtistDownloadsSection() { } downloadsUpdateTimeout = setTimeout(() => { showArtistDownloadsSection(); + showLibraryDownloadsSection(); updateDashboardDownloads(); }, 300); // 300ms debounce } @@ -27096,6 +27138,64 @@ function showArtistDownloadsSection() { }); } +/** + * Show download bubbles on the Library page (mirrors showArtistDownloadsSection) + */ +function showLibraryDownloadsSection() { + const libraryContent = document.querySelector('.library-content'); + if (!libraryContent) return; + + let downloadsSection = document.getElementById('library-downloads-section'); + + // Create section if it doesn't exist + if (!downloadsSection) { + downloadsSection = document.createElement('div'); + downloadsSection.id = 'library-downloads-section'; + downloadsSection.className = 'artist-downloads-section'; + + // Insert before the artist grid + const artistGrid = document.getElementById('library-artists-grid'); + if (artistGrid) { + libraryContent.insertBefore(downloadsSection, artistGrid); + } + } + + // Count active artists (reuses artistDownloadBubbles state) + const activeArtists = Object.keys(artistDownloadBubbles).filter(artistId => + artistDownloadBubbles[artistId].downloads.length > 0 + ); + + if (activeArtists.length === 0) { + downloadsSection.style.display = 'none'; + return; + } + + downloadsSection.style.display = 'block'; + downloadsSection.innerHTML = ` +
Active download processes
+