unity_小功能实现(客户端相互通信功能)
服务器端:在VS中新建项目,用于服务器的搭建
1 using System; 2 using System.Collections.Generic; 3 using System.Net.Sockets; 4 using System.Net; 5 using System.Text; 6 using System.Threading; 7 8 namespace Chat_Server 9 { 10 11 class Client 12 { 13 private Socket clientSocket; 14 private Thread t; 15 private byte[] data = new byte[1024];//接收数据容器 16 17 static List<Client> clientList = new List<Client>(); 18 19 static void Main(string[] args) 20 { 21 Socket tcpServer = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); 22 tcpServer.Bind(new IPEndPoint(IPAddress.Parse("192.168.43.231"), 7788)); 23 tcpServer.Listen(100); 24 25 Console.WriteLine("server is runing"); 26 27 //死循环:解决只能接收一个客户端的问题 28 while (true) 29 { 30 Socket clientSocket = tcpServer.Accept();//暂停,当有客户端连接时执行下面代码 31 Console.WriteLine("有一个客户端连接上了"); 32 Client client = new Client(clientSocket); 33 clientList.Add(client); 34 } 35 36 } 37 //是否连接成功,true为成功 38 public bool Connected 39 { 40 get { return clientSocket.Connected; } 41 } 42 public Client(Socket s) 43 { 44 clientSocket = s; 45 //启动一个线程 处理客户端的数据接收 46 t = new Thread(ReceiveMessage); 47 t.Start(); 48 } 49 //接收从客户端发送的消息 50 private void ReceiveMessage() 51 { 52 //一直接收客户端的数据 53 while (true) 54 { 55 //在接收数据之前 判断一下socket连接是否断开,等待10毫秒响应。断开连接时: 56 if (clientSocket.Poll(10, SelectMode.SelectRead)) 57 { 58 clientSocket.Close(); 59 break;//跳出循环 终止线程的执行 60 } 61 62 //接收消息 63 int length = clientSocket.Receive(data); 64 string message = Encoding.UTF8.GetString(data, 0, length); 65 66 BroadcastMessage(message); 67 Console.WriteLine("收到了消息:" + message); 68 } 69 } 70 //服务器向客户端发消息 71 public void SendMessage(string message) 72 { 73 byte[] data = Encoding.UTF8.GetBytes(message); 74 clientSocket.Send(data); 75 } 76 //服务器端向客户端广播消息 77 public static void BroadcastMessage(string message) 78 { 79 var notConnectedList = new List<Client>(); 80 foreach (var client in clientList) 81 { 82 if (client.Connected) //连接成功的广播消息 83 client.SendMessage(message); 84 else //连接失败的存储在另一个泛型集合里,方便后面移除 85 { 86 notConnectedList.Add(client); 87 } 88 } 89 //移除未连接的客户端 90 foreach (var temp in notConnectedList) 91 { 92 clientList.Remove(temp); 93 } 94 } 95 96 } 97 }
Unity客户端:
1 using UnityEngine; 2 using System.Collections; 3 using System.Net; 4 using System.Net.Sockets; 5 using System.Text; 6 using System.Threading; 7 8 public class ChatManager : MonoBehaviour 9 { 10 public string ipaddress = "192.168.43.231"; 11 public int port = 7788; 12 13 public UIInput textInput; 14 public UILabel chatLabel; 15 16 private Socket clientSocket; 17 private Thread t; 18 19 private byte[] data = new byte[1024];//数据容器 20 private string message = "";//接收到的消息容器 21 22 void Start () { 23 ConnectToServer(); 24 } 25 void Update () { 26 if (message != null && message != "") 27 { 28 chatLabel.text += "\n" + message; 29 message = "";//清空消息 30 } 31 } 32 void ConnectToServer() 33 { 34 clientSocket = new Socket(AddressFamily.InterNetwork,SocketType.Stream, ProtocolType.Tcp); 35 //跟服务器端建立连接 36 clientSocket.Connect( new IPEndPoint(IPAddress.Parse(ipaddress),port) ); 37 38 //创建一个新的线程 用来接收消息 39 t = new Thread(ReceiveMessage); 40 t.Start(); 41 } 42 //接收消息 43 void ReceiveMessage() 44 { 45 while (true) 46 { 47 if (clientSocket.Connected == false) 48 break; 49 int length = clientSocket.Receive(data); 50 message = Encoding.UTF8.GetString(data, 0, length); 51 52 } 53 } 54 //发消息 55 void SendMessage(string message) 56 { 57 byte[] data = Encoding.UTF8.GetBytes(message); 58 clientSocket.Send(data); 59 } 60 //发送按钮 61 public void OnSendButtonClick() 62 { 63 string value = textInput.value; 64 SendMessage(value); 65 textInput.value = ""; 66 } 67 68 void OnDestroy() 69 { 70 clientSocket.Shutdown(SocketShutdown.Both); 71 72 clientSocket.Close();//关闭连接 73 } 74 }
注意:我们在客户端和服务器端都使用了线程,线程的作用在于加快出库速度,提高性能。服务器端,使用线程接收数据,客户端使用线程发送数据。