1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
//! Encoder and decoder for the **Fuzzball** terminal protocol.
//!
//! Fuzzball is a small family of terminal extensions, first implemented in the
//! [Mouser](https://github.com/WeirdBrains/mouser) terminal. Every message is a DCS
//! string with the private marker `=` and the family tag `Fz`:
//!
//! ```text
//! ESC P = F z <subsystem> <verb> ; <params> [: <payload>] ESC \
//! ```
//!
//! This crate has no dependencies and does no I/O. It turns typed values into the exact
//! bytes Mouser emits and parses those bytes back, including partial input:
//!
//! - [`message`]: framing, [`Params`], [`parse`] for one message and a streaming
//! [`Decoder`] that splits terminal input into Fuzzball messages and other bytes.
//! - [`common`]: capability query and reply, error codes, generic replies.
//! - [`keyboard`]: key events, enable / disable / query commands.
//! - [`graphics`]: upload (with chunking), place, delete, query.
//! - [`shell`]: shell-integration silent actions (advertise, change directory, reply).
//! - [`plugins`]: plugin hello, query, bye and replies.
//! - [`passthrough`]: tmux and GNU screen wrapping.
//!
//! The wire format is specified in the `docs/` directory of the repository.
//!
//! # Parsing key events
//!
//! ```
//! use fuzzball::keyboard::{Key, KeyEvent, KeyKind};
//! use fuzzball::{Decoder, Item};
//!
//! let mut d = Decoder::new();
//! d.push(b"x\x1bP=Fzke;t=p,code=KeyA,key=U+0061,te");
//! assert_eq!(d.next(), Some(Item::Text(b"x".to_vec())));
//! assert_eq!(d.next(), None); // the rest of the message has not arrived yet
//! d.push(b"xt=61\x1b\\");
//! let Some(Item::Message(m)) = d.next() else { panic!() };
//! let ev = KeyEvent::from_message(&m).unwrap();
//! assert_eq!(ev.kind, KeyKind::Press);
//! assert_eq!(ev.key, Some(Key::Char('a')));
//! assert_eq!(ev.text.as_deref(), Some("a"));
//! ```
//!
//! # Stability
//!
//! From 1.0.0 on, the wire format and this API follow semantic versioning: public enums
//! and structs that may grow are `#[non_exhaustive]`.
pub use ;
pub use ;
/// Bytes every Fuzzball message starts with: `ESC P = F z`.
pub const PREFIX: & = b"\x1bP=Fz";
/// String terminator: `ESC \`.
pub const ST: & = b"\x1b\\";
/// Wire protocol version (`v=`) this crate speaks.
pub const VERSION: u32 = 0;
/// Largest payload per message Mouser accepts, in wire bytes (`max_chunk`).
pub const MAX_CHUNK: usize = 65536;
/// Default largest message [`parse`] and [`Decoder`] buffer before giving up.
pub const DEFAULT_MAX_MESSAGE: usize = MAX_CHUNK + 1024;