在另一个类VB.nET的线程引发事件时更新GUI项



如何使用另一个类的线程正在接收的消息更新GUI中的数据

我有一个类,它有一个从服务器接收数据的线程。每当该线程从服务器收到消息时,就会引发一个事件。此事件在Starter类(包含GUI的主类)中处理。事件处理程序(比如DisplayData())必须显示其他类接收到的消息。我的代码就像这个

Class GUI
receiverObj = New Receiver()
Addhandler receiverObj.MessageAlert, Addressof DisplayData
...
...
Sub DisplayData()
Dim str As receiverObj.ReceiveData
lbEvents.Add.Items(str)   ' lbEvents is a ListBox inside the GUI that displays messages from Receiver 
End Sub
End Class

Class Receiver
Public Event MessageAlert()
Sub New ()
MyTcpClient = New TcpClient(hostIP, port)               
MyTcpClient.GetStream.BeginRead(ReceiveData, 0, PacketSize, AddressOf ReceiveStream, Nothing)
End Sub
Public Sub ReceiveStream(ByVal ar As IAsyncResult)
Dim ByteCount As Integer
Try
ByteCount = MyTcpClient.GetStream.EndRead(ar)
Dim t As New Threading.Thread(Sub() RaiseEvent MessageAlert())
MyTcpClient.GetStream.BeginRead(ReceiveData, 0, PacketSize, AddressOf ReceiveStream, Nothing)
End Sub
End Class

窗口崩溃或挂起,并且列表框不显示数据。抛出异常称

跨线程操作无效:控件xxx是从创建它的线程以外的线程访问的。

有人能提出解决这个错误的方法吗?如何用另一个类的线程正在接收的消息更新GUI中的数据?

对Windows应用程序GUI元素的更新必须在创建GUI的线程上进行。

为了解决这个问题,有一个名为Invoke的方法,它允许您激发委托,以确保控制权传递给GUI线程并执行您正在尝试的更新。

你需要一些东西来实现这一点:

  1. Delegate类型,如

    Delegate Sub MyGUIUpdateDelegate()
  2. 代表类型的变量

    Public myGUIUpdateDelegate as MyGUIUpdateDelegate
  3. 一种具有与委托匹配的签名并完成工作的方法:

    Public Sub MyGuiEventHandler()
    ' Do work on proper GUI thread, via Control.Invoke, ' such as listbox population
    If (Me.InvokeRequired) Then Me.Invoke( myGUIUpdateDelegate) Else // do control specific work, we're on the GUI thread here End If

    End Sub

  4. An assignment of the event handler to your delegate:

    myGUIUpdateDelegate = New MyGuiUpdateDelegate(AddressOf myForm.MyGuiEventHandler)

  5. 通过Control.Invoke从事件线程调用正确的线程(假设表单实例变量名为myForm):

    myForm.Invoke(myForm.myGUIUpdateDelegate);

这至少是一个可以帮助您入门的框架。这个想法是,想要引发更新的后台线程不应该(实际上也不能)进行直接的GUI更新。启动到GUI线程的上下文切换的正确方法是调用Invoke方法,在正确的GUI线程上调用GUI更新程序。

此外,如果需要将参数传递给委托,只需更改您定义的委托的签名以包括参数,并修改Invoke方法以提供处理程序中的参数,以及Invoke的第二个参数。

希望这能有所帮助。

相关内容

  • 没有找到相关文章

最新更新