diff options
Diffstat (limited to 'vendor/image/src/io/free_functions.rs')
-rw-r--r-- | vendor/image/src/io/free_functions.rs | 312 |
1 files changed, 0 insertions, 312 deletions
diff --git a/vendor/image/src/io/free_functions.rs b/vendor/image/src/io/free_functions.rs deleted file mode 100644 index d6047d7..0000000 --- a/vendor/image/src/io/free_functions.rs +++ /dev/null @@ -1,312 +0,0 @@ -use std::fs::File; -use std::io::{BufRead, BufReader, BufWriter, Seek}; -use std::path::Path; -use std::u32; - -use crate::codecs::*; - -use crate::dynimage::DynamicImage; -use crate::error::{ImageError, ImageFormatHint, ImageResult}; -use crate::image; -use crate::image::ImageFormat; -#[allow(unused_imports)] // When no features are supported -use crate::image::{ImageDecoder, ImageEncoder}; -use crate::{ - color, - error::{UnsupportedError, UnsupportedErrorKind}, - ImageOutputFormat, -}; - -pub(crate) fn open_impl(path: &Path) -> ImageResult<DynamicImage> { - let buffered_read = BufReader::new(File::open(path).map_err(ImageError::IoError)?); - - load(buffered_read, ImageFormat::from_path(path)?) -} - -/// Create a new image from a Reader. -/// -/// Assumes the reader is already buffered. For optimal performance, -/// consider wrapping the reader with a `BufReader::new()`. -/// -/// Try [`io::Reader`] for more advanced uses. -/// -/// [`io::Reader`]: io/struct.Reader.html -#[allow(unused_variables)] -// r is unused if no features are supported. -pub fn load<R: BufRead + Seek>(r: R, format: ImageFormat) -> ImageResult<DynamicImage> { - load_inner(r, super::Limits::default(), format) -} - -pub(crate) trait DecoderVisitor { - type Result; - fn visit_decoder<'a, D: ImageDecoder<'a>>(self, decoder: D) -> ImageResult<Self::Result>; -} - -pub(crate) fn load_decoder<R: BufRead + Seek, V: DecoderVisitor>( - r: R, - format: ImageFormat, - limits: super::Limits, - visitor: V, -) -> ImageResult<V::Result> { - #[allow(unreachable_patterns)] - // Default is unreachable if all features are supported. - match format { - #[cfg(feature = "avif-decoder")] - image::ImageFormat::Avif => visitor.visit_decoder(avif::AvifDecoder::new(r)?), - #[cfg(feature = "png")] - image::ImageFormat::Png => visitor.visit_decoder(png::PngDecoder::with_limits(r, limits)?), - #[cfg(feature = "gif")] - image::ImageFormat::Gif => visitor.visit_decoder(gif::GifDecoder::new(r)?), - #[cfg(feature = "jpeg")] - image::ImageFormat::Jpeg => visitor.visit_decoder(jpeg::JpegDecoder::new(r)?), - #[cfg(feature = "webp")] - image::ImageFormat::WebP => visitor.visit_decoder(webp::WebPDecoder::new(r)?), - #[cfg(feature = "tiff")] - image::ImageFormat::Tiff => visitor.visit_decoder(tiff::TiffDecoder::new(r)?), - #[cfg(feature = "tga")] - image::ImageFormat::Tga => visitor.visit_decoder(tga::TgaDecoder::new(r)?), - #[cfg(feature = "dds")] - image::ImageFormat::Dds => visitor.visit_decoder(dds::DdsDecoder::new(r)?), - #[cfg(feature = "bmp")] - image::ImageFormat::Bmp => visitor.visit_decoder(bmp::BmpDecoder::new(r)?), - #[cfg(feature = "ico")] - image::ImageFormat::Ico => visitor.visit_decoder(ico::IcoDecoder::new(r)?), - #[cfg(feature = "hdr")] - image::ImageFormat::Hdr => visitor.visit_decoder(hdr::HdrAdapter::new(BufReader::new(r))?), - #[cfg(feature = "exr")] - image::ImageFormat::OpenExr => visitor.visit_decoder(openexr::OpenExrDecoder::new(r)?), - #[cfg(feature = "pnm")] - image::ImageFormat::Pnm => visitor.visit_decoder(pnm::PnmDecoder::new(r)?), - #[cfg(feature = "farbfeld")] - image::ImageFormat::Farbfeld => visitor.visit_decoder(farbfeld::FarbfeldDecoder::new(r)?), - #[cfg(feature = "qoi")] - image::ImageFormat::Qoi => visitor.visit_decoder(qoi::QoiDecoder::new(r)?), - _ => Err(ImageError::Unsupported( - ImageFormatHint::Exact(format).into(), - )), - } -} - -pub(crate) fn load_inner<R: BufRead + Seek>( - r: R, - limits: super::Limits, - format: ImageFormat, -) -> ImageResult<DynamicImage> { - struct LoadVisitor(super::Limits); - - impl DecoderVisitor for LoadVisitor { - type Result = DynamicImage; - - fn visit_decoder<'a, D: ImageDecoder<'a>>( - self, - mut decoder: D, - ) -> ImageResult<Self::Result> { - let mut limits = self.0; - // Check that we do not allocate a bigger buffer than we are allowed to - // FIXME: should this rather go in `DynamicImage::from_decoder` somehow? - limits.reserve(decoder.total_bytes())?; - decoder.set_limits(limits)?; - DynamicImage::from_decoder(decoder) - } - } - - load_decoder(r, format, limits.clone(), LoadVisitor(limits)) -} - -pub(crate) fn image_dimensions_impl(path: &Path) -> ImageResult<(u32, u32)> { - let format = image::ImageFormat::from_path(path)?; - let reader = BufReader::new(File::open(path)?); - image_dimensions_with_format_impl(reader, format) -} - -#[allow(unused_variables)] -// fin is unused if no features are supported. -pub(crate) fn image_dimensions_with_format_impl<R: BufRead + Seek>( - buffered_read: R, - format: ImageFormat, -) -> ImageResult<(u32, u32)> { - struct DimVisitor; - - impl DecoderVisitor for DimVisitor { - type Result = (u32, u32); - fn visit_decoder<'a, D: ImageDecoder<'a>>(self, decoder: D) -> ImageResult<Self::Result> { - Ok(decoder.dimensions()) - } - } - - load_decoder(buffered_read, format, super::Limits::default(), DimVisitor) -} - -#[allow(unused_variables)] -// Most variables when no features are supported -pub(crate) fn save_buffer_impl( - path: &Path, - buf: &[u8], - width: u32, - height: u32, - color: color::ColorType, -) -> ImageResult<()> { - let format = ImageFormat::from_path(path)?; - save_buffer_with_format_impl(path, buf, width, height, color, format) -} - -#[allow(unused_variables)] -// Most variables when no features are supported -pub(crate) fn save_buffer_with_format_impl( - path: &Path, - buf: &[u8], - width: u32, - height: u32, - color: color::ColorType, - format: ImageFormat, -) -> ImageResult<()> { - let buffered_file_write = &mut BufWriter::new(File::create(path)?); // always seekable - - let format = match format { - #[cfg(feature = "pnm")] - image::ImageFormat::Pnm => { - let ext = path - .extension() - .and_then(|s| s.to_str()) - .map_or("".to_string(), |s| s.to_ascii_lowercase()); - ImageOutputFormat::Pnm(match &*ext { - "pbm" => pnm::PnmSubtype::Bitmap(pnm::SampleEncoding::Binary), - "pgm" => pnm::PnmSubtype::Graymap(pnm::SampleEncoding::Binary), - "ppm" => pnm::PnmSubtype::Pixmap(pnm::SampleEncoding::Binary), - "pam" => pnm::PnmSubtype::ArbitraryMap, - _ => { - return Err(ImageError::Unsupported( - ImageFormatHint::Exact(format).into(), - )) - } // Unsupported Pnm subtype. - }) - } - // #[cfg(feature = "hdr")] - // image::ImageFormat::Hdr => hdr::HdrEncoder::new(fout).encode(&[Rgb<f32>], width, height), // usize - format => format.into(), - }; - - write_buffer_impl(buffered_file_write, buf, width, height, color, format) -} - -#[allow(unused_variables)] -// Most variables when no features are supported -pub(crate) fn write_buffer_impl<W: std::io::Write + Seek>( - buffered_write: &mut W, - buf: &[u8], - width: u32, - height: u32, - color: color::ColorType, - format: ImageOutputFormat, -) -> ImageResult<()> { - match format { - #[cfg(feature = "png")] - ImageOutputFormat::Png => { - png::PngEncoder::new(buffered_write).write_image(buf, width, height, color) - } - #[cfg(feature = "jpeg")] - ImageOutputFormat::Jpeg(quality) => { - jpeg::JpegEncoder::new_with_quality(buffered_write, quality) - .write_image(buf, width, height, color) - } - #[cfg(feature = "pnm")] - ImageOutputFormat::Pnm(subtype) => pnm::PnmEncoder::new(buffered_write) - .with_subtype(subtype) - .write_image(buf, width, height, color), - #[cfg(feature = "gif")] - ImageOutputFormat::Gif => { - gif::GifEncoder::new(buffered_write).encode(buf, width, height, color) - } - #[cfg(feature = "ico")] - ImageOutputFormat::Ico => { - ico::IcoEncoder::new(buffered_write).write_image(buf, width, height, color) - } - #[cfg(feature = "bmp")] - ImageOutputFormat::Bmp => { - bmp::BmpEncoder::new(buffered_write).write_image(buf, width, height, color) - } - #[cfg(feature = "farbfeld")] - ImageOutputFormat::Farbfeld => { - farbfeld::FarbfeldEncoder::new(buffered_write).write_image(buf, width, height, color) - } - #[cfg(feature = "tga")] - ImageOutputFormat::Tga => { - tga::TgaEncoder::new(buffered_write).write_image(buf, width, height, color) - } - #[cfg(feature = "exr")] - ImageOutputFormat::OpenExr => { - openexr::OpenExrEncoder::new(buffered_write).write_image(buf, width, height, color) - } - #[cfg(feature = "tiff")] - ImageOutputFormat::Tiff => { - tiff::TiffEncoder::new(buffered_write).write_image(buf, width, height, color) - } - #[cfg(feature = "avif-encoder")] - ImageOutputFormat::Avif => { - avif::AvifEncoder::new(buffered_write).write_image(buf, width, height, color) - } - #[cfg(feature = "qoi")] - ImageOutputFormat::Qoi => { - qoi::QoiEncoder::new(buffered_write).write_image(buf, width, height, color) - } - #[cfg(feature = "webp-encoder")] - ImageOutputFormat::WebP => { - webp::WebPEncoder::new(buffered_write).write_image(buf, width, height, color) - } - - image::ImageOutputFormat::Unsupported(msg) => Err(ImageError::Unsupported( - UnsupportedError::from_format_and_kind( - ImageFormatHint::Unknown, - UnsupportedErrorKind::Format(ImageFormatHint::Name(msg)), - ), - )), - } -} - -static MAGIC_BYTES: [(&[u8], ImageFormat); 23] = [ - (b"\x89PNG\r\n\x1a\n", ImageFormat::Png), - (&[0xff, 0xd8, 0xff], ImageFormat::Jpeg), - (b"GIF89a", ImageFormat::Gif), - (b"GIF87a", ImageFormat::Gif), - (b"RIFF", ImageFormat::WebP), // TODO: better magic byte detection, see https://github.com/image-rs/image/issues/660 - (b"MM\x00*", ImageFormat::Tiff), - (b"II*\x00", ImageFormat::Tiff), - (b"DDS ", ImageFormat::Dds), - (b"BM", ImageFormat::Bmp), - (&[0, 0, 1, 0], ImageFormat::Ico), - (b"#?RADIANCE", ImageFormat::Hdr), - (b"P1", ImageFormat::Pnm), - (b"P2", ImageFormat::Pnm), - (b"P3", ImageFormat::Pnm), - (b"P4", ImageFormat::Pnm), - (b"P5", ImageFormat::Pnm), - (b"P6", ImageFormat::Pnm), - (b"P7", ImageFormat::Pnm), - (b"farbfeld", ImageFormat::Farbfeld), - (b"\0\0\0 ftypavif", ImageFormat::Avif), - (b"\0\0\0\x1cftypavif", ImageFormat::Avif), - (&[0x76, 0x2f, 0x31, 0x01], ImageFormat::OpenExr), // = &exr::meta::magic_number::BYTES - (b"qoif", ImageFormat::Qoi), -]; - -/// Guess image format from memory block -/// -/// Makes an educated guess about the image format based on the Magic Bytes at the beginning. -/// TGA is not supported by this function. -/// This is not to be trusted on the validity of the whole memory block -pub fn guess_format(buffer: &[u8]) -> ImageResult<ImageFormat> { - match guess_format_impl(buffer) { - Some(format) => Ok(format), - None => Err(ImageError::Unsupported(ImageFormatHint::Unknown.into())), - } -} - -pub(crate) fn guess_format_impl(buffer: &[u8]) -> Option<ImageFormat> { - for &(signature, format) in &MAGIC_BYTES { - if buffer.starts_with(signature) { - return Some(format); - } - } - - None -} |