pub struct Decoder {
state: Box<dyn Stateful + Send + 'static>,
}
Expand description
The state for decoding data with an LZW algorithm.
The same structure can be utilized with streams as well as your own buffers and driver logic. It may even be possible to mix them if you are sufficiently careful not to lose or skip any already decode data in the process.
This is a sans-IO implementation, meaning that it only contains the state of the decoder and
the caller will provide buffers for input and output data when calling the basic
decode_bytes
method. Nevertheless, a number of adapters are provided in the into_*
methods for decoding with a particular style of common IO.
decode
for decoding once without any IO-loop.into_async
for decoding with thefutures
traits for asynchronous IO.into_stream
for decoding with the standardio
traits.into_vec
for in-memory decoding.
Fields§
§state: Box<dyn Stateful + Send + 'static>
Implementations§
source§impl Decoder
impl Decoder
sourcepub fn new(order: BitOrder, size: u8) -> Self
pub fn new(order: BitOrder, size: u8) -> Self
Create a new decoder with the specified bit order and symbol size.
The algorithm for dynamically increasing the code symbol bit width is compatible with the
original specification. In particular you will need to specify an Lsb
bit oder to decode
the data portion of a compressed gif
image.
§Panics
The size
needs to be in the interval 0..=12
.
sourcepub fn with_tiff_size_switch(order: BitOrder, size: u8) -> Self
pub fn with_tiff_size_switch(order: BitOrder, size: u8) -> Self
Create a TIFF compatible decoder with the specified bit order and symbol size.
The algorithm for dynamically increasing the code symbol bit width is compatible with the TIFF specification, which is a misinterpretation of the original algorithm for increasing the code size. It switches one symbol sooner.
§Panics
The size
needs to be in the interval 0..=12
.
sourcepub fn decode_bytes(&mut self, inp: &[u8], out: &mut [u8]) -> BufferResult
pub fn decode_bytes(&mut self, inp: &[u8], out: &mut [u8]) -> BufferResult
Decode some bytes from inp
and write result to out
.
This will consume a prefix of the input buffer and write decoded output into a prefix of the output buffer. See the respective fields of the return value for the count of consumed and written bytes. For the next call You should have adjusted the inputs accordingly.
The call will try to decode and write as many bytes of output as available. It will be much more optimized (and avoid intermediate buffering) if it is allowed to write a large contiguous chunk at once.
See into_stream
for high-level functions (that are only available with the std
feature).
sourcepub fn decode(&mut self, data: &[u8]) -> Result<Vec<u8>, LzwError>
pub fn decode(&mut self, data: &[u8]) -> Result<Vec<u8>, LzwError>
Decode a single chunk of lzw encoded data.
This method requires the data to contain an end marker, and returns an error otherwise.
This is a convenience wrapper around into_vec
. Use the into_vec
adapter to customize
buffer size, to supply an existing vector, to control whether an end marker is required, or
to preserve partial data in the case of a decoding error.
§Example
use weezl::{BitOrder, decode::Decoder};
// Encoded that was created with an encoder.
let data = b"\x80\x04\x81\x94l\x1b\x06\xf0\xb0 \x1d\xc6\xf1\xc8l\x19 \x10";
let decoded = Decoder::new(BitOrder::Msb, 9)
.decode(data)
.unwrap();
assert_eq!(decoded, b"Hello, world");
sourcepub fn into_stream<W: Write>(&mut self, writer: W) -> IntoStream<'_, W>
pub fn into_stream<W: Write>(&mut self, writer: W) -> IntoStream<'_, W>
Construct a decoder into a writer.
sourcepub fn into_vec<'lt>(&'lt mut self, vec: &'lt mut Vec<u8>) -> IntoVec<'lt>
pub fn into_vec<'lt>(&'lt mut self, vec: &'lt mut Vec<u8>) -> IntoVec<'lt>
Construct a decoder into a vector.
All decoded data is appended and the vector is not cleared.
Compared to into_stream
this interface allows a high-level access to decoding without
requires the std
-feature. Also, it can make full use of the extra buffer control that the
special target exposes.
sourcepub fn has_ended(&self) -> bool
pub fn has_ended(&self) -> bool
Check if the decoding has finished.
No more output is produced beyond the end code that marked the finish of the stream. The decoder may have read additional bytes, including padding bits beyond the last code word but also excess bytes provided.
sourcepub(crate) fn restart(&mut self)
pub(crate) fn restart(&mut self)
Ignore an end code and continue.
This will not reset any of the inner code tables and not have the effect of a clear code. It will instead continue as if the end code had not been present. If no end code has occurred then this is a no-op.
You can test if an end code has occurred with has_ended
.
FIXME: clarify how this interacts with padding introduced after end code.