Skip to content
Snippets Groups Projects
format.rs 1.41 KiB
Newer Older
Louis's avatar
Louis committed
use std::path::Path;

use clap::ArgEnum;
use image::io::Reader;
use image::{ImageError, ImageFormat, RgbaImage};
use serde::{Deserialize, Serialize};
use thiserror::Error;

#[derive(
	Copy, Clone, PartialEq, Eq, PartialOrd, Ord, ArgEnum, Debug, Serialize, Deserialize, Default,
)]
pub enum PaletteFormat {
	TXT,
	#[default]
	PNG,
}

// impl Default for PaletteFormat {
// 	fn default() -> Self {
// 		Self::PNG
// 	}
// }

#[derive(Copy, Clone, PartialEq, Eq, PartialOrd, Ord, ArgEnum, Debug)]
pub enum Format {
	PNG,
	JPG,
	GIF,
	ICO,
	TGA,
	TIFF,
	BMP,
}

impl Format {
	pub fn as_image_format(&self) -> ImageFormat {
		use Format::*;
		match self {
			PNG => ImageFormat::Png,
			JPG => ImageFormat::Jpeg,
			GIF => ImageFormat::Gif,
			ICO => ImageFormat::Ico,
			TGA => ImageFormat::Tga,
			TIFF => ImageFormat::Tiff,
			BMP => ImageFormat::Bmp,
		}
	}
}

#[derive(Error, Debug)]
pub enum ImageLoadingError {
	#[error("Failed to load image data; {0}")]
	IoError(#[from] std::io::Error),
	#[error("Failed to process image; {0}")]
	ImageError(#[from] ImageError),
}

pub fn load_image<T: AsRef<Path>>(
	path: T,
	format: Option<Format>,
) -> anyhow::Result<RgbaImage, ImageLoadingError> {
	let mut image = Reader::open(path)?;
	let file = match format {
		Some(format) => {
			image.set_format(format.as_image_format());
			image.decode()?.into_rgba8()
		}
		None => image.with_guessed_format()?.decode()?.into_rgba8(),
	};

	Ok(file)
}