1use crate::{BitReadStream, BitWriteStream, Endianness, Result};
2use std::borrow::Cow;
3use std::rc::Rc;
4use std::sync::Arc;
5
6pub trait BitWrite<E: Endianness> {
83 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()>;
85}
86
87macro_rules! impl_write_int {
88 ($type:ty) => {
89 impl<E: Endianness> BitWrite<E> for $type {
90 #[inline]
91 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
92 stream.write_int::<$type>(*self, <$type>::BITS as usize)
93 }
94 }
95 };
96}
97
98impl_write_int!(u8);
99impl_write_int!(u16);
100impl_write_int!(u32);
101impl_write_int!(u64);
102impl_write_int!(u128);
103impl_write_int!(i8);
104impl_write_int!(i16);
105impl_write_int!(i32);
106impl_write_int!(i64);
107impl_write_int!(i128);
108
109impl<E: Endianness> BitWrite<E> for f32 {
110 #[inline]
111 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
112 stream.write_float::<f32>(*self)
113 }
114}
115
116impl<E: Endianness> BitWrite<E> for f64 {
117 #[inline]
118 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
119 stream.write_float::<f64>(*self)
120 }
121}
122
123impl<E: Endianness> BitWrite<E> for bool {
124 #[inline]
125 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
126 stream.write_bool(*self)
127 }
128}
129
130impl<E: Endianness> BitWrite<E> for str {
131 #[inline]
132 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
133 stream.write_string(self, None)
134 }
135}
136
137impl<E: Endianness> BitWrite<E> for String {
138 #[inline]
139 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
140 stream.write_string(self, None)
141 }
142}
143
144impl<E: Endianness> BitWrite<E> for BitReadStream<'_, E> {
145 #[inline]
146 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
147 stream.write_bits(self)
148 }
149}
150
151impl<E: Endianness, T: BitWrite<E>, const N: usize> BitWrite<E> for [T; N] {
152 #[inline]
153 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
154 for element in self.iter() {
155 stream.write(element)?;
156 }
157 Ok(())
158 }
159}
160
161impl<T: BitWrite<E>, E: Endianness> BitWrite<E> for Box<T> {
162 #[inline]
163 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
164 stream.write(self.as_ref())
165 }
166}
167
168impl<T: BitWrite<E>, E: Endianness> BitWrite<E> for Rc<T> {
169 #[inline]
170 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
171 stream.write(self.as_ref())
172 }
173}
174
175impl<T: BitWrite<E>, E: Endianness> BitWrite<E> for Arc<T> {
176 #[inline]
177 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
178 stream.write(self.as_ref())
179 }
180}
181
182impl<T: BitWrite<E>, E: Endianness> BitWrite<E> for Vec<T> {
183 #[inline]
184 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
185 for item in self {
186 stream.write(item)?;
187 }
188 Ok(())
189 }
190}
191
192impl<T: BitWrite<E>, E: Endianness> BitWrite<E> for Option<T> {
193 #[inline]
194 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
195 self.is_some().write(stream)?;
196 if let Some(val) = self {
197 val.write(stream)?;
198 }
199 Ok(())
200 }
201}
202
203impl<T: BitWrite<E> + ToOwned + ?Sized, E: Endianness> BitWrite<E> for Cow<'_, T> {
204 #[inline]
205 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
206 self.as_ref().write(stream)
207 }
208}
209
210macro_rules! impl_write_tuple {
211 ($($i:tt: $type:ident),*) => {
212 impl<E: Endianness, $($type: BitWrite<E>),*> BitWrite<E> for ($($type),*) {
213 #[inline]
214 fn write(&self, stream: &mut BitWriteStream<E>) -> Result<()> {
215 $(self.$i.write(stream)?;)*
216 Ok(())
217 }
218 }
219 };
220}
221
222impl_write_tuple!(0: T1, 1: T2);
223impl_write_tuple!(0: T1, 1: T2, 2: T3);
224impl_write_tuple!(0: T1, 1: T2, 2: T3, 3: T4);
225
226pub trait BitWriteSized<E: Endianness> {
289 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()>;
291}
292
293impl<E: Endianness> BitWriteSized<E> for str {
294 #[inline]
295 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
296 stream.write_string(self, Some(len))
297 }
298}
299
300impl<E: Endianness> BitWriteSized<E> for String {
301 #[inline]
302 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
303 stream.write_string(self, Some(len))
304 }
305}
306
307macro_rules! impl_write_sized_int {
308 ($type:ty) => {
309 impl<E: Endianness> BitWriteSized<E> for $type {
310 #[inline]
311 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
312 stream.write_int::<$type>(*self, len)
313 }
314 }
315 };
316}
317
318impl_write_sized_int!(u8);
319impl_write_sized_int!(u16);
320impl_write_sized_int!(u32);
321impl_write_sized_int!(u64);
322impl_write_sized_int!(u128);
323impl_write_sized_int!(usize);
324impl_write_sized_int!(i8);
325impl_write_sized_int!(i16);
326impl_write_sized_int!(i32);
327impl_write_sized_int!(i64);
328impl_write_sized_int!(i128);
329impl_write_sized_int!(isize);
330
331impl<E: Endianness> BitWriteSized<E> for BitReadStream<'_, E> {
332 #[inline]
333 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
334 let bits = self.clone().read_bits(len)?;
335 stream.write_bits(&bits)
336 }
337}
338
339impl<E: Endianness, T: BitWriteSized<E>, const N: usize> BitWriteSized<E> for [T; N] {
340 #[inline]
341 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
342 for element in self.iter() {
343 stream.write_sized(element, len)?;
344 }
345 Ok(())
346 }
347}
348
349impl<T: BitWriteSized<E>, E: Endianness> BitWriteSized<E> for Box<T> {
350 #[inline]
351 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
352 stream.write_sized(self.as_ref(), len)
353 }
354}
355
356impl<T: BitWriteSized<E>, E: Endianness> BitWriteSized<E> for Rc<T> {
357 #[inline]
358 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
359 stream.write_sized(self.as_ref(), len)
360 }
361}
362
363impl<T: BitWriteSized<E>, E: Endianness> BitWriteSized<E> for Arc<T> {
364 #[inline]
365 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
366 stream.write_sized(self.as_ref(), len)
367 }
368}
369
370impl<T: BitWriteSized<E>, E: Endianness> BitWriteSized<E> for Option<T> {
371 #[inline]
372 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
373 self.is_some().write(stream)?;
374 if let Some(val) = self {
375 val.write_sized(stream, len)?;
376 }
377 Ok(())
378 }
379}
380
381impl<T: BitWriteSized<E> + ToOwned + ?Sized, E: Endianness> BitWriteSized<E> for Cow<'_, T> {
382 #[inline]
383 fn write_sized(&self, stream: &mut BitWriteStream<E>, len: usize) -> Result<()> {
384 self.as_ref().write_sized(stream, len)
385 }
386}