簡體   English   中英

在WPF中使用Non-UI線程從Memory Stream設置圖像控件的源

[英]Setting source of an Image control from Memory Stream using Non-UI thread in WPF

我正在從指紋掃描儀捕獲圖像,並且想在Image控件中實時顯示捕獲的圖像。

//Onclick of a Button
 Thread WorkerThread = new Thread(new ThreadStart(CaptureThread));
 WorkerThread.Start();

因此,我如上所述創建了一個線程,並調用了從設備捕獲圖像並按如下所示設置Image控件源的方法。

private void CaptureThread()
    {
        m_bScanning = true;
        while (!m_bCancelOperation)
        {
            GetFrame();
            if (m_Frame != null)
            {

                    MyBitmapFile myFile = new MyBitmapFile(m_hDevice.ImageSize.Width, m_hDevice.ImageSize.Height, m_Frame);
                    MemoryStream BmpStream = new MemoryStream(myFile.BitmatFileData);
                    var imageSource = new BitmapImage();
                    imageSource.BeginInit();
                    imageSource.StreamSource = BmpStream;
                    imageSource.EndInit();
                    if (imgLivePic.Dispatcher.CheckAccess())
                    {
                        imgLivePic.Source = imageSource;
                    }
                    else
                    {
                        Action act = () => { imgLivePic.Source = imageSource; };
                        imgLivePic.Dispatcher.BeginInvoke(act);
                    }
            }

            Thread.Sleep(10);
        }
        m_bScanning = false;
    }

現在,當我運行該項目時,它會在Action act = () => { imgLivePic.Source = imageSource; }; Action act = () => { imgLivePic.Source = imageSource; }; 說“ 調用線程無法訪問該對象,因為另一個線程擁有它 ”。 我做了一些研究,發現如果我想在一個非UI線程上使用UI控件,我應該使用Dispatcher.Invoke方法,如您所見,我仍然可以,但是我仍然遇到相同的異常。 有人可以告訴我我在做什么錯嗎?

不一定需要在UI線程中創建BitmapImage。 如果您Freeze它,則以后可以從UI線程訪問它。 因此,您還將減少應用程序的資源消耗。 通常,如果可能,您應該嘗試凍結所有Freezable,尤其是位圖。

using (var bmpStream = new MemoryStream(myFile.BitmatFileData))
{
    imageSource.BeginInit();
    imageSource.StreamSource = bmpStream;
    imageSource.CacheOption = BitmapCacheOption.OnLoad;
    imageSource.EndInit();
}

imageSource.Freeze(); // here

if (imgLivePic.Dispatcher.CheckAccess())
{
    imgLivePic.Source = imageSource;
}
else
{
    Action act = () => { imgLivePic.Source = imageSource; };
    imgLivePic.Dispatcher.BeginInvoke(act);
}

BitmapImage本身需要在Dispatcher線程上構造。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM