台灣最大程式設計社群網站
線上人數
1739
 
會員總數:241132
討論主題:186803
歡迎您免費加入會員
討論區列表 >> VB.NET >> SerialPort 接收PLC訊號
[ 變換順序 ]  
[我要回覆]
1
回應主題 加入我的關注話題 檢舉此篇討論 將提問者加入個人黑名單
SerialPort 接收PLC訊號
價值 : 30 QP  點閱數:313 回應數:9

樓主

魔力蘇打
門外漢
0 2
69 5
發送站內信

各位大家好!

使用VS 2010 用VB裡的SerialPort元件,
如何可以直接收到完整的三菱PLC回應碼(十六進制)
小弟目前已可以發送一段命令碼到PLC,
而PLC也會回傳一段字串出來。
假設要詢問PLC中D123地址的數值,
當傳送命令碼進去後,即可得到PLC
回應出「chr(2)D204chr(3)DD」
D204為真正所需使用的字串
其中chr(2)、chr(3)是三菱的通訊協議中
所使用的起始字元、終止字元。
而最後二碼的DD為計算出來的檢查碼。

但問題是若小弟詢問的速度小於一秒時,
所得到的回應碼就會不會是「chr(2)D204chr(3)DD」
像是會有漏讀字元的現像產生,
不知版上有無前輩遇過這樣的問題?


搜尋相關Tags的文章: [ SerialPort PLC 通訊 接收資料 ] ,
本篇文章發表於2017-08-31 21:49
別忘捐VP感謝幫助你的人 新手會員瞧一瞧
1樓
回應

P陳
檢舉此回應
Serial port 有緩衝區,所以不太會有漏讀字元的現象
請將您讀取 serial port 那段指令丟上來,才好判斷

詢問的速度小於一秒時??會有漏字??
可能原因 有時 rs232.DataReceived 一串回應字會分二次會觸發,只要加在一起即可。

本篇文章回覆於2017-08-31 22:37
== 簽名檔 ==
--未登入的會員無法查看對方簽名檔--
2樓
作者回應

魔力蘇打
檢舉此回應
我是使用下列這樣的方式來讀的。

Delegate Sub SetTextCallback(ByVal InputString As String)

Private Sub RS232_DataReceived(ByVal sender As Object, ByVal e As System.IO.Ports.SerialDataReceivedEventArgs) Handles xComport.DataReceived

If e.EventType <> SerialData.Chars Then Exit Sub '判斷接收的資訊是否為字元

'----- 資料是為字元
Dim inData As String = xComport.ReadExisting '取得字串

DisplayText(inData) '顯示資料
End Sub

Private Sub DisplayText(ByVal comData As String)

'如果呼叫txtReceive的是另外的執行緒,傳回True
If Me.T_Test_RxStr.InvokeRequired Then
'利用委派型別建立委派物件,並指定委派的函式
Dim d As New SetTextCallback(AddressOf ShowString)
'用大括號 {} 括住初始值,藉以初始化陣列的值。
Me.Invoke(d, New Object() {comData}) '以指定的引數清單叫用函式
'Me.Invoke(New EventHandler(AddressOf ShowString))

Else '相同的執行緒
ShowString(comData) '將收到的資料填入接收文字框中

End If

End Sub

Private Sub ShowString(ByVal comData As String)

T_Test_RxStr.Text = T_Test_RxStr.Text & "PLC返回:" & comData & vbCrLf


End Sub
本篇文章回覆於2017-09-01 08:47
== 簽名檔 ==
--未登入的會員無法查看對方簽名檔--
3樓
回應

P陳
檢舉此回應
這句跟我的不一樣
If e.EventType <> SerialData.Chars Then Exit Sub <--檢查是否為字元 人個人覺得怪怪的

If Rs232.BytesToRead = 0 Then Exit Sub <---檢查是否有資料待讀
本篇文章回覆於2017-09-01 11:30
== 簽名檔 ==
--未登入的會員無法查看對方簽名檔--
4樓
作者回應

魔力蘇打
檢舉此回應
P陳大!
不管是使你的方式或是我原先的方式,跑十次迴圈,出來的結果還是一樣,
還是會有捉錯的問題產生。
Private Sub But_Read_S_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles But_Read_S.Click
'取D123 設定值為1234
xRWDevice = "D123"
xPLCCommand = Chr(2) & "010F602" & Chr(3) & "72"
If (xComport.IsOpen = True) Then
xComport.Write(xPLCCommand)

End If

End Sub

Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

For i = 1 To 10
TimeDelay(400) '固意延時一些時間
Me.But_Read_S_Click(Me.But_Read_S, New System.EventArgs)
Next i
End Sub

出來結果:
PLC返回:D204DD
PLC返回:D
PLC返回:204DD
PLC返回:D204DD
PLC返回:D204DD
PLC返回:
PLC返回:D204DD
PLC返回:D204DD
PLC返回:D204
PLC返回:DD
PLC返回:
PLC返回:D204DD
PLC返回:D204DD
PLC返回:D20
PLC返回:4DD

本篇文章回覆於2017-09-01 17:18
== 簽名檔 ==
--未登入的會員無法查看對方簽名檔--
5樓
回應

P陳
檢舉此回應
資料沒有錯都有取到
在1樓就告知了
有時回應會被分成二段 來觸發 DataReceived

PLC返回:D
PLC返回:204DD =D204DD

PLC返回:D204
PLC返回:DD =D204DD

PLC返回:D20
PLC返回:4DD =D204DD

資料都對 都沒有漏接 (只是被分段而已)
本篇文章回覆於2017-09-01 21:42
== 簽名檔 ==
--未登入的會員無法查看對方簽名檔--
6樓
作者回應

魔力蘇打
檢舉此回應
P陳大

資料都對 都沒有漏接 (只是被分段而已)

這樣是意指要算字元數,然後再想辦法串接起來嗎?
本篇文章回覆於2017-09-01 22:14
== 簽名檔 ==
--未登入的會員無法查看對方簽名檔--
7樓
回應

P陳
檢舉此回應
1.將字串組合起來 (且不要自己加 VBCRLF)
T_Test_RxStr.Text = T_Test_RxStr.Text & comData

2.再來二個判斷方式 是否收完了
組合後 看有沒有 'DD'

組合後 看有沒有 vblf 或 VbCr 或 vbcrlf (以PLC 回給的為準,我沒有相關資源可以測)

本篇文章回覆於2017-09-02 07:13
== 簽名檔 ==
--未登入的會員無法查看對方簽名檔--
8樓
回應

P陳
檢舉此回應
還有您讀取PLC的方式則要由主動改成被動

1.主動是定時輪巡的 (有可能一次讀PLC的 二、三筆資料 也有可能沒有資料)

2.被動是 是當讀到了 DD 或 VBLF 時就觸發作某些事
本篇文章回覆於2017-09-02 07:24
== 簽名檔 ==
--未登入的會員無法查看對方簽名檔--
9樓
回應

誰是誰
檢舉此回應
海角點部落 serialport
建議你先看看這系列的文章
本篇文章回覆於2017-09-02 19:09
== 簽名檔 ==
--未登入的會員無法查看對方簽名檔--
[ 變換順序 ]   
1

回覆
如要回應,請先登入.