mirror of
https://codeberg.org/unspeaker/tek.git
synced 2025-12-07 12:16:42 +01:00
extract input parse functions
This commit is contained in:
parent
5ccc55a76f
commit
a509db7215
3 changed files with 206 additions and 206 deletions
|
|
@ -17,6 +17,7 @@ pub enum TransportFocus {
|
||||||
Clock,
|
Clock,
|
||||||
Quant,
|
Quant,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sections in the sequencer app that may be focused
|
/// Sections in the sequencer app that may be focused
|
||||||
#[derive(Copy, Clone, PartialEq, Eq, Debug)]
|
#[derive(Copy, Clone, PartialEq, Eq, Debug)]
|
||||||
pub enum SequencerFocus {
|
pub enum SequencerFocus {
|
||||||
|
|
@ -27,6 +28,7 @@ pub enum SequencerFocus {
|
||||||
/// The phrase editor (sequencer) is focused
|
/// The phrase editor (sequencer) is focused
|
||||||
PhraseEditor,
|
PhraseEditor,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sections in the arranger app that may be focused
|
/// Sections in the arranger app that may be focused
|
||||||
#[derive(Copy, Clone, PartialEq, Eq, Debug)]
|
#[derive(Copy, Clone, PartialEq, Eq, Debug)]
|
||||||
pub enum ArrangerFocus {
|
pub enum ArrangerFocus {
|
||||||
|
|
@ -67,27 +69,6 @@ impl FocusWrap<TransportFocus> for Option<TransportFocus> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl TransportFocus {
|
|
||||||
pub fn next (&mut self) {
|
|
||||||
*self = match self {
|
|
||||||
Self::PlayPause => Self::Bpm,
|
|
||||||
Self::Bpm => Self::Quant,
|
|
||||||
Self::Quant => Self::Sync,
|
|
||||||
Self::Sync => Self::Clock,
|
|
||||||
Self::Clock => Self::PlayPause,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
pub fn prev (&mut self) {
|
|
||||||
*self = match self {
|
|
||||||
Self::PlayPause => Self::Clock,
|
|
||||||
Self::Bpm => Self::PlayPause,
|
|
||||||
Self::Quant => Self::Bpm,
|
|
||||||
Self::Sync => Self::Quant,
|
|
||||||
Self::Clock => Self::Sync,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
macro_rules! impl_focus {
|
macro_rules! impl_focus {
|
||||||
($Struct:ident $Focus:ident $Grid:expr) => {
|
($Struct:ident $Focus:ident $Grid:expr) => {
|
||||||
impl HasFocus for $Struct {
|
impl HasFocus for $Struct {
|
||||||
|
|
@ -132,24 +113,26 @@ macro_rules! impl_focus {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl_focus!(TransportTui TransportFocus [
|
impl_focus!(TransportTui TransportFocus [
|
||||||
&[Menu],
|
//&[Menu],
|
||||||
&[Content(Bpm), Content(Sync), Content(PlayPause), Content(Clock), Content(Quant)],
|
&[Content(Bpm), Content(Sync), Content(PlayPause), Content(Clock), Content(Quant)],
|
||||||
]);
|
]);
|
||||||
|
|
||||||
impl_focus!(SequencerTui SequencerFocus [
|
impl_focus!(SequencerTui SequencerFocus [
|
||||||
|
//&[
|
||||||
|
//Menu,
|
||||||
|
//Menu,
|
||||||
|
//Menu,
|
||||||
|
//Menu,
|
||||||
|
//Menu,
|
||||||
|
//],
|
||||||
&[
|
&[
|
||||||
Menu,
|
|
||||||
Menu,
|
|
||||||
Menu,
|
|
||||||
Menu,
|
|
||||||
Menu,
|
|
||||||
], &[
|
|
||||||
Content(Transport(TransportFocus::Bpm)),
|
Content(Transport(TransportFocus::Bpm)),
|
||||||
Content(Transport(TransportFocus::Sync)),
|
Content(Transport(TransportFocus::Sync)),
|
||||||
Content(Transport(TransportFocus::PlayPause)),
|
Content(Transport(TransportFocus::PlayPause)),
|
||||||
Content(Transport(TransportFocus::Clock)),
|
Content(Transport(TransportFocus::Clock)),
|
||||||
Content(Transport(TransportFocus::Quant))
|
Content(Transport(TransportFocus::Quant))
|
||||||
], &[
|
],
|
||||||
|
&[
|
||||||
Content(Phrases),
|
Content(Phrases),
|
||||||
Content(Phrases),
|
Content(Phrases),
|
||||||
Content(PhraseEditor),
|
Content(PhraseEditor),
|
||||||
|
|
@ -159,13 +142,14 @@ impl_focus!(SequencerTui SequencerFocus [
|
||||||
]);
|
]);
|
||||||
|
|
||||||
impl_focus!(ArrangerTui ArrangerFocus [
|
impl_focus!(ArrangerTui ArrangerFocus [
|
||||||
|
//&[
|
||||||
|
//Menu,
|
||||||
|
//Menu,
|
||||||
|
//Menu,
|
||||||
|
//Menu,
|
||||||
|
//Menu,
|
||||||
|
//],
|
||||||
&[
|
&[
|
||||||
Menu,
|
|
||||||
Menu,
|
|
||||||
Menu,
|
|
||||||
Menu,
|
|
||||||
Menu,
|
|
||||||
], &[
|
|
||||||
Content(Transport(TransportFocus::Bpm)),
|
Content(Transport(TransportFocus::Bpm)),
|
||||||
Content(Transport(TransportFocus::Sync)),
|
Content(Transport(TransportFocus::Sync)),
|
||||||
Content(Transport(TransportFocus::PlayPause)),
|
Content(Transport(TransportFocus::PlayPause)),
|
||||||
|
|
|
||||||
|
|
@ -9,7 +9,7 @@ impl TryFrom<&Arc<RwLock<JackClient>>> for TransportTui {
|
||||||
clock: ClockModel::from(&Arc::new(jack.read().unwrap().transport())),
|
clock: ClockModel::from(&Arc::new(jack.read().unwrap().transport())),
|
||||||
size: Measure::new(),
|
size: Measure::new(),
|
||||||
cursor: (0, 0),
|
cursor: (0, 0),
|
||||||
focus: FocusState::Entered(AppFocus::Content(TransportFocus::PlayPause))
|
focus: FocusState::Entered(AppFocus::Content(TransportFocus::Bpm))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -30,7 +30,7 @@ impl TryFrom<&Arc<RwLock<JackClient>>> for SequencerTui {
|
||||||
midi_buf: vec![vec![];65536],
|
midi_buf: vec![vec![];65536],
|
||||||
note_buf: vec![],
|
note_buf: vec![],
|
||||||
clock,
|
clock,
|
||||||
focus: FocusState::Entered(AppFocus::Content(SequencerFocus::Transport(TransportFocus::PlayPause)))
|
focus: FocusState::Entered(AppFocus::Content(SequencerFocus::Transport(TransportFocus::Bpm)))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -58,7 +58,7 @@ impl TryFrom<&Arc<RwLock<JackClient>>> for ArrangerTui {
|
||||||
status_bar: None,
|
status_bar: None,
|
||||||
midi_buf: vec![vec![];65536],
|
midi_buf: vec![vec![];65536],
|
||||||
note_buf: vec![],
|
note_buf: vec![],
|
||||||
focus: FocusState::Entered(AppFocus::Content(ArrangerFocus::Transport(TransportFocus::PlayPause)))
|
focus: FocusState::Entered(AppFocus::Content(ArrangerFocus::Transport(TransportFocus::Bpm)))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,26 @@
|
||||||
use crate::*;
|
use crate::*;
|
||||||
|
|
||||||
|
impl<T: TransportControl> InputToCommand<Tui, T> for TransportCommand {
|
||||||
|
fn input_to_command (state: &T, input: &TuiInput) -> Option<Self> {
|
||||||
|
to_transport_command(state, input)
|
||||||
|
.or_else(||to_focus_command(input).map(TransportCommand::Focus))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl InputToCommand<Tui, SequencerTui> for SequencerCommand {
|
||||||
|
fn input_to_command (state: &SequencerTui, input: &TuiInput) -> Option<Self> {
|
||||||
|
to_sequencer_command(state, input)
|
||||||
|
.or_else(||to_focus_command(input).map(SequencerCommand::Focus))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl InputToCommand<Tui, ArrangerTui> for ArrangerCommand {
|
||||||
|
fn input_to_command (state: &ArrangerTui, input: &TuiInput) -> Option<Self> {
|
||||||
|
to_arranger_command(state, input)
|
||||||
|
.or_else(||to_focus_command(input).map(ArrangerCommand::Focus))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn to_focus_command (input: &TuiInput) -> Option<FocusCommand> {
|
fn to_focus_command (input: &TuiInput) -> Option<FocusCommand> {
|
||||||
use KeyCode::{Tab, BackTab, Up, Down, Left, Right, Enter, Esc};
|
use KeyCode::{Tab, BackTab, Up, Down, Left, Right, Enter, Esc};
|
||||||
Some(match input.event() {
|
Some(match input.event() {
|
||||||
|
|
@ -17,182 +38,177 @@ fn to_focus_command (input: &TuiInput) -> Option<FocusCommand> {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T: TransportControl> InputToCommand<Tui, T> for TransportCommand {
|
fn to_transport_command <T> (state: &T, input: &TuiInput) -> Option<TransportCommand>
|
||||||
fn input_to_command (state: &T, input: &TuiInput) -> Option<Self> {
|
where
|
||||||
use ClockCommand::{SetBpm, SetQuant, SetSync};
|
T: TransportControl
|
||||||
use TransportCommand::{Focus, Clock};
|
{
|
||||||
use KeyCode::{Enter, Left, Right, Char};
|
use ClockCommand::{SetBpm, SetQuant, SetSync};
|
||||||
Some(match input.event() {
|
use TransportCommand::{Focus, Clock};
|
||||||
key!(Left) => Focus(FocusCommand::Prev),
|
use KeyCode::{Enter, Left, Right, Char};
|
||||||
key!(Right) => Focus(FocusCommand::Next),
|
Some(match input.event() {
|
||||||
key!(Char(' ')) => todo!("toolbar space"),
|
key!(Left) => Focus(FocusCommand::Prev),
|
||||||
key!(Shift-Char(' ')) => todo!("toolbar shift-space"),
|
key!(Right) => Focus(FocusCommand::Next),
|
||||||
_ => match state.transport_focused().unwrap() {
|
key!(Char(' ')) => todo!("toolbar space"),
|
||||||
TransportFocus::Bpm => match input.event() {
|
key!(Shift-Char(' ')) => todo!("toolbar shift-space"),
|
||||||
key!(Char(',')) => Clock(SetBpm(state.bpm().get() - 1.0)),
|
_ => match state.transport_focused().unwrap() {
|
||||||
key!(Char('.')) => Clock(SetBpm(state.bpm().get() + 1.0)),
|
TransportFocus::Bpm => match input.event() {
|
||||||
key!(Char('<')) => Clock(SetBpm(state.bpm().get() - 0.001)),
|
key!(Char(',')) => Clock(SetBpm(state.bpm().get() - 1.0)),
|
||||||
key!(Char('>')) => Clock(SetBpm(state.bpm().get() + 0.001)),
|
key!(Char('.')) => Clock(SetBpm(state.bpm().get() + 1.0)),
|
||||||
_ => return None,
|
key!(Char('<')) => Clock(SetBpm(state.bpm().get() - 0.001)),
|
||||||
},
|
key!(Char('>')) => Clock(SetBpm(state.bpm().get() + 0.001)),
|
||||||
TransportFocus::Quant => match input.event() {
|
_ => return None,
|
||||||
key!(Char(',')) => Clock(SetQuant(state.prev_quant())),
|
},
|
||||||
key!(Char('.')) => Clock(SetQuant(state.next_quant())),
|
TransportFocus::Quant => match input.event() {
|
||||||
key!(Char('<')) => Clock(SetQuant(state.prev_quant())),
|
key!(Char(',')) => Clock(SetQuant(state.prev_quant())),
|
||||||
key!(Char('>')) => Clock(SetQuant(state.next_quant())),
|
key!(Char('.')) => Clock(SetQuant(state.next_quant())),
|
||||||
_ => return None,
|
key!(Char('<')) => Clock(SetQuant(state.prev_quant())),
|
||||||
},
|
key!(Char('>')) => Clock(SetQuant(state.next_quant())),
|
||||||
TransportFocus::Sync => match input.event() {
|
_ => return None,
|
||||||
key!(Char(',')) => Clock(SetSync(state.prev_sync())),
|
},
|
||||||
key!(Char('.')) => Clock(SetSync(state.next_sync())),
|
TransportFocus::Sync => match input.event() {
|
||||||
key!(Char('<')) => Clock(SetSync(state.prev_sync())),
|
key!(Char(',')) => Clock(SetSync(state.prev_sync())),
|
||||||
key!(Char('>')) => Clock(SetSync(state.next_sync())),
|
key!(Char('.')) => Clock(SetSync(state.next_sync())),
|
||||||
_ => return None,
|
key!(Char('<')) => Clock(SetSync(state.prev_sync())),
|
||||||
},
|
key!(Char('>')) => Clock(SetSync(state.next_sync())),
|
||||||
TransportFocus::Clock => match input.event() {
|
_ => return None,
|
||||||
key!(Char(',')) => todo!("transport seek bar"),
|
},
|
||||||
key!(Char('.')) => todo!("transport seek bar"),
|
TransportFocus::Clock => match input.event() {
|
||||||
key!(Char('<')) => todo!("transport seek beat"),
|
key!(Char(',')) => todo!("transport seek bar"),
|
||||||
key!(Char('>')) => todo!("transport seek beat"),
|
key!(Char('.')) => todo!("transport seek bar"),
|
||||||
_ => return None,
|
key!(Char('<')) => todo!("transport seek beat"),
|
||||||
},
|
key!(Char('>')) => todo!("transport seek beat"),
|
||||||
TransportFocus::PlayPause => match input.event() {
|
_ => return None,
|
||||||
key!(Enter) => todo!("transport play toggle"),
|
},
|
||||||
key!(Shift-Enter) => todo!("transport shift-play toggle"),
|
TransportFocus::PlayPause => match input.event() {
|
||||||
_ => return None,
|
key!(Enter) => todo!("transport play toggle"),
|
||||||
},
|
key!(Shift-Enter) => todo!("transport shift-play toggle"),
|
||||||
}
|
_ => return None,
|
||||||
})
|
},
|
||||||
}
|
}
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
impl InputToCommand<Tui, SequencerTui> for SequencerCommand {
|
fn to_sequencer_command (state: &SequencerTui, input: &TuiInput) -> Option<SequencerCommand> {
|
||||||
fn input_to_command (state: &SequencerTui, input: &TuiInput) -> Option<Self> {
|
use SequencerCommand as Cmd;
|
||||||
use SequencerCommand::*;
|
if !state.entered() {
|
||||||
Some(if state.entered() {
|
return None
|
||||||
match state.focused() {
|
|
||||||
AppFocus::Menu => todo!(),
|
|
||||||
AppFocus::Content(SequencerFocus::Transport(_)) => {
|
|
||||||
use TransportCommand::{Clock, Focus};
|
|
||||||
match TransportCommand::input_to_command(state, input)? {
|
|
||||||
Clock(_) => { todo!() },
|
|
||||||
Focus(_) => { todo!() },
|
|
||||||
}
|
|
||||||
},
|
|
||||||
AppFocus::Content(SequencerFocus::Phrases) =>
|
|
||||||
Phrases(PhrasesCommand::input_to_command(state, input)?),
|
|
||||||
AppFocus::Content(SequencerFocus::PhraseEditor) =>
|
|
||||||
Editor(PhraseCommand::input_to_command(state, input)?),
|
|
||||||
}
|
|
||||||
} else if let Some(command) = to_focus_command(input) {
|
|
||||||
Self::Focus(command)
|
|
||||||
} else {
|
|
||||||
return None
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
Some(match state.focused() {
|
||||||
|
AppFocus::Menu => {
|
||||||
|
todo!()
|
||||||
|
},
|
||||||
|
AppFocus::Content(SequencerFocus::Transport(_)) => {
|
||||||
|
match TransportCommand::input_to_command(state, input)? {
|
||||||
|
TransportCommand::Clock(_) => { todo!() },
|
||||||
|
TransportCommand::Focus(command) => Cmd::Focus(command),
|
||||||
|
}
|
||||||
|
},
|
||||||
|
AppFocus::Content(SequencerFocus::Phrases) => {
|
||||||
|
Cmd::Phrases(PhrasesCommand::input_to_command(state, input)?)
|
||||||
|
},
|
||||||
|
AppFocus::Content(SequencerFocus::PhraseEditor) => {
|
||||||
|
Cmd::Editor(PhraseCommand::input_to_command(state, input)?)
|
||||||
|
},
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
impl InputToCommand<Tui, ArrangerTui> for ArrangerCommand {
|
fn to_arranger_command (state: &ArrangerTui, input: &TuiInput) -> Option<ArrangerCommand> {
|
||||||
fn input_to_command (state: &ArrangerTui, input: &TuiInput) -> Option<Self> {
|
use ArrangerCommand as Cmd;
|
||||||
Some(if state.entered() {
|
if !state.entered() {
|
||||||
match state.focused() {
|
return None
|
||||||
AppFocus::Menu => todo!(),
|
}
|
||||||
AppFocus::Content(ArrangerFocus::Transport(_)) => {
|
Some(match state.focused() {
|
||||||
use TransportCommand::{Clock, Focus};
|
AppFocus::Menu => todo!(),
|
||||||
match TransportCommand::input_to_command(state, input)? {
|
AppFocus::Content(ArrangerFocus::Transport(_)) => {
|
||||||
Clock(_) => { todo!() },
|
use TransportCommand::{Clock, Focus};
|
||||||
Focus(_) => { todo!() }
|
match TransportCommand::input_to_command(state, input)? {
|
||||||
}
|
Clock(_) => { todo!() },
|
||||||
},
|
Focus(command) => Cmd::Focus(command)
|
||||||
AppFocus::Content(ArrangerFocus::PhraseEditor) => {
|
}
|
||||||
Self::Editor(PhraseCommand::input_to_command(state, input)?)
|
},
|
||||||
},
|
AppFocus::Content(ArrangerFocus::PhraseEditor) => {
|
||||||
AppFocus::Content(ArrangerFocus::Phrases) => match input.event() {
|
Cmd::Editor(PhraseCommand::input_to_command(state, input)?)
|
||||||
key!(KeyCode::Char('e')) => {
|
},
|
||||||
Self::EditPhrase(state.phrase_editing().clone())
|
AppFocus::Content(ArrangerFocus::Phrases) => match input.event() {
|
||||||
|
key!(KeyCode::Char('e')) => {
|
||||||
|
Cmd::EditPhrase(state.phrase_editing().clone())
|
||||||
|
},
|
||||||
|
_ => {
|
||||||
|
Cmd::Phrases(PhrasesCommand::input_to_command(state, input)?)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
AppFocus::Content(ArrangerFocus::Arranger) => {
|
||||||
|
use ArrangerSelection as Select;
|
||||||
|
use ArrangerTrackCommand as Track;
|
||||||
|
use ArrangerClipCommand as Clip;
|
||||||
|
use ArrangerSceneCommand as Scene;
|
||||||
|
use KeyCode::{Char, Up, Down, Left, Right, Enter, Delete};
|
||||||
|
match input.event() {
|
||||||
|
key!(Char('e')) => Cmd::EditPhrase(state.phrase_editing().clone()),
|
||||||
|
key!(Char('l')) => Cmd::Clip(Clip::SetLoop(false)),
|
||||||
|
key!(Char('+')) => Cmd::Zoom(0), // TODO
|
||||||
|
key!(Char('=')) => Cmd::Zoom(0), // TODO
|
||||||
|
key!(Char('_')) => Cmd::Zoom(0), // TODO
|
||||||
|
key!(Char('-')) => Cmd::Zoom(0), // TODO
|
||||||
|
key!(Char('`')) => { todo!("toggle state mode") },
|
||||||
|
key!(Ctrl-Char('a')) => Cmd::Scene(Scene::Add),
|
||||||
|
key!(Ctrl-Char('t')) => Cmd::Track(Track::Add),
|
||||||
|
_ => match state.selected() {
|
||||||
|
Select::Mix => match input.event() {
|
||||||
|
key!(Down) => Cmd::Select(Select::Scene(0)),
|
||||||
|
key!(Right) => Cmd::Select(Select::Track(0)),
|
||||||
|
key!(Char(',')) => Cmd::Zoom(0),
|
||||||
|
key!(Char('.')) => Cmd::Zoom(0),
|
||||||
|
key!(Char('<')) => Cmd::Zoom(0),
|
||||||
|
key!(Char('>')) => Cmd::Zoom(0),
|
||||||
|
key!(Delete) => Cmd::Clear,
|
||||||
|
key!(Char('c')) => Cmd::Color(ItemColor::random()),
|
||||||
|
_ => return None
|
||||||
|
},
|
||||||
|
Select::Track(t) => match input.event() {
|
||||||
|
key!(Down) => Cmd::Select(Select::Clip(t, 0)),
|
||||||
|
key!(Left) => Cmd::Select(if t > 0 { Select::Track(t - 1) } else { Select::Mix }),
|
||||||
|
key!(Right) => Cmd::Select(Select::Track(t + 1)),
|
||||||
|
key!(Char(',')) => Cmd::Track(Track::Swap(t, t - 1)),
|
||||||
|
key!(Char('.')) => Cmd::Track(Track::Swap(t, t + 1)),
|
||||||
|
key!(Char('<')) => Cmd::Track(Track::Swap(t, t - 1)),
|
||||||
|
key!(Char('>')) => Cmd::Track(Track::Swap(t, t + 1)),
|
||||||
|
key!(Delete) => Cmd::Track(Track::Delete(t)),
|
||||||
|
//key!(Char('c')) => Cmd::Track(Track::Color(t, ItemColor::random())),
|
||||||
|
_ => return None
|
||||||
|
},
|
||||||
|
Select::Scene(s) => match input.event() {
|
||||||
|
key!(Up) => Cmd::Select(if s > 0 { Select::Scene(s - 1) } else { Select::Mix }),
|
||||||
|
key!(Down) => Cmd::Select(Select::Scene(s + 1)),
|
||||||
|
key!(Right) => Cmd::Select(Select::Clip(0, s)),
|
||||||
|
key!(Char(',')) => Cmd::Scene(Scene::Swap(s, s - 1)),
|
||||||
|
key!(Char('.')) => Cmd::Scene(Scene::Swap(s, s + 1)),
|
||||||
|
key!(Char('<')) => Cmd::Scene(Scene::Swap(s, s - 1)),
|
||||||
|
key!(Char('>')) => Cmd::Scene(Scene::Swap(s, s + 1)),
|
||||||
|
key!(Enter) => Cmd::Scene(Scene::Play(s)),
|
||||||
|
key!(Delete) => Cmd::Scene(Scene::Delete(s)),
|
||||||
|
//key!(Char('c')) => Cmd::Track(Scene::Color(s, ItemColor::random())),
|
||||||
|
_ => return None
|
||||||
|
},
|
||||||
|
Select::Clip(t, s) => match input.event() {
|
||||||
|
key!(Up) => Cmd::Select(if s > 0 { Select::Clip(t, s - 1) } else { Select::Track(t) }),
|
||||||
|
key!(Down) => Cmd::Select(Select::Clip(t, s + 1)),
|
||||||
|
key!(Left) => Cmd::Select(if t > 0 { Select::Clip(t - 1, s) } else { Select::Scene(s) }),
|
||||||
|
key!(Right) => Cmd::Select(Select::Clip(t + 1, s)),
|
||||||
|
key!(Char(',')) => Cmd::Clip(Clip::Set(t, s, None)),
|
||||||
|
key!(Char('.')) => Cmd::Clip(Clip::Set(t, s, None)),
|
||||||
|
key!(Char('<')) => Cmd::Clip(Clip::Set(t, s, None)),
|
||||||
|
key!(Char('>')) => Cmd::Clip(Clip::Set(t, s, None)),
|
||||||
|
key!(Delete) => Cmd::Clip(Clip::Set(t, s, None)),
|
||||||
|
//key!(Char('c')) => Cmd::Clip(Clip::Color(t, s, ItemColor::random())),
|
||||||
|
//key!(Char('g')) => Cmd::Clip(Clip(Clip::Get(t, s))),
|
||||||
|
//key!(Char('s')) => Cmd::Clip(Clip(Clip::Set(t, s))),
|
||||||
|
_ => return None
|
||||||
},
|
},
|
||||||
_ => {
|
|
||||||
Self::Phrases(PhrasesCommand::input_to_command(state, input)?)
|
|
||||||
}
|
|
||||||
},
|
|
||||||
AppFocus::Content(ArrangerFocus::Arranger) => {
|
|
||||||
use ArrangerSelection as Select;
|
|
||||||
use ArrangerTrackCommand as Track;
|
|
||||||
use ArrangerClipCommand as Clip;
|
|
||||||
use ArrangerSceneCommand as Scene;
|
|
||||||
use KeyCode::{Char, Up, Down, Left, Right, Enter, Delete};
|
|
||||||
match input.event() {
|
|
||||||
key!(Char('e')) => Self::EditPhrase(state.phrase_editing().clone()),
|
|
||||||
key!(Char('l')) => Self::Clip(Clip::SetLoop(false)),
|
|
||||||
key!(Char('+')) => Self::Zoom(0), // TODO
|
|
||||||
key!(Char('=')) => Self::Zoom(0), // TODO
|
|
||||||
key!(Char('_')) => Self::Zoom(0), // TODO
|
|
||||||
key!(Char('-')) => Self::Zoom(0), // TODO
|
|
||||||
key!(Char('`')) => { todo!("toggle state mode") },
|
|
||||||
key!(Ctrl-Char('a')) => Self::Scene(Scene::Add),
|
|
||||||
key!(Ctrl-Char('t')) => Self::Track(Track::Add),
|
|
||||||
_ => match state.selected() {
|
|
||||||
Select::Mix => match input.event() {
|
|
||||||
key!(Down) => Self::Select(Select::Scene(0)),
|
|
||||||
key!(Right) => Self::Select(Select::Track(0)),
|
|
||||||
key!(Char(',')) => Self::Zoom(0),
|
|
||||||
key!(Char('.')) => Self::Zoom(0),
|
|
||||||
key!(Char('<')) => Self::Zoom(0),
|
|
||||||
key!(Char('>')) => Self::Zoom(0),
|
|
||||||
key!(Delete) => Self::Clear,
|
|
||||||
key!(Char('c')) => Self::Color(ItemColor::random()),
|
|
||||||
_ => return None
|
|
||||||
},
|
|
||||||
Select::Track(t) => match input.event() {
|
|
||||||
key!(Down) => Self::Select(Select::Clip(t, 0)),
|
|
||||||
key!(Left) => Self::Select(if t > 0 { Select::Track(t - 1) } else { Select::Mix }),
|
|
||||||
key!(Right) => Self::Select(Select::Track(t + 1)),
|
|
||||||
key!(Char(',')) => Self::Track(Track::Swap(t, t - 1)),
|
|
||||||
key!(Char('.')) => Self::Track(Track::Swap(t, t + 1)),
|
|
||||||
key!(Char('<')) => Self::Track(Track::Swap(t, t - 1)),
|
|
||||||
key!(Char('>')) => Self::Track(Track::Swap(t, t + 1)),
|
|
||||||
key!(Delete) => Self::Track(Track::Delete(t)),
|
|
||||||
//key!(Char('c')) => Self::Track(Track::Color(t, ItemColor::random())),
|
|
||||||
_ => return None
|
|
||||||
},
|
|
||||||
Select::Scene(s) => match input.event() {
|
|
||||||
key!(Up) => Self::Select(if s > 0 { Select::Scene(s - 1) } else { Select::Mix }),
|
|
||||||
key!(Down) => Self::Select(Select::Scene(s + 1)),
|
|
||||||
key!(Right) => Self::Select(Select::Clip(0, s)),
|
|
||||||
key!(Char(',')) => Self::Scene(Scene::Swap(s, s - 1)),
|
|
||||||
key!(Char('.')) => Self::Scene(Scene::Swap(s, s + 1)),
|
|
||||||
key!(Char('<')) => Self::Scene(Scene::Swap(s, s - 1)),
|
|
||||||
key!(Char('>')) => Self::Scene(Scene::Swap(s, s + 1)),
|
|
||||||
key!(Enter) => Self::Scene(Scene::Play(s)),
|
|
||||||
key!(Delete) => Self::Scene(Scene::Delete(s)),
|
|
||||||
//key!(Char('c')) => Self::Track(Scene::Color(s, ItemColor::random())),
|
|
||||||
_ => return None
|
|
||||||
},
|
|
||||||
Select::Clip(t, s) => match input.event() {
|
|
||||||
key!(Up) => Self::Select(if s > 0 { Select::Clip(t, s - 1) } else { Select::Track(t) }),
|
|
||||||
key!(Down) => Self::Select(Select::Clip(t, s + 1)),
|
|
||||||
key!(Left) => Self::Select(if t > 0 { Select::Clip(t - 1, s) } else { Select::Scene(s) }),
|
|
||||||
key!(Right) => Self::Select(Select::Clip(t + 1, s)),
|
|
||||||
key!(Char(',')) => Self::Clip(Clip::Set(t, s, None)),
|
|
||||||
key!(Char('.')) => Self::Clip(Clip::Set(t, s, None)),
|
|
||||||
key!(Char('<')) => Self::Clip(Clip::Set(t, s, None)),
|
|
||||||
key!(Char('>')) => Self::Clip(Clip::Set(t, s, None)),
|
|
||||||
key!(Delete) => Self::Clip(Clip::Set(t, s, None)),
|
|
||||||
//key!(Char('c')) => Self::Clip(Clip::Color(t, s, ItemColor::random())),
|
|
||||||
//key!(Char('g')) => Self::Clip(Clip(Clip::Get(t, s))),
|
|
||||||
//key!(Char('s')) => Self::Clip(Clip(Clip::Set(t, s))),
|
|
||||||
_ => return None
|
|
||||||
},
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if let Some(command) = to_focus_command(input) {
|
}
|
||||||
Self::Focus(command)
|
})
|
||||||
} else {
|
|
||||||
return None
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T: PhrasesControl> InputToCommand<Tui, T> for PhrasesCommand {
|
impl<T: PhrasesControl> InputToCommand<Tui, T> for PhrasesCommand {
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue