【发布时间】:2012-05-29 12:34:19
【问题描述】:
我正在使用 AForge.NET 库定期从我的网络摄像头获取图像数据。出于调试原因,我必须将过滤后的图像绘制到屏幕上。 目前,我的主窗体上有 6 个 WPF 图像,每秒钟我都会处理一个事件,该事件给了我一个 UnmanagedImage,我将其转换为 System.Drawing.Bitmap,然后转换为 BitmapSource - 我的代码如下所示:
private void OnImageFiltered(object sender, FilterEventArgs e)
{
var bitmapSource = e.UnmanagedImage.ToManagedImage().ToBitmapSource();
pictureBox.Source = bitmapSource;
}
但正如我之前所说,我有 6 张图片,这会减慢整个程序的速度。 我怎样才能让它更快?
我的 ToBitmapSource 扩展方法在这里:
public static BitmapSource ToBitmapSource(this System.Drawing.Image source)
{
System.Drawing.Bitmap bitmap = new System.Drawing.Bitmap(source);
var bitSrc = bitmap.ToBitmapSource();
bitmap.Dispose();
bitmap = null;
return bitSrc;
}
【问题讨论】:
-
我相信
bitmap.ToBitmapSource()是最昂贵的组件,但您可以使用 bool 参数构造函数节省少量开销,如var bitmapSource = e.UnmanagedImage.ToManagedImage(false).ToBitmapSource();。由于它是事件驱动的,它很可能已经在后台线程上发生,对吗? -
整个事情(我的意思是事件处理程序代码)在 Dispatcher.Invoke 中,使用 DispatcherPriority.Send,因为它在后台线程上运行。
-
所以我会对解决此类问题的“最佳实践”感兴趣?例如,在一个 WPF 表单中绘制 6 个网络摄像头?也许我在重置图像源时完全错了......
-
在后台处理图像不会使程序“更快”,但它会使它看起来更具响应性。尝试在后台线程中获取
BitmapSource,然后只通过Dispatcher.Invoke设置pictureBox.Source。 -
但是当我在后台线程上调用 ToBitmapSource 时,我得到一个错误:“调用线程无法访问这个对象*,因为不同的线程拥有它”(*该对象是 BitmapSource 对象,它是在这种情况下是一个 InteropBitmap)
标签: c# .net wpf performance imagesource