EmguCV:PropertyChanged事件后,GUI上的BitmapSource没有更新:

问题描述 投票:0回答:1

我想简单地捕捉并在我的视图上显示相机图片,每秒更新一次。但是,在运行时,绑定到我的Bitmapsource CurrentFramest的图像容器是空白的。这是我的代码到目前为止(主要是从an answer of another thread with similar topic采用的:

public class CameraViewModel : ViewModelBase
{
    public CameraViewModel()
    {
        StartVideo();
    }

    private DispatcherTimer Timer { get; set; }

    private VideoCapture Capture { get; set; }

    private BitmapSource currentFrame;
    public BitmapSource CurrentFrame
    {
        get { return currentFrame; }
        set
        {
            if (currentFrame != value)
            {
                currentFrame = value;
                SetProperty(ref currentFrame, value);
            }
        }
    }

    private void StartVideo()
    {
        //CurrentFrame = new BitmapImage(new Uri("C:\\Users\\Johannes\\Pictures\\Camera Roll\\asdf.bmp")) as BitmapSource;
        Capture = new VideoCapture();
        Timer = new DispatcherTimer();
        //framerate of 10fps
        Timer.Interval = TimeSpan.FromMilliseconds(1000);
        Timer.Tick += new EventHandler(async (object s, EventArgs a) =>
        {
            //draw the image obtained from camera
            using (Image<Bgr, byte> frame = Capture.QueryFrame().ToImage<Bgr, byte>())
            {
                if (frame != null)
                {
                    CurrentFrame = ToBitmapSource(frame);
                }
            }
        });
        Timer.Start();
    }

    public static BitmapSource ToBitmapSource(IImage image)
    {
        using (System.Drawing.Bitmap source = image.Bitmap)
        {
            IntPtr ptr = source.GetHbitmap(); //obtain the Hbitmap
            BitmapSource bs = System.Windows.Interop.Imaging.CreateBitmapSourceFromHBitmap(ptr, IntPtr.Zero, Int32Rect.Empty, BitmapSizeOptions.FromEmptyOptions());
            DeleteObject(ptr); //release the HBitmap
            return bs;
        }
    }

    /// <summary>
    /// Delete a GDI object
    /// </summary>
    [DllImport("gdi32")]
    private static extern int DeleteObject(IntPtr o);

}

更好理解的一些事情:

  1. ViewModelBase类包含并处理INotifyPropertyChange事件。
  2. 数据绑定正在运行!我已经测试了它,通过在CurrentFrameMethod中为StartVideo()分配一个bmp文件 - 并且图像在运行时显示在GUI中。
  3. SetProperty()Method按预期每1000毫秒发射一次。
  4. 当我分配一个文件到CurrentFrame来测试数据绑定时,我看到它似乎是类型BitmapImage-也许这就是问题所在?但是根据我可以收集的信息,BitmapSource应该工作并在WPF视图中显示...
  5. 摄像机捕获的帧不为空。我试图将其直接写入图像文件,并按预期显示正确的内容。

编辑:为了完整性,这里也是视图的负责部分:

<UserControl.Resources>
    <ResourceDictionary>
        <local:CameraViewModel x:Key="vm" />
    </ResourceDictionary>
</UserControl.Resources>

<Grid DataContext="{StaticResource vm}">
    <Image Source="{Binding CurrentFrame}" HorizontalAlignment="Stretch" VerticalAlignment="Stretch"/>
</Grid>

EDIT2:Link to Github repository to view code

c# wpf binding emgucv
1个回答
2
投票

你不能设置

currentFrame = value;

在打电话之前

SetProperty(ref currentFrame, value);

因为检查

if (Object.Equals(storage, value)) return;

那将永远是真的。

像这样实现属性:

public BitmapSource CurrentFrame
{
    get { return currentFrame; }
    set { SetProperty(ref currentFrame, value); }
}
© www.soinside.com 2019 - 2024. All rights reserved.