diff --git a/src/main.rs b/src/main.rs index 5b56c33..fee40cb 100644 --- a/src/main.rs +++ b/src/main.rs @@ -148,11 +148,9 @@ fn unfuck_color_type(color_type: &str) -> Result { } #[allow(clippy::too_many_lines)] // bruh -fn decoder(inputfile: &str, outputfile: &str) -> Result<()> { +fn decoder(inputfile: &str) -> Result<(u32, u32, ColorType, ArrayVec, ArrayVec, Vec)> { let infile = File::open(inputfile)?; - let outfile = File::create(outputfile)?; let mut lines = BufReader::new(infile).lines(); - let rawriter = BufWriter::new(outfile); // "CIF: " if !lines.next().transpose()?.ok_or(InvalidHeaderError)?.starts_with("CIF:") { @@ -204,14 +202,12 @@ fn decoder(inputfile: &str, outputfile: &str) -> Result<()> { return Err(NoDataError) } - let mut outpng = png::Encoder::new(rawriter, width, height); - outpng.set_color(format); - outpng.set_depth(BitDepth::Eight); - let bytes_per_pixel = if format == ColorType::Rgb { 3 } else { 4 }; let mut md_keylock = false; let mut md_key = ArrayString::<2048>::new(); + let mut md_key_vec = ArrayVec::::new(); + let mut md_val = ArrayVec::::new(); let first = loop { if let Some(line) = lines_read_noempty(&mut lines)? { @@ -221,7 +217,8 @@ fn decoder(inputfile: &str, outputfile: &str) -> Result<()> { if split.len() != 2 { continue } - outpng.add_itxt_chunk(md_key.to_string(), split[1].trim_start().to_string())?; + md_key_vec.push(md_key.to_string()); + md_val.push(split[1].trim_start().to_string()); md_keylock = false; md_key.clear(); continue @@ -233,12 +230,13 @@ fn decoder(inputfile: &str, outputfile: &str) -> Result<()> { 1 => { md_key.try_push_str(&sline)?; md_keylock = true; - }, + } _ => { md_key.try_push_str(&sline)?; - outpng.add_itxt_chunk(split[0].trim_start().to_string(), split[1].trim_start().to_string())?; + md_key_vec.push(split[0].trim_start().to_string()); + md_val.push(split[1].trim_start().to_string()); md_key.clear(); - }, + } } continue } @@ -247,8 +245,6 @@ fn decoder(inputfile: &str, outputfile: &str) -> Result<()> { return Err(NoDataError) }; - let mut outpng = outpng.write_header()?; - let mut pixmap = Vec::with_capacity((bytes_per_pixel * width * height) as usize); if !first.is_empty() { @@ -271,8 +267,26 @@ fn decoder(inputfile: &str, outputfile: &str) -> Result<()> { } } - outpng.write_image_data(&pixmap)?; + Ok((width, height, format, md_key_vec, md_val, pixmap)) +} +fn write_png(outfile: &str, width: u32, height: u32, format: ColorType, md_key: ArrayVec, md_val: ArrayVec, pixmap: Vec) -> Result<()> { + let outfile = File::create(outfile)?; + let rawriter = BufWriter::new(outfile); + let mut outpng = png::Encoder::new(rawriter, width, height); + + for i in 0..md_key.len() { + if md_key[i].is_empty() { + break + } + outpng.add_itxt_chunk(md_key[i].clone(), md_val[i].clone())?; + } + + outpng.set_color(format); + outpng.set_depth(BitDepth::Eight); + + let mut outpng = outpng.write_header()?; + outpng.write_image_data(&pixmap)?; Ok(()) } @@ -282,8 +296,13 @@ fn main() { eprintln!("Invalid usage:\nUsage: zardzewialy-dekoder-cif "); process::exit(1); } - if let Err(e) = decoder(&argv[0], &argv[1]) { - eprintln!("Error: {}", e); + let data = decoder(&argv[0]); + if let Err(e) = data { + eprintln!("Error while parsing cif: {}", e); process::exit(1); } + let data = data.unwrap(); + if let Err(e) = write_png(&argv[1], data.0, data.1, data.2, data.3, data.4, data.5) { + eprintln!("Error while writing image: {}", e); + } }