vt100/parser.rs
1/// A parser for terminal output which produces an in-memory representation of
2/// the terminal contents.
3pub struct Parser {
4 parser: vte::Parser,
5 screen: crate::screen::Screen,
6}
7
8impl Parser {
9 /// Creates a new terminal parser of the given size and with the given
10 /// amount of scrollback.
11 #[must_use]
12 pub fn new(rows: u16, cols: u16, scrollback_len: usize) -> Self {
13 Self {
14 parser: vte::Parser::new(),
15 screen: crate::screen::Screen::new(
16 crate::grid::Size { rows, cols },
17 scrollback_len,
18 ),
19 }
20 }
21
22 /// Processes the contents of the given byte string, and updates the
23 /// in-memory terminal state.
24 pub fn process(&mut self, bytes: &[u8]) {
25 for byte in bytes {
26 self.parser.advance(&mut self.screen, *byte);
27 }
28 }
29
30 /// Resizes the terminal.
31 pub fn set_size(&mut self, rows: u16, cols: u16) {
32 self.screen.set_size(rows, cols);
33 }
34
35 /// Scrolls to the given position in the scrollback.
36 ///
37 /// This position indicates the offset from the top of the screen, and
38 /// should be `0` to put the normal screen in view.
39 ///
40 /// This affects the return values of methods called on `parser.screen()`:
41 /// for instance, `parser.screen().cell(0, 0)` will return the top left
42 /// corner of the screen after taking the scrollback offset into account.
43 /// It does not affect `parser.process()` at all.
44 ///
45 /// The value given will be clamped to the actual size of the scrollback.
46 pub fn set_scrollback(&mut self, rows: usize) {
47 self.screen.set_scrollback(rows);
48 }
49
50 /// Returns a reference to a `Screen` object containing the terminal
51 /// state.
52 #[must_use]
53 pub fn screen(&self) -> &crate::screen::Screen {
54 &self.screen
55 }
56}
57
58impl Default for Parser {
59 /// Returns a parser with dimensions 80x24 and no scrollback.
60 fn default() -> Self {
61 Self::new(24, 80, 0)
62 }
63}
64
65impl std::io::Write for Parser {
66 fn write(&mut self, buf: &[u8]) -> std::io::Result<usize> {
67 self.process(buf);
68 Ok(buf.len())
69 }
70
71 fn flush(&mut self) -> std::io::Result<()> {
72 Ok(())
73 }
74}