我又回来了,代码比上次多了。我可以在这里和那里参考我以前的问题,但这个问题是独立的
我设法说服我的雇主放弃我使用的专有串口通信库,所以现在我从头开始使用SerialPorts和BackgroundWorkers,以便我知道它们是如何工作的。
这是我的代码:
Imports System
Imports System.IO.Ports
Public Class Form1
'SerialPort Port and BackgroundWorker Worker declared in form
Delegate Sub AppendText_Delegate(ByVal txtBox As TextBox, ByVal str As String)
Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load
Port.PortName = ("COM9")
Port.BaudRate = 115200
Port.Parity = Parity.None
Port.StopBits = StopBits.One
Port.Handshake = Handshake.None
Port.ReadTimeout = 1000
Port.WriteTimeout = 1000
Port.Open()
AddHandler Port.DataReceived, AddressOf DataReceived
Worker.WorkerReportsProgress = True
Worker.WorkerSupportsCancellation = True
End Sub
Private Sub btnSend_Click(sender As System.Object, e As System.EventArgs) Handles btnSend.Click
Port.Write(txtInput.Text & vbCrLf)
End Sub
Private Sub DataReceived(sender As Object, e As SerialDataReceivedEventArgs)
Worker.RunWorkerAsync()
End Sub
Private Sub BackgroundWorker1_DoWork(sender As System.Object, e As System.ComponentModel.DoWorkEventArgs) Handles Worker.DoWork
If Worker.CancellationPending Then
e.Cancel = True
End If
AppendText_ThreadSafe(Me.txtOutput, Port.ReadLine())
End Sub
Private Sub AppendText_ThreadSafe(ByVal txtBox As TextBox, ByVal str As String)
If txtBox.InvokeRequired Then
Dim MyDelegate As New AppendText_Delegate(AddressOf AppendText_ThreadSafe)
Me.Invoke(MyDelegate, New Object() {txtBox, str})
Else
txtBox.AppendText(str)
End If
End Sub
End Class
此刻我真的不确定DataReceived
事件和BackgroundWorker
如何协同工作。我应该在哪里放置Worker.RunWorkerAsync()
,以便仅在DataReceived
事件被引发时调用DoWork()?我应该将两个事件绑定到同一个方法吗?
感谢您的帮助,并为此问题的简单性道歉。我刚刚开始使用BackgroundWorkers并且仍然可以找到我的立足点。可以这么说。
答案 0 :(得分:2)
DataReceived
类的SerialPort
事件是在后台线程上引发的,因此它不会阻止UI线程,因此您不需要在此使用BackgroundWorker
案件。因为在后台线程上调用DataReceived
,所以如果需要更新该处理程序中的任何UI控件,则需要使用Invoke
。