Skip to main content

steel_protocol/packets/common/
s_client_information.rs

1use steel_macros::{ReadFrom, ServerPacket};
2pub use steel_registry::entity_data::HumanoidArm;
3
4#[derive(ReadFrom, Clone, Debug)]
5pub enum ChatVisibility {
6    Full = 0,
7    System = 1,
8    Hidden = 2,
9}
10
11#[derive(ReadFrom, Clone, Debug)]
12pub enum ParticleStatus {
13    All = 0,
14    Depraced = 1,
15    Minimal = 2,
16}
17
18#[derive(ReadFrom, ServerPacket, Clone, Debug)]
19pub struct SClientInformation {
20    #[read(as = Prefixed(VarInt), bound = 16)]
21    pub language: String,
22    pub view_distance: i8,
23    pub chat_visibility: ChatVisibility,
24    pub chat_colors: bool,
25    pub model_customization: u8,
26    pub main_hand: HumanoidArm,
27    pub text_filtering_enabled: bool,
28    pub allows_listing: bool,
29    pub particle_status: ParticleStatus,
30}
31
32#[cfg(test)]
33mod tests {
34    use std::io::Cursor;
35
36    use steel_utils::serial::ReadFrom as _;
37
38    use super::{ChatVisibility, HumanoidArm, ParticleStatus, SClientInformation};
39
40    #[test]
41    fn reads_vanilla_byte_fields_without_consuming_following_settings() {
42        const SIGNED_VIEW_DISTANCE: i8 = -2;
43        const MODEL_CUSTOMIZATION_WITH_HIGH_BIT_SET: u8 = 0xff;
44
45        let bytes = [
46            5,
47            b'e',
48            b'n',
49            b'_',
50            b'u',
51            b's',
52            SIGNED_VIEW_DISTANCE.cast_unsigned(),
53            0,
54            1,
55            MODEL_CUSTOMIZATION_WITH_HIGH_BIT_SET,
56            1,
57            0,
58            1,
59            2,
60        ];
61        let mut cursor = Cursor::new(bytes.as_slice());
62
63        let packet = SClientInformation::read(&mut cursor)
64            .unwrap_or_else(|error| panic!("client information should decode: {error}"));
65
66        assert_eq!(packet.language, "en_us");
67        assert_eq!(packet.view_distance, SIGNED_VIEW_DISTANCE);
68        assert!(matches!(packet.chat_visibility, ChatVisibility::Full));
69        assert!(packet.chat_colors);
70        assert_eq!(
71            packet.model_customization,
72            MODEL_CUSTOMIZATION_WITH_HIGH_BIT_SET
73        );
74        assert_eq!(packet.main_hand, HumanoidArm::Right);
75        assert!(!packet.text_filtering_enabled);
76        assert!(packet.allows_listing);
77        assert!(matches!(packet.particle_status, ParticleStatus::Minimal));
78        assert_eq!(cursor.position() as usize, bytes.len());
79    }
80}