jag

showKey_rust

public

Shows what key you pressed last

Star0
Watch0
78de904080fc8be965c2ec996911b5d8b10b8831
1
ssh://git@git.jaglekon.de:30/jag/showKey_rust.git
src/main.rsRust179 lines4.0 KB
1
use std::{
2
    io,
3
    time::{
4
        Duration,
5
        Instant,
6
    },
7
};
8
9
use crossterm::event::{
10
    self, 
11
    poll,
12
    KeyCode,
13
    KeyModifiers,
14
    KeyEvent,
15
    KeyEventKind,
16
    Event,
17
};
18
19
use ratatui::{
20
    buffer::Buffer,
21
    layout::{Rect, Constraint},
22
    text::{Line, Span},
23
    style::Stylize,
24
    symbols::border,
25
    DefaultTerminal,
26
    widgets::{Widget, Block},
27
    Frame,
28
};
29
30
#[derive(Debug, PartialEq, Eq)]
31
enum State {
32
    Run,
33
    Consider,
34
    Quit,
35
}
36
37
#[derive(Debug)]
38
pub struct ShowKey {
39
    state: State,
40
    current_key: Option<KeyEvent>,
41
    key_time: Option<Instant>,
42
}
43
44
impl Default for ShowKey {
45
    fn default() -> Self {
46
        Self {
47
            state: State::Run,
48
            current_key: None,
49
            key_time: None,
50
        }
51
    }
52
}
53
54
impl Widget for &ShowKey {
55
    fn render(self, area: Rect, buf: &mut Buffer) {
56
57
        let title = Line::from(" Show Key ".bold());
58
59
        let block = Block::bordered()
60
            .title(title.centered())
61
            .border_set(border::ROUNDED);
62
63
        let block_area = area.centered(
64
            Constraint::Length(25),
65
            Constraint::Length(7),
66
        );
67
68
        let pressed = Line::from(self
69
            .current_key.map(|key| vec![
70
                Span::from(match key.modifiers {
71
                    KeyModifiers::NONE => "".into(),
72
                    other => format!("{other} + "),
73
                }),
74
                Span::from(match key.code {
75
                    KeyCode::Char(c) => if c == ' ' {
76
                        "\" \"".into()
77
                    }  else {
78
                        c.to_lowercase().to_string()
79
                    },
80
                    KeyCode::F(f) => format!("F{f}"),
81
                    other => format!("{other}"),
82
                }),
83
            ]
84
85
86
            )
87
            .unwrap_or(vec![Span::from("Fuck you")])
88
        );
89
90
        let pressed_area = block
91
            .inner(block_area)
92
            .centered(
93
                Constraint::Length(pressed.width() as u16),
94
                Constraint::Length(1),
95
            );
96
97
        block.render(block_area, buf);
98
        pressed.render(pressed_area, buf);
99
    }
100
}
101
102
impl ShowKey {
103
    fn run(&mut self, terminal: &mut DefaultTerminal) -> io::Result<()> {
104
            
105
        terminal.draw(|frame| self.draw(frame))?;
106
107
        while self.state != State::Quit {
108
            
109
            if poll(Duration::from_millis(100))? {
110
                self.handle_events()?;
111
            }
112
113
            match self.key_time {
114
                Some(time)  if time.elapsed() >= Duration::from_secs(1) => {
115
                    self.unset();
116
                    self.detime();
117
                },
118
                _ => {},
119
            }
120
            
121
            terminal.draw(|frame| self.draw(frame))?;
122
        }
123
        Ok(())
124
    }
125
126
    fn draw(&self, frame: &mut Frame) {
127
        frame.render_widget(self, frame.area());
128
    }
129
130
    fn handle_events(&mut self) -> io::Result<()> {
131
        match event::read()? {
132
            Event::Key(key_event) if key_event.kind == KeyEventKind::Press => {
133
                    self.key_time = Some(Instant::now());
134
                    self.handle_key_event(key_event);
135
                },
136
            _ => {},
137
        }
138
        Ok(())
139
    }
140
141
    fn handle_key_event(&mut self, key_event: KeyEvent) {
142
        
143
        self.current_key = Some(key_event);
144
145
        match key_event.code {
146
            KeyCode::Esc => self.deeper(),
147
            _ => self.higher(),
148
        }
149
    }
150
151
    fn unset(&mut self) {
152
        self.current_key = None;
153
    }
154
155
    fn detime(&mut self) {
156
        self.key_time = None;
157
    }
158
159
    fn deeper(&mut self) {
160
        match self.state {
161
            State::Run => self.state = State::Consider,
162
            State::Consider => self.state = State::Quit,
163
            State::Quit => {}
164
        }
165
    }
166
167
    fn higher(&mut self) {
168
        match self.state {
169
            State::Run => {}
170
            State::Consider => self.state = State::Run,
171
            State::Quit => self.state = State::Consider,
172
        }
173
    }
174
}
175
176
177
fn main() -> io::Result<()> {
178
    ratatui::run(|term| ShowKey::default().run(term))
179
}