Skip to content

Commit

Permalink
Merge pull request #20 from elomatreb/add-replay-gain-commands
Browse files Browse the repository at this point in the history
Add ReplayGain commands
  • Loading branch information
elomatreb authored Oct 30, 2023
2 parents 34b25f7 + 433c626 commit f54f7f6
Show file tree
Hide file tree
Showing 3 changed files with 89 additions and 2 deletions.
41 changes: 40 additions & 1 deletion mpd_client/src/commands/definitions.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ use mpd_protocol::{
};

use crate::{
commands::{Command, SeekMode, SingleMode, Song, SongId, SongPosition},
commands::{Command, ReplayGainMode, SeekMode, SingleMode, Song, SongId, SongPosition},
filter::Filter,
responses::{self as res, value, TypedResponseError},
tag::Tag,
Expand Down Expand Up @@ -94,6 +94,22 @@ single_arg_command!(SetRepeat, bool, "repeat");
single_arg_command!(SubscribeToChannel<'a>, &'a str, "subscribe");
single_arg_command!(UnsubscribeFromChannel<'a>, &'a str, "unsubscribe");

/// `replay_gain_status` command.
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub struct ReplayGainStatus;

impl Command for ReplayGainStatus {
type Response = res::ReplayGainStatus;

fn command(&self) -> RawCommand {
RawCommand::new("replay_gain_status")
}

fn response(self, frame: Frame) -> Result<Self::Response, TypedResponseError> {
res::ReplayGainStatus::from_frame(frame)
}
}

/// `status` command.
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub struct Status;
Expand Down Expand Up @@ -262,6 +278,29 @@ impl Command for SetSingle {
}
}

/// 'replay_gain_mode' command
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub struct SetReplayGainMode(pub ReplayGainMode);

impl Command for SetReplayGainMode {
type Response = ();

fn command(&self) -> RawCommand {
let rgm = match self.0 {
ReplayGainMode::Off => "off",
ReplayGainMode::Track => "track",
ReplayGainMode::Album => "album",
ReplayGainMode::Auto => "auto",
};

RawCommand::new("replay_gain_mode").argument(rgm)
}

fn response(self, _: Frame) -> Result<Self::Response, TypedResponseError> {
Ok(())
}
}

/// `crossfade` command.
///
/// The given duration is rounded down to whole seconds.
Expand Down
14 changes: 14 additions & 0 deletions mpd_client/src/commands/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,20 @@ pub enum SingleMode {
Oneshot,
}

/// Possible `replay_gain_mode` modes.
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
#[allow(missing_docs)]
pub enum ReplayGainMode {
/// Replay Gain off
Off,
/// Replay Gain Track mode
Track,
/// Replay Gain Album mode
Album,
/// Replay Gain Track if shuffle is on, Album otherwise
Auto,
}

/// Modes to target a song with a command.
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub enum Song {
Expand Down
36 changes: 35 additions & 1 deletion mpd_client/src/responses/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ pub use self::{
sticker::{StickerFind, StickerGet, StickerList},
timestamp::Timestamp,
};
use crate::commands::{SingleMode, SongId, SongPosition};
use crate::commands::{ReplayGainMode, SingleMode, SongId, SongPosition};

type KeyValuePair = (Arc<str>, String);

Expand Down Expand Up @@ -157,6 +157,18 @@ impl FromFieldValue for PlayState {
}
}

impl FromFieldValue for ReplayGainMode {
fn from_value(v: String, field: &str) -> Result<Self, TypedResponseError> {
match &*v {
"off" => Ok(ReplayGainMode::Off),
"track" => Ok(ReplayGainMode::Track),
"album" => Ok(ReplayGainMode::Album),
"auto" => Ok(ReplayGainMode::Auto),
_ => Err(TypedResponseError::invalid_value(field, v)),
}
}
}

fn parse_integer<I: FromStr<Err = ParseIntError>>(
v: String,
field: &str,
Expand Down Expand Up @@ -257,6 +269,28 @@ pub enum PlayState {
Paused,
}

/// Response to the [`replay_gain_status`] command.
///
/// See the [MPD documentation][replay-gain-status-command] for the specific meanings of the fields.
///
/// [`replay_gain_status`]: crate::commands::definitions::ReplayGainStatus
/// [replay-gain-status-command]: https://www.musicpd.org/doc/html/protocol.html#command-replay-gain-status
#[derive(Clone, Debug, PartialEq, Eq)]
#[allow(missing_docs)]
#[non_exhaustive]
pub struct ReplayGainStatus {
pub mode: ReplayGainMode,
}

impl ReplayGainStatus {
pub(crate) fn from_frame(mut raw: Frame) -> Result<Self, TypedResponseError> {
let f = &mut raw;
Ok(Self {
mode: value(f, "replay_gain_mode")?,
})
}
}

/// Response to the [`status`] command.
///
/// See the [MPD documentation][status-command] for the specific meanings of the fields.
Expand Down

0 comments on commit f54f7f6

Please sign in to comment.