Cleanup code
This commit is contained in:
parent
6177f37f36
commit
05ec879113
|
@ -96,22 +96,23 @@ impl Default for ListSelection {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub struct ConsoleUI {
|
pub struct ConsoleUI {
|
||||||
|
data: ConsoleUIData,
|
||||||
rx: EventReceiver,
|
rx: EventReceiver,
|
||||||
terminal: Terminal,
|
terminal: Terminal,
|
||||||
cur_size: Rect,
|
console_size: Rect,
|
||||||
main_chunks: Vec<Rect>,
|
|
||||||
stats_chunks: Vec<Rect>,
|
|
||||||
menu_selection: MenuSelection,
|
menu_selection: MenuSelection,
|
||||||
content_selection: ListSelection,
|
content_selection: ListSelection,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ConsoleUI {
|
impl ConsoleUI {
|
||||||
pub fn new(rx: EventReceiver, terminal: Terminal) -> ConsoleUI {
|
pub fn new(rx: EventReceiver, terminal: Terminal) -> ConsoleUI {
|
||||||
ConsoleUI{rx, terminal, cur_size: Rect::default(), main_chunks: Vec::default(), stats_chunks: Vec::default(), menu_selection: MenuSelection::Stats, content_selection: ListSelection::default()}
|
ConsoleUI{data: ConsoleUIData::default(), rx, terminal, console_size: Rect::default(), menu_selection: MenuSelection::Stats, content_selection: ListSelection::default()}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn update(&mut self, data: &ConsoleUIData) -> Result<UIState, Error> {
|
pub fn update_data(&mut self, memory_map: &MemoryMap) -> Result<(), Error> {
|
||||||
if data.list.len() > 0 {
|
self.data.update(memory_map)?;
|
||||||
|
|
||||||
|
if self.data.list.len() > 0 {
|
||||||
if !self.content_selection.is_active() {
|
if !self.content_selection.is_active() {
|
||||||
self.content_selection.activate();
|
self.content_selection.activate();
|
||||||
}
|
}
|
||||||
|
@ -120,7 +121,10 @@ impl ConsoleUI {
|
||||||
else {
|
else {
|
||||||
self.content_selection.deactivate();
|
self.content_selection.deactivate();
|
||||||
}
|
}
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn update(&mut self) -> Result<UIState, Error> {
|
||||||
match self.rx.recv()? {
|
match self.rx.recv()? {
|
||||||
Event::Input(event) => {
|
Event::Input(event) => {
|
||||||
match event.code {
|
match event.code {
|
||||||
|
@ -129,17 +133,17 @@ impl ConsoleUI {
|
||||||
self.menu_selection = MenuSelection::Stats;
|
self.menu_selection = MenuSelection::Stats;
|
||||||
Ok(UIState::Render)
|
Ok(UIState::Render)
|
||||||
},
|
},
|
||||||
KeyCode::Left => {
|
KeyCode::Left => {
|
||||||
self.menu_selection = self.menu_selection.prev();
|
self.menu_selection = self.menu_selection.prev();
|
||||||
Ok(UIState::Render)
|
Ok(UIState::Render)
|
||||||
},
|
},
|
||||||
KeyCode::Right => {
|
KeyCode::Right => {
|
||||||
self.menu_selection = self.menu_selection.next();
|
self.menu_selection = self.menu_selection.next();
|
||||||
Ok(UIState::Render)
|
Ok(UIState::Render)
|
||||||
},
|
},
|
||||||
KeyCode::Down => {
|
KeyCode::Down => {
|
||||||
if matches!(self.menu_selection, MenuSelection::Stats) {
|
if matches!(self.menu_selection, MenuSelection::Stats) {
|
||||||
self.content_selection.increment(data.list.len());
|
self.content_selection.increment(self.data.list.len());
|
||||||
Ok(UIState::Render)
|
Ok(UIState::Render)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -147,9 +151,9 @@ impl ConsoleUI {
|
||||||
Ok(UIState::Alive)
|
Ok(UIState::Alive)
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
KeyCode::Up => {
|
KeyCode::Up => {
|
||||||
if matches!(self.menu_selection, MenuSelection::Stats) {
|
if matches!(self.menu_selection, MenuSelection::Stats) {
|
||||||
self.content_selection.decrement(data.list.len());
|
self.content_selection.decrement(self.data.list.len());
|
||||||
Ok(UIState::Render)
|
Ok(UIState::Render)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -157,7 +161,7 @@ impl ConsoleUI {
|
||||||
Ok(UIState::Alive)
|
Ok(UIState::Alive)
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
KeyCode::Enter => {
|
KeyCode::Enter => {
|
||||||
if matches!(self.menu_selection, MenuSelection::Quit) {
|
if matches!(self.menu_selection, MenuSelection::Quit) {
|
||||||
Ok(UIState::Terminated)
|
Ok(UIState::Terminated)
|
||||||
}
|
}
|
||||||
|
@ -168,8 +172,10 @@ impl ConsoleUI {
|
||||||
_ => Ok(UIState::Alive)
|
_ => Ok(UIState::Alive)
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
Event::Tick => {
|
Event::Tick => {
|
||||||
if self.terminal.size().expect("Getting size of terminal") != self.cur_size {
|
let terminal_size = self.terminal.size().expect("Getting size of terminal");
|
||||||
|
if terminal_size != self.console_size {
|
||||||
|
self.console_size = terminal_size;
|
||||||
Ok(UIState::Render)
|
Ok(UIState::Render)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -181,18 +187,59 @@ impl ConsoleUI {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn render(&mut self, data: &mut ConsoleUIData) -> Result<(), Error> {
|
pub fn render(&mut self) -> Result<(), Error> {
|
||||||
self.terminal.draw(|frame| {
|
self.terminal.draw(|frame| {
|
||||||
Self::update_sub_frames(&mut self.main_chunks, &mut self.stats_chunks, &mut self.cur_size, frame.size());
|
// Create layout elements
|
||||||
|
let main_layout = Layout::default().direction(Direction::Vertical).constraints([
|
||||||
|
Constraint::Length(3),
|
||||||
|
Constraint::Length(3),
|
||||||
|
Constraint::Min(3)
|
||||||
|
]).split(frame.size()).to_vec();
|
||||||
|
let stats_layout = Layout::default().direction(Direction::Vertical).constraints([
|
||||||
|
Constraint::Min(3),
|
||||||
|
Constraint::Length(3)
|
||||||
|
]).split(main_layout[2]).to_vec();
|
||||||
|
|
||||||
frame.render_widget(Self::create_titel(), self.main_chunks[0]);
|
// Elements
|
||||||
frame.render_widget(Self::create_menu(&self.menu_selection), self.main_chunks[1]);
|
let titel_bar = {
|
||||||
|
Paragraph::new("psxreadmap")
|
||||||
|
.style(Style::default().fg(Color::White))
|
||||||
|
.alignment(Alignment::Center)
|
||||||
|
.block(Block::default()
|
||||||
|
.borders(Borders::ALL)
|
||||||
|
.style(Style::default().fg(Color::White))
|
||||||
|
.border_type(BorderType::Plain)
|
||||||
|
)
|
||||||
|
};
|
||||||
|
let menu_bar = {
|
||||||
|
const MENU_TITLES: &'static [&'static str] = &["Stats", "Quit"];
|
||||||
|
|
||||||
|
let menu = MENU_TITLES.iter().map(|t| {
|
||||||
|
let (first, rest) = t.split_at(1);
|
||||||
|
Line::from(vec![
|
||||||
|
Span::styled(first, Style::default().fg(Color::Yellow).add_modifier(Modifier::UNDERLINED),),
|
||||||
|
Span::styled(rest, Style::default().fg(Color::White)),
|
||||||
|
])
|
||||||
|
}).collect();
|
||||||
|
|
||||||
|
Tabs::new(menu).select(self.menu_selection.get_id()).block(
|
||||||
|
Block::default()
|
||||||
|
.title("Menu").borders(Borders::ALL))
|
||||||
|
.style(Style::default().fg(Color::White))
|
||||||
|
.highlight_style(Style::default().bg(Color::LightYellow))
|
||||||
|
.divider(Span::raw("|")
|
||||||
|
)
|
||||||
|
};
|
||||||
|
|
||||||
|
// Render screen
|
||||||
|
frame.render_widget(titel_bar, main_layout[0]);
|
||||||
|
frame.render_widget(menu_bar, main_layout[1]);
|
||||||
match self.menu_selection {
|
match self.menu_selection {
|
||||||
MenuSelection::Stats => {
|
MenuSelection::Stats => {
|
||||||
Self::render_stats(frame, &self.stats_chunks, &self.content_selection, data);
|
Self::render_stats(frame, &stats_layout, &self.content_selection, &mut self.data);
|
||||||
},
|
},
|
||||||
MenuSelection::Quit => {
|
MenuSelection::Quit => {
|
||||||
frame.render_widget(Self::create_exit_message(), self.main_chunks[2]);
|
frame.render_widget(Self::create_exit_message(), main_layout[2]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
})?;
|
})?;
|
||||||
|
@ -207,54 +254,6 @@ impl ConsoleUI {
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
fn update_sub_frames(sub_frames: &mut Vec<Rect>, stats_frames: &mut Vec<Rect>, frame: &mut Rect, new_frame: Rect) {
|
|
||||||
if new_frame != *frame {
|
|
||||||
*sub_frames = Layout::default().direction(Direction::Vertical).constraints([
|
|
||||||
Constraint::Length(3),
|
|
||||||
Constraint::Length(3),
|
|
||||||
Constraint::Min(3)
|
|
||||||
]).split(new_frame).to_vec();
|
|
||||||
|
|
||||||
*stats_frames = Layout::default().direction(Direction::Vertical).constraints([
|
|
||||||
Constraint::Min(3),
|
|
||||||
Constraint::Length(3)
|
|
||||||
]).split(sub_frames[2]).to_vec();
|
|
||||||
|
|
||||||
*frame = new_frame;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn create_titel<'a>() -> Paragraph<'a> {
|
|
||||||
Paragraph::new("psxreadmap")
|
|
||||||
.style(Style::default().fg(Color::White))
|
|
||||||
.alignment(Alignment::Center)
|
|
||||||
.block(Block::default()
|
|
||||||
.borders(Borders::ALL)
|
|
||||||
.style(Style::default().fg(Color::White))
|
|
||||||
.border_type(BorderType::Plain)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn create_menu<'a>(menu_selection: &MenuSelection) -> Tabs<'a> {
|
|
||||||
const MENU_TITLES: &'static [&'static str] = &["Stats", "Quit"];
|
|
||||||
|
|
||||||
let menu = MENU_TITLES.iter().map(|t| {
|
|
||||||
let (first, rest) = t.split_at(1);
|
|
||||||
Line::from(vec![
|
|
||||||
Span::styled(first, Style::default().fg(Color::Yellow).add_modifier(Modifier::UNDERLINED),),
|
|
||||||
Span::styled(rest, Style::default().fg(Color::White)),
|
|
||||||
])
|
|
||||||
}).collect();
|
|
||||||
|
|
||||||
Tabs::new(menu).select(menu_selection.get_id()).block(
|
|
||||||
Block::default()
|
|
||||||
.title("Menu").borders(Borders::ALL))
|
|
||||||
.style(Style::default().fg(Color::White))
|
|
||||||
.highlight_style(Style::default().bg(Color::LightYellow))
|
|
||||||
.divider(Span::raw("|")
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn render_stats(frame: &mut ConsoleFrame, frames: &Vec<Rect>, content_selection: &ListSelection, data: &mut ConsoleUIData) {
|
fn render_stats(frame: &mut ConsoleFrame, frames: &Vec<Rect>, content_selection: &ListSelection, data: &mut ConsoleUIData) {
|
||||||
let content_list = List::new({
|
let content_list = List::new({
|
||||||
let mut vec = Vec::new();
|
let mut vec = Vec::new();
|
||||||
|
@ -270,7 +269,7 @@ impl ConsoleUI {
|
||||||
.border_type(BorderType::Plain)
|
.border_type(BorderType::Plain)
|
||||||
)
|
)
|
||||||
.highlight_style(Style::default().bg(Color::Yellow));
|
.highlight_style(Style::default().bg(Color::Yellow));
|
||||||
let mem_gauge = Self::create_overall_mem_gauge(data.highest_adr);
|
let mem_gauge = Self::create_mem_gauge("Overall memory usage", data.highest_adr, Color::Cyan);
|
||||||
let mut list_state = ListState::default();
|
let mut list_state = ListState::default();
|
||||||
|
|
||||||
list_state.select(content_selection.selection);
|
list_state.select(content_selection.selection);
|
||||||
|
@ -279,16 +278,16 @@ impl ConsoleUI {
|
||||||
frame.render_widget(mem_gauge, frames[1]);
|
frame.render_widget(mem_gauge, frames[1]);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn create_overall_mem_gauge<'a>(highest_adr: u64) -> Gauge<'a> {
|
fn create_mem_gauge<'a>(name: &str, adr: u64, color: Color) -> Gauge<'a> {
|
||||||
const RAM_TOP:u64 = ConsoleUIData::HIGHEST_RAM_ADDRESS & !ConsoleUIData::RAM_BASE_ADDRESS;
|
const RAM_TOP:u64 = ConsoleUIData::HIGHEST_RAM_ADDRESS & !ConsoleUIData::RAM_BASE_ADDRESS;
|
||||||
|
|
||||||
let highest_adr_masked = highest_adr & !ConsoleUIData::RAM_BASE_ADDRESS;
|
let adr_masked = adr & !ConsoleUIData::RAM_BASE_ADDRESS;
|
||||||
let adr_ratio = (highest_adr_masked as f64)/RAM_TOP as f64;
|
let adr_ratio = (adr_masked as f64)/RAM_TOP as f64;
|
||||||
|
|
||||||
Gauge::default().block(Block::default().borders(Borders::ALL)
|
Gauge::default().block(Block::default().borders(Borders::ALL)
|
||||||
.title(format!("Memory Usage: {}% [0x{:x}/0x{:x}]", adr_ratio*100.0f64, highest_adr, ConsoleUIData::HIGHEST_RAM_ADDRESS)))
|
.title(format!("{} [0x{:x}/0x{:x}]", name, adr, ConsoleUIData::HIGHEST_RAM_ADDRESS)))
|
||||||
.gauge_style(Style::default().fg(Color::Cyan).bg(Color::Black).add_modifier(Modifier::BOLD))
|
.gauge_style(Style::default().fg(color).bg(Color::Black).add_modifier(Modifier::BOLD))
|
||||||
.ratio(adr_ratio)
|
.ratio(adr_ratio).label(format!("{}%", adr_ratio*100.0f64))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn create_exit_message<'a>() -> Paragraph<'a> {
|
fn create_exit_message<'a>() -> Paragraph<'a> {
|
||||||
|
@ -304,7 +303,7 @@ impl ConsoleUI {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Default)]
|
#[derive(Default)]
|
||||||
pub struct ConsoleUIData {
|
struct ConsoleUIData {
|
||||||
highest_adr: u64,
|
highest_adr: u64,
|
||||||
list: Vec<String>
|
list: Vec<String>
|
||||||
}
|
}
|
||||||
|
@ -313,7 +312,7 @@ impl ConsoleUIData {
|
||||||
pub const RAM_BASE_ADDRESS:u64 = 0x80000000;
|
pub const RAM_BASE_ADDRESS:u64 = 0x80000000;
|
||||||
pub const HIGHEST_RAM_ADDRESS:u64 = Self::RAM_BASE_ADDRESS + (2*1024*1024);
|
pub const HIGHEST_RAM_ADDRESS:u64 = Self::RAM_BASE_ADDRESS + (2*1024*1024);
|
||||||
|
|
||||||
pub fn new(memory_map: &MemoryMap) -> Result<ConsoleUIData, Error> {
|
fn _new(memory_map: &MemoryMap) -> Result<ConsoleUIData, Error> {
|
||||||
let mut ui_data = ConsoleUIData::default();
|
let mut ui_data = ConsoleUIData::default();
|
||||||
|
|
||||||
ui_data.update(memory_map)?;
|
ui_data.update(memory_map)?;
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
use clap::Parser;
|
use clap::Parser;
|
||||||
use crossterm::{event::{self, Event as CEvent, KeyboardEnhancementFlags, KeyEventKind, PushKeyboardEnhancementFlags}, execute, terminal};
|
use crossterm::{event::{self, Event as CEvent, KeyboardEnhancementFlags, KeyEventKind, PushKeyboardEnhancementFlags}, execute, terminal};
|
||||||
use psxreadmap::{ConsoleUI, ConsoleUIData, Event, EventReceiver, Terminal, load_memory_map, UIState};
|
use psxreadmap::{ConsoleUI, Event, EventReceiver, Terminal, load_memory_map, UIState};
|
||||||
use std::{io, path::PathBuf, sync::mpsc, thread, time::{Duration, Instant}};
|
use std::{io, path::PathBuf, sync::mpsc, thread, time::{Duration, Instant}};
|
||||||
use tool_helper::{Error, exit_with_error};
|
use tool_helper::{Error, exit_with_error};
|
||||||
use ratatui::backend::CrosstermBackend;
|
use ratatui::backend::CrosstermBackend;
|
||||||
|
@ -34,13 +34,13 @@ fn run_main(cmd: CommandLine) -> Result<(), Error> {
|
||||||
let memory_map = load_memory_map(cmd.use_wsl, cmd.input)?; dump_memory_map(cmd.output, &memory_map)?;
|
let memory_map = load_memory_map(cmd.use_wsl, cmd.input)?; dump_memory_map(cmd.output, &memory_map)?;
|
||||||
let rx = start_event_loop();
|
let rx = start_event_loop();
|
||||||
let terminal = setup_console()?;
|
let terminal = setup_console()?;
|
||||||
let mut ui_data = ConsoleUIData::new(&memory_map)?;
|
|
||||||
let mut console_ui = ConsoleUI::new(rx, terminal);
|
let mut console_ui = ConsoleUI::new(rx, terminal);
|
||||||
|
|
||||||
|
console_ui.update_data(&memory_map)?;
|
||||||
loop {
|
loop {
|
||||||
match console_ui.update(&ui_data)? {
|
match console_ui.update()? {
|
||||||
UIState::Alive => (),
|
UIState::Alive => (),
|
||||||
UIState::Render => {console_ui.render(&mut ui_data)?;}
|
UIState::Render => {console_ui.render()?;}
|
||||||
UIState::Terminated => break
|
UIState::Terminated => break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue