Unity中Socket的使用

Socket的使用

在unity中使用Socket连接服务器进行消息发送和接收

客户端逻辑

脚步TcpSocket.cs


public class TcpSocket
{
	private Socket mSocket;
	private byte[] mData;
	private int mOffect;
	/// <summary>
	///	一次性接收数据的最大字节
	/// </summary>
	private int mSize = 1024*1024*1;
	
	
	public TcpSocket(string varIp,int varPort)
	{
		IPEndPoint point = new IPEndPoint(IPAddress.Parse(varIp), varPort);
		mSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
		mSocket.BeginConnect(point, Connect, null);
	}
	~TcpSocket()
	{
		CloseConnect();
	}
	/// <summary>
	///	连接服务器结果
	/// </summary>
	private void Connect(IAsyncResult result)
	{
		if(result.IsCompleted)
		{
			//连接成功
			mData = new byte[mSize];
			//开启数据接收的异步监听
			mSocket.BeginReceive(mData, mOffect, mSize - mOffect, SocketFlags.None, Receive, null);
		}
		else
		{
			//连接失败
		}
	}
	/// <summary>
	///	接收到服务器数据
	/// </summary>
	private void Receive(IAsyncResult result)
	{
		//结束当前监听进行数据处理
		int size = mSocket.EndReceive(result, out SocketError error);
		if(error == 0)
		{
			//接收数据成功
			if(size != 0)
			{
				//当数据大小不为0时进行数据内容处理
				//此处理方式为测试数据
				byte[] bytes = new byte[size + mOffect];
				Array.Copy(mData, 0, bytes, 0, size + mOffect);
				string message = Encoding.UTF8.GetString(bytes);
				
				Debug.LogError(message);
			}
			//开启数据接收的异步监听
			mSocket.BeginReceive(mData, mOffect, mSize - mOffect, SocketFlags.None, Receive, null);
		}
		else
		{
			//接收数据发生错误-自动断开连接
			CloseConnect();
		}
	}
	/// <summary>
	///	发生数据给服务器
	/// </summary>
	public void Send(byte[] bytes)
	{
		try
		{
			mSocket.Send(bytes);
		}
		catch(Exception exp)
		{
			Debug.LogError(exp.Message);
			//发生数据异常-自动断开连接
			CloseConnect();
		}
	}
	/// <summary>
	///	关闭服务器连接
	/// </summary>
	public void CloseConnect()
	{
		if(mSocket.Connected)
		{
			mSocket.Close();
		}
	}
}

测试脚本


public void Client:MonoBehaviour
{
	TcpSocket mTcpSocket;

	public void Init()
	{
		mTcpSocket = new TcpSocket("127.0.0.1", 4488);
	}
	public void Send()
	{
		mTcpSocket.Send(Encoding.UTF8.GetBytes("测试数据"));
	}
	
}

服务器端数据

控制客户端的Socke的脚本ClientSocket.cs


public class ClientSocket
{
 	Socket mSocket;
 	byte[] mData;
 	int mOffect;
	/// <summary>
	///	一次性接收数据的最大字节
	/// </summary>
 	int mSize = 1024*1024*1;
	
	Action<ClientSocket> CloseCallBack;
	
	public ClientSocket(Socket varSocket, Action<ClientSocket> action)
	{
		CloseCallBack = action;
		mSocket = varSocket;
		//获取当前连接的客户端的IP和端口
		IPEndPoint  IPEnd = mSocket.RemoteEndPoint as IPEndPoint;
		//IP地址
 		string IP = IPEnd.Address.ToString();
 		//Port端口
 		int Port = IPEnd.Port;
 		
		mData = new byte[mSize];
		//开启数据接口监听
		mSocket.BeginReceive(mData, mOffect, mSize - mOffect, SocketFlags.None, Receive, null);
	}
	private void Receive(IAsyncResult result)
	{
		//结束当前监听进行数据处理
		int size = mSocket.EndReceive(result, out SocketError error);
		if(error == 0)
		{
			//接收数据成功
			if(size != 0)
			{
				//当数据大小不为0时进行数据内容处理
				byte[] bytes = new byte[size + mOffect];
				Array.Copy(mData, 0, bytes, 0, size + mOffect);
				string message = Encoding.UTF8.GetString(bytes);
				
				Debug.LogError(message);
			}
			//开启数据接收的异步监听
			mSocket.BeginReceive(mData, mOffect, mSize - mOffect, SocketFlags.None, Receive, null);
		}
		else
		{
			//接收数据发生错误-自动断开连接
			CloseConnect();
		}
	}
	
