Skip to main content

cardinal_gui/
e_midi.rs

1#[cfg(all(feature = "uses_e_midi", not(target_arch = "wasm32")))]
2use e_midi::MidiPlayer;
3#[cfg(feature = "uses_e_midi")]
4pub fn init() {
5    // Initialize e_midi functionality here
6}
7
8#[cfg(feature = "uses_e_midi")]
9#[allow(unused_imports)]
10use std::sync::{
11    atomic::{AtomicBool, Ordering},
12    mpsc, Arc,
13};
14#[cfg(feature = "uses_e_midi")]
15use std::thread;
16
17#[cfg(feature = "uses_e_midi")]
18#[allow(dead_code)]
19pub struct MidiPlayerThread {
20    handle: thread::JoinHandle<()>,
21    shutdown_tx: mpsc::Sender<()>,
22}
23
24#[cfg(all(feature = "uses_e_midi", not(target_arch = "wasm32")))]
25impl MidiPlayerThread {
26    pub fn start() -> Self {
27        let (shutdown_tx, shutdown_rx) = mpsc::channel();
28        let running = Arc::new(AtomicBool::new(true));
29        let running_clone = running.clone();
30
31        let handle = thread::spawn(move || {
32            let mut player = match MidiPlayer::new() {
33                Ok(p) => p,
34                Err(e) => {
35                    eprintln!("Failed to create MidiPlayer: {e}");
36                    return;
37                }
38            };
39            let numsongs = player.get_total_song_count();
40            println!("Total songs: {numsongs}");
41
42            'outer: for i in 0..numsongs {
43                println!("Playing song {}", i + 1);
44                if let Err(e) = player.play_song(i, None, None) {
45                    eprintln!("Failed to play song {}: {e}", i + 1);
46                    continue;
47                }
48                // Wait until the song finishes or shutdown is requested
49                loop {
50                    // Check for shutdown signal
51                    if shutdown_rx.try_recv().is_ok() {
52                        running_clone.store(false, Ordering::SeqCst);
53                        // Stop playback immediately if playing
54                        // if player.is_playing() {
55                        player.stop_playback();
56                        // }
57                        break 'outer;
58                    }
59                    if !player.is_playing() {
60                        break;
61                    }
62                    std::thread::yield_now();
63                    // std::thread::sleep(std::time::Duration::from_millis(100));
64                }
65            }
66            // Optionally: stop playback if still playing
67            if player.is_playing() {
68                player.stop_playback();
69            }
70        });
71
72        MidiPlayerThread {
73            handle,
74            shutdown_tx,
75        }
76    }
77
78    pub fn shutdown(self) {
79        println!("Shutting down MidiPlayerThread...");
80        let _ = self.shutdown_tx.send(());
81        // Wait a short time to allow the thread to break out of its loop
82        std::thread::sleep(std::time::Duration::from_millis(200));
83        let _ = self.handle.join();
84        println!("MidiPlayerThread has shut down.");
85        // std::process::exit(0); // Remove this, let the main thread exit naturally
86    }
87}