diff --git a/apps/music-player/Cargo.toml b/apps/music-player/Cargo.toml index 2aed4fe..36582b5 100644 --- a/apps/music-player/Cargo.toml +++ b/apps/music-player/Cargo.toml @@ -11,9 +11,10 @@ required-features = ["bin"] [dependencies] canary-magpie = { path = "../magpie", optional = true } -mpris = { version = "2.0.0-rc3", optional = true } serde = { version = "1", features = ["derive"] } serde_json = "1" +smol = { version = "1.2", optional = true } +zbus = { version = "3.5", optional = true } [features] -bin = ["dep:canary-magpie", "dep:mpris"] +bin = ["dep:canary-magpie", "dep:smol", "dep:zbus"] diff --git a/apps/music-player/src/main.rs b/apps/music-player/src/main.rs index 5f07f12..23ad88e 100644 --- a/apps/music-player/src/main.rs +++ b/apps/music-player/src/main.rs @@ -1,46 +1,52 @@ // Copyright (c) 2022 Marceline Cramer // SPDX-License-Identifier: AGPL-3.0-or-later -use canary_music_player::*; use canary_magpie::client::MagpieClient; use canary_magpie::protocol::{CreatePanel, MagpieServerMsg}; use canary_music_player::*; -use mpris::PlayerFinder; -pub struct MetadataTracker { +pub mod mpris; + +use mpris::*; + +pub struct Metadata { pub album: AlbumInfo, pub track: TrackInfo, } -impl From<&mpris::Metadata> for MetadataTracker { - fn from(metadata: &mpris::Metadata) -> Self { +impl<'a> From<&MetadataMap<'a>> for Metadata { + fn from(map: &MetadataMap<'a>) -> Self { let album = AlbumInfo { - title: metadata.album_name().map(ToString::to_string), - artists: metadata - .album_artists() - .unwrap_or(Vec::new()) - .iter() - .map(ToString::to_string) - .collect(), + title: map + .get("xesam:album") + .and_then(|v| TryFrom::try_from(v).ok()), + artists: map + .get("xesam:albumArtist") + .cloned() + .and_then(|v| TryFrom::try_from(v).ok()) + .unwrap_or(Vec::new()), }; let track = TrackInfo { - title: metadata.title().map(ToString::to_string), - artists: metadata - .artists() - .unwrap_or(Vec::new()) - .iter() - .map(ToString::to_string) - .collect(), - track_number: metadata.track_number(), + title: map + .get("xesam:title") + .and_then(|v| TryFrom::try_from(v).ok()), + artists: map + .get("xesam:artist") + .cloned() + .and_then(|v| TryFrom::try_from(v).ok()) + .unwrap_or(Vec::new()), + track_number: map + .get("xesam:trackNumber") + .and_then(|v| TryFrom::try_from(v).ok()), }; Self { album, track } } } -impl MetadataTracker { - pub fn new(magpie: &mut MagpieClient, metadata: &mpris::Metadata) -> Self { +/*impl MetadataTracker { + pub fn new(magpie: &mut MagpieClient, metadata: &MetadataMap) -> Self { let new: Self = metadata.into(); magpie.send_json_message(0, &InMsg::AlbumChanged(new.album.clone())); magpie.send_json_message(0, &InMsg::TrackChanged(new.track.clone())); @@ -54,7 +60,7 @@ impl MetadataTracker { new } - pub fn update(&mut self, messenger: &mut MagpieClient, metadata: &mpris::Metadata) { + pub fn update(&mut self, messenger: &mut MagpieClient, metadata: &MetadataMap) { let new: Self = metadata.into(); if self.album != new.album { @@ -74,7 +80,7 @@ impl MetadataTracker { *self = new; } -} +}*/ fn main() { let args: Vec = std::env::args().collect(); @@ -83,16 +89,32 @@ fn main() { .expect("Please pass a path to a Canary script!") .to_owned(); - let player_finder = PlayerFinder::new().expect("Could not connect to D-Bus"); - let mut magpie = MagpieClient::new().unwrap(); - let protocol = "tebibyte-media.desktop.music-player-controller".to_string(); - let script = std::path::PathBuf::from(&module_path); - let msg = CreatePanel { id: 0, protocol, script }; - let msg = MagpieServerMsg::CreatePanel(msg); - magpie.messenger.send(&msg).unwrap(); - let mut first_loop = true; + let result: Result<(), Box> = smol::block_on(async { + let dbus = zbus::Connection::session().await?; + let player = PlayerProxy::new(&dbus).await?; + + let protocol = "tebibyte-media.desktop.music-player-controller".to_string(); + let script = std::path::PathBuf::from(&module_path); + let msg = CreatePanel { + id: 0, + protocol, + script, + }; + let msg = MagpieServerMsg::CreatePanel(msg); + magpie.messenger.send(&msg).unwrap(); + + std::future::pending::<()>().await; + + Ok(()) + }); + + if let Err(err) = result { + eprintln!("Music player error: {:?}", err); + } + + /*let mut first_loop = true; let mut connected = false; loop { @@ -183,5 +205,5 @@ fn main() { magpie.send_json_message(0, &msg); } } - } + }*/ } diff --git a/apps/music-player/src/mpris.rs b/apps/music-player/src/mpris.rs new file mode 100644 index 0000000..0402bcd --- /dev/null +++ b/apps/music-player/src/mpris.rs @@ -0,0 +1,25 @@ +use std::collections::HashMap; + +use zbus::zvariant::Value; +use zbus::{dbus_proxy, Result}; + +pub type MetadataMap<'a> = HashMap>; + +#[dbus_proxy(interface = "org.mpris.MediaPlayer2.Player")] +trait Player { + fn next(&self) -> Result<()>; + fn previous(&self) -> Result<()>; + fn pause(&self) -> Result<()>; + fn play_pause(&self) -> Result<()>; + fn stop(&self) -> Result<()>; + fn play(&self) -> Result<()>; + + #[dbus_proxy(property)] + fn playback_status(&self) -> Result; + + #[dbus_proxy(property)] + fn position(&self) -> Result; + + #[dbus_proxy(property)] + fn metadata(&self) -> Result; +}