C#上位机之—WinForm实现Socket异步通讯示例
程序员文章站
2023-12-26 21:40:09
工作中常用到的一些知识点,总是用完就忘,第一次尝试用博客记录下来,以备后用; Socket通讯,Socket(套接字)是基于TCP/IP通讯方式的封装好的类,调用时需要添加下面的服务引用: .......10 using System.Net; 11 using System.Net.Sockets ......
工作中常用到的一些知识点,总是用完就忘,第一次尝试用博客记录下来,以备后用;
socket通讯,socket(套接字)是基于tcp/ip通讯方式的封装好的类,调用时需要添加下面的服务引用:
.......
10 using system.net; 11 using system.net.sockets;
窗体页面搭建,上面为服务器区,下面为客户端区:
建立两个类,一个表示服务器,一个表示客户端,
首先建立服务器类:
1.声明变量:ip地址,端口号,endpoint,socket类,数据buffer等
1 string ip;//ip地址 2 string port;//端口号 3 ipendpoint endpoint;//网络端点 4 socket socserver;//侦听连接套接字 5 socket socclient;//通讯套接字 6 byte[] datareceived = new byte[50000]; 7 8 public delegate void delegatedisplaymsg(string type,string msg); 9 public delegatedisplaymsg ondisplay; 10 11 public socketserver() 12 { 13 socserver = new socket(addressfamily.internetwork, sockettype.stream, protocoltype.tcp); 14 }
2.侦听连接函数:
public void startlisten(string ip,string port) { this.ip = ip; this.port = port; endpoint = new ipendpoint(ipaddress.parse(this.ip), int.parse(port)); socserver.bind(endpoint); socserver.listen(0); socserver.beginaccept(new asynccallback(onclientconnect), null); showmsg("wait connect"); }
3.接受数据函数:
public void onclientconnect(iasyncresult asyn) { socclient = socserver.endaccept(asyn); waitfordata(); showmsg("client connected " + socclient.remoteendpoint.tostring()); } public void waitfordata() { if (socclient != null) socclient.beginreceive(datareceived, 0, datareceived.length, socketflags.none, new asynccallback(ondatareceived), null); } public void ondatareceived(iasyncresult asyn) { int datalength = socclient.endreceive(asyn); byte[] chars = new byte[datalength]; buffer.blockcopy(datareceived, 0, chars, 0, datalength); string msg = encoding.ascii.getstring(chars); showmsg("<=" + msg); waitfordata(); }
4.发送数据函数:
public void sendmsg(string msg) { byte[] data = encoding.default.getbytes(msg); socclient.send(data); showmsg("=>" + msg); }
然后建立客户端类:
1.声明变量
string ip;//ip地址 string port;//端口号 ipendpoint endpoint;//网络端点 socket socclient;//通讯套接字 byte[] datareceived = new byte[50000];//数据buffer public delegate void delegatedisplaymsg(string type,string msg); public delegatedisplaymsg ondisplay; public socketclient() { socclient = new socket(addressfamily.internetwork, sockettype.stream, protocoltype.tcp); }
2.连接服务器函数:
public void connect(string ip, string port) { this.ip = ip; this.port = port; endpoint = new ipendpoint(ipaddress.parse(this.ip), int.parse(port)); socclient.beginconnect(endpoint, new asynccallback(ontoconnected), null); }
3.接受数据函数:
public void ontoconnected(iasyncresult asyn) { socclient.endconnect(asyn); waitfordata(); showmsg("connect success"); } public void waitfordata() { if (socclient != null) socclient.beginreceive(datareceived, 0, datareceived.length, socketflags.none, new asynccallback(ondatareceived), null); } public void ondatareceived(iasyncresult asyn) { int datalenth = socclient.endreceive(asyn); byte[] chars = new byte[datalenth]; buffer.blockcopy(datareceived, 0, chars, 0, datalenth); string msg = encoding.ascii.getstring(chars); showmsg("<=" + msg); waitfordata(); }
4.发送数据函数:
public void sendmsg(string msg) { byte[] data = encoding.default.getbytes(msg); socclient.send(data); showmsg("=>" + msg); }
服务器类与客户端类,已经建立完成,下面对两个类进行实例化,并link窗体控件的事件函数,如下:
1.实例化:
public void init() { server = new socketserver(); client = new socketclient(); server.ondisplay += showmsg; client.ondisplay += showmsg; }
2.按钮点击事件:
private void btn_startlisten_click(object sender, eventargs e) { server.startlisten(txt_serverip.text.tostring(), txt_serverport.text.tostring()); btn_startlisten.backcolor = color.limegreen; } private void btn_connect_click(object sender, eventargs e) { client.connect(txt_clientip.text.tostring(), txt_clientport.text.tostring()); } private void btn_serversend_click(object sender, eventargs e) { button b = (button)sender; bool isserver = b.name.contains("server"); if (isserver) server.sendmsg(txt_servermsg.text.tostring()); else client.sendmsg(txt_clientmsg.text.tostring()); }
现在启动程序,测试发送接收功能是否正常
至此,一个简单的socket通讯模型已经完成,实际应用中还需考虑通讯异常,通讯协议,多个客户端通讯等事项,第一次写博,欢迎大家多多指正;