Skip to main content

bee_tui/
components.rs

1use crossterm::event::{KeyEvent, MouseEvent};
2use ratatui::{
3    Frame,
4    layout::{Rect, Size},
5};
6use tokio::sync::mpsc::UnboundedSender;
7
8use crate::{action::Action, config::Config, tui::Event};
9
10pub mod api_health;
11pub mod feed_timeline;
12pub mod health;
13pub mod log_pane;
14pub mod lottery;
15pub mod manifest;
16pub mod network;
17pub mod peers;
18pub mod pins;
19pub mod scroll;
20pub mod stamps;
21pub mod swap;
22pub mod tags;
23pub mod warmup;
24pub mod watchlist;
25
26/// `Component` is a trait that represents a visual and interactive element of the user interface.
27///
28/// Implementors of this trait can be registered with the main application loop and will be able to
29/// receive events, update state, and be rendered on the screen.
30pub trait Component {
31    /// Register an action handler that can send actions for processing if necessary.
32    ///
33    /// # Arguments
34    ///
35    /// * `tx` - An unbounded sender that can send actions.
36    ///
37    /// # Returns
38    ///
39    /// * [`color_eyre::Result<()>`] - An Ok result or an error.
40    fn register_action_handler(&mut self, tx: UnboundedSender<Action>) -> color_eyre::Result<()> {
41        let _ = tx; // to appease clippy
42        Ok(())
43    }
44    /// Register a configuration handler that provides configuration settings if necessary.
45    ///
46    /// # Arguments
47    ///
48    /// * `config` - Configuration settings.
49    ///
50    /// # Returns
51    ///
52    /// * [`color_eyre::Result<()>`] - An Ok result or an error.
53    fn register_config_handler(&mut self, config: Config) -> color_eyre::Result<()> {
54        let _ = config; // to appease clippy
55        Ok(())
56    }
57    /// Initialize the component with a specified area if necessary.
58    ///
59    /// # Arguments
60    ///
61    /// * `area` - Rectangular area to initialize the component within.
62    ///
63    /// # Returns
64    ///
65    /// * [`color_eyre::Result<()>`] - An Ok result or an error.
66    fn init(&mut self, area: Size) -> color_eyre::Result<()> {
67        let _ = area; // to appease clippy
68        Ok(())
69    }
70    /// Handle incoming events and produce actions if necessary.
71    ///
72    /// # Arguments
73    ///
74    /// * `event` - An optional event to be processed.
75    ///
76    /// # Returns
77    ///
78    /// * [`color_eyre::Result<Option<Action>>`] - An action to be processed or none.
79    fn handle_events(&mut self, event: Option<Event>) -> color_eyre::Result<Option<Action>> {
80        let action = match event {
81            Some(Event::Key(key_event)) => self.handle_key_event(key_event)?,
82            Some(Event::Mouse(mouse_event)) => self.handle_mouse_event(mouse_event)?,
83            _ => None,
84        };
85        Ok(action)
86    }
87    /// Handle key events and produce actions if necessary.
88    ///
89    /// # Arguments
90    ///
91    /// * `key` - A key event to be processed.
92    ///
93    /// # Returns
94    ///
95    /// * [`color_eyre::Result<Option<Action>>`] - An action to be processed or none.
96    fn handle_key_event(&mut self, key: KeyEvent) -> color_eyre::Result<Option<Action>> {
97        let _ = key; // to appease clippy
98        Ok(None)
99    }
100    /// Handle mouse events and produce actions if necessary.
101    ///
102    /// # Arguments
103    ///
104    /// * `mouse` - A mouse event to be processed.
105    ///
106    /// # Returns
107    ///
108    /// * [`color_eyre::Result<Option<Action>>`] - An action to be processed or none.
109    fn handle_mouse_event(&mut self, mouse: MouseEvent) -> color_eyre::Result<Option<Action>> {
110        let _ = mouse; // to appease clippy
111        Ok(None)
112    }
113    /// Update the state of the component based on a received action. (REQUIRED)
114    ///
115    /// # Arguments
116    ///
117    /// * `action` - An action that may modify the state of the component.
118    ///
119    /// # Returns
120    ///
121    /// * [`color_eyre::Result<Option<Action>>`] - An action to be processed or none.
122    fn update(&mut self, action: Action) -> color_eyre::Result<Option<Action>> {
123        let _ = action; // to appease clippy
124        Ok(None)
125    }
126    /// Render the component on the screen. (REQUIRED)
127    ///
128    /// # Arguments
129    ///
130    /// * `f` - A frame used for rendering.
131    /// * `area` - The area in which the component should be drawn.
132    ///
133    /// # Returns
134    ///
135    /// * [`color_eyre::Result<()>`] - An Ok result or an error.
136    fn draw(&mut self, frame: &mut Frame, area: Rect) -> color_eyre::Result<()>;
137
138    /// Downcast hook so the App can reach a concrete screen type
139    /// (e.g. to call `Manifest::load(reference)` from the command bar).
140    /// Default returns `None` so screens that don't need it can ignore
141    /// this method.
142    fn as_any_mut(&mut self) -> Option<&mut dyn std::any::Any> {
143        None
144    }
145}