diff options
Diffstat (limited to 'src/encode.rs')
-rw-r--r-- | src/encode.rs | 44 |
1 files changed, 34 insertions, 10 deletions
diff --git a/src/encode.rs b/src/encode.rs index a8c58e0..30edc49 100644 --- a/src/encode.rs +++ b/src/encode.rs | |||
@@ -3,8 +3,11 @@ use std::borrow::Borrow; | |||
3 | use bitvec::{prelude::*, vec::BitVec}; | 3 | use bitvec::{prelude::*, vec::BitVec}; |
4 | use byteorder::{LittleEndian, WriteBytesExt}; | 4 | use byteorder::{LittleEndian, WriteBytesExt}; |
5 | 5 | ||
6 | use crate::error::{OBIError, OBIResult}; | 6 | use crate::{ |
7 | use crate::Image; | 7 | error::{OBIError, OBIResult}, |
8 | rle::RLE, | ||
9 | CompressionType, Image, | ||
10 | }; | ||
8 | 11 | ||
9 | pub fn encode_image<I>(obi_image: I) -> OBIResult<Vec<u8>> | 12 | pub fn encode_image<I>(obi_image: I) -> OBIResult<Vec<u8>> |
10 | where | 13 | where |
@@ -40,17 +43,38 @@ where | |||
40 | .write_u32::<LittleEndian>(image_info_header.post_compression_size) | 43 | .write_u32::<LittleEndian>(image_info_header.post_compression_size) |
41 | .map_err(|_| OBIError::Encode)?; | 44 | .map_err(|_| OBIError::Encode)?; |
42 | 45 | ||
46 | let write_pixel_data = |pixels: &Vec<bool>, obi_data: &mut Vec<u8>| -> OBIResult<()> { | ||
47 | for byte in pixels.chunks(8) { | ||
48 | let mut bv = BitVec::<Lsb0, u8>::new(); | ||
49 | for &b in byte { | ||
50 | bv.push(b) | ||
51 | } | ||
52 | obi_data | ||
53 | .write_u8(bv.load::<u8>()) | ||
54 | .map_err(|_| OBIError::Encode)?; | ||
55 | } | ||
56 | Ok(()) | ||
57 | }; | ||
58 | |||
43 | // pixmap data | 59 | // pixmap data |
44 | let pixmap = &obi_image.data; | 60 | let pixmap = &obi_image.data; |
45 | for byte in pixmap.chunks(8) { | 61 | match CompressionType::from_u32(obi_image.image_info_header.compression_type) { |
46 | let mut bv = BitVec::<Lsb0, u8>::new(); | 62 | CompressionType::RLE => { |
47 | for &b in byte { | 63 | let (data_points, lengths): (Vec<_>, Vec<_>) = pixmap.compress().into_iter().unzip(); |
48 | bv.push(b); | 64 | for l in lengths { |
65 | obi_data | ||
66 | .write_u32::<LittleEndian>(l as u32) | ||
67 | .map_err(|_| OBIError::Encode)?; | ||
68 | } | ||
69 | // end length sequence with zero | ||
70 | obi_data | ||
71 | .write_u32::<LittleEndian>(0) | ||
72 | .map_err(|_| OBIError::Encode)?; | ||
73 | // begin data point sequence | ||
74 | write_pixel_data(&data_points, &mut obi_data)?; | ||
49 | } | 75 | } |
50 | obi_data | 76 | _ => write_pixel_data(pixmap, &mut obi_data)?, |
51 | .write_u8(bv.load::<u8>()) | 77 | }; |
52 | .map_err(|_| OBIError::Encode)?; | ||
53 | } | ||
54 | 78 | ||
55 | return Ok(obi_data); | 79 | return Ok(obi_data); |
56 | } | 80 | } |