zune_core/bytestream/
traits.rs

1/*
2 * Copyright (c) 2023.
3 *
4 * This software is free software;
5 *
6 * You can redistribute it or modify it under terms of the MIT, Apache License or Zlib license
7 */
8//! Traits for reading and writing images in zune
9//!
10//!
11//! This exposes the traits and implementations for readers
12//! and writers in the zune family of decoders and encoders.
13
14use alloc::vec::Vec;
15use core::ops::Range;
16
17/// The underlying reader trait
18///
19/// # Considerations
20///
21///- When implementing this for a type, it is recommended to implement methods with
22/// `#inline[(always)]` directive to allow the functions to get inlined in call sites,
23/// this may make it faster on some situations since the call sites may be in hot loop.
24///
25/// - If you are reading from a file and it's small , it is preferable to read it into memory
26/// instead of using a file reader.
27pub trait ZReaderTrait {
28    /// Get a single byte which is at position `index`
29    ///
30    /// # Arguments
31    /// - `index`: The position of the bytes
32    fn get_byte(&self, index: usize) -> Option<&u8>;
33
34    /// Get a slice of bytes from a range of start..end
35    ///
36    /// # Arguments
37    ///
38    /// * `index`:  The range of the bytes to read
39    ///
40    /// returns: `Option<&[u8]>`
41    ///
42    /// # Examples
43    ///
44    /// - Read 10 bytes from
45    /// ```
46    /// extern crate alloc;
47    /// use alloc::vec::Vec;
48    /// use zune_core::bytestream::ZReaderTrait;
49    ///
50    /// let bytes = vec![0_u8;100];
51    ///
52    /// // get ten bytes from 0..10
53    /// let re = bytes.get_slice(0..10).unwrap();
54    /// assert_eq!(10,re.len())
55    ///
56    /// ```
57    fn get_slice(&self, index: Range<usize>) -> Option<&[u8]>;
58
59    /// Get total length of the underlying buffer.
60    ///
61    /// This should be the total bytes that are present in
62    /// the buffer.
63    ///
64    /// For files, this includes the file  length.
65    /// For buffers this includes the internal buffer length
66    fn get_len(&self) -> usize;
67}
68
69impl ZReaderTrait for &[u8] {
70    #[inline(always)]
71    fn get_byte(&self, index: usize) -> Option<&u8> {
72        self.get(index)
73    }
74
75    #[inline(always)]
76    fn get_slice(&self, index: Range<usize>) -> Option<&[u8]> {
77        self.get(index)
78    }
79
80    #[inline(always)]
81    fn get_len(&self) -> usize {
82        self.len()
83    }
84}
85
86impl ZReaderTrait for Vec<u8> {
87    #[inline(always)]
88    fn get_byte(&self, index: usize) -> Option<&u8> {
89        self.get(index)
90    }
91
92    #[inline(always)]
93    fn get_slice(&self, index: Range<usize>) -> Option<&[u8]> {
94        self.get(index)
95    }
96
97    #[inline(always)]
98    fn get_len(&self) -> usize {
99        self.len()
100    }
101}
102
103impl ZReaderTrait for &Vec<u8> {
104    #[inline(always)]
105    fn get_byte(&self, index: usize) -> Option<&u8> {
106        self.get(index)
107    }
108
109    #[inline(always)]
110    fn get_slice(&self, index: Range<usize>) -> Option<&[u8]> {
111        self.get(index)
112    }
113
114    #[inline(always)]
115    fn get_len(&self) -> usize {
116        self.len()
117    }
118}
119
120impl<const N: usize> ZReaderTrait for &[u8; N] {
121    fn get_byte(&self, index: usize) -> Option<&u8> {
122        self.get(index)
123    }
124
125    fn get_slice(&self, index: Range<usize>) -> Option<&[u8]> {
126        self.get(index)
127    }
128
129    fn get_len(&self) -> usize {
130        N
131    }
132}
133
134impl<const N: usize> ZReaderTrait for [u8; N] {
135    fn get_byte(&self, index: usize) -> Option<&u8> {
136        self.get(index)
137    }
138
139    fn get_slice(&self, index: Range<usize>) -> Option<&[u8]> {
140        self.get(index)
141    }
142
143    fn get_len(&self) -> usize {
144        N
145    }
146}
147
148impl ZReaderTrait for dyn AsRef<&[u8]> {
149    fn get_byte(&self, index: usize) -> Option<&u8> {
150        self.as_ref().get(index)
151    }
152
153    fn get_slice(&self, index: Range<usize>) -> Option<&[u8]> {
154        self.as_ref().get(index)
155    }
156
157    fn get_len(&self) -> usize {
158        self.as_ref().len()
159    }
160}