muster/adapter/tui/
terminal.rs1use std::io::{self, Stdout};
2
3use crossterm::{
4 execute,
5 terminal::{EnterAlternateScreen, LeaveAlternateScreen, disable_raw_mode, enable_raw_mode},
6};
7use getset::MutGetters;
8use ratatui::{Terminal, backend::CrosstermBackend};
9
10use crate::error::Result;
11
12pub type Tui = Terminal<CrosstermBackend<Stdout>>;
14
15#[derive(MutGetters)]
18pub struct TerminalGuard {
19 #[getset(get_mut = "pub")]
20 terminal: Tui,
21}
22
23impl TerminalGuard {
24 pub fn new() -> Result<Self> {
30 enable_raw_mode()?;
31 let mut stdout = io::stdout();
32 if let Err(error) = execute!(stdout, EnterAlternateScreen) {
33 let _ = disable_raw_mode();
34 return Err(error.into());
35 }
36 match Terminal::new(CrosstermBackend::new(stdout)) {
37 Ok(terminal) => Ok(Self { terminal }),
38 Err(error) => {
39 let _ = Self::restore();
40 Err(error.into())
41 },
42 }
43 }
44
45 pub fn restore() -> io::Result<()> {
52 let raw = disable_raw_mode();
53 let screen = execute!(io::stdout(), LeaveAlternateScreen);
54 raw.and(screen)
55 }
56}
57
58impl Drop for TerminalGuard {
59 fn drop(&mut self) {
60 let _ = Self::restore();
61 }
62}