mirror of
https://gitee.com/jisol/jisol-game/
synced 2025-09-27 02:36:14 +00:00
提交
This commit is contained in:
@@ -1,6 +1,8 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Threading.Tasks;
|
||||
using Cysharp.Threading.Tasks;
|
||||
using Plugins.JNGame.Sync.Frame.game;
|
||||
using Plugins.JNGame.System;
|
||||
using Plugins.JNGame.Util;
|
||||
using UnityEngine;
|
||||
@@ -22,7 +24,7 @@ namespace Plugins.JNGame.Sync.Frame
|
||||
|
||||
|
||||
//帧队列
|
||||
private List<JNFrameInfo> _nFrameQueue = new();
|
||||
private Queue<JNFrameInfo> _nFrameQueue = new();
|
||||
|
||||
//本地帧数
|
||||
private int _nLocalFrame = 0;
|
||||
@@ -32,6 +34,9 @@ namespace Plugins.JNGame.Sync.Frame
|
||||
//暂存帧列表
|
||||
private Dictionary<int,JNFrameInfo> _nFrameTempQueue = new();
|
||||
|
||||
//需要同步的Actor
|
||||
private List<JNSyncFrameComponent<object>> _nSyncActors = new();
|
||||
|
||||
//ID 每添加 JNSyncFrameComponent + 1
|
||||
public Func<int> nSyncID = RandomUtil.Next(0);
|
||||
|
||||
@@ -44,6 +49,9 @@ namespace Plugins.JNGame.Sync.Frame
|
||||
//是否开始同步
|
||||
Boolean _isStart = false;
|
||||
|
||||
//是否请求后台数据
|
||||
private Boolean _isRequestServerData = false;
|
||||
|
||||
//帧更新
|
||||
int dtTotal = 0;
|
||||
//输入更新
|
||||
@@ -56,9 +64,15 @@ namespace Plugins.JNGame.Sync.Frame
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
//开始
|
||||
public void onStart(){
|
||||
this._isStart = true;
|
||||
}
|
||||
|
||||
//重置数据
|
||||
public void Reset()
|
||||
public void onStop()
|
||||
{
|
||||
this._isStart = false;
|
||||
this.nSyncID = RandomUtil.Next(0);
|
||||
this.nRandom = RandomUtil.SyncRandom(100);
|
||||
this.nRandomInt = RandomUtil.SyncRandomInt(100);
|
||||
@@ -94,7 +108,35 @@ namespace Plugins.JNGame.Sync.Frame
|
||||
//运行帧
|
||||
public void onUpdate()
|
||||
{
|
||||
if(!(_nFrameQueue.TryDequeue(out var frame))) return;
|
||||
|
||||
int dt = this._nSyncTime / this._nDivideFrame;
|
||||
|
||||
//拆出输入
|
||||
Dictionary<int, JNFrameInput> inputs = new();
|
||||
foreach (var message in frame.Messages)
|
||||
{
|
||||
inputs.Add(message.NId,message);
|
||||
}
|
||||
|
||||
//更新帧
|
||||
this._nSyncActors.ForEach(child =>
|
||||
{
|
||||
if (inputs.ContainsKey(child.NID))
|
||||
{
|
||||
child.OnSyncUpdate(dt,frame,child.Decoder(inputs[child.NID].Input.ToByteArray()));
|
||||
}
|
||||
else
|
||||
{
|
||||
child.OnSyncUpdate(dt,frame,null);
|
||||
}
|
||||
});
|
||||
|
||||
//执行下一帧物理
|
||||
Physics.Simulate((float)dt / 1000);
|
||||
Physics.SyncTransforms();
|
||||
|
||||
|
||||
}
|
||||
|
||||
//自适应间隔时间
|
||||
@@ -127,12 +169,16 @@ namespace Plugins.JNGame.Sync.Frame
|
||||
* @param frame 帧数据
|
||||
* @param isLatestData 是否最新的帧数据
|
||||
*/
|
||||
public void AddInput(JNFrameInfo frame,Boolean isLatestData = false){
|
||||
public void AddInput(JNFrameInfo frame,Boolean isLatestData = true)
|
||||
{
|
||||
|
||||
if (!_isStart) return;
|
||||
|
||||
if(isLatestData){
|
||||
//如果推的帧小于本地帧 则 重开
|
||||
if(frame.Index < _nLocalFrame){
|
||||
Reset();
|
||||
onStop();
|
||||
onStart();
|
||||
return;
|
||||
}
|
||||
}
|
||||
@@ -143,14 +189,31 @@ namespace Plugins.JNGame.Sync.Frame
|
||||
//判断接受的帧是否下一帧 如果不是则加入未列入
|
||||
if (frame.Index != index){
|
||||
|
||||
_nFrameTempQueue.Add(frame.Index,frame);
|
||||
_nFrameTempQueue.TryAdd(frame.Index,frame);
|
||||
|
||||
//在未列入中拿到需要的帧
|
||||
JNFrameInfo tamp = null;
|
||||
|
||||
if ((tamp = _nFrameTempQueue[index]) == null){
|
||||
if ((tamp = _nFrameTempQueue.GetValueOrDefault(index,null)) == null){
|
||||
|
||||
//如果没有则向服务器请求我需要的帧数
|
||||
if (!this._isRequestServerData)
|
||||
{
|
||||
this._isRequestServerData = true;
|
||||
|
||||
//请求
|
||||
this.OnServerData(this._nLocalFrame, 0).ContinueWith(infos =>
|
||||
{
|
||||
foreach (var frameInfo in infos.Frames)
|
||||
{
|
||||
this.AddInput(frameInfo,false);
|
||||
}
|
||||
|
||||
this._isRequestServerData = false;
|
||||
}).Forget();
|
||||
}
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
else
|
||||
@@ -167,15 +230,17 @@ namespace Plugins.JNGame.Sync.Frame
|
||||
_nLocalFrame = index;
|
||||
|
||||
//分帧插入
|
||||
_nFrameQueue.Add(frame);
|
||||
for (var i = 0; i < this._nDivideFrame - 1; index++) {
|
||||
_nFrameQueue.Add(new JNFrameInfo());
|
||||
_nFrameQueue.Enqueue(frame);
|
||||
for (var i = 0; i < this._nDivideFrame - 1; i++) {
|
||||
_nFrameQueue.Enqueue(new JNFrameInfo());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//发送帧数据
|
||||
protected abstract void OnSendInput(JNFrameInputs inputs);
|
||||
//获取帧数据
|
||||
protected abstract UniTask<JNFrameInfos> OnServerData(int start,int end);
|
||||
|
||||
}
|
||||
}
|
@@ -1,4 +1,6 @@
|
||||
using System;
|
||||
using System.Text;
|
||||
using Newtonsoft.Json;
|
||||
using UnityEngine;
|
||||
|
||||
namespace Plugins.JNGame.Sync.Frame.game
|
||||
@@ -10,7 +12,8 @@ namespace Plugins.JNGame.Sync.Frame.game
|
||||
|
||||
//标识
|
||||
private int _nId;
|
||||
|
||||
public int NID => _nId;
|
||||
|
||||
//当前输入
|
||||
private T _input;
|
||||
|
||||
@@ -42,8 +45,21 @@ namespace Plugins.JNGame.Sync.Frame.game
|
||||
//加载
|
||||
public abstract void OnSyncLoad();
|
||||
|
||||
|
||||
//解析
|
||||
public T Decoder(byte[] bytes)
|
||||
{
|
||||
return JsonConvert.DeserializeObject<T>(Encoding.UTF8.GetString(bytes));
|
||||
}
|
||||
|
||||
//编码
|
||||
public byte[] Encoder(T input){
|
||||
return Encoding.UTF8.GetBytes(JsonConvert.SerializeObject(input));
|
||||
}
|
||||
|
||||
|
||||
//帧同步
|
||||
public abstract void OnSyncUpdate(int dt,JNFrameInfo frame,Input input = null);
|
||||
public abstract void OnSyncUpdate(int dt,JNFrameInfo frame,T input);
|
||||
|
||||
|
||||
|
||||
|
Reference in New Issue
Block a user