Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,9 @@ repository = "https://github.com/shuoli84/tui-menu"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html

[dependencies]
ratatui = "0.29.0"
ratatui-core = "0.1.0"
ratatui-widgets = "0.3.0"

[dev-dependencies]
color-eyre = "0.6.3"
ratatui = { version = "0.30.0", features = ["crossterm"] }
48 changes: 5 additions & 43 deletions examples/basic.rs
Original file line number Diff line number Diff line change
@@ -1,55 +1,17 @@
use color_eyre::config::HookBuilder;
use ratatui::{
crossterm::{
event::{self, Event, KeyCode},
execute,
terminal::{disable_raw_mode, enable_raw_mode, EnterAlternateScreen, LeaveAlternateScreen},
},
prelude::{
Backend, Buffer, Constraint, CrosstermBackend, Layout, Rect, StatefulWidget, Stylize,
Terminal, Widget,
},
crossterm::event::{self, Event, KeyCode},
prelude::{Buffer, Constraint, Layout, Rect, StatefulWidget, Stylize, Widget},
widgets::{Block, Paragraph},
};
use std::io::{self, stdout, Stdout};
use tui_menu::{Menu, MenuEvent, MenuItem, MenuState};

fn main() -> color_eyre::Result<()> {
Comment thread
shuoli84 marked this conversation as resolved.
let mut terminal = init_terminal()?;
App::new().run(&mut terminal)?;
restore_terminal()?;
Ok(())
}

/// Install panic and error hooks that restore the terminal before printing the error.
pub fn init_hooks() -> color_eyre::Result<()> {
let (panic, error) = HookBuilder::default().into_hooks();
let panic = panic.into_panic_hook();
let error = error.into_eyre_hook();

std::panic::set_hook(Box::new(move |info| {
let _ = restore_terminal(); // ignore failure to restore terminal
panic(info);
}));
color_eyre::eyre::set_hook(Box::new(move |e| {
let _ = restore_terminal(); // ignore failure to restore terminal
error(e)
}))?;
color_eyre::install()?;

ratatui::run(|t| App::new().run(t))?;
Ok(())
}

fn init_terminal() -> io::Result<Terminal<CrosstermBackend<Stdout>>> {
enable_raw_mode()?;
execute!(stdout(), EnterAlternateScreen)?;
Terminal::new(CrosstermBackend::new(stdout()))
}

fn restore_terminal() -> io::Result<()> {
disable_raw_mode()?;
execute!(stdout(), LeaveAlternateScreen,)
}

