feat: implemented download queue fab

This commit is contained in:
eddyizm 2025-11-28 09:57:29 -08:00
parent 1ff0b83a19
commit 540aa9ba73
No known key found for this signature in database
GPG key ID: CF5F671829E8158A
6 changed files with 70 additions and 14 deletions

View file

@ -18,8 +18,10 @@ import com.cappielloantonio.tempo.databinding.ItemPlayerQueueSongBinding;
import com.cappielloantonio.tempo.glide.CustomGlideRequest;
import com.cappielloantonio.tempo.interfaces.ClickCallback;
import com.cappielloantonio.tempo.interfaces.MediaIndexCallback;
import com.cappielloantonio.tempo.service.DownloaderManager;
import com.cappielloantonio.tempo.service.MediaManager;
import com.cappielloantonio.tempo.subsonic.models.Child;
import com.cappielloantonio.tempo.util.DownloadUtil;
import com.cappielloantonio.tempo.util.Constants;
import com.cappielloantonio.tempo.util.MusicUtil;
import com.cappielloantonio.tempo.util.Preferences;
@ -94,6 +96,20 @@ public class PlayerSongQueueAdapter extends RecyclerView.Adapter<PlayerSongQueue
}
});
DownloaderManager downloaderManager = DownloadUtil.getDownloadTracker(holder.itemView.getContext());
if (downloaderManager != null) {
boolean isDownloaded = downloaderManager.isDownloaded(song.getId());
if (isDownloaded) {
holder.item.downloadIndicatorIcon.setVisibility(View.VISIBLE);
} else {
holder.item.downloadIndicatorIcon.setVisibility(View.GONE);
}
} else {
holder.item.downloadIndicatorIcon.setVisibility(View.GONE);
}
if (Preferences.showItemRating()) {
if (song.getStarred() == null && song.getUserRating() == null) {
holder.item.ratingIndicatorImageView.setVisibility(View.GONE);

View file

@ -15,6 +15,7 @@ import androidx.lifecycle.ViewModelProvider;
import androidx.lifecycle.Observer;
import androidx.media3.common.util.UnstableApi;
import androidx.media3.session.MediaBrowser;
import androidx.media3.common.MediaItem;
import androidx.media3.session.SessionToken;
import androidx.recyclerview.widget.ItemTouchHelper;
import androidx.recyclerview.widget.LinearLayoutManager;
@ -22,6 +23,8 @@ import androidx.recyclerview.widget.RecyclerView;
import com.cappielloantonio.tempo.databinding.InnerFragmentPlayerQueueBinding;
import com.cappielloantonio.tempo.interfaces.ClickCallback;
import com.cappielloantonio.tempo.model.Download;
import com.cappielloantonio.tempo.service.DownloaderManager;
import com.cappielloantonio.tempo.service.MediaManager;
import com.cappielloantonio.tempo.service.MediaService;
import com.cappielloantonio.tempo.subsonic.models.Child;
@ -29,6 +32,8 @@ import com.cappielloantonio.tempo.subsonic.models.PlayQueue;
import com.cappielloantonio.tempo.ui.adapter.PlayerSongQueueAdapter;
import com.cappielloantonio.tempo.ui.dialog.PlaylistChooserDialog;
import com.cappielloantonio.tempo.util.Constants;
import com.cappielloantonio.tempo.util.DownloadUtil;
import com.cappielloantonio.tempo.util.MappingUtil;
import com.cappielloantonio.tempo.util.Preferences;
import com.cappielloantonio.tempo.viewmodel.PlaybackViewModel;
import com.cappielloantonio.tempo.viewmodel.PlayerBottomSheetViewModel;
@ -383,14 +388,43 @@ public class PlayerQueueFragment extends Fragment implements ClickCallback {
}
private void handleDownloadAllClick() {
Log.d(TAG, "Download All Clicked! (Placeholder)");
Log.d(TAG, "Download All Clicked!");
List<Child> queueSongs = playerSongQueueAdapter.getItems();
if (queueSongs == null || queueSongs.isEmpty()) {
Toast.makeText(requireContext(), "Queue is empty", Toast.LENGTH_SHORT).show();
toggleFabMenu();
return;
}
List<MediaItem> mediaItemsToDownload = MappingUtil.mapMediaItems(queueSongs);
List<com.cappielloantonio.tempo.model.Download> downloadModels = new ArrayList<>();
for (Child child : queueSongs) {
com.cappielloantonio.tempo.model.Download downloadModel =
new com.cappielloantonio.tempo.model.Download(child);
downloadModel.setArtist(child.getArtist());
downloadModel.setAlbum(child.getAlbum());
downloadModel.setCoverArtId(child.getCoverArtId());
downloadModels.add(downloadModel);
}
DownloaderManager downloaderManager = DownloadUtil.getDownloadTracker(requireContext());
if (downloaderManager != null) {
downloaderManager.download(mediaItemsToDownload, downloadModels);
Toast.makeText(requireContext(), "Starting download of " + queueSongs.size() + " songs in the background.", Toast.LENGTH_SHORT).show();
} else {
Log.e(TAG, "DownloaderManager not initialized. Check DownloadUtil.");
Toast.makeText(requireContext(), "Download service unavailable.", Toast.LENGTH_SHORT).show();
}
toggleFabMenu();
}
private void handleLoadQueueClick() {
Log.d(TAG, "Load Queue Clicked!");
// Double-check that sync is enabled (shouldn't be visible if disabled, but just in case)
if (!Preferences.isSyncronizationEnabled()) {
toggleFabMenu();
return;

View file

@ -9,7 +9,6 @@ import androidx.lifecycle.LiveData;
import androidx.lifecycle.MutableLiveData;
import com.cappielloantonio.tempo.repository.AlbumRepository;
import com.cappielloantonio.tempo.repository.DownloadRepository;
import com.cappielloantonio.tempo.subsonic.models.AlbumID3;
import com.cappielloantonio.tempo.subsonic.models.ArtistID3;
import com.cappielloantonio.tempo.util.Constants;
@ -21,7 +20,6 @@ import java.util.List;
public class AlbumListPageViewModel extends AndroidViewModel {
private final AlbumRepository albumRepository;
private final DownloadRepository downloadRepository;
public String title;
public ArtistID3 artist;
@ -32,9 +30,7 @@ public class AlbumListPageViewModel extends AndroidViewModel {
public AlbumListPageViewModel(@NonNull Application application) {
super(application);
albumRepository = new AlbumRepository();
downloadRepository = new DownloadRepository();
}
public LiveData<List<AlbumID3>> getAlbumList(LifecycleOwner owner) {

View file

@ -35,8 +35,7 @@
android:layout_height="wrap_content"
android:layout_marginBottom="8dp"
android:visibility="gone"
android:text="Save Queue to Playlist"
tools:ignore="HardcodedText"
android:text="@string/player_queue_save_to_playlist"
app:icon="@android:drawable/ic_menu_edit" />
<com.google.android.material.floatingactionbutton.ExtendedFloatingActionButton
@ -45,8 +44,7 @@
android:layout_height="wrap_content"
android:layout_marginBottom="8dp"
android:visibility="gone"
android:text="Download All (TODO)"
tools:ignore="HardcodedText"
android:text="@string/menu_download_all_button"
app:icon="@android:drawable/stat_sys_download_done" />
@ -56,8 +54,7 @@
android:layout_height="wrap_content"
android:layout_marginBottom="8dp"
android:visibility="gone"
android:text="Load Queue"
tools:ignore="HardcodedText"
android:text="@string/player_queue_load_queue"
app:icon="@android:drawable/ic_menu_revert" />
<com.google.android.material.floatingactionbutton.ExtendedFloatingActionButton
@ -82,7 +79,7 @@
android:id="@+id/fab_menu_toggle"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:contentDescription="Toggle action menu (TODO: Fix Localization)"
android:contentDescription="Toggle FAB Action menu"
tools:ignore="HardcodedText"
app:srcCompat="@drawable/ic_add" />

View file

@ -139,6 +139,17 @@
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
<ImageView
android:id="@+id/download_indicator_icon"
android:layout_width="20dp"
android:layout_height="20dp"
android:layout_marginEnd="8dp"
android:visibility="gone"
android:src="@drawable/ic_download" app:layout_constraintBottom_toBottomOf="@+id/queue_song_cover_image_view"
app:layout_constraintEnd_toStartOf="@+id/queue_song_holder_image"
app:layout_constraintTop_toTopOf="@+id/queue_song_cover_image_view"
tools:visibility="visible" />
<ImageView
android:id="@+id/queue_song_holder_image"
android:layout_width="wrap_content"

View file

@ -212,6 +212,8 @@
<string name="player_playback_speed">%1$.2fx</string>
<string name="player_queue_clean_all_button">Clean play queue</string>
<string name="player_queue_save_queue_success">Saved play queue</string>
<string name="player_queue_save_to_playlist">Save Queue to Playlist</string>
<string name="player_queue_load_queue">Load Queue</string>
<string name="player_lyrics_download_content_description">Download lyrics for offline playback</string>
<string name="player_lyrics_downloaded_content_description">Lyrics downloaded for offline playback</string>
<string name="player_lyrics_download_success">Lyrics saved for offline playback.</string>