mirror of
https://codeberg.org/unspeaker/tek.git
synced 2025-12-06 19:56:42 +01:00
perf: use Vec instead of BTreeMap in Phrase
This commit is contained in:
parent
db25099268
commit
4a8f5b267f
7 changed files with 150 additions and 221 deletions
|
|
@ -11,6 +11,8 @@ use crate::{core::*, model::App};
|
|||
}}
|
||||
}
|
||||
|
||||
pub type PhraseData = Vec<Vec<MidiMessage>>;
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct Phrase {
|
||||
pub name: String,
|
||||
|
|
@ -30,13 +32,20 @@ impl Phrase {
|
|||
Self {
|
||||
name: name.to_string(),
|
||||
length,
|
||||
notes: notes.unwrap_or(BTreeMap::new()),
|
||||
notes: notes.unwrap_or(vec![Vec::with_capacity(16);length]),
|
||||
looped: Some((0, length))
|
||||
}
|
||||
}
|
||||
pub fn record_event (&mut self, pulse: usize, message: MidiMessage) {
|
||||
if pulse >= self.length {
|
||||
panic!("extend phrase first")
|
||||
}
|
||||
self.notes[pulse].push(message);
|
||||
}
|
||||
/// Check if a range `start..end` contains MIDI Note On `k`
|
||||
pub fn contains_note_on (&self, k: u7, start: usize, end: usize) -> bool {
|
||||
for (_, (_, events)) in self.notes.range(start..end).enumerate() {
|
||||
//panic!("{:?} {start} {end}", &self);
|
||||
for events in self.notes[start.max(0)..end.min(self.notes.len())].iter() {
|
||||
for event in events.iter() {
|
||||
match event {
|
||||
MidiMessage::NoteOn {key,..} => {
|
||||
|
|
@ -63,31 +72,20 @@ impl Phrase {
|
|||
frame0, frame0 + frames
|
||||
) {
|
||||
let tick = tick % self.length;
|
||||
if let Some(events) = self.notes.get(&(tick as usize)) {
|
||||
for message in events.iter() {
|
||||
buf.clear();
|
||||
let channel = 0.into();
|
||||
let message = *message;
|
||||
LiveEvent::Midi { channel, message }.write(&mut buf).unwrap();
|
||||
output[time as usize].push(buf.clone());
|
||||
match message {
|
||||
MidiMessage::NoteOn { key, .. } => notes_on[key.as_int() as usize] = true,
|
||||
MidiMessage::NoteOff { key, .. } => notes_on[key.as_int() as usize] = false,
|
||||
_ => {}
|
||||
}
|
||||
for message in self.notes[tick].iter() {
|
||||
buf.clear();
|
||||
let channel = 0.into();
|
||||
let message = *message;
|
||||
LiveEvent::Midi { channel, message }.write(&mut buf).unwrap();
|
||||
output[time as usize].push(buf.clone());
|
||||
match message {
|
||||
MidiMessage::NoteOn { key, .. } => notes_on[key.as_int() as usize] = true,
|
||||
MidiMessage::NoteOff { key, .. } => notes_on[key.as_int() as usize] = false,
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn record_event (&mut self, pulse: usize, message: MidiMessage) {
|
||||
let contains = self.notes.contains_key(&pulse);
|
||||
if contains {
|
||||
self.notes.get_mut(&pulse).unwrap().push(message.clone());
|
||||
} else {
|
||||
self.notes.insert(pulse, vec![message.clone()]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl App {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue