From e13bf0b75b387a62ef1351008c23bd074d2ffd8f Mon Sep 17 00:00:00 2001 From: Erik Kundt Date: Tue, 18 Apr 2023 18:06:46 +0200 Subject: [PATCH] tui: Move shortcuts to root widget --- radicle-tui/src/app.rs | 50 +-------- radicle-tui/src/ui.rs | 71 +++++++++++-- radicle-tui/src/ui/components/workspace.rs | 113 ++++++++++++++++----- radicle-tui/src/ui/layout.rs | 30 +++--- 4 files changed, 172 insertions(+), 92 deletions(-) diff --git a/radicle-tui/src/app.rs b/radicle-tui/src/app.rs index e17478c0..50cd5c12 100644 --- a/radicle-tui/src/app.rs +++ b/radicle-tui/src/app.rs @@ -4,7 +4,6 @@ use tui_realm_stdlib::Phantom; use tuirealm::application::PollStrategy; use tuirealm::command::{Cmd, CmdResult, Direction as MoveDirection}; use tuirealm::event::{Event, Key, KeyEvent}; -use tuirealm::props::{AttrValue, Attribute}; use tuirealm::{Application, Frame, MockComponent, NoUserEvent, State, StateValue}; use radicle_tui::cob::patch::{self}; @@ -40,7 +39,6 @@ pub enum PatchCid { Navigation, Activity, Files, - Context, } /// All component ids known to this application. @@ -48,7 +46,6 @@ pub enum PatchCid { pub enum Cid { Home(HomeCid), Patch(PatchCid), - Shortcuts, GlobalListener, } @@ -232,15 +229,6 @@ impl ViewPage for Home { let issue_browser = ui::issue_browser(theme).to_boxed(); let patch_browser = ui::patch_browser(theme, &context.patches, &context.profile).to_boxed(); - let shortcuts = ui::shortcuts( - theme, - vec![ - ui::shortcut(theme, "tab", "section"), - ui::shortcut(theme, "q", "quit"), - ], - ) - .to_boxed(); - app.remount( Cid::Home(HomeCid::Navigation), navigation, @@ -251,7 +239,6 @@ impl ViewPage for Home { app.remount(Cid::Home(HomeCid::IssueBrowser), issue_browser, vec![])?; app.remount(Cid::Home(HomeCid::PatchBrowser), patch_browser, vec![])?; - app.remount(Cid::Shortcuts, shortcuts, vec![])?; Ok(()) } @@ -269,17 +256,10 @@ impl ViewPage for Home { fn view(&mut self, app: &mut Application, frame: &mut Frame) { let area = frame.size(); let navigation_h = 2u16; - let shortcuts_h = app - .query(&Cid::Shortcuts, Attribute::Height) - .ok() - .flatten() - .unwrap_or(AttrValue::Size(0)) - .unwrap_size(); - let layout = layout::default_page(area, navigation_h, shortcuts_h); + let layout = layout::default_page(area, navigation_h); app.view(&Cid::Home(HomeCid::Navigation), frame, layout[0]); app.view(&self.active_component, frame, layout[1]); - app.view(&Cid::Shortcuts, frame, layout[2]); } fn activate(&self, app: &mut Application) -> Result<()> { @@ -312,18 +292,8 @@ impl ViewPage for PatchView { ) -> Result<()> { if let Some((id, patch)) = context.patches.get(context.selected_patch) { let navigation = ui::patch_navigation(theme).to_boxed(); - let activity = ui::patch_activity(theme).to_boxed(); - let files = ui::patch_files(theme).to_boxed(); - let context = ui::patch_context(theme, (*id, patch), &context.profile).to_boxed(); - let shortcuts = ui::shortcuts( - theme, - vec![ - ui::shortcut(theme, "esc", "back"), - ui::shortcut(theme, "tab", "section"), - ui::shortcut(theme, "q", "quit"), - ], - ) - .to_boxed(); + let activity = ui::patch_activity(theme, (*id, patch), &context.profile).to_boxed(); + let files = ui::patch_files(theme, (*id, patch), &context.profile).to_boxed(); app.remount( Cid::Patch(PatchCid::Navigation), @@ -332,8 +302,6 @@ impl ViewPage for PatchView { )?; app.remount(Cid::Patch(PatchCid::Activity), activity, vec![])?; app.remount(Cid::Patch(PatchCid::Files), files, vec![])?; - app.remount(Cid::Patch(PatchCid::Context), context, vec![])?; - app.remount(Cid::Shortcuts, shortcuts, vec![])?; } Ok(()) } @@ -351,19 +319,11 @@ impl ViewPage for PatchView { fn view(&mut self, app: &mut Application, frame: &mut Frame) { let area = frame.size(); let navigation_h = 2u16; - let context_h = 1u16; - let shortcuts_h = app - .query(&Cid::Shortcuts, Attribute::Height) - .ok() - .flatten() - .unwrap_or(AttrValue::Size(0)) - .unwrap_size(); - let layout = layout::page_with_context(area, navigation_h, context_h, shortcuts_h); + + let layout = layout::default_page(area, navigation_h); app.view(&Cid::Patch(PatchCid::Navigation), frame, layout[0]); app.view(&self.active_component, frame, layout[1]); - app.view(&Cid::Patch(PatchCid::Context), frame, layout[2]); - app.view(&Cid::Shortcuts, frame, layout[3]); } fn activate(&self, app: &mut Application) -> Result<()> { diff --git a/radicle-tui/src/ui.rs b/radicle-tui/src/ui.rs index 8ad88457..6f89cb01 100644 --- a/radicle-tui/src/ui.rs +++ b/radicle-tui/src/ui.rs @@ -122,8 +122,16 @@ pub fn table(theme: &theme::Theme, items: &[impl List], profile: &Profile) -> Wi } pub fn issue_browser(theme: &theme::Theme) -> Widget { + let shortcuts = shortcuts( + theme, + vec![ + shortcut(theme, "tab", "section"), + shortcut(theme, "q", "quit"), + ], + ); + let not_implemented = label("not implemented").foreground(theme.colors.default_fg); - let browser = IssueBrowser::new(not_implemented); + let browser = IssueBrowser::new(not_implemented, shortcuts); Widget::new(browser) } @@ -133,6 +141,16 @@ pub fn patch_browser( items: &[(PatchId, Patch)], profile: &Profile, ) -> Widget> { + let shortcuts = shortcuts( + theme, + vec![ + shortcut(theme, "tab", "section"), + shortcut(theme, "↑/↓", "navigate"), + shortcut(theme, "enter", "show"), + shortcut(theme, "q", "quit"), + ], + ); + let widths = AttrValue::Payload(PropPayload::Vec(vec![ PropValue::U16(2), PropValue::U16(43), @@ -153,21 +171,51 @@ pub fn patch_browser( let table = table(theme, items, profile) .custom("widths", widths) .custom("header", header); - let browser: Browser<(PatchId, Patch)> = Browser::new(table); + let browser: Browser<(PatchId, Patch)> = Browser::new(table, shortcuts); Widget::new(browser) } -pub fn patch_activity(theme: &theme::Theme) -> Widget { +pub fn patch_activity( + theme: &theme::Theme, + patch: (PatchId, &Patch), + profile: &Profile, +) -> Widget { + let (id, patch) = patch; + let shortcuts = shortcuts( + theme, + vec![ + shortcut(theme, "esc", "back"), + shortcut(theme, "tab", "section"), + shortcut(theme, "q", "quit"), + ], + ); + let context = patch_context(theme, (id, patch), profile); + let not_implemented = label("not implemented").foreground(theme.colors.default_fg); - let activity = PatchActivity::new(not_implemented); + let activity = PatchActivity::new(not_implemented, context, shortcuts); Widget::new(activity) } -pub fn patch_files(theme: &theme::Theme) -> Widget { +pub fn patch_files( + theme: &theme::Theme, + patch: (PatchId, &Patch), + profile: &Profile, +) -> Widget { + let (id, patch) = patch; + let shortcuts = shortcuts( + theme, + vec![ + shortcut(theme, "esc", "back"), + shortcut(theme, "tab", "section"), + shortcut(theme, "q", "quit"), + ], + ); + let context = patch_context(theme, (id, patch), profile); + let not_implemented = label("not implemented").foreground(theme.colors.default_fg); - let files = PatchFiles::new(not_implemented); + let files = PatchFiles::new(not_implemented, context, shortcuts); Widget::new(files) } @@ -198,7 +246,7 @@ pub fn patch_context( .background(Color::Rgb(50, 50, 50)); let context_bar = ContextBar::new(context, id, author, title, comments); - Widget::new(context_bar) + Widget::new(context_bar).height(1) } pub fn home_navigation(theme: &theme::Theme) -> Widget { @@ -226,7 +274,14 @@ pub fn dashboard(theme: &theme::Theme, id: &Id, project: &Project) -> Widget { list: Widget, + shortcuts: Widget, phantom: PhantomData, } impl Browser { - pub fn new(list: Widget
) -> Self { + pub fn new(list: Widget
, shortcuts: Widget) -> Self { Self { list, + shortcuts, phantom: PhantomData, } } @@ -28,12 +31,15 @@ impl Browser { impl WidgetComponent for Browser { fn view(&mut self, _properties: &Props, frame: &mut Frame, area: Rect) { - let layout = Layout::default() - .direction(Direction::Vertical) - .constraints(vec![Constraint::Min(1)].as_ref()) - .split(area); + let shortcuts_h = self + .shortcuts + .query(Attribute::Height) + .unwrap_or(AttrValue::Size(0)) + .unwrap_size(); + let layout = layout::root_component(area, shortcuts_h); self.list.view(frame, layout[0]); + self.shortcuts.view(frame, layout[1]); } fn state(&self) -> State { @@ -47,20 +53,25 @@ impl WidgetComponent for Browser { pub struct Dashboard { about: Widget, + shortcuts: Widget, } impl Dashboard { - pub fn new(about: Widget) -> Self { - Self { about } + pub fn new(about: Widget, shortcuts: Widget) -> Self { + Self { about, shortcuts } } } impl WidgetComponent for Dashboard { fn view(&mut self, _properties: &Props, frame: &mut Frame, area: Rect) { - let layout = Layout::default() - .direction(Direction::Vertical) - .constraints(vec![Constraint::Length(4)].as_ref()) - .split(area); + let shortcuts_h = self + .shortcuts + .query(Attribute::Height) + .unwrap_or(AttrValue::Size(0)) + .unwrap_size(); + let layout = layout::root_component(area, shortcuts_h); + self.about.view(frame, layout[0]); + self.shortcuts.view(frame, layout[1]); } fn state(&self) -> State { @@ -74,11 +85,12 @@ impl WidgetComponent for Dashboard { pub struct IssueBrowser { label: Widget