Skip to content

Commit

Permalink
Add support for audio files
Browse files Browse the repository at this point in the history
  • Loading branch information
mtkennerly committed Dec 10, 2024
1 parent 50c2531 commit b097f18
Show file tree
Hide file tree
Showing 14 changed files with 856 additions and 13 deletions.
415 changes: 410 additions & 5 deletions Cargo.lock

Large diffs are not rendered by default.

1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ realia = "0.2.0"
regex = "1.10.6"
reqwest = { version = "0.12.7", features = ["blocking", "gzip", "rustls-tls"], default-features = false }
rfd = { version = "0.15.0", features = ["gtk3"], default-features = false }
rodio = { version = "0.20.1", features = ["symphonia-aac", "symphonia-aiff", "symphonia-alac", "symphonia-flac", "symphonia-isomp4", "symphonia-mp3", "symphonia-vorbis", "symphonia-wav"], default-features = false }
schemars = { version = "0.8.21", features = ["chrono"] }
semver = { version = "1.0.23", features = ["serde"] }
serde = { version = "1.0.210", features = ["derive"] }
Expand Down
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
# <img src="assets/icon.svg" alt="Logo" width="64" height="64"> Madamiru
Madamiru is a cross-platform media player written in [Rust](https://www.rust-lang.org)
that can automatically shuffle multiple videos and images at once in a grid layout.
that can automatically shuffle multiple videos, images, and songs at once in a grid layout.

## Features
* Video formats: AVI, M4V, MKV, MOV, MP4, WebM
* Image formats: BMP, GIF, ICO, JPEG, PNG, TIFF, SVG, WebP
* Audio formats: FLAC, M4A, MP3, WAV
* Subtitles are supported within MKV (but not as separate files)

If you'd like to help translate Madamiru into other languages,
Expand Down
3 changes: 3 additions & 0 deletions assets/linux/com.mtkennerly.madamiru.metainfo.xml
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,9 @@
<keyword>images</keyword>
<keyword>media</keyword>
<keyword>multimedia</keyword>
<keyword>music</keyword>
<keyword>song</keyword>
<keyword>songs</keyword>
<keyword>video</keyword>
<keyword>videos</keyword>

Expand Down
1 change: 1 addition & 0 deletions lang/en-US.ftl
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ tell-playlist-has-unsaved-changes = Your playlist has unsaved changes.
tell-playlist-is-invalid = The playlist file is invalid.
tell-new-version-available = An application update is available: {$version}.
tell-no-media-found = No more media matching your filter.
tell-unable-to-determine-media-duration = Unable to determine media duration.
tell-unable-to-open-directory = Unable to open directory.
tell-unable-to-open-url = Unable to open URL.
tell-unable-to-save-playlist = Unable to save playlist.
Expand Down
40 changes: 40 additions & 0 deletions src/gui/app.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,7 @@ pub struct App {
viewing_pane_controls: Option<grid::Id>,
playlist_path: Option<StrictPath>,
playlist_dirty: bool,
default_audio_output_device: Option<String>,
}

impl App {
Expand Down Expand Up @@ -204,6 +205,7 @@ impl App {
viewing_pane_controls: None,
playlist_path,
playlist_dirty,
default_audio_output_device: Self::get_audio_device(),
},
Task::batch(commands),
)
Expand Down Expand Up @@ -394,6 +396,34 @@ impl App {
}
}

fn get_audio_device() -> Option<String> {
use rodio::cpal::traits::{DeviceTrait, HostTrait};
let host = rodio::cpal::default_host();
host.default_output_device().and_then(|d| d.name().ok())
}

/// Rodio/CPAL don't automatically follow changes to the default output device,
/// so we need to reload the streams if that happens.
/// More info:
/// * https://github.com/RustAudio/cpal/issues/740
/// * https://github.com/RustAudio/rodio/issues/327
/// * https://github.com/RustAudio/rodio/issues/544
fn did_audio_device_change(&mut self) -> bool {
let device = Self::get_audio_device();

if self.default_audio_output_device != device {
log::info!(
"Default audio device changed: {:?} -> {:?}",
self.default_audio_output_device.as_ref(),
device.as_ref()
);
self.default_audio_output_device = device;
true
} else {
false
}
}

pub fn update(&mut self, message: Message) -> Task<Message> {
match message {
Message::Ignore => Task::none(),
Expand All @@ -412,11 +442,20 @@ impl App {
Message::Tick(instant) => {
let elapsed = instant - self.last_tick;
self.last_tick = instant;

for (_id, grid) in self.grids.iter_mut() {
grid.tick(elapsed, &mut self.media, &self.config.playback);
}
Task::none()
}
Message::CheckAudio => {
if self.did_audio_device_change() {
for (_id, grid) in self.grids.iter_mut() {
grid.reload_audio(&self.config.playback);
}
}
Task::none()
}
Message::Save => {
self.save();
Task::none()
Expand Down Expand Up @@ -1027,6 +1066,7 @@ impl App {
_ => None,
}),
iced::time::every(Duration::from_millis(100)).map(Message::Tick),
iced::time::every(Duration::from_millis(1000)).map(|_| Message::CheckAudio),
iced::time::every(Duration::from_secs(60 * 10)).map(|_| Message::FindMedia),
];

Expand Down
1 change: 1 addition & 0 deletions src/gui/common.rs
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ pub enum Message {
force: bool,
},
Tick(Instant),
CheckAudio,
Save,
CloseModal,
Config {
Expand Down
6 changes: 6 additions & 0 deletions src/gui/grid.rs
Original file line number Diff line number Diff line change
Expand Up @@ -135,6 +135,12 @@ impl Grid {
}
}

pub fn reload_audio(&mut self, playback: &Playback) {
for player in &mut self.players {
player.reload_audio(playback);
}
}

pub fn remove(&mut self, id: player::Id) {
self.players.remove(id.0);
}
Expand Down
2 changes: 2 additions & 0 deletions src/gui/icon.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ pub enum Icon {
Loop,
MoreVert,
Movie,
Music,
Mute,
OpenInBrowser,
OpenInNew,
Expand Down Expand Up @@ -53,6 +54,7 @@ impl Icon {
Self::Loop => '\u{e040}',
Self::MoreVert => '\u{E5D4}',
Self::Movie => '\u{e02c}',
Self::Music => '\u{e405}',
Self::Mute => '\u{e04f}',
Self::OpenInBrowser => '\u{e89d}',
Self::OpenInNew => '\u{E89E}',
Expand Down
Loading

0 comments on commit b097f18

Please sign in to comment.