You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Unity UDP通信问题:服务器回发数据提示客户端未连接

问题:UDP回发时提示客户端未连接,Socket接收数据后断开

我正在用Unity开发游戏,想要实现客户端通过UDP向服务器发送数据,服务器再将数据回发给客户端(用来保存游戏实例)。目前遇到的问题是:客户端能成功把数据发送到服务器,但服务器接收数据后回发时,会提示UDP客户端未连接,而且数据到达服务器后Socket就断开了,完全没法完成回发操作。我已经尝试设置过多播相关的Socket选项,但没有效果。

客户端代码

private void SetupConnection() {
    try {
        _thread = new Thread(ReceiveData);
        _thread.IsBackground = true;
        udpClient = new UdpClient();
        udpClient.Client.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
        udpClient.ExclusiveAddressUse = false;
        udpClient.Client.Bind(new IPEndPoint(IPAddress.Parse(serverAdress), 32212));
        udpClient.BeginReceive(new AsyncCallback(ReceiveUdpCallback), udpClient);
        _client = new TcpClient(serverAdress, port);
        _stream = _client.GetStream();
        _thread.Start();
        isConnected = true;
    } catch(Exception e) {
        CloseConnection();
        connectionError = true;
        Debug.Log(e.ToString());
    }
}
public void ReceiveUdpCallback(IAsyncResult ar) {
    UdpClient c = (UdpClient)ar.AsyncState;
    IPEndPoint receivedIpEndPoint = new IPEndPoint(IPAddress.Any, 0);
    Byte[] receivedBytes1 = c.EndReceive(ar, ref receivedIpEndPoint);
    Debug.Log("coming in receiveudpcallback!: " + receivedBytes1);
    Dictionary<string, string> values = new Dictionary<string, string>();
    Byte[] receivedBytes;
    try {
        receivedBytes = c.EndReceive(ar, ref receivedIpEndPoint);
    } catch (Exception e) {
        Console.WriteLine(e.StackTrace);
        return;
    }
    if (receivedBytes != null) {
        string textReceived = Encoding.ASCII.GetString(receivedBytes);
        Dictionary<string, string> data = GetDicValues(textReceived);
        HandleInputMessage(c, data);
    }
    udpClient.BeginReceive(ReceiveUdpCallback, ar.AsyncState);
}

服务器代码

private void SetupServer() {
    Console.WriteLine("Setting up Server...");
    _serverSocket.Bind(new IPEndPoint(IPAddress.Any, 32211));
    _serverSocket.Listen(1);
    Console.WriteLine("Server is running...");
    _serverSocket.BeginAccept(new AsyncCallback(AcceptCallback), null);
    IPEndPoint localpt = new IPEndPoint(IPAddress.Any, 32212);
    udpServer = new UdpClient();
    udpServer.Client.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
    udpServer.ExclusiveAddressUse = false;
    // only if you want to send/receive on same machine.
    udpServer.Client.Bind(new IPEndPoint(IPAddress.Any, 32212));
    udpServer.BeginReceive(new AsyncCallback(ReceiveUdpCallback), udpServer);
}
public void ReceiveUdpCallback(IAsyncResult ar) {
    UdpClient c = (UdpClient)ar.AsyncState;
    IPEndPoint receivedIpEndPoint = new IPEndPoint(IPAddress.Any, 0);
    Console.WriteLine("coming in receiveudpcallback!");
    Dictionary<string, string> values = new Dictionary<string, string>();
    Byte[] receivedBytes;
    try {
        receivedBytes = c.EndReceive(ar, ref receivedIpEndPoint);
    } catch (Exception e) {
        Console.WriteLine(e.StackTrace);
        return;
    }
    if (receivedBytes != null) {
        string textReceived = Encoding.ASCII.GetString(receivedBytes);
        HandleInputMessage(c, textReceived);
    } else {
    }
    c.BeginReceive(ReceiveUdpCallback, ar.AsyncState);
}

服务器端的UdpClient实例已经保存到玩家对象中,后续通过以下方法回发数据:

public void FlushUdp() {
    string msgToSend = "<opcode:" + opcode + ">";
    msgToSend += "<username:" + player.username + ">";
    foreach (KeyValuePair<string, string> entry in values) {
        msgToSend += "<" + entry.Key + ":" + entry.Value + ">";
    }
    byte[] bytesToSend = Encoding.ASCII.GetBytes(msgToSend);
    udpClient.Send(bytesToSend, bytesToSend.Length);
}

问题解决

我已经解决了这个问题,方法是每次接收消息后重新连接服务器/客户端。

内容的提问来源于stack exchange,提问作者Evan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 04:37:05