music: add more playlist messages
Add more types of playlist messages corresponding to other actions, so they can be indicated in the UI only when the process is complete. This is somewhat incomplete. It does not include indicating errors for other playlist operations (Which I want to do), and neither does it handle situations in which some playlist operations and up reducing to others (i.e import -> create). I need to do that later.
This commit is contained in:
parent
21970349cc
commit
c5a3f72b99
13 changed files with 128 additions and 54 deletions
|
@ -44,6 +44,7 @@ import org.oxycblt.auxio.music.Music
|
|||
import org.oxycblt.auxio.music.MusicParent
|
||||
import org.oxycblt.auxio.music.MusicViewModel
|
||||
import org.oxycblt.auxio.music.PlaylistDecision
|
||||
import org.oxycblt.auxio.music.PlaylistMessage
|
||||
import org.oxycblt.auxio.music.Song
|
||||
import org.oxycblt.auxio.music.info.Disc
|
||||
import org.oxycblt.auxio.playback.PlaybackDecision
|
||||
|
@ -55,6 +56,7 @@ import org.oxycblt.auxio.util.logD
|
|||
import org.oxycblt.auxio.util.navigateSafe
|
||||
import org.oxycblt.auxio.util.overrideOnOverflowMenuClick
|
||||
import org.oxycblt.auxio.util.setFullWidthLookup
|
||||
import org.oxycblt.auxio.util.showToast
|
||||
import org.oxycblt.auxio.util.unlikelyToBeNull
|
||||
|
||||
/**
|
||||
|
@ -126,6 +128,7 @@ class AlbumDetailFragment :
|
|||
collect(listModel.menu.flow, ::handleMenu)
|
||||
collectImmediately(listModel.selected, ::updateSelection)
|
||||
collect(musicModel.playlistDecision.flow, ::handlePlaylistDecision)
|
||||
collect(musicModel.playlistMessage.flow, ::handlePlaylistMessage)
|
||||
collectImmediately(
|
||||
playbackModel.song, playbackModel.parent, playbackModel.isPlaying, ::updatePlayback)
|
||||
collect(playbackModel.playbackDecision.flow, ::handlePlaybackDecision)
|
||||
|
@ -281,6 +284,12 @@ class AlbumDetailFragment :
|
|||
findNavController().navigateSafe(directions)
|
||||
}
|
||||
|
||||
private fun handlePlaylistMessage(message: PlaylistMessage?) {
|
||||
if (message == null) return
|
||||
requireContext().showToast(message.stringRes)
|
||||
musicModel.playlistMessage.consume()
|
||||
}
|
||||
|
||||
private fun updatePlayback(song: Song?, parent: MusicParent?, isPlaying: Boolean) {
|
||||
albumListAdapter.setPlaying(
|
||||
song.takeIf { parent == detailModel.currentAlbum.value }, isPlaying)
|
||||
|
|
|
@ -45,6 +45,7 @@ import org.oxycblt.auxio.music.Music
|
|||
import org.oxycblt.auxio.music.MusicParent
|
||||
import org.oxycblt.auxio.music.MusicViewModel
|
||||
import org.oxycblt.auxio.music.PlaylistDecision
|
||||
import org.oxycblt.auxio.music.PlaylistMessage
|
||||
import org.oxycblt.auxio.music.Song
|
||||
import org.oxycblt.auxio.playback.PlaybackDecision
|
||||
import org.oxycblt.auxio.playback.PlaybackViewModel
|
||||
|
@ -54,6 +55,7 @@ import org.oxycblt.auxio.util.logD
|
|||
import org.oxycblt.auxio.util.navigateSafe
|
||||
import org.oxycblt.auxio.util.overrideOnOverflowMenuClick
|
||||
import org.oxycblt.auxio.util.setFullWidthLookup
|
||||
import org.oxycblt.auxio.util.showToast
|
||||
import org.oxycblt.auxio.util.unlikelyToBeNull
|
||||
|
||||
/**
|
||||
|
@ -128,6 +130,7 @@ class ArtistDetailFragment :
|
|||
collect(listModel.menu.flow, ::handleMenu)
|
||||
collectImmediately(listModel.selected, ::updateSelection)
|
||||
collect(musicModel.playlistDecision.flow, ::handlePlaylistDecision)
|
||||
collect(musicModel.playlistMessage.flow, ::handlePlaylistMessage)
|
||||
collectImmediately(
|
||||
playbackModel.song, playbackModel.parent, playbackModel.isPlaying, ::updatePlayback)
|
||||
collect(playbackModel.playbackDecision.flow, ::handlePlaybackDecision)
|
||||
|
@ -284,6 +287,12 @@ class ArtistDetailFragment :
|
|||
findNavController().navigateSafe(directions)
|
||||
}
|
||||
|
||||
private fun handlePlaylistMessage(message: PlaylistMessage?) {
|
||||
if (message == null) return
|
||||
requireContext().showToast(message.stringRes)
|
||||
musicModel.playlistMessage.consume()
|
||||
}
|
||||
|
||||
private fun updatePlayback(song: Song?, parent: MusicParent?, isPlaying: Boolean) {
|
||||
val currentArtist = unlikelyToBeNull(detailModel.currentArtist.value)
|
||||
val playingItem =
|
||||
|
|
|
@ -45,6 +45,7 @@ import org.oxycblt.auxio.music.Music
|
|||
import org.oxycblt.auxio.music.MusicParent
|
||||
import org.oxycblt.auxio.music.MusicViewModel
|
||||
import org.oxycblt.auxio.music.PlaylistDecision
|
||||
import org.oxycblt.auxio.music.PlaylistMessage
|
||||
import org.oxycblt.auxio.music.Song
|
||||
import org.oxycblt.auxio.playback.PlaybackDecision
|
||||
import org.oxycblt.auxio.playback.PlaybackViewModel
|
||||
|
@ -54,6 +55,7 @@ import org.oxycblt.auxio.util.logD
|
|||
import org.oxycblt.auxio.util.navigateSafe
|
||||
import org.oxycblt.auxio.util.overrideOnOverflowMenuClick
|
||||
import org.oxycblt.auxio.util.setFullWidthLookup
|
||||
import org.oxycblt.auxio.util.showToast
|
||||
import org.oxycblt.auxio.util.unlikelyToBeNull
|
||||
|
||||
/**
|
||||
|
@ -125,7 +127,8 @@ class GenreDetailFragment :
|
|||
collect(detailModel.toShow.flow, ::handleShow)
|
||||
collect(listModel.menu.flow, ::handleMenu)
|
||||
collectImmediately(listModel.selected, ::updateSelection)
|
||||
collect(musicModel.playlistDecision.flow, ::handleDecision)
|
||||
collect(musicModel.playlistDecision.flow, ::handlePlaylistDecision)
|
||||
collect(musicModel.playlistMessage.flow, ::handlePlaylistMessage)
|
||||
collectImmediately(
|
||||
playbackModel.song, playbackModel.parent, playbackModel.isPlaying, ::updatePlayback)
|
||||
collect(playbackModel.playbackDecision.flow, ::handlePlaybackDecision)
|
||||
|
@ -259,7 +262,7 @@ class GenreDetailFragment :
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleDecision(decision: PlaylistDecision?) {
|
||||
private fun handlePlaylistDecision(decision: PlaylistDecision?) {
|
||||
if (decision == null) return
|
||||
val directions =
|
||||
when (decision) {
|
||||
|
@ -277,6 +280,12 @@ class GenreDetailFragment :
|
|||
findNavController().navigateSafe(directions)
|
||||
}
|
||||
|
||||
private fun handlePlaylistMessage(message: PlaylistMessage?) {
|
||||
if (message == null) return
|
||||
requireContext().showToast(message.stringRes)
|
||||
musicModel.playlistMessage.consume()
|
||||
}
|
||||
|
||||
private fun updatePlayback(song: Song?, parent: MusicParent?, isPlaying: Boolean) {
|
||||
val currentGenre = unlikelyToBeNull(detailModel.currentGenre.value)
|
||||
val playingItem =
|
||||
|
|
|
@ -49,6 +49,7 @@ import org.oxycblt.auxio.music.MusicParent
|
|||
import org.oxycblt.auxio.music.MusicViewModel
|
||||
import org.oxycblt.auxio.music.Playlist
|
||||
import org.oxycblt.auxio.music.PlaylistDecision
|
||||
import org.oxycblt.auxio.music.PlaylistMessage
|
||||
import org.oxycblt.auxio.music.Song
|
||||
import org.oxycblt.auxio.music.external.M3U
|
||||
import org.oxycblt.auxio.playback.PlaybackDecision
|
||||
|
@ -61,6 +62,7 @@ import org.oxycblt.auxio.util.logW
|
|||
import org.oxycblt.auxio.util.navigateSafe
|
||||
import org.oxycblt.auxio.util.overrideOnOverflowMenuClick
|
||||
import org.oxycblt.auxio.util.setFullWidthLookup
|
||||
import org.oxycblt.auxio.util.showToast
|
||||
import org.oxycblt.auxio.util.unlikelyToBeNull
|
||||
|
||||
/**
|
||||
|
@ -159,7 +161,8 @@ class PlaylistDetailFragment :
|
|||
collect(detailModel.toShow.flow, ::handleShow)
|
||||
collect(listModel.menu.flow, ::handleMenu)
|
||||
collectImmediately(listModel.selected, ::updateSelection)
|
||||
collect(musicModel.playlistDecision.flow, ::handleDecision)
|
||||
collect(musicModel.playlistDecision.flow, ::handlePlaylistDecision)
|
||||
collect(musicModel.playlistMessage.flow, ::handlePlaylistMessage)
|
||||
collectImmediately(
|
||||
playbackModel.song, playbackModel.parent, playbackModel.isPlaying, ::updatePlayback)
|
||||
collect(playbackModel.playbackDecision.flow, ::handlePlaybackDecision)
|
||||
|
@ -333,7 +336,7 @@ class PlaylistDetailFragment :
|
|||
updateMultiToolbar()
|
||||
}
|
||||
|
||||
private fun handleDecision(decision: PlaylistDecision?) {
|
||||
private fun handlePlaylistDecision(decision: PlaylistDecision?) {
|
||||
if (decision == null) return
|
||||
val directions =
|
||||
when (decision) {
|
||||
|
@ -369,6 +372,12 @@ class PlaylistDetailFragment :
|
|||
findNavController().navigateSafe(directions)
|
||||
}
|
||||
|
||||
private fun handlePlaylistMessage(message: PlaylistMessage?) {
|
||||
if (message == null) return
|
||||
requireContext().showToast(message.stringRes)
|
||||
musicModel.playlistMessage.consume()
|
||||
}
|
||||
|
||||
private fun updatePlayback(song: Song?, parent: MusicParent?, isPlaying: Boolean) {
|
||||
// Prefer songs that are playing from this playlist.
|
||||
playlistListAdapter.setPlaying(
|
||||
|
|
|
@ -70,7 +70,7 @@ import org.oxycblt.auxio.music.NoMusicException
|
|||
import org.oxycblt.auxio.music.PERMISSION_READ_AUDIO
|
||||
import org.oxycblt.auxio.music.Playlist
|
||||
import org.oxycblt.auxio.music.PlaylistDecision
|
||||
import org.oxycblt.auxio.music.PlaylistError
|
||||
import org.oxycblt.auxio.music.PlaylistMessage
|
||||
import org.oxycblt.auxio.music.Song
|
||||
import org.oxycblt.auxio.music.external.M3U
|
||||
import org.oxycblt.auxio.playback.PlaybackViewModel
|
||||
|
@ -211,7 +211,7 @@ class HomeFragment :
|
|||
collectImmediately(listModel.selected, ::updateSelection)
|
||||
collectImmediately(musicModel.indexingState, ::updateIndexerState)
|
||||
collect(musicModel.playlistDecision.flow, ::handleDecision)
|
||||
collectImmediately(musicModel.playlistError.flow, ::handlePlaylistError)
|
||||
collectImmediately(musicModel.playlistMessage.flow, ::handlePlaylistMessage)
|
||||
collect(detailModel.toShow.flow, ::handleShow)
|
||||
}
|
||||
|
||||
|
@ -503,19 +503,10 @@ class HomeFragment :
|
|||
findNavController().navigateSafe(directions)
|
||||
}
|
||||
|
||||
private fun handlePlaylistError(error: PlaylistError?) {
|
||||
when (error) {
|
||||
is PlaylistError.ImportFailed -> {
|
||||
requireContext().showToast(R.string.err_import_failed)
|
||||
musicModel.importError.consume()
|
||||
}
|
||||
is PlaylistError.ExportFailed -> {
|
||||
requireContext().showToast(R.string.err_export_failed)
|
||||
musicModel.importError.consume()
|
||||
}
|
||||
null -> {}
|
||||
}
|
||||
musicModel.playlistError.consume()
|
||||
private fun handlePlaylistMessage(message: PlaylistMessage?) {
|
||||
if (message == null) return
|
||||
requireContext().showToast(message.stringRes)
|
||||
musicModel.playlistMessage.consume()
|
||||
}
|
||||
|
||||
private fun updateFab(songs: List<Song>, isFastScrolling: Boolean) {
|
||||
|
|
|
@ -27,6 +27,7 @@ import kotlinx.coroutines.Dispatchers
|
|||
import kotlinx.coroutines.flow.MutableStateFlow
|
||||
import kotlinx.coroutines.flow.StateFlow
|
||||
import kotlinx.coroutines.launch
|
||||
import org.oxycblt.auxio.R
|
||||
import org.oxycblt.auxio.list.ListSettings
|
||||
import org.oxycblt.auxio.music.external.ExportConfig
|
||||
import org.oxycblt.auxio.music.external.ExternalPlaylistManager
|
||||
|
@ -65,19 +66,9 @@ constructor(
|
|||
val playlistDecision: Event<PlaylistDecision>
|
||||
get() = _playlistDecision
|
||||
|
||||
private val _playlistError = MutableEvent<PlaylistError>()
|
||||
val playlistError: Event<PlaylistError>
|
||||
get() = _playlistError
|
||||
|
||||
private val _importError = MutableEvent<Unit>()
|
||||
/** Flag for when playlist importing failed. Consume this and show an error if active. */
|
||||
val importError: Event<Unit>
|
||||
get() = _importError
|
||||
|
||||
private val _exportError = MutableEvent<Unit>()
|
||||
/** Flag for when playlist exporting failed. Consume this and show an error if active. */
|
||||
val exportError: Event<Unit>
|
||||
get() = _exportError
|
||||
private val _playlistMessage = MutableEvent<PlaylistMessage>()
|
||||
val playlistMessage: Event<PlaylistMessage>
|
||||
get() = _playlistMessage
|
||||
|
||||
init {
|
||||
musicRepository.addUpdateListener(this)
|
||||
|
@ -127,7 +118,10 @@ constructor(
|
|||
fun createPlaylist(name: String? = null, songs: List<Song> = listOf()) {
|
||||
if (name != null) {
|
||||
logD("Creating $name with ${songs.size} songs]")
|
||||
viewModelScope.launch(Dispatchers.IO) { musicRepository.createPlaylist(name, songs) }
|
||||
viewModelScope.launch(Dispatchers.IO) {
|
||||
musicRepository.createPlaylist(name, songs)
|
||||
_playlistMessage.put(PlaylistMessage.NewPlaylistSuccess)
|
||||
}
|
||||
} else {
|
||||
logD("Launching creation dialog for ${songs.size} songs")
|
||||
_playlistDecision.put(PlaylistDecision.New(songs))
|
||||
|
@ -148,7 +142,7 @@ constructor(
|
|||
viewModelScope.launch(Dispatchers.IO) {
|
||||
val importedPlaylist = externalPlaylistManager.import(uri)
|
||||
if (importedPlaylist == null) {
|
||||
_playlistError.put(PlaylistError.ImportFailed)
|
||||
_playlistMessage.put(PlaylistMessage.ImportFailed)
|
||||
return@launch
|
||||
}
|
||||
|
||||
|
@ -156,14 +150,16 @@ constructor(
|
|||
val songs = importedPlaylist.paths.mapNotNull(deviceLibrary::findSongByPath)
|
||||
|
||||
if (songs.isEmpty()) {
|
||||
_playlistError.put(PlaylistError.ImportFailed)
|
||||
_playlistMessage.put(PlaylistMessage.ImportFailed)
|
||||
return@launch
|
||||
}
|
||||
// TODO Require the user to name it something else if the name is a duplicate of
|
||||
// a prior playlist
|
||||
if (target !== null) {
|
||||
musicRepository.rewritePlaylist(target, songs)
|
||||
_playlistMessage.put(PlaylistMessage.ImportSuccess)
|
||||
} else {
|
||||
// TODO: Have to properly propagate the "Playlist Created" message
|
||||
createPlaylist(importedPlaylist.name, songs)
|
||||
}
|
||||
}
|
||||
|
@ -183,8 +179,10 @@ constructor(
|
|||
if (uri != null && config != null) {
|
||||
logD("Exporting playlist to $uri")
|
||||
viewModelScope.launch(Dispatchers.IO) {
|
||||
if (!externalPlaylistManager.export(playlist, uri, config)) {
|
||||
_playlistError.put(PlaylistError.ExportFailed)
|
||||
if (externalPlaylistManager.export(playlist, uri, config)) {
|
||||
_playlistMessage.put(PlaylistMessage.ExportSuccess)
|
||||
} else {
|
||||
_playlistMessage.put(PlaylistMessage.ExportFailed)
|
||||
}
|
||||
}
|
||||
} else {
|
||||
|
@ -202,7 +200,10 @@ constructor(
|
|||
fun renamePlaylist(playlist: Playlist, name: String? = null) {
|
||||
if (name != null) {
|
||||
logD("Renaming $playlist to $name")
|
||||
viewModelScope.launch(Dispatchers.IO) { musicRepository.renamePlaylist(playlist, name) }
|
||||
viewModelScope.launch(Dispatchers.IO) {
|
||||
musicRepository.renamePlaylist(playlist, name)
|
||||
_playlistMessage.put(PlaylistMessage.RenameSuccess)
|
||||
}
|
||||
} else {
|
||||
logD("Launching rename dialog for $playlist")
|
||||
_playlistDecision.put(PlaylistDecision.Rename(playlist))
|
||||
|
@ -219,7 +220,10 @@ constructor(
|
|||
fun deletePlaylist(playlist: Playlist, rude: Boolean = false) {
|
||||
if (rude) {
|
||||
logD("Deleting $playlist")
|
||||
viewModelScope.launch(Dispatchers.IO) { musicRepository.deletePlaylist(playlist) }
|
||||
viewModelScope.launch(Dispatchers.IO) {
|
||||
musicRepository.deletePlaylist(playlist)
|
||||
_playlistMessage.put(PlaylistMessage.DeleteSuccess)
|
||||
}
|
||||
} else {
|
||||
logD("Launching deletion dialog for $playlist")
|
||||
_playlistDecision.put(PlaylistDecision.Delete(playlist))
|
||||
|
@ -279,7 +283,10 @@ constructor(
|
|||
fun addToPlaylist(songs: List<Song>, playlist: Playlist? = null) {
|
||||
if (playlist != null) {
|
||||
logD("Adding ${songs.size} songs to $playlist")
|
||||
viewModelScope.launch(Dispatchers.IO) { musicRepository.addToPlaylist(songs, playlist) }
|
||||
viewModelScope.launch(Dispatchers.IO) {
|
||||
musicRepository.addToPlaylist(songs, playlist)
|
||||
_playlistMessage.put(PlaylistMessage.AddSuccess)
|
||||
}
|
||||
} else {
|
||||
logD("Launching addition dialog for songs=${songs.size}")
|
||||
_playlistDecision.put(PlaylistDecision.Add(songs))
|
||||
|
@ -354,8 +361,46 @@ sealed interface PlaylistDecision {
|
|||
data class Add(val songs: List<Song>) : PlaylistDecision
|
||||
}
|
||||
|
||||
sealed interface PlaylistError {
|
||||
data object ImportFailed : PlaylistError
|
||||
sealed interface PlaylistMessage {
|
||||
val stringRes: Int
|
||||
|
||||
data object ExportFailed : PlaylistError
|
||||
data object NewPlaylistSuccess : PlaylistMessage {
|
||||
override val stringRes: Int
|
||||
get() = R.string.lng_playlist_created
|
||||
}
|
||||
|
||||
data object ImportSuccess : PlaylistMessage {
|
||||
override val stringRes: Int
|
||||
get() = R.string.lng_playlist_imported
|
||||
}
|
||||
|
||||
data object ImportFailed : PlaylistMessage {
|
||||
override val stringRes: Int
|
||||
get() = R.string.err_import_failed
|
||||
}
|
||||
|
||||
data object RenameSuccess : PlaylistMessage {
|
||||
override val stringRes: Int
|
||||
get() = R.string.lng_playlist_renamed
|
||||
}
|
||||
|
||||
data object DeleteSuccess : PlaylistMessage {
|
||||
override val stringRes: Int
|
||||
get() = R.string.lng_playlist_deleted
|
||||
}
|
||||
|
||||
data object AddSuccess : PlaylistMessage {
|
||||
override val stringRes: Int
|
||||
get() = R.string.lng_playlist_added
|
||||
}
|
||||
|
||||
data object ExportSuccess : PlaylistMessage {
|
||||
override val stringRes: Int
|
||||
get() = R.string.lng_playlist_exported
|
||||
}
|
||||
|
||||
data object ExportFailed : PlaylistMessage {
|
||||
override val stringRes: Int
|
||||
get() = R.string.err_export_failed
|
||||
}
|
||||
}
|
||||
|
|
|
@ -37,7 +37,6 @@ import org.oxycblt.auxio.ui.ViewBindingMaterialDialogFragment
|
|||
import org.oxycblt.auxio.util.collectImmediately
|
||||
import org.oxycblt.auxio.util.logD
|
||||
import org.oxycblt.auxio.util.navigateSafe
|
||||
import org.oxycblt.auxio.util.showToast
|
||||
|
||||
/**
|
||||
* A dialog that allows the user to pick a specific playlist to add song(s) to.
|
||||
|
@ -86,7 +85,6 @@ class AddToPlaylistDialog :
|
|||
|
||||
override fun onClick(item: PlaylistChoice, viewHolder: RecyclerView.ViewHolder) {
|
||||
musicModel.addToPlaylist(pickerModel.currentSongsToAdd.value ?: return, item.playlist)
|
||||
requireContext().showToast(R.string.lng_playlist_added)
|
||||
findNavController().navigateUp()
|
||||
}
|
||||
|
||||
|
|
|
@ -33,7 +33,6 @@ import org.oxycblt.auxio.music.Playlist
|
|||
import org.oxycblt.auxio.ui.ViewBindingMaterialDialogFragment
|
||||
import org.oxycblt.auxio.util.collectImmediately
|
||||
import org.oxycblt.auxio.util.logD
|
||||
import org.oxycblt.auxio.util.showToast
|
||||
import org.oxycblt.auxio.util.unlikelyToBeNull
|
||||
|
||||
/**
|
||||
|
@ -56,7 +55,6 @@ class DeletePlaylistDialog : ViewBindingMaterialDialogFragment<DialogDeletePlayl
|
|||
// Now we can delete the playlist for-real this time.
|
||||
musicModel.deletePlaylist(
|
||||
unlikelyToBeNull(pickerModel.currentPlaylistToDelete.value), rude = true)
|
||||
requireContext().showToast(R.string.lng_playlist_deleted)
|
||||
}
|
||||
.setNegativeButton(R.string.lbl_cancel, null)
|
||||
}
|
||||
|
|
|
@ -98,7 +98,6 @@ class ExportPlaylistDialog : ViewBindingMaterialDialogFragment<DialogPlaylistExp
|
|||
|
||||
binding.exportWindowsPaths.setOnClickListener { _ ->
|
||||
val current = pickerModel.currentExportConfig.value
|
||||
logD("change")
|
||||
pickerModel.setExportConfig(current.copy(windowsPaths = !current.windowsPaths))
|
||||
}
|
||||
|
||||
|
|
|
@ -33,7 +33,6 @@ import org.oxycblt.auxio.music.MusicViewModel
|
|||
import org.oxycblt.auxio.ui.ViewBindingMaterialDialogFragment
|
||||
import org.oxycblt.auxio.util.collectImmediately
|
||||
import org.oxycblt.auxio.util.logD
|
||||
import org.oxycblt.auxio.util.showToast
|
||||
import org.oxycblt.auxio.util.unlikelyToBeNull
|
||||
|
||||
/**
|
||||
|
@ -62,7 +61,6 @@ class NewPlaylistDialog : ViewBindingMaterialDialogFragment<DialogPlaylistNameBi
|
|||
}
|
||||
// TODO: Navigate to playlist if there are songs in it
|
||||
musicModel.createPlaylist(name, pendingPlaylist.songs)
|
||||
requireContext().showToast(R.string.lng_playlist_created)
|
||||
findNavController().apply {
|
||||
navigateUp()
|
||||
// Do an additional navigation away from the playlist addition dialog, if
|
||||
|
|
|
@ -34,7 +34,6 @@ import org.oxycblt.auxio.music.Playlist
|
|||
import org.oxycblt.auxio.ui.ViewBindingMaterialDialogFragment
|
||||
import org.oxycblt.auxio.util.collectImmediately
|
||||
import org.oxycblt.auxio.util.logD
|
||||
import org.oxycblt.auxio.util.showToast
|
||||
import org.oxycblt.auxio.util.unlikelyToBeNull
|
||||
|
||||
/**
|
||||
|
@ -58,7 +57,6 @@ class RenamePlaylistDialog : ViewBindingMaterialDialogFragment<DialogPlaylistNam
|
|||
val playlist = unlikelyToBeNull(pickerModel.currentPlaylistToRename.value)
|
||||
val chosenName = pickerModel.chosenName.value as ChosenName.Valid
|
||||
musicModel.renamePlaylist(playlist, chosenName.value)
|
||||
requireContext().showToast(R.string.lng_playlist_renamed)
|
||||
findNavController().navigateUp()
|
||||
}
|
||||
.setNegativeButton(R.string.lbl_cancel, null)
|
||||
|
|
|
@ -52,6 +52,7 @@ import org.oxycblt.auxio.music.MusicParent
|
|||
import org.oxycblt.auxio.music.MusicViewModel
|
||||
import org.oxycblt.auxio.music.Playlist
|
||||
import org.oxycblt.auxio.music.PlaylistDecision
|
||||
import org.oxycblt.auxio.music.PlaylistMessage
|
||||
import org.oxycblt.auxio.music.Song
|
||||
import org.oxycblt.auxio.music.external.M3U
|
||||
import org.oxycblt.auxio.playback.PlaybackDecision
|
||||
|
@ -64,6 +65,7 @@ import org.oxycblt.auxio.util.logD
|
|||
import org.oxycblt.auxio.util.logW
|
||||
import org.oxycblt.auxio.util.navigateSafe
|
||||
import org.oxycblt.auxio.util.setFullWidthLookup
|
||||
import org.oxycblt.auxio.util.showToast
|
||||
|
||||
/**
|
||||
* The [ListFragment] providing search functionality for the music library.
|
||||
|
@ -160,7 +162,8 @@ class SearchFragment : ListFragment<Music, FragmentSearchBinding>() {
|
|||
collectImmediately(searchModel.searchResults, ::updateSearchResults)
|
||||
collectImmediately(listModel.selected, ::updateSelection)
|
||||
collect(listModel.menu.flow, ::handleMenu)
|
||||
collect(musicModel.playlistDecision.flow, ::handleDecision)
|
||||
collect(musicModel.playlistDecision.flow, ::handlePlaylistDecision)
|
||||
collect(musicModel.playlistMessage.flow, ::handlePlaylistMessage)
|
||||
collectImmediately(
|
||||
playbackModel.song, playbackModel.parent, playbackModel.isPlaying, ::updatePlayback)
|
||||
collect(playbackModel.playbackDecision.flow, ::handlePlaybackDecision)
|
||||
|
@ -302,7 +305,7 @@ class SearchFragment : ListFragment<Music, FragmentSearchBinding>() {
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleDecision(decision: PlaylistDecision?) {
|
||||
private fun handlePlaylistDecision(decision: PlaylistDecision?) {
|
||||
if (decision == null) return
|
||||
val directions =
|
||||
when (decision) {
|
||||
|
@ -340,6 +343,12 @@ class SearchFragment : ListFragment<Music, FragmentSearchBinding>() {
|
|||
findNavController().navigateSafe(directions)
|
||||
}
|
||||
|
||||
private fun handlePlaylistMessage(message: PlaylistMessage?) {
|
||||
if (message == null) return
|
||||
requireContext().showToast(message.stringRes)
|
||||
musicModel.playlistMessage.consume()
|
||||
}
|
||||
|
||||
private fun updatePlayback(song: Song?, parent: MusicParent?, isPlaying: Boolean) {
|
||||
searchAdapter.setPlaying(parent ?: song, isPlaying)
|
||||
}
|
||||
|
|
|
@ -196,7 +196,9 @@
|
|||
<string name="lng_observing">Monitoring your music library for changes…</string>
|
||||
<string name="lng_queue_added">Added to queue</string>
|
||||
<string name="lng_playlist_created">Playlist created</string>
|
||||
<string name="lng_playlist_imported">Playlist imported</string>
|
||||
<string name="lng_playlist_renamed">Playlist renamed</string>
|
||||
<string name="lng_playlist_exported">Playlist exported</string>
|
||||
<string name="lng_playlist_deleted">Playlist deleted</string>
|
||||
<string name="lng_playlist_added">Added to playlist</string>
|
||||
<string name="lng_author">Developed by Alexander Capehart</string>
|
||||
|
|
Loading…
Reference in a new issue