Initial IronStorage project structure
This commit is contained in:
16
apps/tui/Cargo.toml
Normal file
16
apps/tui/Cargo.toml
Normal file
@@ -0,0 +1,16 @@
|
||||
[package]
|
||||
name = "ironstorage-tui"
|
||||
description = "Ratatui frontend for IronStorage"
|
||||
version.workspace = true
|
||||
edition.workspace = true
|
||||
rust-version.workspace = true
|
||||
publish = false
|
||||
|
||||
[[bin]]
|
||||
name = "ironstorage-tui"
|
||||
path = "src/main.rs"
|
||||
|
||||
[dependencies]
|
||||
crossterm.workspace = true
|
||||
ironstorage.workspace = true
|
||||
ratatui.workspace = true
|
||||
49
apps/tui/src/main.rs
Normal file
49
apps/tui/src/main.rs
Normal file
@@ -0,0 +1,49 @@
|
||||
#![forbid(unsafe_code)]
|
||||
#![deny(clippy::disallowed_types)]
|
||||
|
||||
use std::io;
|
||||
|
||||
use crossterm::event::{self, Event, KeyCode};
|
||||
use ratatui::{
|
||||
DefaultTerminal, Frame,
|
||||
widgets::{Block, Paragraph},
|
||||
};
|
||||
|
||||
fn main() -> io::Result<()> {
|
||||
ratatui::run(run)
|
||||
}
|
||||
|
||||
fn run(terminal: &mut DefaultTerminal) -> io::Result<()> {
|
||||
loop {
|
||||
terminal.draw(draw)?;
|
||||
if let Event::Key(key) = event::read()?
|
||||
&& is_quit(key.code)
|
||||
{
|
||||
return Ok(());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn draw(frame: &mut Frame) {
|
||||
frame.render_widget(
|
||||
Paragraph::new("No password store is open. Press q to quit.")
|
||||
.block(Block::bordered().title(ironstorage::PRODUCT_NAME)),
|
||||
frame.area(),
|
||||
);
|
||||
}
|
||||
|
||||
fn is_quit(key: KeyCode) -> bool {
|
||||
matches!(key, KeyCode::Char('q') | KeyCode::Esc)
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use crossterm::event::KeyCode;
|
||||
|
||||
#[test]
|
||||
fn q_and_escape_quit() {
|
||||
assert!(super::is_quit(KeyCode::Char('q')));
|
||||
assert!(super::is_quit(KeyCode::Esc));
|
||||
assert!(!super::is_quit(KeyCode::Enter));
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user