unityzgy/Assets/Scripts/StuentNet/UDP/Udp/UdpOuter.cs
ayuan9957 bf12e02276 feat: 多语言本地化系统 - 支持中/英/法/俄实时切换
- LocalizationManager: 新增翻译表(SetFormatted/SetDuration/LocalizeOperateMsg)
- LoginPanel: InputField placeholder本地化、字体颜色保持
- HistoryPanel: 用时数据本地化、placeholder本地化
- RecordDetailPanel: 操作详情消息本地化(LanguageChanged重建)
- AppraiseWindowBase: 评价等级本地化、操作消息重建
- EditorAppraiser: 所有评估消息改用InjectOperateMsgLocalized
- StudentOperateRecorder: 新增InjectOperateMsgLocalized方法
- LocalizationLanguageTestBar: 单例模式、ScreenSpaceOverlay筛选
- 字体切换时保留颜色和verticalOverflow
2026-07-16 10:05:59 +08:00

166 lines
5.6 KiB
C#

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using UnityEngine;
using UnityEngine.Events;
namespace XFramework.NetOuter
{
public class UdpOuter : IUDPHander
{
protected ProtocolBase protocol = new ProtocolByte();
UdpClient client;
IPEndPoint targetPoint; //默认的发送地址
//地址不确定时的默认端口
int otherPort;
UDPType uDPType;
MsgDistribution msgDistribution;
/// <summary>
/// 初始化UDP
/// </summary>
/// <param name="ip">默认绑定的IP 点播可为空 为空时发送时必须指定地址 组播不可为空</param>
/// <param name="otherPort"> 默认绑定的端口 不可为空</param>
/// <param name="localport"> 自身端口 组播时other=local 不同时默认使用other</param>
public UdpOuter(string ip, int otherPort, int localport, UDPType type)
{
uDPType = type;
this.otherPort = otherPort;
targetPoint = new IPEndPoint(IPAddress.Parse(ip), otherPort);
switch (type)
{
case UDPType.Point:
CreatPointUDP(ip, otherPort, localport);
break;
case UDPType.Group:
if (otherPort != localport)
{
Debug.LogWarning("组播模式端口须保持一致,不一致时默认使用otherPort");
}
CreatGroupUDP(ip, otherPort);
break;
default:
break;
}
msgDistribution = new MsgDistribution();
}
//创建点播UDP
private void CreatPointUDP(string otherIP, int otherPort, int localport)
{
if (!string.IsNullOrEmpty(otherIP) && otherPort != 0)
client = new UdpClient(otherIP, otherPort);//设置默认发送端地址及端口
else
client = new UdpClient();//不设置默认地址
IPEndPoint endPoint = new IPEndPoint(IPAddress.Any, localport);//初始化接收端口
client = new UdpClient(endPoint);
UDPState state = new UDPState(endPoint, client);
client.BeginReceive(ReceiveCb, state);
}
UDPState state;
//创建组播UDP
private void CreatGroupUDP(string groupIP, int groupPort)
{
IPEndPoint endPoint = new IPEndPoint(IPAddress.Any, groupPort);//初始化接收端口
client = new UdpClient(endPoint);
client.JoinMulticastGroup(IPAddress.Parse(groupIP));
client.MulticastLoopback = false;//是否接收自身消息
state = new UDPState(endPoint, client);
client.BeginReceive(ReceiveCb, state);
}
protected void ReceiveCb(IAsyncResult ar)
{
UDPState state = ar.AsyncState as UDPState;
try
{
if (state != null)
{
IPEndPoint end = state.ipendPoint;
byte[] bytes = state.UDPClient.EndReceive(ar, ref end);
ProtocolBase proto = protocol.Decode(bytes, sizeof(Int32), bytes.Length - 4); //udp 消息不需要判定消息长短直接处理即可
string protoName = proto.GetProtocolName();
ExcuteParam excuteParam = new ExcuteParam(end.Address.ToString(), protoName, (ProtocolByte)proto);
msgDistribution.Enqueue(excuteParam);
state.UDPClient.BeginReceive(ReceiveCb, state);
}
}
catch (Exception )
{
//Debug.LogError($"UDP接收消息异常{e.Message}");
}
}
/// <summary>
/// 发送消息 给绑定好地址的接口
/// </summary>
/// <param name="proto"></param>
public void SendNetMess(ProtocolBase proto)
{
byte[] bytes = proto.Encode();
byte[] length = BitConverter.GetBytes(bytes.Length);
byte[] sendBytes = length.Concat(bytes).ToArray();
client.Send(sendBytes, sendBytes.Length, targetPoint);
}
public void SendNetMess(string ip, int port, ProtocolBase protocol)
{
byte[] bytes = protocol.Encode();
byte[] length = BitConverter.GetBytes(bytes.Length);
byte[] sendBytes = length.Concat(bytes).ToArray();
client.Send(sendBytes, sendBytes.Length, ip, port);
}
public void AddListener(string eventName, INetExcute excute, bool isOnce = false)
{
if (isOnce)
msgDistribution.AddOnceListener(eventName, excute);
else
msgDistribution.AddListener(eventName, excute);
}
public void RemovListener(string eventName)
{
msgDistribution.RemoveListener(eventName);
}
public void Close()
{
client?.Close();
}
public void ExtractingMsg()
{
msgDistribution.Distribution();
}
}
public class UDPState
{
private UdpClient udpClient;
public UdpClient UDPClient
{
get { return udpClient; }
}
public IPEndPoint ipendPoint;
public UDPState(IPEndPoint ipendPoint, UdpClient client)
{
this.ipendPoint = ipendPoint;
udpClient = client;
}
}
public enum UDPType
{
//单点通信
Point,
//组播
Group,
}
}