using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using ExitGames.Client.Photon;
using Proto.MyProto;
using Google.Protobuf;
using I2.Loc;
using System;
public class ServerEngine:MonoSingleton<ServerEngine> , IPhotonPeerListener
{
private PhotonPeer peer;
/// <summary>
/// 接受返回消息的回调方法字典
/// </summary>
private Dictionary<byte, Response> Dic_OP = new Dictionary<byte, Response>();
/// <summary>
/// 接受服务器主动推送消息的回调方法字典
/// </summary>
private Dictionary<byte, Response> Dic_OnEvent = new Dictionary<byte, Response>();
private ulong sendbyteCount;
private int sendCount;
private int maxSendByte;
private ulong receiveByteCount;
private int maxReceiveByte;
private int receiveCount;
/// <summary>
/// 是否主动切换到登陆界面
/// </summary>
public bool isSwitchLogin;
public enum ServerIp
/// <summary>
/// 服务器选择
/// </summary>
public ServerIp serverIp;
/// <summary>
/// 发送数据
/// </summary>
/// <param name="opCode">消息头ID</param>
/// <param name="obj">请求数据体</param>
/// <param name="resCallback">接受返回消息的回调方法</param>
public void SendRequest(byte opCode, IMessage obj, Response resCallback)
{
//新建一个字典用来向服务器发送消息
Dictionary<byte, object> dic = new Dictionary<byte, object>();
//将请求数据体序列化成字节数组
byte[] byteBody = new byte[0];
if (obj != null)
{
byteBody = MessageExtensions.ToByteArray(obj);
}
if(byteBody.Length > maxSendByte)
{
maxSendByte = byteBody.Length;
Debug.Log("MaxSendByte=" + maxSendByte);
}
sendbyteCount = sendbyteCount + (ulong)byteBody.Length;
sendCount++;
//将请求数据体添加进字典里,默认只有一个数据
dic.Add(1, byteBody);
//如果字典里没有这个消息头,则添加进字典
if (!Dic_OP.ContainsKey(opCode))
{
Dic_OP.Add(opCode, resCallback);
}
else
{
Dic_OP[opCode] = resCallback;
}
//像服务器发送消息
peer.OpCustom(opCode, dic, true);
}
/// <summary>
/// 注册服务器主动推送消息的处理回调
/// </summary>
/// <param name="opCode">消息头ID</param>
/// <param name="eventCallback">接受返回消息的回调方法</param>
public void OnEventCallback(byte opCode, Response eventCallback)
{
//如果字典里没有这个消息头,则添加进字典
if (!Dic_OnEvent.ContainsKey(opCode))
{
Dic_OnEvent.Add(opCode, eventCallback);
}
else
{
Dic_OnEvent[opCode] += eventCallback;
}
}
/// <summary>
/// 移除服务器主动推送消息的处理回调
/// </summary>
/// <param name="opCode">消息头ID</param>
/// <param name="eventCallback">接受返回消息的回调方法</param>
public void OnDesEventCallback(byte opCode, Response eventCallback)
{
//如果字典里没有这个消息头,则直接返回
if (!Dic_OnEvent.ContainsKey(opCode))
{
return;
}
else
{
Dic_OnEvent[opCode] -= eventCallback;
}
}
protected override void Awake()
{
base.Awake();
ReConnect();
}
private void Start()
{
MessageCenter.Instance.RegiseterMessage(Message.Switch_Login_Scene, this, SwitchLoginSceneCallback);
}
private void OnDestroy()
{
MessageCenter.Instance.RemoveMessageByTarget(Message.Switch_Login_Scene, this);
}
private void SwitchLoginSceneCallback(object[] parms)
{
isSwitchLogin = true;
ToReConnect();
}
public void ReConnect()
{
if (peer != null)
{
peer.Disconnect();
}
peer = new PhotonPeer(this, ConnectionProtocol.Udp);
peer.MaximumTransferUnit = 102400;
switch (serverIp)
{
case ServerIp.1:
peer.Connect("***.***.***:****", "ElvesMainland");
break;
default:
break;
}
Debug.Log("重新连接:" + peer.PeerID);
}
private void Update( )
{
if (peer != null)
{
peer.Service();
}
if (Input.GetKeyDown(KeyCode.T))
{
Debug.Log("平均发送长度:" + (sendbyteCount / (ulong)sendCount) + ",最大发送长度:" + maxSendByte + ",平均接收长度:" + (receiveByteCount / (ulong)receiveCount) + ",最大接收长度:" + maxReceiveByte);
}
}
/// <summary>
/// 接受服务器返回的消息
/// </summary>
/// <param name="response">服务器返回的数据</param>
public void OnOperationResponse( OperationResponse response )
{
//接受回调方法的委托
Response controller;
//取出服务器返回数据中的参数
byte[] responseValue = (byte[])response.Parameters[1];
//从字典中取出回调方法
Dic_OP.TryGetValue(response.OperationCode, out controller);
//如果方法不为空,则执行回调方法
if (controller != null)
{
controller(responseValue);
}
}
/// <summary>
/// 接收服务器主动推送的消息
/// </summary>
/// <param name="eventData"></param>
public void OnEvent(EventData eventData)
{
//接受回调方法的委托
Response controller;
//取出服务器返回数据中的参数
byte[] responseValue = (byte[])eventData.Parameters[1];
receiveByteCount = receiveByteCount + (ulong)responseValue.Length;
receiveCount++;
if(maxReceiveByte < responseValue.Length)
{
maxReceiveByte = responseValue.Length;
Debug.Log(" maxReceiveByte=" + maxReceiveByte);
}
//从字典中取出回调方法
Dic_OnEvent.TryGetValue(eventData.Code, out controller);
//如果方法不为空,则执行回调方法
if (controller != null)
{
controller(responseValue);
}
}
public void UnRegistController(byte code)
{
Dic_OP.Remove(code);
}
public void OnStatusChanged( StatusCode statusCode )
{
switch (statusCode)
{
case StatusCode.Connect:
Debug.Log("Connected");
MessageCenter.Instance.BoradCastMessage("NetWorkConnect");
break;
case StatusCode.Disconnect:
Debug.LogError("Disconnect");
if (!isSwitchLogin)
{
MUIAlert alert = MUIMgr.Instance.ShowAlert(OpenType.Long, ToReConnect, null,
LocalizationManager.GetTranslation("error", false), LocalizationManager.GetTranslation("networkerror", false), LocalizationManager.GetTranslation("confirm", false));
alert.close.gameObject.SetActive(false);
}
isSwitchLogin = false;
break;
}
}
public void ToReConnect()
{
SceneMgr.Instance.LoadSceneAsync("Login");
ReConnect();
}
public void DebugReturn(DebugLevel level, string message)
{
}
}
Protot
于 2022-04-27 11:26:47 首次发布