	/// <summary>
	///	发生数据给指定客服端
	/// </summary>
	public void Send(byte[] bytes)
	{
		try
		{
			mSocket.Send(bytes);
		}
		catch(Exception exp)
		{
			//发生数据异常-自动断开连接
			CloseConnect();
		}
	}
	/// <summary>
	///	关闭指定客服端连接
	/// </summary>
	public void CloseConnect()
	{
		if(mSocket.Connected)
		{
			CloseCallBack(this);
			mSocket.Close();
		}
	}
}

服务器Socket的脚本ServerSocket.cs


public class ServerSocket
{
	Socket mSocket;
	List<ClientSocket> mClients = new List<ClientSocket>();
	
	/// <summary>
	///	启动服务器
	/// </summary>
	///	<param name="varIP">服务器的IP</param>
	///	<param name="varPort">服务器的端口</param>
	public ServerSocket(string varIP, int varPort)
	{
		mSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
		mSocket.Bind(new IPEndPoint(IPAddress.Parse(varIP), varPort));
		//开启连接监听并设置最大连接数
		mSocket.Listen(100);
		//开启连接响应监听
		mSocket.BeginAccept(Accept, null);
	}
	private void Accept(IAsyncResult result)
	{
		//收到连接后结束连接监听并获取当前连接的客户端Socket
		Socket TempClient = mSocket.EndAccept(result);
		
		 ClientSocket client = new ClientSocket(TempClient, CloseClient);
		 //将连接的客户端记录下来
		 mClients.Add(client);
		 //重新开启客户端的连接监听
		mSocket.BeginAccept(Accept, null);
	}
	/// <summary>
	///	关闭客户端连接
	/// </summary>
	private void CloseClient(ClientSocket  client)
	{
		if(mClients.Contains(client))
		{
			mClients.Remove(client);
		}
	}
}


测试脚本


class Program
{
	static void Main(string[] args)
	{
		ServerSocket socket = new ServerSocket("127.0.0.1", 4488);
		Console.Read();
	}
}

  • 1
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Unity使用socket可以通过引入socket模块来实现。首先需要构造一个socket对象,可以使用socket.socket()方法来创建。该方法需要传入两个参数,分别是socket.AF_INET和socket.SOCK_STREAM,分别表示使用IPv4地址和流式Socket。\[1\] 在Unity常用到的Socket方法包括: - IPAddress类:包含了一个IP地址 - IPEndPoint类:包含了一对IP地址和端口号 - Socket类的方法: - 创建一个Socket对象:Socket() - 绑定一个本地的IP和端口号:Bind() - 让Socket侦听传入的连接尝试,并指定侦听队列容量:Listen() - 初始化与另一个Socket的连接:Connect() - 接收连接并返回一个新的socket:Accept() - 输出数据到Socket:Send() - 从Socket读取数据:Receive() - 关闭Socket(销毁连接):Close()\[2\] 需要注意的是,至少要定义一个要连接的远程主机的IP和端口号。端口号必须在1和65535之间,最好在1024以后。要连接的远程主机必须正在监听指定端口,也就是说你无法随意连接远程主机。一个Socket一次只能连接一台主机。Socket关闭后无法再次使用,每个Socket对象只能连接一台远程主机。如果你想连接到多台远程主机,你必须创建多个Socket对象。\[2\] 另外,需要注意的是,在Unity 5.1 ~ Unity2018可以使用UNet(Unity Networking),但在Unity 2019之后,UNet已经被废弃,Mirror成为了替代UNet的解决方案。因此,不建议再使用UNet进行网络通信。\[3\] #### 引用[.reference_title] - *1* *3* [【游戏开发实战】Unity使用Socket通信实现简单的多人聊天室(万字详解 | 网络 | TCP | 通信 | Mirror | ...](https://blog.csdn.net/linxinfa/article/details/118888064)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^control_2,239^v3^insert_chatgpt"}} ] [.reference_item] - *2* [UnitySocket网络编程](https://blog.csdn.net/weixin_45348216/article/details/128084313)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^control_2,239^v3^insert_chatgpt"}} ] [.reference_item] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值