gpt4 book ai didi

c# - 如何在后台加载图像?

转载 作者:行者123 更新时间:2023-11-30 13:21:26 26 4
gpt4 key购买 nike

我正在尝试在后台加载图像,然后更新 UI。我整天都在玩这个,我不知道我错过了什么。我不断收到以下错误:

"The calling thread cannot access this object because a different thread owns it."

我搜索了一个又一个示例,但似乎找不到答案。我还将接触 UI 的代码包装在另一个 BeginInvoke 中。

更新 3:故事的寓意。 ImageSource 不是线程安全的访问。

更新 2:这必须是一个简单的解决方案 :)。我尝试了克隆,但没有成功,但我确实收到了一个不同的错误:“调用的目标抛出了异常。”

更新 1:我尝试了 BackgroundWorker,但我仍然遇到同样的错误,但它发生在 brush.ImageSource.Height 上。我是否正确地向 UI 发出信号?有什么建议吗?

这是我的 XAML:

<Window x:Class="Slideshow.Show"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<DockPanel>
<Canvas Background="Black" Name="canvas">
<Viewbox Name="background" Stretch="Uniform">
<Rectangle name="background" />
</Viewbox>
</Canvas>
</DockPanel>
</Window>

下面是一些背后的代码:

namespace Slideshow
{
public class Show
{
public Show()
{
BackgroundWorker bw = new BackgroundWorker();
bw.DoWork += new DoWorkEventHandler(bw_DoWork);
bw.RunWorkerCompleted +=
new RunWorkerCompletedEventHandler(bw_RunWorkerCompleted);
bw.RunWorkerAsync();
}

void bw_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
BitmapSource bitmap = e.Result as BitmapSource;

if (bitmap != null)
{
this.Dispatcher.BeginInvoke(DispatcherPriority.Normal
(ThreadStart)delegate()
{
Image image = new Image();
image.Source = bitmap;
background.Child = image;
});
}
}

void bw_DoWork(object sender, DoWorkEventArgs e)
{
BitmapSource bitmapSource = CreateBrush(GetRandomFile());
e.Result = bitmapSource;
}
}
}

最佳答案

我倾向于使用ThreadPool.QueueUserWorkItem加载图像,然后当操作完成时,我使用线程安全的 Dispatcher 回调到 UI 线程目的。图像源不是线程安全的,您将不得不使用类似JpegBitmapDecoder 的东西,还有一个PngBitmapDecoder

例如:

public Window()
{
InitializeComponent();

ThreadPool.QueueUserWorkItem(LoadImage,
"http://z.about.com/d/animatedtv/1/0/1/m/simp2006_HomerArmsCrossed_f.jpg");
}

public void LoadImage(object uri)
{
var decoder = new JpegBitmapDecoder(new Uri(uri.ToString()), BitmapCreateOptions.PreservePixelFormat, BitmapCacheOption.OnLoad);
decoder.Frames[0].Freeze();
this.Dispatcher.Invoke(DispatcherPriority.Send, new Action<ImageSource>(SetImage), decoder.Frames[0]);
}

public void SetImage(ImageSource source)
{
this.BackgroundImage.Source = source;
}

关于c# - 如何在后台加载图像?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/716472/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com