diff options
| author | Fuwn <[email protected]> | 2022-03-01 14:38:36 -0800 |
|---|---|---|
| committer | Fuwn <[email protected]> | 2022-03-01 14:38:36 -0800 |
| commit | 2a8df03dc636d3ee385ac35116186b12345855fb (patch) | |
| tree | 370d379d1e839e4ab08741a053c2bc7c7cf85755 /src | |
| parent | 0d96a9d011dad9144a4ef178db9a7933fbdb8094 (diff) | |
| download | para-2a8df03dc636d3ee385ac35116186b12345855fb.tar.xz para-2a8df03dc636d3ee385ac35116186b12345855fb.zip | |
refactor(ppm): use rust generator instead of crate
Diffstat (limited to 'src')
| -rw-r--r-- | src/main.rs | 2 | ||||
| -rw-r--r-- | src/ppm.rs | 82 |
2 files changed, 44 insertions, 40 deletions
diff --git a/src/main.rs b/src/main.rs index 7d10479..8541135 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,7 +1,7 @@ // Copyright (C) 2022-2022 Fuwn <[email protected]> // SPDX-License-Identifier: MIT -#![feature(decl_macro)] +#![feature(decl_macro, generators, generator_trait)] #![deny( warnings, nonstandard_style, @@ -7,6 +7,7 @@ use std::{ collections::HashMap, fs, io::{Cursor, Read}, + ops::Generator, }; use byteorder::{LittleEndian, ReadBytesExt}; @@ -316,15 +317,13 @@ impl PPMParser { self.stream.read_uint::<LittleEndian>(1).unwrap() >> 7 & 0x1 != 0 } - fn read_line_types(line_types: Vec<u8>) -> generator::Generator<'static, (), (usize, u8)> { - generator::Gn::new_scoped(move |mut s| { + fn read_line_types(line_types: Vec<u8>) -> impl Generator<Yield = (usize, u8), Return = ()> { + move || { for index in 0..192 { let line_type = line_types.get(index / 4).unwrap() >> ((index % 4) * 2) & 0x03; - s.yield_((index, line_type)); + yield (index, line_type); } - - generator::done!(); - }) + } } fn read_frame(&mut self, index: usize) -> &Vec<Vec<Vec<u8>>> { @@ -370,29 +369,47 @@ impl PPMParser { for layer in 0..2 { let bitmap = &mut self.layers[layer]; - for (line, line_type) in Self::read_line_types(line_types[layer].clone()) { - let mut pixel = 0; - - // No data stored for this line - if line_type == 0 { - // pass; - } else if line_type == 1 || line_type == 2 { - // Compressed line - // If `line_type == 2`, the line starts off with all the pixels set to one - if line_type == 2 { - for i in 0..256 { - bitmap[line][i] = 1; + { + let mut generator = Self::read_line_types(line_types[layer].clone()); + while let std::ops::GeneratorState::Yielded((line, line_type)) = + std::pin::Pin::new(&mut generator).resume(()) + { + let mut pixel = 0; + + // No data stored for this line + if line_type == 0 { + // pass; + } else if line_type == 1 || line_type == 2 { + // Compressed line + // If `line_type == 2`, the line starts off with all the pixels set to one + if line_type == 2 { + for i in 0..256 { + bitmap[line][i] = 1; + } } - } - // Unpack chunk usage - let mut chunk_usage = self.stream.read_u32::<byteorder::BigEndian>().unwrap(); + // Unpack chunk usage + let mut chunk_usage = self.stream.read_u32::<byteorder::BigEndian>().unwrap(); + + // Unpack pixel chunks + while pixel < 256 { + if chunk_usage & 0x8000_0000 == 0 { + pixel += 8; + } else { + let chunk = self.stream.read_uint::<LittleEndian>(1).unwrap(); - // Unpack pixel chunks - while pixel < 256 { - if chunk_usage & 0x8000_0000 == 0 { - pixel += 8; - } else { + for bit in 0..8 { + bitmap[line][pixel] = (chunk >> bit & 0x1) as u8; + pixel += 1; + } + } + + chunk_usage <<= 1; + } + // Raw line + } else if line_type == 3 { + // Unpack pixel chunks + while pixel < 256 { let chunk = self.stream.read_uint::<LittleEndian>(1).unwrap(); for bit in 0..8 { @@ -400,19 +417,6 @@ impl PPMParser { pixel += 1; } } - - chunk_usage <<= 1; - } - // Raw line - } else if line_type == 3 { - // Unpack pixel chunks - while pixel < 256 { - let chunk = self.stream.read_uint::<LittleEndian>(1).unwrap(); - - for bit in 0..8 { - bitmap[line][pixel] = (chunk >> bit & 0x1) as u8; - pixel += 1; - } } } } |