From b5b6c973ff80b79ea6342823f786c0e06675ef06 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Florian=20Mei=C3=9Fner?= Date: Sat, 2 Sep 2023 23:14:58 +0200 Subject: [PATCH 1/2] WIP --- doc/users.md | 11 ++++++----- src/command.rs | 4 ++++ src/commands.rs | 5 +++++ src/mpris.rs | 6 ++++++ src/queue.rs | 15 +++++++++++++++ 5 files changed, 36 insertions(+), 5 deletions(-) diff --git a/doc/users.md b/doc/users.md index 5c1501709..fcb4a9f31 100644 --- a/doc/users.md +++ b/doc/users.md @@ -128,11 +128,12 @@ When pressing O: | Shift+X | Copy the URL to the **currently playing track** to the system clipboard. | ### Queue -| Key | Command | -|------------------------------|--------------------------------------| -| C | Clear the entire queue. | -| D | Delete the currently selected track. | -| Ctrl+S | Delete the currently selected track. | +| Key | Command | +|------------------------------|------------------------------------------------------------------| +| C | Clear the entire queue. | +| D | Delete the currently selected track. | +| Ctrl+S | Delete the currently selected track. | +| Z | Randomize the queue tracks (put into random order). | ### Library | Key | Command | diff --git a/src/command.rs b/src/command.rs index 5d48a0182..064246b09 100644 --- a/src/command.rs +++ b/src/command.rs @@ -143,6 +143,7 @@ pub enum Command { VolumeDown(u16), Repeat(Option), Shuffle(Option), + Randomize, #[cfg(feature = "share_clipboard")] Share(TargetMode), Back, @@ -220,6 +221,7 @@ impl fmt::Display for Command { | Command::SaveQueue | Command::Add | Command::AddCurrent + | Command::Randomize | Command::Delete | Command::Back | Command::Help @@ -259,6 +261,7 @@ impl Command { Command::VolumeDown(_) => "voldown", Command::Repeat(_) => "repeat", Command::Shuffle(_) => "shuffle", + Command::Randomize => "randomize", #[cfg(feature = "share_clipboard")] Command::Share(_) => "share", Command::Back => "back", @@ -547,6 +550,7 @@ pub fn parse(input: &str) -> Result, CommandParseError> { }?; Command::Shuffle(switch) } + "randomize" => Command::Randomize, #[cfg(feature = "share_clipboard")] "share" => { let &target_mode_raw = args.first().ok_or(InsufficientArgs { diff --git a/src/commands.rs b/src/commands.rs index 94d663275..dcca97170 100644 --- a/src/commands.rs +++ b/src/commands.rs @@ -173,6 +173,10 @@ impl CommandManager { self.queue.set_shuffle(mode); Ok(None) } + Command::Randomize => { + self.queue.randomize(); + Ok(None) + } Command::Repeat(mode) => { let mode = mode.unwrap_or_else(|| match self.queue.get_repeat() { RepeatSetting::None => RepeatSetting::RepeatPlaylist, @@ -452,6 +456,7 @@ impl CommandManager { kb.insert("r".into(), vec![Command::Repeat(None)]); kb.insert("z".into(), vec![Command::Shuffle(None)]); + kb.insert("Ctrl+z".into(), vec![Command::Randomize]); #[cfg(feature = "share_clipboard")] { diff --git a/src/mpris.rs b/src/mpris.rs index 365ed036a..3dbdd9ee1 100644 --- a/src/mpris.rs +++ b/src/mpris.rs @@ -263,6 +263,12 @@ impl MprisPlayer { self.event.trigger(); } + #[dbus_interface(property)] + fn randomize(&self) { + self.queue.randomize(); + self.event.trigger(); + } + #[dbus_interface(property)] fn volume(&self) -> f64 { self.spotify.volume() as f64 / 65535_f64 diff --git a/src/queue.rs b/src/queue.rs index 09324c221..e7af001b2 100644 --- a/src/queue.rs +++ b/src/queue.rs @@ -467,6 +467,21 @@ impl Queue { } } + /// Randomize the queue ("shuffle" all the entries of the underlying Vec). Different from the `Shuffle` + /// option in that this actually changes the track positions in the queue (that gets displayed to the user), + /// but leaves the play order running from top to bottom. Useful If you want to shuffle a playlist, + /// but still want to add songs to be played next. + /// + /// This deactivates `Shuffle`. + pub fn randomize(&self) { + let mut queue = self.queue.write().unwrap(); + queue.shuffle(&mut thread_rng()); + + if self.get_shuffle() == true { + self.set_shuffle(false); + } + } + /// Handle events that are specific to the queue. pub fn handle_event(&self, event: QueueEvent) { match event { From fd02fe414c0876d32dbea4253fdce1e4ea169819 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Florian=20Mei=C3=9Fner?= <936176+t-nil@users.noreply.github.com> Date: Sun, 3 Sep 2023 01:25:22 +0200 Subject: [PATCH 2/2] - remember and restore previous playback state - add comments --- src/mpris.rs | 6 +++--- src/queue.rs | 18 ++++++++++++++++-- 2 files changed, 19 insertions(+), 5 deletions(-) diff --git a/src/mpris.rs b/src/mpris.rs index 3dbdd9ee1..afa2b4701 100644 --- a/src/mpris.rs +++ b/src/mpris.rs @@ -263,11 +263,11 @@ impl MprisPlayer { self.event.trigger(); } - #[dbus_interface(property)] - fn randomize(&self) { + /*#[dbus_interface(property)] + fn randomize(&self, _b: bool) { self.queue.randomize(); self.event.trigger(); - } + }*/ #[dbus_interface(property)] fn volume(&self) -> f64 { diff --git a/src/queue.rs b/src/queue.rs index e7af001b2..f21a9e0a0 100644 --- a/src/queue.rs +++ b/src/queue.rs @@ -474,12 +474,26 @@ impl Queue { /// /// This deactivates `Shuffle`. pub fn randomize(&self) { - let mut queue = self.queue.write().unwrap(); - queue.shuffle(&mut thread_rng()); + // stop playlist, because we completely invalidate any playing order + let previous_playback_state = self.cfg.state().playback_state.clone(); + self.stop(); + // deactivate `Shuffle` feature, because it usually wouldn't make sense to use both if self.get_shuffle() == true { self.set_shuffle(false); } + + // permutate the queue Vec + let mut queue = self.queue.write().unwrap(); + queue.shuffle(&mut thread_rng()); + + // resetting playing position to start of queue doesn't seem necessary + // my guess is that stop() does that + + // resume playback if we were playing before + if previous_playback_state == PlaybackState::Playing { + self.toggleplayback(); + } } /// Handle events that are specific to the queue.