我正在从收发器读取温度值到串口,我希望这个值改变我的Visual Basic窗体中的标签值。该值每隔几秒就会改变一次。我使用下面的代码:
Me.dataReceived.Text &= [text]
其中dataReceived是我正在使用的标签,[text]是我从串口读取的数据。这会导致显示数据,但不会覆盖标签,而是将值相互写入。 (附加数据)。我试图删除&在=之前,但由于没有出现,这不起作用。关于我能做什么的任何想法?
我使用的代码如下:
'To receive data into the text field
Private Sub SerialPort1_DataReceived(ByVal sender As Object, ByVal e As System.IO.Ports.SerialDataReceivedEventArgs) Handles SerialPort1.DataReceived
While (SerialPort1.IsOpen)
ReceivedText(SerialPort1.ReadExisting()) 'This is called automatically every time data is received at the Serial Port
End While
End Sub
Private Sub ReceivedText(ByVal [text] As String)
Dim temperature As String
'This function compares the creating Thread's ID with the calling Thread's ID
If Me.dataReceived.InvokeRequired Then
Dim x As New SetTextCallback(AddressOf ReceivedText)
Me.Invoke(x, New Object() {(text)})
Else
'To output to the text box:
Me.dataReceived.Text = text
'To output to the label
temperature = text
Me.temp.Text = text
hmd.Text = temperature
End If
End Sub
答案 0 :(得分:5)
如果您要覆盖旧值,则不应使用&=
,而应使用=
来分配新值:
Me.dataReceived.Text = newText
&=
与Me.dataReceived.Text = Me.dataReceived.Text & newText
来自MSDN:
&=
运算符将其右侧的String表达式连接到 左侧的String变量或属性,并将结果赋给 左边的变量或属性。
答案 1 :(得分:1)
试试这个:
If (text IsNot Nothing) AndAlso (text.Trim().Length <> 0) Then
Me.dataReceived.Text = text
End If
我对SerialPort类并不熟悉,但我会尽力解释发生了什么。当新数据通过串行端口进入时,串行端口会引发数据接收事件。然后,您的代码将读取已收到的所有现有数据。当您调用ReadExisting方法时,它只返回到那时为止收到的内容。在返回之前,它不会等待所有数据进入。然后它调用ReceivedText方法,该方法将某些控件的值设置为接收的文本。 InvokeRequired和Invoke调用仅用于返回UI线程。显然,SerialPort的DataReceived事件可能是在一个单独的线程上引发的,因此您需要先返回UI线程,然后才能对表单上的任何控件执行任何操作。我建议的更改只是检查以确保在更改文本框的值之前收到的文本不为null或为空。关于代码的奇怪之处在于它继续从串口读取,直到它不再打开。我不认为你想这样做。相反,我认为在每个DataReceived事件中,您只需调用ReadExisting一次,然后只希望在下次收到更多数据时再次引发它。通过在循环中连续调用ReadExisting,如果没有更多数据要读取,它必须返回空字符串或空字符串,这就是文本框被清空的原因。
答案 2 :(得分:0)
&=
正在连接您的文字。使用=
覆盖标签。
Me.dataReceived.Text = text
答案 3 :(得分:0)
我不确定发生了什么,但设置text
时dataReceived.Text
可能没有值。试试这个,
Private Sub ReceivedText(ByVal datatext As String)
Me.Invoke(Sub()
'To output to the text box:
Me.dataReceived.Text = datatext
Me.temp.Text = datatext
hmd.Text = datatext
End Sub)
End If
End Sub
我将text
更改为datatext
,因为text
可能会与表单本地text
属性混淆。我还使用lambda将标签/文本框的文本属性设置移动到调用(请注意,此语法是新的,只能在VB 2010中使用)。我觉得你的invoke语句可能没有正确传递字符串值。我还删除了InvokeRequired
的检查,因为执行调用将在两种情况下都有效,看起来你可能每次都在进行线程调用。
如果为你编译,它应该有效。如果没有,可能永远不会调用RecievedText
。设置一些断点并逐步执行代码,以查看datatext
是否有值,并且ReceivedText
实际上已被调用。