我正在尝试编写一个WPF应用程序,使用线程在运行时更新一组文本框和标签,但问题是每当线程试图更新文本框和标签时,都会出现以下错误:“调用线程无法访问此对象,因为不同的线程拥有它。” 是否可能在运行时更新控件?
我正在尝试编写一个WPF应用程序,使用线程在运行时更新一组文本框和标签,但问题是每当线程试图更新文本框和标签时,都会出现以下错误:“调用线程无法访问此对象,因为不同的线程拥有它。” 是否可能在运行时更新控件?
是的,但是你必须使用Dispatcher.Invoke在UI线程中更新UI元素。
C#示例:不要使用以下代码:
myTextBox.Text = myText;
使用
Dispatcher.Invoke(new Action(() => myTextBox.Text = myText));
VB.NET(版本4之前)不支持匿名方法,因此您需要使用匿名函数来解决:
Dispatcher.Invoke(Function() UpdateMyTextBox(myText))
...
Function UpdateMyTextBox(ByVal text As String) As Object
myTextBox.Text = text
Return Nothing
End Function
或者,您可以使用BackgroundWorker类来启动后台线程,该类支持通过ProgressChanged
和RunWorkerCompleted
事件在UI中更新:两个事件都会自动在UI线程中触发。这里有一个使用BackgroundWorker的示例:SO问题1754827。
WPF中的控件有一个名为Dispatcher
的属性,你可以在其上调用Invoke
方法,并传递一个委托,其中包含你想要在GUI线程上下文中执行的代码。
myCheckBox.Dispatcher.Invoke(DispatcherPriority.Normal,
() => myCheckBox.IsChecked = true);