My personal-knowledge-system, with deeply integrated task tracking and long term goal planning capabilities.
at tui 119 lines 4.0 kB view raw
1use crossterm::event::{KeyEvent, MouseEvent}; 2use ratatui::{ 3 Frame, 4 layout::{Rect, Size}, 5}; 6use tokio::sync::mpsc::UnboundedSender; 7 8use crate::{config::Config, signal::Signal, tui::Event}; 9 10/// `Component` is a trait that represents a visual and interactive element of the user interface. 11/// 12/// Implementers of this trait can be registered with the main application loop and will be able to 13/// receive events, update state, and be rendered on the screen. 14pub trait Component: Send { 15 /// Register a signal handler that can send signals for processing if necessary. 16 /// 17 /// # Arguments 18 /// 19 /// * `tx` - An unbounded sender that can send signals. 20 /// 21 /// # Returns 22 /// 23 /// * [`color_eyre::Result<()>`] - An Ok result or an error. 24 fn register_signal_handler(&mut self, tx: UnboundedSender<Signal>) -> color_eyre::Result<()> { 25 let _ = tx; // to appease clippy 26 Ok(()) 27 } 28 /// Register a configuration handler that provides configuration settings if necessary. 29 /// 30 /// # Arguments 31 /// 32 /// * `config` - Configuration settings. 33 /// 34 /// # Returns 35 /// 36 /// * [`color_eyre::Result<()>`] - An Ok result or an error. 37 fn register_config_handler(&mut self, config: Config) -> color_eyre::Result<()> { 38 let _ = config; // to appease clippy 39 Ok(()) 40 } 41 /// Initialize the component with a specified area if necessary. 42 /// 43 /// # Arguments 44 /// 45 /// * `area` - Rectangular area to initialize the component within. 46 /// 47 /// # Returns 48 /// 49 /// * [`color_eyre::Result<()>`] - An Ok result or an error. 50 fn init(&mut self, area: Size) -> color_eyre::Result<()> { 51 let _ = area; // to appease clippy 52 Ok(()) 53 } 54 /// Handle incoming events and produce signals if necessary. 55 /// 56 /// # Arguments 57 /// 58 /// * `event` - An optional event to be processed. 59 /// 60 /// # Returns 61 /// 62 /// * [`color_eyre::Result<Option<signal>>`] - A signal to be processed or none. 63 fn handle_events(&mut self, event: Option<Event>) -> color_eyre::Result<Option<Signal>> { 64 let signal = match event { 65 Some(Event::Key(key_event)) => self.handle_key_event(key_event)?, 66 Some(Event::Mouse(mouse_event)) => self.handle_mouse_event(mouse_event)?, 67 _ => None, 68 }; 69 Ok(signal) 70 } 71 /// Handle key events and produce signals if necessary. 72 /// 73 /// # Arguments 74 /// 75 /// * `key` - A key event to be processed. 76 /// 77 /// # Returns 78 /// 79 /// * [`color_eyre::Result<Option<signal>>`] - A signal to be processed or none. 80 fn handle_key_event(&mut self, key: KeyEvent) -> color_eyre::Result<Option<Signal>> { 81 let _ = key; // to appease clippy 82 Ok(None) 83 } 84 /// Handle mouse events and produce signals if necessary. 85 /// 86 /// # Arguments 87 /// 88 /// * `mouse` - A mouse event to be processed. 89 /// 90 /// # Returns 91 /// 92 /// * [`color_eyre::Result<Option<signal>>`] - A signal to be processed or none. 93 fn handle_mouse_event(&mut self, mouse: MouseEvent) -> color_eyre::Result<Option<Signal>> { 94 let _ = mouse; // to appease clippy 95 Ok(None) 96 } 97 /// Update the state of the component based on a received signal. (REQUIRED) 98 /// 99 /// # Arguments 100 /// 101 /// * `signal` - A signal that may modify the state of the component. 102 /// 103 /// # Returns 104 /// 105 /// * [`color_eyre::Result<Option<signal>>`] - A signal to be processed or none. 106 fn update(&mut self, signal: Signal) -> color_eyre::Result<Option<Signal>>; 107 108 /// Render the component on the screen. (REQUIRED) 109 /// 110 /// # Arguments 111 /// 112 /// * `f` - A frame used for rendering. 113 /// * `area` - The area in which the component should be drawn. 114 /// 115 /// # Returns 116 /// 117 /// * [`color_eyre::Result<()>`] - An Ok result or an error. 118 fn draw(&mut self, frame: &mut Frame, area: Rect) -> color_eyre::Result<()>; 119}