项目上有一个功能是往一个第三方的电子病历编辑器中插入图片,第一次插入时正常显示。第二次三次之后再插入,就会报OutOfMemoryException。。。
查看了下Image.FromStream方法的官方文档,当流不是一个有效的图像格式时会报OutOfMemoryException的异常,如下图红框部分。
很明显实际的原因并不是这个。因为我第一次可以正常把图片插入进去,第二次就不行了。
由于第三方的编辑器代码是混淆的,也没有去深究了。
推测应该是插入图片后没有释放掉图片资源,尤其是插入尺寸比较大的图片时,这个错误发生的几率变高。
解决办法
解决不了第三方类库的问题,那么我们就从自己的代码上着手。
好在它支持传递Image对象的重载方法(上述报错的代码是使用传递文件路径的方法),
那我们可以自行加载图片,然后把图片压缩尺寸,再把压缩后的图片传递给第三方类库就好了。
压缩图片的代码如下:
/// <summary>
/// 压缩图片
/// </summary>
/// <param name="imageStream">图片文件流</param>
/// <param name="size">指定压缩后的尺寸(像素)</param>
/// <returns>压缩后的图片</returns>
public static Image Compress(Stream imageStream, Size size)
{
using (var img = Image.FromStream(imageStream))
using (var bitmap = new Bitmap(size.Width, size.Height))
using (var g = Graphics.FromImage(bitmap))
{
g.Clear(Color.Transparent);
g.CompositingQuality = CompositingQuality.HighSpeed;
g.SmoothingMode = SmoothingMode.HighSpeed;
g.InterpolationMode = InterpolationMode.Low;
g.DrawImage(img, new Rectangle(0, 0, size.Width, size.Height), 0, 0, img.Width, img.Height, GraphicsUnit.Pixel);
var memStream = new MemoryStream()
bitmap.Save(memStream, img.RawFormat);
return Image.FromStream(memStream);
}
}
调用代码如下:
//加载图片文件流
using (var imgStream = new FileStream(文件名路径, FileMode.Open, FileAccess.Read, FileShare.Read))
{
//按指定尺寸压缩图片
var img = Compress(imgStream, new Size(280, 384));
//插入图片
InsertImage(img);
}
至此完美解决,插入了十多张10MB以上的图片也没有报错了