ssh_utils_lib/widgets/
popup_input_box.rs1use crossterm::event::{self, Event, KeyCode, KeyEventKind};
2use ratatui::backend::Backend;
3use ratatui::style::Style;
4use ratatui::text::Line;
5use ratatui::widgets::{Block, Borders, Paragraph};
6use ratatui::Terminal;
7use anyhow::Result;
8
9use crate::helper;
10
11pub struct PopupInputBox {
12 title: String,
13 input: String,
14}
15
16impl PopupInputBox {
17 pub fn new(title: String) -> Self {
18 Self {
19 title,
20 input: String::new(),
21 }
22 }
23
24 fn render(&self) -> Paragraph {
25 let mask_text = "*".repeat(self.input.len());
26 let input_text = format!("{}", mask_text);
27 let content = vec![Line::from(input_text)];
28
29 Paragraph::new(content)
30 .block(
31 Block::default()
32 .title(self.title.clone())
33 .borders(Borders::ALL),
34 )
35 .style(Style::default())
36 }
37
38 fn input(&mut self, c: char) {
39 self.input.push(c);
40 }
41
42 fn backspace(&mut self) {
43 self.input.pop();
44 }
45
46 fn draw(&self, terminal: &mut Terminal<impl Backend>) -> Result<()> {
47 terminal.draw(|f| {
48 let area = helper::centered_rect(50, 60, f.area());
49 f.render_widget(self.render(), area)
50 })?;
51 Ok(())
52 }
53
54 pub fn run(&mut self, mut terminal: &mut Terminal<impl Backend>) -> Result<Option<String>> {
55 loop {
56 self.draw(&mut terminal)?;
57 if let Event::Key(key) = event::read()? {
58 if key.kind == KeyEventKind::Press {
59 match key.code {
60 KeyCode::Char(to_insert) => {
61 self.input(to_insert);
62 }
63 KeyCode::Backspace => {
64 self.backspace();
65 }
66 KeyCode::Enter => {
67 return Ok(Some(self.input.clone()));
68 }
69 KeyCode::Esc => {
70 return Ok(None);
71 }
72 _ => {}
73 }
74 }
75 }
76 }
77 }
78}