use crate::*; #[tengri_proc::expose] impl Arrangement { fn _todo_usize_stub_ (&self) -> usize { todo!() } fn _todo_arc_str_stub_ (&self) -> Arc { todo!() } fn _todo_item_theme_stub (&self) -> ItemTheme { todo!() } fn _todo_opt_item_theme_stub (&self) -> Option { todo!() } fn select_nothing (&self) -> Selection { Selection::Nothing } } #[tengri_proc::command(Arrangement)] impl ArrangementCommand { fn home (arranger: &mut Arrangement) -> Perhaps { arranger.editor = None; Ok(None) } fn edit (arranger: &mut Arrangement) -> Perhaps { let selection = arranger.selection().clone(); arranger.editor = if arranger.editor.is_some() { None } else { match selection { Selection::TrackClip { track, scene } => { let clip = &mut arranger.scenes_mut()[scene].clips[track]; if clip.is_none() { //app.clip_auto_create(); *clip = Some(Arc::new(RwLock::new(MidiClip::new( &format!("t{track:02}s{scene:02}"), false, 384, None, Some(ItemTheme::random()) )))); } clip.as_ref().map(|c|c.into()) } _ => { None } } }; if let Some(editor) = arranger.editor.as_mut() { if let Some(clip) = editor.clip() { let length = clip.read().unwrap().length.max(1); let width = arranger.inner_size.w().saturating_sub(20).max(1); editor.set_time_zoom(length / width); editor.redraw(); } } Ok(None) } /// Set the selection fn select (arranger: &mut Arrangement, s: Selection) -> Perhaps { *arranger.selection_mut() = s; Ok(None) } /// Launch a clip or scene fn launch (arranger: &mut Arrangement) -> Perhaps { match *arranger.selection() { Selection::Track(t) => { arranger.tracks[t].sequencer.enqueue_next(None) }, Selection::TrackClip { track, scene } => { arranger.tracks[track].sequencer.enqueue_next(arranger.scenes[scene].clips[track].as_ref()) }, Selection::Scene(s) => { for t in 0..arranger.tracks.len() { arranger.tracks[t].sequencer.enqueue_next(arranger.scenes[s].clips[t].as_ref()) } }, _ => {} }; Ok(None) } /// Set the color of the selected entity fn set_color (arranger: &mut Arrangement, palette: Option) -> Perhaps { let mut palette = palette.unwrap_or_else(||ItemTheme::random()); let selection = *arranger.selection(); Ok(Some(Self::SetColor { palette: Some(match selection { Selection::Mix => { std::mem::swap(&mut palette, &mut arranger.color); palette }, Selection::Scene(s) => { std::mem::swap(&mut palette, &mut arranger.scenes[s].color); palette } Selection::Track(t) => { std::mem::swap(&mut palette, &mut arranger.tracks[t].color); palette } Selection::TrackClip { track, scene } => { if let Some(ref clip) = arranger.scenes[scene].clips[track] { let mut clip = clip.write().unwrap(); std::mem::swap(&mut palette, &mut clip.color); palette } else { return Ok(None) } }, _ => todo!() }) })) } fn track (arranger: &mut Arrangement, track: TrackCommand) -> Perhaps { todo!("delegate") } fn track_add (arranger: &mut Arrangement) -> Perhaps { let index = arranger.track_add(None, None, &[], &[])?.0; *arranger.selection_mut() = match arranger.selection() { Selection::Track(_) => Selection::Track(index), Selection::TrackClip { track, scene } => Selection::TrackClip { track: index, scene: *scene }, _ => *arranger.selection() }; Ok(Some(Self::TrackDelete { index })) } fn track_swap (arranger: &mut Arrangement, index: usize, other: usize) -> Perhaps { todo!(); Ok(Some(Self::TrackSwap { index, other })) } fn track_delete (arranger: &mut Arrangement, index: usize) -> Perhaps { let exists = arranger.tracks().get(index).is_some(); if exists { let track = arranger.tracks_mut().remove(index); let Track { sequencer: Sequencer { midi_ins, midi_outs, .. }, .. } = track; for port in midi_ins.into_iter() { port.close()?; } for port in midi_outs.into_iter() { port.close()?; } for scene in arranger.scenes_mut().iter_mut() { scene.clips.remove(index); } } Ok(None) //TODO:Ok(Some(Self::TrackAdd ( index, track: Some(deleted_track) }) } fn midi_in (arranger: &mut Arrangement, input: MidiInputCommand) -> Perhaps { todo!("delegate"); Ok(None) } fn midi_in_add (arranger: &mut Arrangement) -> Perhaps { arranger.midi_in_add()?; Ok(None) } fn midi_out (arranger: &mut Arrangement, input: MidiOutputCommand) -> Perhaps { todo!("delegate"); Ok(None) } fn midi_out_add (arranger: &mut Arrangement) -> Perhaps { arranger.midi_out_add()?; Ok(None) } fn device (arranger: &mut Arrangement, input: DeviceCommand) -> Perhaps { todo!("delegate"); Ok(None) } fn device_add (arranger: &mut Arrangement, i: usize) -> Perhaps { todo!("delegate"); Ok(None) } fn scene (arranger: &mut Arrangement, scene: SceneCommand) -> Perhaps { todo!("delegate"); Ok(None) } fn output_add (arranger: &mut Arrangement) -> Perhaps { arranger.midi_outs.push(JackMidiOut::new( arranger.jack(), format!("/M{}", arranger.midi_outs.len() + 1), &[] )?); Ok(None) } fn input_add (arranger: &mut Arrangement) -> Perhaps { arranger.midi_ins.push(JackMidiIn::new( arranger.jack(), format!("M{}/", arranger.midi_ins.len() + 1), &[] )?); Ok(None) } fn scene_add (arranger: &mut Arrangement) -> Perhaps { let index = arranger.scene_add(None, None)?.0; *arranger.selection_mut() = match arranger.selection() { Selection::Scene(_) => Selection::Scene(index), Selection::TrackClip { track, scene } => Selection::TrackClip { track: *track, scene: index }, _ => *arranger.selection() }; Ok(None) // TODO } fn scene_swap (arranger: &mut Arrangement, index: usize, other: usize) -> Perhaps { todo!(); Ok(Some(Self::SceneSwap { index, other })) } fn scene_delete (arranger: &mut Arrangement, index: usize) -> Perhaps { let scenes = arranger.scenes_mut(); Ok(if scenes.get(index).is_some() { let _scene = scenes.remove(index); None } else { None }) } fn scene_launch (arranger: &mut Arrangement, index: usize) -> Perhaps { for track in 0..arranger.tracks.len() { let clip = arranger.scenes[index].clips[track].as_ref(); arranger.tracks[track].sequencer.enqueue_next(clip); } Ok(None) } fn clip (arranger: &mut Arrangement, scene: ClipCommand) -> Perhaps { todo!("delegate") } fn clip_get (arranger: &mut Arrangement, a: usize, b: usize) -> Perhaps { //(Get [a: usize, b: usize] cmd_todo!("\n\rtodo: clip: get: {a} {b}")) //("get" [a: usize, b: usize] Some(Self::Get(a.unwrap(), b.unwrap()))) todo!() } fn clip_put (arranger: &mut Arrangement, a: usize, b: usize) -> Perhaps { //(Put [t: usize, s: usize, c: MaybeClip] //Some(Self::Put(t, s, arranger.clip_put(t, s, c)))) //("put" [a: usize, b: usize, c: MaybeClip] Some(Self::Put(a.unwrap(), b.unwrap(), c.unwrap()))) todo!() } fn clip_del (arranger: &mut Arrangement, a: usize, b: usize) -> Perhaps { //("delete" [a: usize, b: usize] Some(Self::Put(a.unwrap(), b.unwrap(), None)))) todo!() } fn clip_enqueue (arranger: &mut Arrangement, a: usize, b: usize) -> Perhaps { //(Enqueue [t: usize, s: usize] //cmd!(arranger.tracks[t].sequencer.enqueue_next(arranger.scenes[s].clips[t].as_ref()))) //("enqueue" [a: usize, b: usize] Some(Self::Enqueue(a.unwrap(), b.unwrap()))) todo!() } fn clip_edit (arranger: &mut Arrangement, a: usize, b: usize) -> Perhaps { //(Edit [clip: MaybeClip] cmd_todo!("\n\rtodo: clip: edit: {clip:?}")) //("edit" [a: MaybeClip] Some(Self::Edit(a.unwrap()))) todo!() } } impl<'state> Context<'state, TrackCommand> for Arrangement { fn get <'source> (&'state self, iter: &mut TokenIter<'source>) -> Option { Context::get(&self, iter) } } impl<'state> Context<'state, MidiInputCommand> for Arrangement { fn get <'source> (&'state self, iter: &mut TokenIter<'source>) -> Option { Context::get(&self, iter) } } impl<'state> Context<'state, MidiOutputCommand> for Arrangement { fn get <'source> (&'state self, iter: &mut TokenIter<'source>) -> Option { Context::get(&self, iter) } } impl<'state> Context<'state, DeviceCommand> for Arrangement { fn get <'source> (&'state self, iter: &mut TokenIter<'source>) -> Option { Context::get(&self, iter) } } impl<'state> Context<'state, SceneCommand> for Arrangement { fn get <'source> (&'state self, iter: &mut TokenIter<'source>) -> Option { Context::get(&self, iter) } } impl<'state> Context<'state, ClipCommand> for Arrangement { fn get <'source> (&'state self, iter: &mut TokenIter<'source>) -> Option { Context::get(&self, iter) } }