tek/src/midi/midi_launch.rs

35 lines
1.5 KiB
Rust

use crate::*;
pub trait HasPlayPhrase: HasClock {
fn reset (&self) -> bool;
fn reset_mut (&mut self) -> &mut bool;
fn play_phrase (&self) -> &Option<(Moment, Option<Arc<RwLock<MidiClip>>>)>;
fn play_phrase_mut (&mut self) -> &mut Option<(Moment, Option<Arc<RwLock<MidiClip>>>)>;
fn next_phrase (&self) -> &Option<(Moment, Option<Arc<RwLock<MidiClip>>>)>;
fn next_phrase_mut (&mut self) -> &mut Option<(Moment, Option<Arc<RwLock<MidiClip>>>)>;
fn pulses_since_start (&self) -> Option<f64> {
if let Some((started, Some(_))) = self.play_phrase().as_ref() {
let elapsed = self.clock().playhead.pulse.get() - started.pulse.get();
Some(elapsed)
} else {
None
}
}
fn pulses_since_start_looped (&self) -> Option<f64> {
if let Some((started, Some(phrase))) = self.play_phrase().as_ref() {
let elapsed = self.clock().playhead.pulse.get() - started.pulse.get();
let length = phrase.read().unwrap().length.max(1); // prevent div0 on empty phrase
let elapsed = (elapsed as usize % length) as f64;
Some(elapsed)
} else {
None
}
}
fn enqueue_next (&mut self, phrase: Option<&Arc<RwLock<MidiClip>>>) {
let start = self.clock().next_launch_pulse() as f64;
let instant = Moment::from_pulse(self.clock().timebase(), start);
*self.next_phrase_mut() = Some((instant, phrase.cloned()));
*self.reset_mut() = true;
}
}