用VB编写modbus源代码的过程
今天是周六,现在刚从单位自愿加班回来。为什么自愿加班呢?因为自己和老板夸下海口说:一个礼拜把modbus上位机程序写好(也就是这个礼拜拉)。现在终于把这个程序写好拉。
感想很多啊!该如何说起呢?我语文不好,把自己想表达的意思说出来就行拉。
首先:还是那句话:一切得靠自己!上周一时,老板说让我做个modbus界面,我想:这个简单啊。不就是串口收发么?于是我计划安排上写了1个礼拜搞定。然后开始安装DELPHI(我在单位一直搞C编程,机子没有装这些),完后就打开我那曾经熟悉的界面。恩?怎么看似熟悉的界面怎么这么陌生呢/于是上网找资料。。。这个3天的期间我感慨好深啊:因为我大四学习的DELPHI,所以我感觉这个还熟悉点,可是当时做课程设计的时候也没有用过串口,这个串口编程咋得和MCU串口不一样呢?它就是不一样!晕晕。上网找SPCOMM。。。,学习了一天也不会用。于是徒劳了3天也没有效果。转眼就到了周四,我心里那个急呀。唉!还是忍痛抛弃delphi吧!为什么呢?它没有自带串口控件,下载并安装了还是出错啊。
VB好象是我大二学的,具体时间我也忘了,反正就记得做课设的时候用它连个ACCESS实现了插入删除查询工作。以后知道这个周四我也没有用过,甚至没有见到过它的界面。我选择它一个因为我选择,我喜欢。更重要的是它安装了自带串口控件,不用下载什么的了,用起来实打实的心里有底。
大家现在知道我的底子了吧?周四我借公司里的一本VB书看了一天的串口,然后心理有底了,周五动手一天,收获很大,今天早晨8点起床,心理还琢磨着程序的事情,由于家里没有实验仪器,于是打算去公司,一直做到现在,终于搞定拉。这个礼拜上网找源代码的时候看着好多像我一样找源码的人发帖子要源程序,但是大多只是网页写了一大堆代码。没有用!为什么呢?你怎么知道人家用什么控件,什么功能呢?还是老老实实的自己写吧。没什么的,很简单的啊。说实话,这个程序只要你把浮躁的心放下来写就可以了。我自从毕业一直没有做过WINDOWS编程,都是直接对单片机的,上学那会也是天天乐呼呼的,没学到什
么东西,就这样我还不是搞定了吗?(当然这个建立在看网上那堆源程序的基础上)。
现在我就把这个程序发在网页上,这个程序已经调通了,写在这里的目的是让大家做个程序参考,你也不知道我界面上的控件,所以没有必要复制粘贴。(不是我小气,是因为这个工程涉及到公司机密,这个产品还没有送检,所以不给。 发布啊,望谅解)欢迎大家和我讨论,谢谢! 'Global Data Definitions
Dim MyHandle As Long 'Handle to Connection
Dim MyStatus As Integer 'Status returned from mbMasterV7 Control Dim Slave As Integer 'Slave, Cmd, Address, & Length Dim Cmd As Integer Dim Address As Long Dim Length As Integer Dim LoopbackMsg(20) As Byte
Public Sub show_status(ErrCode As Integer) If (ErrCode = 0) Then
STATUS.Text = \正常通行ing\ ElseIf (ErrCode < 255) Then
' STATUS.Text = \ STATUS.Text = \从设备没有响应\ ElseIf (ErrCode = 256) Then STATUS.Text = \无效连接\ ElseIf (ErrCode = 257) Then STATUS.Text = \消息超时\ ElseIf (ErrCode = 258) Then STATUS.Text = \无效地址\ ElseIf (ErrCode = 259) Then STATUS.Text = \无效从设备地址\ ElseIf (ErrCode = 260) Then
STATUS.Text = \无效数据长度\ ElseIf (ErrCode = 261) Then
STATUS.Text = \不支持modbus命令格式\ ElseIf (ErrCode = 263) Then STATUS.Text = \从设备超时\ ElseIf (ErrCode = 264) Then STATUS.Text = \无效传输模式\ ElseIf (ErrCode = 265) Then STATUS.Text = \校验错误\ ElseIf (ErrCode = 266) Then STATUS.Text = \没有建立连接\ ElseIf (ErrCode = 267) Then STATUS.Text = \无效从设备响应\ ElseIf (ErrCode = 271) Then STATUS.Text = \演示时间到\ ElseIf (ErrCode = 272) Then
STATUS.Text = \无效 modbus/TCP 命令\ End If End Sub
' Hide the contrtol when the form loads Private Sub Form_Activate() MbMasterV71.HideControl End Sub
' Handler for the CONNECT SERIAL Button Private Sub ConnectSerial_Click() ' Connect to COMM Port
MbMasterV71.BaudRate = 9600 '9600 Baud
MbMasterV71.Parity = 0 '0=NOPARITY, 1=ODDPARITY, 2=EVENPARITY,
3=MARKPARITY, 4=SPACEPARITY
MbMasterV71.DataBits = 8 '8 DataBits
MbMasterV71.StopBits = 0 '0=ONESTOPBIT, 1=ONE5STOPBITS, 2=TWOSTOPBITS
MbMasterV71.TimeOut = 2000 '2000 msec
MbMasterV71.TransmissionMode = 1 '0=ASCII, 1=RTU
MyHandle = MbMasterV71.ConnectSerial(1) ' Connect to COMM Port 1 If MyHandle > 0 Then
' Connection was successful
' (This example only allows a single connection) ' Disable All Connection Buttons
' Enable the Read, Write & Disconnect Buttons ConnectSerial.Enabled = False ConnectTAPI.Enabled = False ConnectTCP.Enabled = False Disconnect.Enabled = True ' LoopBackTst.Enabled = True STATUS.Text = \正在连接ing\ READMODBUS.Enabled = True WRITEMODBUS.Enabled = True Else
'Connection Attempt Failed
'(Another application must have control of the COM Port) STATUS.Text = \串口忙,请稍候\ End If End Sub
' Handler for the CONNECT TAPI Button Private Sub ConnectTAPI_Click()
Dim nTAPIDevices As Long Dim TAPIDevice As String
'Go through the motions of getting the TAPI Device List nTAPIDevices = MbMasterV71.NumberOfTAPIDevices() TAPIDevice = MbMasterV71.GetTAPIDeviceName(0) 'Setup the phone number to dial MbMasterV71.PhoneNumber = \ 'Dial the call
MyHandle = MbMasterV71.DialTAPIDevice(0) If MyHandle > 0 Then
'Call should be in progress now 'Don't enable the Read & Write Buttons 'until we get the CallEstablished Event STATUS.Text = \正在连接ing\ ConnectSerial.Enabled = False ConnectTAPI.Enabled = False ConnectTCP.Enabled = False Disconnect.Enabled = False 'LoopBackTst.Enabled = False READMODBUS.Enabled = False WRITEMODBUS.Enabled = False Else
STATUS.Text = \没有连接\ End If End Sub
' Handler for the CONNECT TCP Button Private Sub ConnectTCP_Click() ' Select the Device to connec to
' In this case use the IP Loopback address to
' connect to the local machine MbMasterV71.TCPDevice = \
MyHandle = MbMasterV71.ConnectModbusTCP(502) If MyHandle > 0 Then
'Connection should be in progress now 'Don't enable the Read & Write Buttons 'until we get the CallEstablished Event STATUS.Text = \正在连接ing\ ConnectSerial.Enabled = False ConnectTAPI.Enabled = False ConnectTCP.Enabled = False Disconnect.Enabled = False ' LoopBackTst.Enabled = False READMODBUS.Enabled = False WRITEMODBUS.Enabled = False Else
STATUS.Text = \没有连接\ End If End Sub
' ConnectionEstablished Event Handler
' Initiated from either ConnectModbusTCP() or DialTAPIDevice() Private Sub MbMasterV71_ConnectionEstablished(ByVal hConnect As Long) 'Enable the Disconnect Button 'Enable Read & Write Buttons ConnectSerial.Enabled = False ConnectTAPI.Enabled = False ConnectTCP.Enabled = False
Disconnect.Enabled = True 'LoopBackTst.Enabled = True STATUS.Text = \正常通信ing\ READMODBUS.Enabled = True WRITEMODBUS.Enabled = True End Sub
' ConnectionDropped Event Handler
Private Sub MbMasterV71_ConnectionDropped(ByVal hConnect As Long) 'Either the TCP or TAPI connection attempt failed
'or something has happened to abort the connection after it 'has been established for a while.
'In either case we're now disconnected so enable the 'buttons accordingly MyHandle = -1
ConnectSerial.Enabled = True ConnectTAPI.Enabled = True ConnectTCP.Enabled = True Disconnect.Enabled = False 'LoopBackTst.Enabled = False STATUS.Text = \没有连接\ READMODBUS.Enabled = False WRITEMODBUS.Enabled = False End Sub
' Handler for the DISCONNECT Button Private Sub Disconnect_Click() 'Tell the control to Disconnect
MyStatus = MbMasterV71.Disconnect(MyHandle) MyHandle = -1
'ReEnable the Connect Buttons for new connection attempt ConnectSerial.Enabled = True ConnectTAPI.Enabled = True ConnectTCP.Enabled = True Disconnect.Enabled = False 'LoopBackTst.Enabled = False STATUS.Text = \没有连接\ READMODBUS.Enabled = False WRITEMODBUS.Enabled = False End Sub
Private Sub Frame2_DragDrop(Source As Control, X As Single, Y As Single) End Sub
' Handler for the READ Button Private Sub READMODBUS_Click()
'Get the Slave Node Address, Modbus Command, Address & Length ' from the appropriate Edit controls Slave = NODEADDRESS.Text Cmd = POINTTYPE.Text Address = READADDRESS.Text Length = READLENGTH.Text
'We must remember these parameters so we can use 'them in the ReadResponse method to make sure we 'get what we ask for '
'Initiate the Read Request
MyStatus = MbMasterV71.PollModbus(MyHandle, Slave, Cmd, Address, Length)
'Check the status to make sure the request went out.
If MyStatus = 0 Then
STATUS.Text = \串口忙,请稍侯\ Else
show_status (MyStatus) End If End Sub
'Process the Slave Read Response Message 'Modbus_Master SlaveReadResponse Event Handler
Private Sub MbMasterV71_SlaveReadResponse(ByVal hConnect As Long) Dim MyData As Long Dim i As Integer
' Read the data returned from the slave ' and update the text controls For i = 0 To Length - 1
MyStatus = MbMasterV71.ReadResults(hConnect, Slave, Cmd, Address + i, MyData)
show_status (MyStatus) If MyStatus = 0 Then 'Text1(i).Text = MyData
If i = 0 Or i = 8 Or i = 16 Then Text1(i).Text = MyData * 系数 End If
If i = 2 Or i = 10 Or i = 18 Then Text1(i).Text = MyData * 系数 End If
If i = 4 Or i = 12 Or i = 20 Or i = 6 Or i = 14 Or i = 22 Then Text1(i).Text = MyData * 系数 End If
If i = 28 Or i = 30 Then '3P,3Q
Text1(i).Text = MyData * 系数 End If
If i = 29 Then 'cosq
Text1(i).Text = MyData * 系数 End If
If i = 27 Then 'F
Text1(i).Text = MyData * 系数 End If
If i = 1 Or i = 5 Or i = 7 Or i = 9 Or i = 13 Or i = 15 Or i = 17 Or i = 21 Or i = 23 Or i = 25 Or i = 23 Or i = 26 Or i = 31 Then Text1(i).Text = 0 '没有测量的量默认为0 End If ' Else
' Text1(i).Text = \ End If Next i End Sub
Private Sub WRITEMODBUS_Click() Dim IsRegister As Boolean Dim i As Integer Dim junk As Integer
Slave = NODEADDRESS.Text Address = WRITEADDRESS.Text
Length = WRITELENGTH.Text If Length > 200 Then Length = 200 End If
For i = 0 To Length - 1
junk = MbMasterV71.FillWriteBuffer(MyHandle, i, PATTERN.Text) Next i
If POINTTYPE.Text < 2 Then If Length = 1 Then
Cmd = 5 'write single coil Else
Cmd = 15 'write multiple coils End If Else
If Length = 1 Then
Cmd = 6 'write single register Else
Cmd = 16 'write multiple registers End If End If
MyStatus = MbMasterV71.WRITEMODBUS(MyHandle, Slave, Cmd, Address, Length)
' Make sure the write request was transmitted If MyStatus = 0 Then
STATUS.Text = \串口忙,请稍侯\ Else
show_status (MyStatus) End If
End Sub
'Process the Slave Write Response Message 'Modbus_Master SlaveWriteResponse Event Handler
Private Sub MbMasterV71_SlaveWriteResponse(ByVal hConnect As Long) 'read the results of the write request
MyStatus = MbMasterV71.WriteResults(hConnect, Slave, Cmd, Address, Length)
' and update the status display show_status (MyStatus) End Sub
Private Sub LoopBackTst_Click() Slave = NODEADDRESS.Text Cmd = 8
MyStatus = MbMasterV71.FillUserMsgBuffer(MyHandle, 0, Slave) MyStatus = MbMasterV71.FillUserMsgBuffer(MyHandle, 1, Cmd) MyStatus = MbMasterV71.FillUserMsgBuffer(MyHandle, 2, 0) MyStatus = MbMasterV71.FillUserMsgBuffer(MyHandle, 3, 0) MyStatus = MbMasterV71.FillUserMsgBuffer(MyHandle, 4, 0) MyStatus = MbMasterV71.FillUserMsgBuffer(MyHandle, 5, 0)
MyStatus = MbMasterV71.SendUserMsg(MyHandle, 6) 'Check the status to make sure the request went out. If MyStatus = 0 Then
STATUS.Text = \串口忙,请稍侯\ Else
show_status (MyStatus)
End If End Sub
Private Sub MbMasterV71_UserMsgResponse(ByVal hConnect As Long, ByVal NumberOfBytes As Long) Dim temp As Integer
If NumberOfBytes > 0 Then
For i = 0 To NumberOfBytes - 1
MyStatus = MbMasterV71.ReadUserMsgResponse(hConnect, i, temp)
LoopbackMsg(i) = temp Next i
STATUS.Text = LoopbackMsg End If End Sub