ble_data_struct/windows/descriptors/windows_client_characteristic_configuration.rs
1//! Client Characteristic Configuration (Attribute Type: 0x2902) module for windows.
2
3#[cfg(target_os = "windows")]
4use windows::{
5 Devices::Bluetooth::GenericAttributeProfile::GattClientCharacteristicConfigurationDescriptorValue,
6 Storage::Streams::IBuffer,
7};
8
9#[cfg(target_os = "windows")]
10use crate::{
11 descriptors::client_characteristic_configuration::ClientCharacteristicConfiguration,
12 windows::buffer::{i_buffer_to_vec, vec_to_i_buffer},
13};
14
15#[cfg(target_os = "windows")]
16impl TryFrom<&GattClientCharacteristicConfigurationDescriptorValue>
17 for ClientCharacteristicConfiguration
18{
19 type Error = String;
20 /// Create [`ClientCharacteristicConfiguration`] from [`GattClientCharacteristicConfigurationDescriptorValue`].
21 ///
22 /// # Examples
23 ///
24 /// ```
25 /// use windows::{
26 /// Devices::Bluetooth::GenericAttributeProfile::GattClientCharacteristicConfigurationDescriptorValue,
27 /// Storage::Streams::DataWriter,
28 /// };
29 ///
30 /// use ble_data_struct::descriptors::client_characteristic_configuration::{
31 /// ClientCharacteristicConfiguration, INDICATION, NOTIFICATION,
32 /// };
33 ///
34 /// let result = ClientCharacteristicConfiguration::try_from(
35 /// &GattClientCharacteristicConfigurationDescriptorValue::None,
36 /// );
37 /// assert!(result.is_ok());
38 /// let value = result.unwrap();
39 /// assert!(!value.is_notification());
40 /// assert!(!value.is_indication());
41 ///
42 /// let result = ClientCharacteristicConfiguration::try_from(
43 /// &GattClientCharacteristicConfigurationDescriptorValue::Notify,
44 /// );
45 /// assert!(result.is_ok());
46 /// let value = result.unwrap();
47 /// assert!(value.is_notification());
48 /// assert!(!value.is_indication());
49 ///
50 /// let result = ClientCharacteristicConfiguration::try_from(
51 /// &GattClientCharacteristicConfigurationDescriptorValue::Indicate,
52 /// );
53 /// assert!(result.is_ok());
54 /// let value = result.unwrap();
55 /// assert!(!value.is_notification());
56 /// assert!(value.is_indication());
57 /// ```
58 fn try_from(
59 value: &GattClientCharacteristicConfigurationDescriptorValue,
60 ) -> Result<Self, String> {
61 Ok(Self {
62 configuration: u16::from_le_bytes(value.0.to_le_bytes()[0..2].try_into().unwrap()),
63 })
64 }
65}
66
67#[cfg(target_os = "windows")]
68impl TryFrom<IBuffer> for ClientCharacteristicConfiguration {
69 type Error = String;
70 /// Create [`ClientCharacteristicConfiguration`] from [`IBuffer`].
71 ///
72 /// # Examples
73 ///
74 /// ```
75 /// use windows::Storage::Streams::{DataWriter, IBuffer};
76 ///
77 /// use ble_data_struct::descriptors::client_characteristic_configuration::{
78 /// ClientCharacteristicConfiguration, INDICATION, NOTIFICATION,
79 /// };
80 ///
81 /// let client_characteristic_configuration =
82 /// ClientCharacteristicConfiguration::new(NOTIFICATION);
83 /// let data_writer = DataWriter::new().unwrap();
84 /// let ble_packet: Vec<u8> = client_characteristic_configuration.into();
85 /// data_writer.WriteBytes(&ble_packet).unwrap();
86 /// let buffer = data_writer.DetachBuffer().unwrap();
87
88 /// let result = ClientCharacteristicConfiguration::try_from(buffer);
89 /// assert!(result.is_ok());
90 /// let value = result.unwrap();
91 /// assert!(value.is_notification());
92 /// ```
93 fn try_from(value: IBuffer) -> Result<Self, String> {
94 let vec = i_buffer_to_vec(value).unwrap();
95 let configuration = u16::from_le_bytes(vec.try_into().unwrap());
96 Ok(Self {
97 configuration: configuration,
98 })
99 }
100}
101
102#[cfg(target_os = "windows")]
103impl Into<GattClientCharacteristicConfigurationDescriptorValue>
104 for ClientCharacteristicConfiguration
105{
106 /// Create [`GattClientCharacteristicConfigurationDescriptorValue`] from [`ClientCharacteristicConfiguration`].
107 ///
108 /// # Examples
109 ///
110 /// ```
111 /// use windows::{
112 /// Devices::Bluetooth::GenericAttributeProfile::GattClientCharacteristicConfigurationDescriptorValue,
113 /// Storage::Streams::DataWriter,
114 /// };
115 ///
116 /// use ble_data_struct::descriptors::client_characteristic_configuration::{
117 /// ClientCharacteristicConfiguration, INDICATION, NOTIFICATION,
118 /// };
119 ///
120 /// let value: GattClientCharacteristicConfigurationDescriptorValue =
121 /// ClientCharacteristicConfiguration::new(0).into();
122 /// assert_eq!(
123 /// GattClientCharacteristicConfigurationDescriptorValue::None,
124 /// value
125 /// );
126 ///
127 /// let value: GattClientCharacteristicConfigurationDescriptorValue =
128 /// ClientCharacteristicConfiguration::new(NOTIFICATION).into();
129 /// assert_eq!(
130 /// GattClientCharacteristicConfigurationDescriptorValue::Notify,
131 /// value
132 /// );
133 ///
134 /// let value: GattClientCharacteristicConfigurationDescriptorValue =
135 /// ClientCharacteristicConfiguration::new(INDICATION).into();
136 /// assert_eq!(
137 /// GattClientCharacteristicConfigurationDescriptorValue::Indicate,
138 /// value
139 /// );
140 /// ```
141 fn into(self) -> GattClientCharacteristicConfigurationDescriptorValue {
142 if self.is_notification() {
143 GattClientCharacteristicConfigurationDescriptorValue::Notify
144 } else if self.is_indication() {
145 GattClientCharacteristicConfigurationDescriptorValue::Indicate
146 } else {
147 GattClientCharacteristicConfigurationDescriptorValue::None
148 }
149 }
150}
151
152#[cfg(target_os = "windows")]
153impl Into<IBuffer> for ClientCharacteristicConfiguration {
154 /// Create [`IBuffer`] from [`ClientCharacteristicConfiguration`].
155 ///
156 /// # Examples
157 ///
158 /// ```
159 /// use windows::{
160 /// Devices::Bluetooth::GenericAttributeProfile::GattClientCharacteristicConfigurationDescriptorValue,
161 /// Storage::Streams::{DataWriter, IBuffer},
162 /// };
163 ///
164 /// use ble_data_struct::{
165 /// descriptors::client_characteristic_configuration::{
166 /// ClientCharacteristicConfiguration, INDICATION, NOTIFICATION,
167 /// },
168 /// windows::buffer::i_buffer_to_vec,
169 /// };
170 ///
171 /// let value = ClientCharacteristicConfiguration::new(0);
172 /// let buffer: IBuffer = value.clone().into();
173 /// let vec: Vec<u8> = value.into();
174 /// assert_eq!(vec, i_buffer_to_vec(buffer).unwrap());
175 ///
176 /// let value = ClientCharacteristicConfiguration::new(NOTIFICATION);
177 /// let buffer: IBuffer = value.clone().into();
178 /// let vec: Vec<u8> = value.into();
179 /// assert_eq!(vec, i_buffer_to_vec(buffer).unwrap());
180 ///
181 /// let value = ClientCharacteristicConfiguration::new(INDICATION);
182 /// let buffer: IBuffer = value.clone().into();
183 /// let vec: Vec<u8> = value.into();
184 /// assert_eq!(vec, i_buffer_to_vec(buffer).unwrap());
185 /// ```
186 fn into(self) -> IBuffer {
187 let vec: Vec<u8> = self.into();
188 vec_to_i_buffer(&vec).unwrap()
189 }
190}
191
192#[cfg(target_os = "windows")]
193#[cfg(test)]
194mod tests {
195 use windows::{
196 Devices::Bluetooth::GenericAttributeProfile::GattClientCharacteristicConfigurationDescriptorValue,
197 Storage::Streams::{DataWriter, IBuffer},
198 };
199
200 use crate::{
201 descriptors::client_characteristic_configuration::{
202 ClientCharacteristicConfiguration, INDICATION, NOTIFICATION,
203 },
204 windows::buffer::i_buffer_to_vec,
205 };
206
207 #[test]
208 fn test_try_from_gatt_client_characteristic_configuration_descriptor_value() {
209 let result = ClientCharacteristicConfiguration::try_from(
210 &GattClientCharacteristicConfigurationDescriptorValue::None,
211 );
212 assert!(result.is_ok());
213 let value = result.unwrap();
214 assert!(!value.is_notification());
215 assert!(!value.is_indication());
216
217 let result = ClientCharacteristicConfiguration::try_from(
218 &GattClientCharacteristicConfigurationDescriptorValue::Notify,
219 );
220 assert!(result.is_ok());
221 let value = result.unwrap();
222 assert!(value.is_notification());
223 assert!(!value.is_indication());
224
225 let result = ClientCharacteristicConfiguration::try_from(
226 &GattClientCharacteristicConfigurationDescriptorValue::Indicate,
227 );
228 assert!(result.is_ok());
229 let value = result.unwrap();
230 assert!(!value.is_notification());
231 assert!(value.is_indication());
232 }
233
234 #[test]
235 fn test_try_from_i_buffer() {
236 let client_characteristic_configuration =
237 ClientCharacteristicConfiguration::new(NOTIFICATION);
238 let data_writer = DataWriter::new().unwrap();
239 let ble_packet: Vec<u8> = client_characteristic_configuration.into();
240 data_writer.WriteBytes(&ble_packet).unwrap();
241 let buffer = data_writer.DetachBuffer().unwrap();
242
243 let result = ClientCharacteristicConfiguration::try_from(buffer);
244 assert!(result.is_ok());
245 let value = result.unwrap();
246 assert!(value.is_notification());
247 }
248
249 #[test]
250 fn test_into_gatt_client_characteristic_configuration_descriptor_value() {
251 let value: GattClientCharacteristicConfigurationDescriptorValue =
252 ClientCharacteristicConfiguration::new(0).into();
253 assert_eq!(
254 GattClientCharacteristicConfigurationDescriptorValue::None,
255 value
256 );
257
258 let value: GattClientCharacteristicConfigurationDescriptorValue =
259 ClientCharacteristicConfiguration::new(NOTIFICATION).into();
260 assert_eq!(
261 GattClientCharacteristicConfigurationDescriptorValue::Notify,
262 value
263 );
264
265 let value: GattClientCharacteristicConfigurationDescriptorValue =
266 ClientCharacteristicConfiguration::new(INDICATION).into();
267 assert_eq!(
268 GattClientCharacteristicConfigurationDescriptorValue::Indicate,
269 value
270 );
271 }
272
273 #[test]
274 fn test_into_i_buffer() {
275 let value = ClientCharacteristicConfiguration::new(0);
276 let buffer: IBuffer = value.clone().into();
277 let vec: Vec<u8> = value.into();
278 assert_eq!(vec, i_buffer_to_vec(buffer).unwrap());
279
280 let value = ClientCharacteristicConfiguration::new(NOTIFICATION);
281 let buffer: IBuffer = value.clone().into();
282 let vec: Vec<u8> = value.into();
283 assert_eq!(vec, i_buffer_to_vec(buffer).unwrap());
284
285 let value = ClientCharacteristicConfiguration::new(INDICATION);
286 let buffer: IBuffer = value.clone().into();
287 let vec: Vec<u8> = value.into();
288 assert_eq!(vec, i_buffer_to_vec(buffer).unwrap());
289 }
290}