大约10秒钟后,我得到一个例外,即内存不足。
此代码中出现错误,其中捕获图像并在UI上显示:
private void onFrameEvent(object sender, EventArgs e)
{
uEye.Camera Camera = sender as uEye.Camera;
Int32 s32MemID;
Camera.Memory.GetActive(out s32MemID);
// Read Camera bitmap
Bitmap bitmap;
Camera.Memory.ToBitmap(s32MemID, out bitmap);
Dispatcher.Invoke(new Action(() =>
{
// Convert bitmap to WPF-Image
var bmp = new Bitmap(bitmap);
var hBitmap = bmp.GetHbitmap();
System.Windows.Media.ImageSource wpfBitmap = System.Windows.Interop.Imaging.CreateBitmapSourceFromHBitmap(
hBitmap, IntPtr.Zero, Int32Rect.Empty,
BitmapSizeOptions.FromEmptyOptions());
image1.Source = wpfBitmap;
image1.Stretch = System.Windows.Media.Stretch.UniformToFill;
DeleteObject(hBitmap);
}));
}
如何避免如此庞大的内存访问?
答案 0 :(得分:0)
几年前,我对WPF和图像存在内存问题。它似乎是WPF中的一个错误。
以下代码似乎已经处理过了。差异似乎是你没有调用source.Freeze(),bitmap.Dispose()和GC.Collect()。我假设DeleteObject与我的相同。
public static class BitmapEx
{
/// <summary>
/// Converts a Bitmap object to WPF 'ImageSource' object and
/// garbage collects to Bitmap object.
/// </summary>
public static ImageSource ToImageSource(this Bitmap bitmap)
{
IntPtr hBitmap = bitmap.GetHbitmap();
try
{
ImageSource source = Imaging.CreateBitmapSourceFromHBitmap(
hBitmap,
IntPtr.Zero,
Int32Rect.Empty,
BitmapSizeOptions.FromEmptyOptions()
);
source.Freeze();
return source;
}
finally
{
if (!Win32Image.DeleteObject(hBitmap))
Debug.WriteLine("BitmapEx.ToImageSource() - Unable to Delete hBitmap");
bitmap.Dispose();
bitmap = null;
GC.Collect();
}
}
}
[SecurityPermission(SecurityAction.LinkDemand, Flags = SecurityPermissionFlag.UnmanagedCode)]
public static class Win32Image
{
public static bool DeleteObject(IntPtr handle)
{
return NativeMethods.DeleteObject(handle);
}
private static class NativeMethods
{
[DllImport("gdi32.dll", SetLastError = true)]
public static extern bool DeleteObject(IntPtr hObject);
}
}
在将大量图像(50+)加载到窗口时仍然遇到问题,事后看来这可能是由GC.Collect()调用引起的(我只是没有将图像加载到该窗口上)页)。如果遇到该问题,您可能会尝试限制调用GC.Collect()的次数。
[编辑]
调用GC.Collect()被认为是个坏主意(请参阅注释)。
尝试使用不带GC.Collect()的代码。如果它适合你,那么我将从这个答案中删除GC.Collect()行。