通过心跳包对时间

 

using UnityEngine;


namespace YouYou
{
    /// <summary>
    /// Socket组件
    /// </summary>
    public class SocketComponent : YouYouBaseComponent, IUpdateComponent
    {
        /// <summary>
        /// Socket管理器
        /// </summary>
        private SocketManager m_SocketManager;


        [Header("每帧最大发送数量")]
        public int MaxSendCount = 5;

        [Header("每次发包最大字节数量")]
        public int MaxSendByteCount = 1024;

        [Header("每帧最大接收数量")]
        public int MaxReceiveCount = 5;

        [Header("心跳间隔 秒")]
        public int HeartbeatInterval = 10;

        /// <summary>
        /// 上次心跳时间
        /// </summary>
        private float m_PrevHeartbeatInterval = 0;

        /// <summary>
        /// PING值(毫秒)
        /// </summary>
        [HideInInspector]
        public int PingValue;

        /// <summary>
        /// 游戏服务器的时间
        /// </summary>
        [HideInInspector]
        public long GameServerTime;

        /// <summary>
        /// 和服务器对表的时刻
        /// </summary>
        [HideInInspector]
        public float CheckServerTime;

        /// <summary>
        /// 当前是否处于连接状态
        /// </summary>
        private bool m_IsConnectToMainSocket = false;


        /// <summary>
        /// 发送数据的MemoryStream
        /// </summary>
        public MMO_MemoryStream SocketSendMS { get; private set; }
        /// <summary>
        /// 接收数据的MemoryStream
        /// </summary>
        public MMO_MemoryStream SocketReceiveMS { get; private set; }

        protected override void OnAwake()
        {
            base.OnAwake();
            GameEntry.RegisterUpdateComponent(this);
            m_SocketManager = new SocketManager();

            SocketSendMS = new MMO_MemoryStream();
            SocketReceiveMS = new MMO_MemoryStream();
        }

        /// <summary>
        /// 主Socket
        /// </summary>
        private SocketTcpRoutine m_MainSocket;
        protected override void OnStart()
        {
            base.OnStart();
            //创建Socket访问器
            m_MainSocket = CreateSocketTcpRoutine();
            //连接成功的回调
            m_MainSocket.OnConnectOK = () =>
            {
                //已经建立了连接
                m_IsConnectToMainSocket = true;
            };


            SocketProtoListener.AddProtoListener();
        }

        /// <summary>
        /// 创建SocketTcp访问器
        /// </summary>
        /// <returns></returns>
        public SocketTcpRoutine CreateSocketTcpRoutine()
        {
            //从对象池中取出访问器
            return GameEntry.Pool.DequeueClassObject<SocketTcpRoutine>();
        }

        /// <summary>
        /// 注册SocketTcp访问器进链表
        /// </summary>
        /// <param name="routine"></param>
        internal void RegisterSocketTcpRoutine(SocketTcpRoutine routine)
        {
            m_SocketManager.RegisterSocketTcpRoutine(routine);
        }

        /// <summary>
        /// 从链表移除SocketTcp访问器
        /// </summary>
        /// <param name="routine"></param>
        internal void RemoveSocketTcpRoutine(SocketTcpRoutine routine)
        {
            m_SocketManager.RemoveSocketTcpRoutine(routine);
        }



        public void OnUpdate()
        {
            m_SocketManager.OnUpdate();

            //如果建立连接
            if (m_IsConnectToMainSocket)
            {
                //发送心跳                           上次心跳时间             心跳间隔
                if (Time.realtimeSinceStartup > m_PrevHeartbeatInterval + HeartbeatInterval)
                {
                    //循环定时
                    m_PrevHeartbeatInterval = Time.realtimeSinceStartup;

                    //发送心跳
                    System_HeartbeatProto proto = new System_HeartbeatProto();
                    proto.LocalTime = Time.realtimeSinceStartup * 1000;
                    CheckServerTime = Time.realtimeSinceStartup;//和服务器的对表时刻
                    SendMainMsg(proto);
                }
            }
        }

        public override void Shutdown()
        {
            m_IsConnectToMainSocket = false;

            m_SocketManager.Dispose();
            //回池
            GameEntry.Pool.EnqueueClassObject(m_MainSocket);
            SocketProtoListener.RemoveProtoListener();

            SocketSendMS.Dispose();
            SocketSendMS.Close();
            SocketReceiveMS.Dispose();
            SocketReceiveMS.Close();
        }




        //=====================================

        /// <summary>
        /// 主Socket连接服务器
        /// </summary>
        /// <param name="ip"></param>
        /// <param name="port"></param>
        public void ConnectToMainSocket(string ip, int port)
        {
            m_MainSocket.Connect(ip, port);
        }


        /// <summary>
        /// 主Socket发送消息
        /// </summary>
        /// <param name="buffer"></param>
        public void SendMainMsg(byte[] buffer)
        {
            m_MainSocket.SendMsg(buffer);
        }
        /// <summary>
        /// 主Socket发送消息
        /// </summary>
        /// <param name="buffer"></param>
        public void SendMainMsg(IProto proto)
        {
#if DEBUG_LOG_PROTO
            Debug.Log("<color=#ffa200>发送消息:</color><color=#FFFB80>" + proto.ProtoEnName + " " + proto.ProtoCode + "</color>");
            Debug.Log("<color=#ffdeb3>==>>" + JsonUtility.ToJson(proto) + "</color>");
#endif
            m_MainSocket.SendMsg(proto.ToArray());
        }
    }
}

 

using UnityEngine;
using YouYou;

/// <summary>
/// 服务器返回心跳(工具只生成一次)
/// </summary>
public sealed class System_HeartbeatReturnHandler
{
    public static void OnSystem_HeartbeatReturn(byte[] buffer)
    {
        System_HeartbeatReturnProto proto = System_HeartbeatReturnProto.GetProto(buffer);
#if DEBUG_LOG_PROTO
        Debug.Log("<color=#00eaff>接收消息:</color><color=#00ff9c>" + proto.ProtoEnName + " " + proto.ProtoCode + "</color>");
        Debug.Log("<color=#c5e1dc>==>>" + JsonUtility.ToJson(proto) + "</color>");
#endif

        float localTime = proto.LocalTime;
        long serverTime = proto.ServerTime;

        //得到ping值
        GameEntry.Socket.PingValue = (int)((Time.realtimeSinceStartup * 1000 - localTime) * 0.5f);
        //得到本地计算的服务器时间
        GameEntry.Socket.GameServerTime = serverTime - GameEntry.Socket.PingValue;

        Debug.Log("服务器时间==" + GameEntry.Socket.GameServerTime);
        Debug.Log("得到ping值==" + GameEntry.Socket.PingValue);
    }
}

 

服务端

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值