wip: global enter

This commit is contained in:
🪞👃🪞 2024-11-09 01:17:41 +01:00
parent 2105d86428
commit 9b770c468f
6 changed files with 43 additions and 28 deletions

View file

@ -8,6 +8,8 @@ pub enum FocusCommand {
Down,
Left,
Right,
Enter,
Exit
}
pub trait FocusGrid<T: Copy + PartialEq> {

View file

@ -74,6 +74,8 @@ pub struct Arrangement<E: Engine> {
pub color: ItemColor,
/// Width and height of arrangement area at last render
pub size: Measure<E>,
/// Whether this is currently in edit mode
pub entered: bool,
}
/// Represents a track in the arrangement
pub struct ArrangementTrack {
@ -308,6 +310,7 @@ impl<E: Engine> Arrangement<E> {
focused: false,
color: Color::Rgb(28, 35, 25).into(),
size: Measure::new(),
entered: false,
}
}
fn is_stopped (&self) -> bool {

View file

@ -2,12 +2,7 @@ use crate::*;
#[derive(Clone, PartialEq)]
pub enum ArrangerCommand {
FocusNext,
FocusPrev,
FocusUp,
FocusDown,
FocusLeft,
FocusRight,
Focus(FocusCommand),
Transport(TransportCommand),
Phrases(PhrasePoolCommand),
Editor(PhraseEditorCommand),
@ -41,13 +36,18 @@ pub enum ArrangementCommand {
impl<E: Engine> Command<Arranger<E>> for ArrangerCommand {
fn execute (self, state: &mut Arranger<E>) -> Perhaps<Self> {
use ArrangerCommand::*;
use FocusCommand::*;
match self {
FocusNext => { state.focus_next(); },
FocusPrev => { state.focus_prev(); },
FocusUp => { state.focus_up(); },
FocusDown => { state.focus_down(); },
FocusLeft => { state.focus_left(); },
FocusRight => { state.focus_right(); },
Focus(command) => match command {
Next => { state.focus_next(); },
Prev => { state.focus_prev(); },
Up => { state.focus_up(); },
Down => { state.focus_down(); },
Left => { state.focus_left(); },
Right => { state.focus_right(); },
Enter => { unimplemented!() },
Exit => { unimplemented!() },
},
Transport(cmd) => if let Some(ref transport) = state.transport {
return cmd.execute(&mut*transport.write().unwrap()).map(|x|x.map(Transport))
},

View file

@ -23,7 +23,11 @@ impl Content for Arranger<Tui> {
lay!(
widget(&self.arrangement).grow_y(1).border(border),
widget(&self.arrangement.size),
widget(&"[ ] Arrangement").fg(title_color).push_x(1),
widget(&format!("[{}] Arrangement", if self.arrangement.entered {
""
} else {
" "
})).fg(title_color).push_x(1),
),
Split::right(
self.phrases_split,
@ -544,30 +548,34 @@ impl Handle<Tui> for Arrangement<Tui> {
}
impl MatchInput<Tui, Arranger<Tui>> for ArrangerCommand {
fn match_input (state: &Arranger<Tui>, input: &TuiInput) -> Option<Self> {
use FocusCommand::*;
use ArrangerCommand::*;
match input.event() {
key!(KeyCode::Tab) => Some(Self::FocusNext),
key!(Shift-KeyCode::Tab) => Some(Self::FocusPrev),
key!(KeyCode::BackTab) => Some(Self::FocusPrev),
key!(Shift-KeyCode::BackTab) => Some(Self::FocusPrev),
key!(KeyCode::Up) => Some(Self::FocusUp),
key!(KeyCode::Down) => Some(Self::FocusDown),
key!(KeyCode::Left) => Some(Self::FocusLeft),
key!(KeyCode::Right) => Some(Self::FocusRight),
key!(KeyCode::Char(' ')) => Some(Self::Transport(TransportCommand::PlayToggle)),
key!(KeyCode::Tab) => Some(Focus(Next)),
key!(Shift-KeyCode::Tab) => Some(Focus(Prev)),
key!(KeyCode::BackTab) => Some(Focus(Prev)),
key!(Shift-KeyCode::BackTab) => Some(Focus(Prev)),
key!(KeyCode::Up) => Some(Focus(Up)),
key!(KeyCode::Down) => Some(Focus(Down)),
key!(KeyCode::Left) => Some(Focus(Left)),
key!(KeyCode::Right) => Some(Focus(Right)),
key!(KeyCode::Enter) => Some(Focus(Enter)),
key!(KeyCode::Esc) => Some(Focus(Exit)),
key!(KeyCode::Char(' ')) => Some(Transport(TransportCommand::PlayToggle)),
_ => match state.focused() {
ArrangerFocus::Transport => state.transport.as_ref()
.map(|t|TransportCommand::match_input(&*t.read().unwrap(), input)
.map(Self::Transport))
.map(Transport))
.flatten(),
ArrangerFocus::PhrasePool =>
PhrasePoolCommand::match_input(&*state.phrases.read().unwrap(), input)
.map(Self::Phrases),
.map(Phrases),
ArrangerFocus::PhraseEditor =>
PhraseEditorCommand::match_input(&state.editor, input)
.map(Self::Editor),
.map(Editor),
ArrangerFocus::Arrangement =>
ArrangementCommand::match_input(&state.arrangement, &input)
.map(Self::Arrangement)
.map(Arrangement)
}
}
}

View file

@ -83,6 +83,8 @@ impl<E: Engine> Command<Sequencer<E>> for SequencerCommand {
Down => { state.focus_down(); },
Left => { state.focus_left(); },
Right => { state.focus_right(); },
Enter => { unimplemented!() },
Exit => { unimplemented!() }
},
Transport(command) => if let Some(ref transport) = state.transport {
return command.execute(&mut*transport.write().unwrap()).map(|x|x.map(Transport))

View file

@ -79,7 +79,7 @@ impl Content for PhrasePool<Tui> {
let border = Lozenge(Style::default().bg(Color::Rgb(40, 50, 30)).fg(border_color));
let content = content.fill_xy().bg(Color::Rgb(28, 35, 25)).border(border);
let title_color = if *focused {Color::Rgb(150, 160, 90)} else {Color::Rgb(120, 130, 100)};
let title = format!("[ ] Phrases ({})", phrases.len());
let title = format!("[{}] Phrases ({})", phrases.len(), " ");
let title = TuiStyle::fg(title, title_color).push_x(1);
Layers::new(move|add|{ add(&content)?; Ok(add(&title)?) })
}
@ -267,7 +267,7 @@ impl Content for PhraseEditor<Tui> {
let piano_roll = row!(keys, note_area).fill_x();
let content = piano_roll.bg(Color::Rgb(40, 50, 30)).border(border);
let content = lay!(content, playhead);
let mut upper_left = format!("[ ] Sequencer");
let mut upper_left = format!("[{}] Sequencer", if *entered {""} else {" "});
if let Some(phrase) = phrase {
upper_left = format!("{upper_left}: {}", phrase.read().unwrap().name);
}