vb.net使用Winsock控件编程心得

来源:互联网 发布:成都真人cs 知乎 编辑:程序博客网 时间:2024/05/13 20:44

最近做一个数据采集器的服务器软件,数据采集器客户端采集到的数据是通过以太网传输到主机上的。由于时间紧,加上以前我有一点VB6的编程基础,我就用vb.net开发。用的控件还是VB6中的Winsock控件。

       在vb.net中要使用Winsock控件有两种方法:第一,就是先安装VB6,然后在vb.net的选项卡中,就可以添加Winsock控件了;第二,是先找到Winsock的文件mswinsck.ocx,复制到windows/system32/目录下,并注册。这样就可以使用Winsock控件了。

       我做的服务器用TCP传输,主要的控件有以下几个:一个按钮“btReceiveState”,一个Winsock“wskRtDatReceive”,两个TextBox“tbRemoteIP”和“tbRemotePort”

    '-------------------------------------------------------------------
    '点击“接收”按钮响应函数
    '-------------------------------------------------------------------
    Private Sub btReceiveState_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btReceiveState.Click
        '当“开始接收”时
        If bLinkState = False Then
                '参数过滤,防止有不正确的参数
                If tbRemoteIP.Text = "" Then
                    MsgBox("请输入IP地址", MsgBoxStyle.Critical, "Error!")
                    Exit Sub
                End If
                If nudRemotePort.Value < 1024 Or nudRemotePort.Value > 65535 Then
                    MsgBox("端口号的范围应该在1024-65535之间,请重新输入", MsgBoxStyle.Critical, "Error!")
                    nudRemotePort.Value = 1024
                    Exit Sub
                End If

                Try
                    '设置以太网参数,使用TCP连接,本地端口号为7777
                    wskRtDatReceive.Protocol = MSWinsockLib.ProtocolConstants.sckTCPProtocol
                    wskRtDatReceive.LocalPort = 7777
                    '监听端口
                    wskRtDatReceive.Listen()
                Catch ex As Exception
                    MsgBox(ex.ToString)
                    Exit Sub
                End Try

            '改变“接收”按钮状态
            btReceiveState.Text = "停止接收"
            bLinkState = True

            '当“停止接收”时
        Else
                Try
                '关闭以太网口

                wskRtDatReceive.Close()
            Catch ex As Exception
                MsgBox(ex.ToString)
                Exit Sub
            End Try


            '改变“接收”按钮状态
            btReceiveState.Text = "开始接收"
            bLinkState = False
        End If
    End Sub

#Region "以太网传输相关"
    '-------------------------------------------------------------------
    '客户端请求以太网传输,TCP的连接事件响应函数
    '-------------------------------------------------------------------
    Private Sub wskRtDatReceive_ConnectionRequest(ByVal sender As Object, ByVal e As AxMSWinsockLib.DMSWinsockControlEvents_ConnectionRequestEvent) Handles wskRtDatReceive.ConnectionRequest
        If wskRtDatReceive.RemoteHostIP <> tbRemoteIP.Text Then
            MsgBox(wskRtDatReceive.RemoteHostIP & " " & wskRtDatReceive.RemotePort & "请求被拒绝")
            Exit Sub
        End If
        If wskRtDatReceive.RemotePort <> nudRemotePort.Value Then
            MsgBox(wskRtDatReceive.RemoteHostIP & " " & wskRtDatReceive.RemotePort & "请求被拒绝")
            Exit Sub
        End If
        Try
            If wskRtDatReceive.SocketHandle <> -1 Then
                wskRtDatReceive.Close()
            End If
            wskRtDatReceive.Accept(e.requestID)

        Catch ex As Exception
            MsgBox(ex.ToString)
            Exit Sub
        End Try
    End Sub

    '-------------------------------------------------------------------
    '以太网,接收事件响应函数
    '-------------------------------------------------------------------
    Private Sub wskRtDatReceive_DataArrival(ByVal sender As Object, ByVal e As AxMSWinsockLib.DMSWinsockControlEvents_DataArrivalEvent) Handles wskRtDatReceive.DataArrival
        wskRtDatReceive.GetData(tbRdTest.Text)
    End Sub
#End Region

这里着重说明,蓝色代码的地方:

第一,是与VB6不同,vb.net将事件发生后所要传递的变量都放在e这个结构体中,并且作为第二个参数传递给事件响应函数,例如:

Private Sub wskRtDatReceive_ConnectionRequest(ByVal sender As Object, ByVal e As AxMSWinsockLib.DMSWinsockControlEvents_ConnectionRequestEvent) Handles

调用:

            wskRtDatReceive.Accept(e.requestID)

第二,是在使用Winsock的Accept方法时一定要先判断winsock的状态,以前在vb6中,使用State属性,现在使用SocketHandle属性,如果不等于-1,说明winsock的状体不是关闭状态,就调用Close方法,如

            If wskRtDatReceive.SocketHandle <> -1 Then
                wskRtDatReceive.Close()
            End If
            wskRtDatReceive.Accept(e.requestID)


否则会无法正确接收连接请求。

第三,是接收数据的GetData函数与VB6中的,有较大区别,(虽然我的程序没有用到区别之处)

在vb6中,可以在WinsockControlName_DataArrival中使用,如下语句接收

Dim ReadMsg As String
WinsockControlName.GetData ReadMsg

但是,在vb.net中上面语句会产生错误,在vb.net中,使用如下语句会达到同样的效果

Dim ReadMsg As Object
WinsockControlName.GetData(ReadMsg, vbString, 1500)

原创粉丝点击