struct App {
content: String,
menu: MenuState<Action>,
Expand Down Expand Up @@ -111,7 +73,7 @@ enum Action {
}

impl App {
fn run<B: Backend>(mut self, terminal: &mut Terminal<B>) -> io::Result<()> {
fn run(mut self, terminal: &mut ratatui::DefaultTerminal) -> std::io::Result<()> {
loop {
terminal.draw(|frame| frame.render_widget(&mut self, frame.area()))?;

Expand Down
44 changes: 4 additions & 40 deletions examples/nested_group.rs
Original file line number Diff line number Diff line change
@@ -1,52 +1,17 @@
use color_eyre::config::HookBuilder;
use ratatui::{
crossterm::{
event::{self, Event, KeyCode},
execute,
terminal::{disable_raw_mode, enable_raw_mode, EnterAlternateScreen, LeaveAlternateScreen},
},
crossterm::event::{self, Event, KeyCode},
prelude::*,
widgets::{Block, Paragraph},
};
use std::io::{self, stdout, Stdout};
use tui_menu::{Menu, MenuEvent, MenuItem, MenuState};

fn main() -> color_eyre::Result<()> {
let mut terminal = init_terminal()?;
App::new().run(&mut terminal)?;
restore_terminal()?;
Ok(())
}

/// Install panic and error hooks that restore the terminal before printing the error.
pub fn init_hooks() -> color_eyre::Result<()> {
let (panic, error) = HookBuilder::default().into_hooks();
let panic = panic.into_panic_hook();
let error = error.into_eyre_hook();

std::panic::set_hook(Box::new(move |info| {
let _ = restore_terminal(); // ignore failure to restore terminal
panic(info);
}));
color_eyre::eyre::set_hook(Box::new(move |e| {
let _ = restore_terminal(); // ignore failure to restore terminal
error(e)
}))?;
color_eyre::install()?;

ratatui::run(|t| App::new().run(t))?;
Ok(())
}

fn init_terminal() -> io::Result<Terminal<CrosstermBackend<Stdout>>> {
enable_raw_mode()?;
execute!(stdout(), EnterAlternateScreen)?;
Terminal::new(CrosstermBackend::new(stdout()))
}

fn restore_terminal() -> io::Result<()> {
disable_raw_mode()?;
execute!(stdout(), LeaveAlternateScreen,)
}

struct App {
content: String,
menu: MenuState<Action>,
Expand Down Expand Up @@ -100,7 +65,7 @@ enum Action {
}

impl App {
fn run<B: Backend>(mut self, terminal: &mut Terminal<B>) -> io::Result<()> {
fn run(mut self, terminal: &mut ratatui::DefaultTerminal) -> std::io::Result<()> {
loop {
terminal.draw(|frame| frame.render_widget(&mut self, frame.area()))?;

Expand All @@ -118,7 +83,6 @@ impl App {
}
},
}
self.menu.reset();
}
}
}
Expand Down
19 changes: 10 additions & 9 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,13 +17,14 @@ will be stored in MenuState.events.
To define a menu, see examples in [MenuState].
*/

use ratatui::{
layout::Rect,
prelude::*,
use ratatui_core::{
buffer::Buffer,
layout::{Margin, Rect},
style::{Color, Style},
text::{Line, Span},
widgets::{Block, Borders, Clear, StatefulWidget, Widget},
widgets::{StatefulWidget, Widget},
};
use ratatui_widgets::{block::Block, borders::Borders, clear::Clear};
use std::{borrow::Cow, marker::PhantomData};

/// Events this widget produce
Expand Down Expand Up @@ -116,7 +117,7 @@ impl<T: Clone> MenuState<T> {
///
/// case 3:
///
/// group 1 group 2
/// group 1 group 2
/// sub item 1
/// > sub item 2 > sub sub item 1
/// sub sub item 2
Expand Down Expand Up @@ -163,7 +164,7 @@ impl<T: Clone> MenuState<T> {
/// down does nothing
///
/// case 3:
/// group 1 group 2
/// group 1 group 2
/// > sub item 1
/// sub item 2
///
Expand Down Expand Up @@ -193,7 +194,7 @@ impl<T: Clone> MenuState<T> {
/// left first pop "sub item group", then highlights "group 1"
///
/// case 3:
/// group 1 group 2
/// group 1 group 2
/// > sub item 1 sub sub item 1
/// sub item 2 > sub sub item 2
///
Expand Down Expand Up @@ -593,7 +594,7 @@ impl<T> Menu<T> {
x: u16,
y: u16,
group: &[MenuItem<T>],
buf: &mut ratatui::buffer::Buffer,
buf: &mut Buffer,
dropdown_count_to_go: u16, // including current, it is not drawn yet
) {
// Compute width of all menu items
Expand Down Expand Up @@ -695,7 +696,7 @@ impl<T> Default for Menu<T> {
impl<T: Clone> StatefulWidget for Menu<T> {
type State = MenuState<T>;

fn render(self, area: Rect, buf: &mut ratatui::buffer::Buffer, state: &mut Self::State) {
fn render(self, area: Rect, buf: &mut Buffer, state: &mut Self::State) {
let area = area.clamp(*buf.area());

let mut spans = vec![];
Expand Down