我正在尝试调整用户上传的大图片的大小,并将其缩小为缩略图大小。
我read that memory issues can cause problems with very large files,因为它需要连续的记忆,但是my test image is only 5.78MB。
我正在使用的代码如下:
public static byte[] GetThumbnailImage(Stream imageStream, ImageFormat format, int thumbnailWidth)
{
using (var thumbnailStream = new MemoryStream())
{
imageStream.Position = 0;
using (var image = Image.FromStream(imageStream))
{
var thumbnailSize = GetThumbnailSize(image, thumbnailWidth);
using (var thumbnail = image.GetThumbnailImage(
thumbnailSize.Width,
thumbnailSize.Height,
null,
IntPtr.Zero))
{
thumbnail.Save(thumbnailStream, format);
return thumbnailStream.ToArray();
}
}
}
}
它被称为这样:
var thumbnailBytes = ImageHelper.GetThumbnailImage(imageStream, ImageFormat.Jpeg, 150);
使用此确切代码,其他较小尺寸的图像可以正常工作而没有任何错误。有什么办法可以改变这段代码来支持更大的图像吗?
更新:按照@ Hans-Passant,@ Matias-Cicero和@Plutonix
的建议添加答案 0 :(得分:-1)
我过去遇到过类似的问题,我认为这是由图像的大小引起的,等于0 ......
我解决了使用此类的LoadImage方法。
您可以调整它以在此调用之前加载图像: var thumbnailSize = GetThumbnailSize(image,thumbnailWidth);
public static class ImageLoader
{
// This isn’t going to help much – you’ll run out of memory anyway on very large images – but if you are keeping several in memory it might …
public const int MaximumImageDimension = 10000;
///
/// Method to safely load an image from a file without leaving the file open,
/// also gets the size down to a manageable size in the case of HUGE images
///
/// An Image – don’t forget to dispose of it later
public static Image LoadImage(string filePath)
{
try
{
FileInfo fi = new FileInfo(filePath);
if (!fi.Exists) throw new FileNotFoundException("File not found.");
if (fi.Length == 0) throw new FileNotFoundException("File zero lenght");
// Image.FromFile is known to leave files open, so we use a stream instead to read it
using (FileStream fs = new FileStream(filePath, FileMode.Open, FileAccess.Read))
{
if (!fs.CanRead) throw new FileLoadException("Can't read the file stream");
if (fs.Length == 0) throw new FileLoadException("File stream zero lenght");
using (Image original = Image.FromStream(fs))
{
// Make a copy of the file in memory, then release the one GDI+ gave us
// thus ensuring that all file handles are closed properly (which GDI+ doesn’t do for us in a timely fashion)
int width = original.Width;
int height = original.Height;
if (width == 0)
throw new DataException("Bad image dimension width=0");
if (height == 0) throw new DataException("Bad image dimension height=0");
// Now shrink it to Max size to control memory consumption
if (width > MaximumImageDimension)
{
height = height * MaximumImageDimension / width;
width = MaximumImageDimension;
}
if (height > MaximumImageDimension)
{
width = width * MaximumImageDimension / height;
height = MaximumImageDimension;
}
Bitmap copy = new Bitmap(width, height);
using (Graphics graphics = Graphics.FromImage(copy))
{
graphics.DrawImage(original, 0, 0, copy.Width, copy.Height);
}
return copy;
}
}
}
catch (Exception ex)
{
ex.Data.Add("File", filePath);
throw;
}
}
}