ble_data_struct/descriptors/
characteristic_presentation_format.rs

1//! Characteristic Presentation Format (Attribute Type: 0x2904) module.
2
3use crate::Uuid16bit;
4
5/// Characteristic Presentation Format.
6#[derive(Debug, PartialEq, Clone)]
7pub struct CharacteristicPresentationFormat {
8    /// Format
9    pub format: u8,
10    /// Exponent
11    pub exponent: i8,
12    /// Unit
13    pub unit: u16,
14    /// Name Space
15    pub name_space: u8,
16    /// Description
17    pub description: u16,
18}
19
20impl CharacteristicPresentationFormat {
21    /// Create [`CharacteristicPresentationFormat`] from `Format`, `Exponent`, `Unit`, `Exponent`, `Name Space`, `Description`.
22    ///
23    /// # Examples
24    ///
25    /// ```
26    /// use ble_data_struct::descriptors::characteristic_presentation_format::{
27    ///     CharacteristicPresentationFormat,
28    /// };
29    ///
30    /// let format = 0x01u8;
31    /// let exponent = 0x02i8;
32    /// let unit = 0x0403u16;
33    /// let name_space = 0x05u8;
34    /// let description = 0x0706u16;
35    ///
36    /// let result =
37    ///     CharacteristicPresentationFormat::new(format, exponent, unit, name_space, description);
38    /// assert_eq!(format, result.format);
39    /// assert_eq!(exponent, result.exponent);
40    /// assert_eq!(unit, result.unit);
41    /// assert_eq!(name_space, result.name_space);
42    /// assert_eq!(description, result.description);
43    /// ```
44    pub fn new(format: u8, exponent: i8, unit: u16, name_space: u8, description: u16) -> Self {
45        Self {
46            format,
47            exponent,
48            unit,
49            name_space,
50            description,
51        }
52    }
53}
54
55impl TryFrom<&Vec<u8>> for CharacteristicPresentationFormat {
56    type Error = String;
57    /// Create [`CharacteristicPresentationFormat`] from [`Vec<u8>`].
58    ///
59    /// # Examples
60    ///
61    /// ```
62    /// use ble_data_struct::descriptors::characteristic_presentation_format::{
63    ///     CharacteristicPresentationFormat,
64    /// };
65    ///
66    /// let format = 0x01u8;
67    /// let exponent = 0x02i8;
68    /// let unit = 0x0403u16;
69    /// let name_space = 0x05u8;
70    /// let description = 0x0706u16;
71    ///
72    /// let mut data: Vec<u8> = Vec::new();
73    /// data.push(format);
74    /// data.push(exponent as u8);
75    /// data.append(&mut unit.to_le_bytes().to_vec());
76    /// data.push(name_space);
77    /// data.append(&mut description.to_le_bytes().to_vec());
78    /// let result = CharacteristicPresentationFormat::try_from(&data);
79    /// assert!(result.is_ok());
80    /// let descriptor = result.unwrap();
81    /// assert_eq!(format, descriptor.format);
82    /// assert_eq!(exponent, descriptor.exponent);
83    /// assert_eq!(unit, descriptor.unit);
84    /// assert_eq!(name_space, descriptor.name_space);
85    /// assert_eq!(description, descriptor.description);
86    ///
87    /// let data = Vec::new();
88    /// let result = CharacteristicPresentationFormat::try_from(&data);
89    /// assert!(!result.is_ok());
90    /// ```
91    fn try_from(value: &Vec<u8>) -> Result<Self, String> {
92        let len = value.len();
93        if len != 7 {
94            return Err(format!("Invalid data size :{}", len).to_string());
95        }
96        Ok(Self {
97            format: value[0],
98            exponent: value[1] as i8,
99            unit: u16::from_le_bytes(value[2..4].try_into().unwrap()),
100            name_space: value[4],
101            description: u16::from_le_bytes(value[5..7].try_into().unwrap()),
102        })
103    }
104}
105
106impl Into<Vec<u8>> for CharacteristicPresentationFormat {
107    /// Create [`Vec<u8>`] from [`CharacteristicPresentationFormat`].
108    ///
109    /// # Examples
110    ///
111    /// ```
112    /// use ble_data_struct::descriptors::characteristic_presentation_format::{
113    ///     CharacteristicPresentationFormat,
114    /// };
115    ///
116    /// let format = 0x01u8;
117    /// let exponent = 0x02i8;
118    /// let unit = 0x0403u16;
119    /// let name_space = 0x05u8;
120    /// let description = 0x0706u16;
121    ///
122    /// let result =
123    ///     CharacteristicPresentationFormat::new(format, exponent, unit, name_space, description);
124    /// let mut data: Vec<u8> = Vec::new();
125    /// data.push(format);
126    /// data.push(exponent as u8);
127    /// data.append(&mut unit.to_le_bytes().to_vec());
128    /// data.push(name_space);
129    /// data.append(&mut description.to_le_bytes().to_vec());
130    /// let into_data: Vec<u8> = result.into();
131    /// assert_eq!(data, into_data);
132    /// ```
133    fn into(self) -> Vec<u8> {
134        let mut data: Vec<u8> = Vec::new();
135        data.push(self.format);
136        data.push(self.exponent as u8);
137        data.append(&mut self.unit.to_le_bytes().to_vec());
138        data.push(self.name_space);
139        data.append(&mut self.description.to_le_bytes().to_vec());
140        return data;
141    }
142}
143
144impl Uuid16bit for CharacteristicPresentationFormat {
145    /// return `0x2904`.
146    ///
147    /// # Examples
148    ///
149    /// ```
150    /// use ble_data_struct::Uuid16bit;
151    /// use ble_data_struct::descriptors::characteristic_presentation_format::CharacteristicPresentationFormat;
152    ///
153    /// assert_eq!(0x2904, CharacteristicPresentationFormat::uuid_16bit());
154    /// ```
155    fn uuid_16bit() -> u16 {
156        0x2904
157    }
158}
159
160#[cfg(test)]
161mod tests {
162    use crate::{
163        descriptors::characteristic_presentation_format::CharacteristicPresentationFormat,
164        Uuid16bit,
165    };
166
167    #[test]
168    fn test_new() {
169        let format = 0x01u8;
170        let exponent = 0x02i8;
171        let unit = 0x0403u16;
172        let name_space = 0x05u8;
173        let description = 0x0706u16;
174
175        let result =
176            CharacteristicPresentationFormat::new(format, exponent, unit, name_space, description);
177        assert_eq!(format, result.format);
178        assert_eq!(exponent, result.exponent);
179        assert_eq!(unit, result.unit);
180        assert_eq!(name_space, result.name_space);
181        assert_eq!(description, result.description);
182    }
183
184    #[test]
185    fn test_try_from() {
186        let format = 0x01u8;
187        let exponent = 0x02i8;
188        let unit = 0x0403u16;
189        let name_space = 0x05u8;
190        let description = 0x0706u16;
191
192        let mut data: Vec<u8> = Vec::new();
193        data.push(format);
194        data.push(exponent as u8);
195        data.append(&mut unit.to_le_bytes().to_vec());
196        data.push(name_space);
197        data.append(&mut description.to_le_bytes().to_vec());
198        let result = CharacteristicPresentationFormat::try_from(&data);
199        assert!(result.is_ok());
200        let descriptor = result.unwrap();
201        assert_eq!(format, descriptor.format);
202        assert_eq!(exponent, descriptor.exponent);
203        assert_eq!(unit, descriptor.unit);
204        assert_eq!(name_space, descriptor.name_space);
205        assert_eq!(description, descriptor.description);
206
207        let data = Vec::new();
208        let result = CharacteristicPresentationFormat::try_from(&data);
209        assert!(!result.is_ok());
210    }
211
212    #[test]
213    fn test_into() {
214        let format = 0x01u8;
215        let exponent = 0x02i8;
216        let unit = 0x0403u16;
217        let name_space = 0x05u8;
218        let description = 0x0706u16;
219
220        let result =
221            CharacteristicPresentationFormat::new(format, exponent, unit, name_space, description);
222        let mut data: Vec<u8> = Vec::new();
223        data.push(format);
224        data.push(exponent as u8);
225        data.append(&mut unit.to_le_bytes().to_vec());
226        data.push(name_space);
227        data.append(&mut description.to_le_bytes().to_vec());
228        let into_data: Vec<u8> = result.into();
229        assert_eq!(data, into_data);
230    }
231
232    #[test]
233    fn test_uuid_16bit() {
234        assert_eq!(0x2904, CharacteristicPresentationFormat::uuid_16bit());
235    }
236}