forked from sin365/AxibugEmuOnline
完成基础房间逻辑封装 | NetRePlay
This commit is contained in:
parent
a66835c091
commit
9e427d1532
8
AxibugEmuOnline.Client/Assets/AlienUICore.meta
Normal file
8
AxibugEmuOnline.Client/Assets/AlienUICore.meta
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 3b3f84ffc19016f4dbc28b308894bb4a
|
||||||
|
folderAsset: yes
|
||||||
|
DefaultImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
8
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay.meta
Normal file
8
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay.meta
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 86a02c697fd26264cb5ee552b582449b
|
||||||
|
folderAsset: yes
|
||||||
|
DefaultImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
@ -0,0 +1,3 @@
|
|||||||
|
{
|
||||||
|
"name": "AxiReplay"
|
||||||
|
}
|
@ -0,0 +1,7 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 0a45db2096af23647aaafe5b70ccb4d7
|
||||||
|
AssemblyDefinitionImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
@ -0,0 +1,11 @@
|
|||||||
|
using System;
|
||||||
|
|
||||||
|
namespace AxiReplay
|
||||||
|
{
|
||||||
|
internal interface IReplayReader : IDisposable
|
||||||
|
{
|
||||||
|
bool NextFrame(out ReplayStep data);
|
||||||
|
bool TakeFrame(int addFrame, out ReplayStep data);
|
||||||
|
bool NextFramebyFrameIdx(int FrameID, out ReplayStep data);
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,11 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 896ff07370157db46b612575616020ed
|
||||||
|
MonoImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
serializedVersion: 2
|
||||||
|
defaultReferences: []
|
||||||
|
executionOrder: 0
|
||||||
|
icon: {instanceID: 0}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
@ -0,0 +1,12 @@
|
|||||||
|
using System;
|
||||||
|
|
||||||
|
namespace AxiReplay
|
||||||
|
{
|
||||||
|
internal interface IReplayWriter : IDisposable
|
||||||
|
{
|
||||||
|
void NextFrame(UInt64 frameInput);
|
||||||
|
void NextFramebyFrameIdx(int FrameID, UInt64 frameInput);
|
||||||
|
void TakeFrame(int addFrame, UInt64 frameInput);
|
||||||
|
void SaveData(string path, bool bNeedDump = false, string dumpFilePath = null);
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,11 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 6a8fcda365e5a7f428f88bc130eb913b
|
||||||
|
MonoImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
serializedVersion: 2
|
||||||
|
defaultReferences: []
|
||||||
|
executionOrder: 0
|
||||||
|
icon: {instanceID: 0}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
74
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay/NetReplay.cs
Normal file
74
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay/NetReplay.cs
Normal file
@ -0,0 +1,74 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
|
||||||
|
namespace AxiReplay
|
||||||
|
{
|
||||||
|
public class NetReplay
|
||||||
|
{
|
||||||
|
int MaxInFrame = 0;
|
||||||
|
int mCurrPlayFrame = -1;
|
||||||
|
Queue<ReplayStep> mQueueReplay;
|
||||||
|
ReplayStep mNextReplay;
|
||||||
|
ReplayStep mCurrReplay;
|
||||||
|
int byFrameIdx = 0;
|
||||||
|
public NetReplay()
|
||||||
|
{
|
||||||
|
mQueueReplay = new Queue<ReplayStep>();
|
||||||
|
}
|
||||||
|
public void InData(ReplayStep inputData)
|
||||||
|
{
|
||||||
|
mQueueReplay.Enqueue(inputData);
|
||||||
|
MaxInFrame = inputData.FrameStartID;
|
||||||
|
}
|
||||||
|
public bool NextFrame(out ReplayStep data, out int FrameDiff)
|
||||||
|
{
|
||||||
|
return TakeFrame(0, out data, out FrameDiff);
|
||||||
|
}
|
||||||
|
/// <summary>
|
||||||
|
/// 往前推进帧的,指定帧下标
|
||||||
|
/// </summary>
|
||||||
|
public bool NextFramebyFrameIdx(int FrameID, out ReplayStep data, out int FrameDiff)
|
||||||
|
{
|
||||||
|
bool res = TakeFrame(FrameID - byFrameIdx, out data, out FrameDiff);
|
||||||
|
byFrameIdx = FrameID;
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
public bool TakeFrame(int addFrame, out ReplayStep data, out int FrameDiff)
|
||||||
|
{
|
||||||
|
bool Changed = false;
|
||||||
|
mCurrPlayFrame += addFrame;
|
||||||
|
if (mCurrPlayFrame >= mNextReplay.FrameStartID)
|
||||||
|
{
|
||||||
|
Changed = mCurrReplay.InPut != mNextReplay.InPut;
|
||||||
|
mCurrReplay = mNextReplay;
|
||||||
|
data = mCurrReplay;
|
||||||
|
UpdateNextFrame(mCurrPlayFrame, out FrameDiff);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
data = mCurrReplay;
|
||||||
|
FrameDiff = MaxInFrame - mCurrPlayFrame;
|
||||||
|
}
|
||||||
|
return Changed;
|
||||||
|
}
|
||||||
|
void UpdateNextFrame(int targetFrame,out int FrameDiff)
|
||||||
|
{
|
||||||
|
FrameDiff = MaxInFrame - targetFrame;
|
||||||
|
//如果已经超过
|
||||||
|
while (targetFrame > mNextReplay.FrameStartID)
|
||||||
|
{
|
||||||
|
if (mNextReplay.FrameStartID >= MaxInFrame)
|
||||||
|
{
|
||||||
|
//TODO
|
||||||
|
//bEnd = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mQueueReplay.Count > 0)
|
||||||
|
{
|
||||||
|
mNextReplay = mQueueReplay.Dequeue();
|
||||||
|
}
|
||||||
|
targetFrame++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,11 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 452b58ff73a0853449845fd9e1134cc2
|
||||||
|
MonoImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
serializedVersion: 2
|
||||||
|
defaultReferences: []
|
||||||
|
executionOrder: 0
|
||||||
|
icon: {instanceID: 0}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
101
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay/ReplayData.cs
Normal file
101
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay/ReplayData.cs
Normal file
@ -0,0 +1,101 @@
|
|||||||
|
using System;
|
||||||
|
using System.Runtime.InteropServices;
|
||||||
|
using System.Text;
|
||||||
|
|
||||||
|
namespace AxiReplay
|
||||||
|
{
|
||||||
|
[StructLayout(LayoutKind.Explicit,Size = 44)]
|
||||||
|
public struct ReplayHandler
|
||||||
|
{
|
||||||
|
[FieldOffset(0)]
|
||||||
|
public int Format;
|
||||||
|
[FieldOffset(sizeof(int) * 1)]
|
||||||
|
public int RomID;
|
||||||
|
[FieldOffset(sizeof(int) * 2)]
|
||||||
|
public int RomType;
|
||||||
|
[FieldOffset(sizeof(int) * 3)]
|
||||||
|
public int DataOffset;
|
||||||
|
[FieldOffset(sizeof(int) * 4)]
|
||||||
|
public int TitleOffset;
|
||||||
|
[FieldOffset(sizeof(int) * 5)]
|
||||||
|
public int NoteOffset;
|
||||||
|
[FieldOffset(sizeof(int) * 6)]
|
||||||
|
public int AllFrame;
|
||||||
|
[FieldOffset(sizeof(int) * 7)]
|
||||||
|
public int AllTime;
|
||||||
|
[FieldOffset(sizeof(int) * 8)]
|
||||||
|
public int SingleLenght;
|
||||||
|
[FieldOffset(sizeof(int) * 9)]
|
||||||
|
public long CreateTime;
|
||||||
|
}
|
||||||
|
|
||||||
|
[StructLayout(LayoutKind.Explicit)]
|
||||||
|
public struct ReplayStep
|
||||||
|
{
|
||||||
|
[FieldOffset(0)]
|
||||||
|
public UInt64 All64Data;
|
||||||
|
[FieldOffset(0)]
|
||||||
|
public Int32 FrameStartID;
|
||||||
|
[FieldOffset(4)]
|
||||||
|
public UInt64 InPut;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class ReplayData
|
||||||
|
{
|
||||||
|
public static int HandlerLenght = sizeof(int) * 9 + sizeof(long);
|
||||||
|
public enum ReplayFormat : byte
|
||||||
|
{
|
||||||
|
None = 0,
|
||||||
|
FM32IPBYTE,
|
||||||
|
FM32IP16,
|
||||||
|
FM32IP32,
|
||||||
|
FM32IP64,
|
||||||
|
}
|
||||||
|
public static void GetStringByteData(string str,out byte[] data,out int lenghtWithEnd,Encoding encoding)
|
||||||
|
{
|
||||||
|
data = encoding.GetBytes(str);
|
||||||
|
lenghtWithEnd = data.Length + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static byte[] GetHandlerData(ReplayHandler replayhandler)
|
||||||
|
{
|
||||||
|
int size = Marshal.SizeOf(typeof(ReplayHandler));
|
||||||
|
byte[] arr = new byte[size];
|
||||||
|
|
||||||
|
IntPtr ptr = Marshal.AllocHGlobal(size);
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Marshal.StructureToPtr(replayhandler, ptr, false);
|
||||||
|
Marshal.Copy(ptr, arr, 0, size);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
Marshal.FreeHGlobal(ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
return arr;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static ReplayHandler GetReplayHandlerFromData(byte[] data)
|
||||||
|
{
|
||||||
|
if (data == null || data.Length < ReplayData.HandlerLenght)
|
||||||
|
{
|
||||||
|
throw new ArgumentException("Invalid data length or null data.");
|
||||||
|
}
|
||||||
|
|
||||||
|
IntPtr ptr = Marshal.AllocHGlobal(ReplayData.HandlerLenght);
|
||||||
|
try
|
||||||
|
{
|
||||||
|
// 将byte数组的内容复制到非托管内存中
|
||||||
|
Marshal.Copy(data, 0, ptr, ReplayData.HandlerLenght);
|
||||||
|
// 从非托管内存将内容转换回ReplayHandler结构体
|
||||||
|
return (ReplayHandler)Marshal.PtrToStructure(ptr, typeof(ReplayHandler));
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
// 释放非托管内存
|
||||||
|
Marshal.FreeHGlobal(ptr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,11 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 42df5a138f4f4ae488815f35d8e748da
|
||||||
|
MonoImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
serializedVersion: 2
|
||||||
|
defaultReferences: []
|
||||||
|
executionOrder: 0
|
||||||
|
icon: {instanceID: 0}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
174
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay/ReplayReader.cs
Normal file
174
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay/ReplayReader.cs
Normal file
@ -0,0 +1,174 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
|
using System.Text;
|
||||||
|
using static AxiReplay.ReplayData;
|
||||||
|
|
||||||
|
namespace AxiReplay
|
||||||
|
{
|
||||||
|
public class ReplayReader : IReplayReader
|
||||||
|
{
|
||||||
|
public ReplayData.ReplayFormat mFormat { get; private set; }
|
||||||
|
public Encoding TexEncoding { get; private set; }
|
||||||
|
ReplayHandler handler;
|
||||||
|
string mTitle;
|
||||||
|
string mNote;
|
||||||
|
int mAllFrame;
|
||||||
|
int mAllTime;
|
||||||
|
long mData;
|
||||||
|
int mSingleInputLenght;
|
||||||
|
int mSingleDataLenght;
|
||||||
|
FileStream mStream;
|
||||||
|
BinaryReader mBinaryReader;
|
||||||
|
|
||||||
|
int mCurrFrame = -1;
|
||||||
|
byte[] mNextOutbytes;
|
||||||
|
public ReplayStep currStep;
|
||||||
|
public ReplayStep nextStep;
|
||||||
|
bool bEnd;
|
||||||
|
|
||||||
|
List<string> dbgList = new List<string>();
|
||||||
|
bool bdbg = false;
|
||||||
|
string dumpPath;
|
||||||
|
|
||||||
|
public ReplayReader(string path, bool bWithDump = false, string dumppath = null)
|
||||||
|
{
|
||||||
|
dbgList.Clear();
|
||||||
|
bdbg = bWithDump;
|
||||||
|
dumpPath = dumppath;
|
||||||
|
mStream = new FileStream(path, FileMode.Open, FileAccess.Read);
|
||||||
|
mBinaryReader = new BinaryReader(mStream);
|
||||||
|
byte[] Outbytes;
|
||||||
|
Outbytes = mBinaryReader.ReadBytes(ReplayData.HandlerLenght);
|
||||||
|
handler = ReplayData.GetReplayHandlerFromData(Outbytes);
|
||||||
|
mFormat = (ReplayFormat)handler.Format;
|
||||||
|
switch (mFormat)
|
||||||
|
{
|
||||||
|
case ReplayData.ReplayFormat.FM32IP64: mSingleInputLenght = sizeof(UInt64); break;
|
||||||
|
case ReplayData.ReplayFormat.FM32IP32: mSingleInputLenght = sizeof(UInt32); break;
|
||||||
|
case ReplayData.ReplayFormat.FM32IP16: mSingleInputLenght = sizeof(UInt16); break;
|
||||||
|
case ReplayData.ReplayFormat.FM32IPBYTE: mSingleInputLenght = sizeof(byte); break;
|
||||||
|
}
|
||||||
|
//Frame+Lenght
|
||||||
|
mSingleDataLenght = (sizeof(UInt32)) + mSingleInputLenght;
|
||||||
|
nextStep = new ReplayStep();
|
||||||
|
nextStep.FrameStartID = -1;
|
||||||
|
bEnd = false;
|
||||||
|
|
||||||
|
dbgList.Add($"Format => {handler.Format}");
|
||||||
|
dbgList.Add($"DataOffset => {handler.DataOffset}");
|
||||||
|
dbgList.Add($"CreateTime => {handler.CreateTime}");
|
||||||
|
dbgList.Add($"AllFrame => {handler.AllFrame}");
|
||||||
|
dbgList.Add($"SingleLenght => {handler.SingleLenght}");
|
||||||
|
|
||||||
|
|
||||||
|
mNextOutbytes = new byte[mSingleDataLenght];
|
||||||
|
|
||||||
|
if (bWithDump)
|
||||||
|
{
|
||||||
|
int TestFrameIdx = -1;
|
||||||
|
while (!bEnd)
|
||||||
|
{
|
||||||
|
UpdateNextFrame(TestFrameIdx++);
|
||||||
|
}
|
||||||
|
File.WriteAllLines(dumppath, dbgList);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
UpdateNextFrame(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void UpdateNextFrame(int targetFrame)
|
||||||
|
{
|
||||||
|
//如果已经超过
|
||||||
|
while (targetFrame >= nextStep.FrameStartID)
|
||||||
|
{
|
||||||
|
if (nextStep.FrameStartID >= handler.AllFrame)
|
||||||
|
{
|
||||||
|
bEnd = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
mBinaryReader.Read(mNextOutbytes, 0, mSingleDataLenght);
|
||||||
|
switch (mFormat)
|
||||||
|
{
|
||||||
|
case ReplayFormat.FM32IP64:
|
||||||
|
{
|
||||||
|
nextStep.FrameStartID = BitConverter.ToInt32(mNextOutbytes, 0);
|
||||||
|
nextStep.InPut = BitConverter.ToUInt64(mNextOutbytes, sizeof(UInt32));
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case ReplayFormat.FM32IP32:
|
||||||
|
{
|
||||||
|
nextStep.All64Data = BitConverter.ToUInt64(mNextOutbytes, 0);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case ReplayFormat.FM32IP16:
|
||||||
|
{
|
||||||
|
nextStep.All64Data = BitConverter.ToUInt64(mNextOutbytes, 0);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case ReplayFormat.FM32IPBYTE:
|
||||||
|
{
|
||||||
|
nextStep.All64Data = BitConverter.ToUInt64(mNextOutbytes, 0);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
dbgList.Add($"{nextStep.FrameStartID} | {nextStep.InPut}");
|
||||||
|
|
||||||
|
targetFrame++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int byFrameIdx = 0;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 往前推进1帧的Input(返回是否变化)
|
||||||
|
/// </summary>
|
||||||
|
public bool NextFrame(out ReplayStep data)
|
||||||
|
{
|
||||||
|
return TakeFrame(1,out data);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 往前推进指定帧数量的Input (返回是否变化)
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="addFrame"></param>
|
||||||
|
public bool TakeFrame(int addFrame,out ReplayStep data)
|
||||||
|
{
|
||||||
|
bool Changed = false;
|
||||||
|
mCurrFrame += addFrame;
|
||||||
|
if (mCurrFrame >= nextStep.FrameStartID)
|
||||||
|
{
|
||||||
|
Changed = currStep.InPut != nextStep.InPut;
|
||||||
|
currStep = nextStep;
|
||||||
|
data = currStep;
|
||||||
|
UpdateNextFrame(mCurrFrame);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
data = currStep;
|
||||||
|
}
|
||||||
|
return Changed;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 往前推进帧的,指定帧下标
|
||||||
|
/// </summary>
|
||||||
|
public bool NextFramebyFrameIdx(int FrameID, out ReplayStep data)
|
||||||
|
{
|
||||||
|
bool res = TakeFrame(FrameID - byFrameIdx, out data);
|
||||||
|
byFrameIdx = FrameID;
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
mStream.Dispose();
|
||||||
|
mBinaryReader.Dispose();
|
||||||
|
//TODO
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,11 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 66e0e18d1f5981745a3078e8460cb0e6
|
||||||
|
MonoImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
serializedVersion: 2
|
||||||
|
defaultReferences: []
|
||||||
|
executionOrder: 0
|
||||||
|
icon: {instanceID: 0}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
156
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay/ReplayWriter.cs
Normal file
156
AxibugEmuOnline.Client/Assets/Plugins/AxiReplay/ReplayWriter.cs
Normal file
@ -0,0 +1,156 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
|
using System.Text;
|
||||||
|
|
||||||
|
namespace AxiReplay
|
||||||
|
{
|
||||||
|
public class ReplayWriter : IReplayWriter
|
||||||
|
{
|
||||||
|
public ReplayData.ReplayFormat mFormat { get; private set; }
|
||||||
|
public Encoding TexEncoding { get; private set; }
|
||||||
|
ReplayHandler handler;
|
||||||
|
string mTitle;
|
||||||
|
string mNote;
|
||||||
|
int mAllFrame;
|
||||||
|
int mAllTime;
|
||||||
|
long mData;
|
||||||
|
int mSingleInputLenght;
|
||||||
|
int mSingleDataLenght;
|
||||||
|
MemoryStream mStream;
|
||||||
|
BinaryWriter mBinaryWriter;
|
||||||
|
|
||||||
|
int mCurrFrame;
|
||||||
|
UInt64 mCurrInput;
|
||||||
|
ReplayStep wirteStep;
|
||||||
|
|
||||||
|
List<string> dbgList = new List<string>();
|
||||||
|
|
||||||
|
public ReplayWriter(string Title, string Note, ReplayData.ReplayFormat format, Encoding encoding)
|
||||||
|
{
|
||||||
|
mTitle = Title;
|
||||||
|
mNote = Note;
|
||||||
|
TexEncoding = encoding;
|
||||||
|
mFormat = format;
|
||||||
|
switch (mFormat)
|
||||||
|
{
|
||||||
|
case ReplayData.ReplayFormat.FM32IP64: mSingleInputLenght = sizeof(UInt64); break;
|
||||||
|
case ReplayData.ReplayFormat.FM32IP32: mSingleInputLenght = sizeof(UInt32); break;
|
||||||
|
case ReplayData.ReplayFormat.FM32IP16: mSingleInputLenght = sizeof(UInt16); break;
|
||||||
|
case ReplayData.ReplayFormat.FM32IPBYTE: mSingleInputLenght = sizeof(byte); break;
|
||||||
|
}
|
||||||
|
mSingleDataLenght = (sizeof(UInt32)) + mSingleInputLenght;
|
||||||
|
|
||||||
|
mStream = new MemoryStream();
|
||||||
|
mBinaryWriter = new BinaryWriter(mStream);
|
||||||
|
|
||||||
|
mCurrFrame = -1;
|
||||||
|
mCurrInput = int.MaxValue;
|
||||||
|
wirteStep = new ReplayStep();
|
||||||
|
|
||||||
|
dbgList.Clear();
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
int byFrameIdx = 0;
|
||||||
|
/// <summary>
|
||||||
|
/// 往前推进帧的,指定帧下标
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="frameInput"></param>
|
||||||
|
public void NextFramebyFrameIdx(int FrameID,UInt64 frameInput)
|
||||||
|
{
|
||||||
|
TakeFrame(FrameID - byFrameIdx, frameInput);
|
||||||
|
byFrameIdx = FrameID;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 往前推进1帧的Input
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="frameInput"></param>
|
||||||
|
public void NextFrame(UInt64 frameInput)
|
||||||
|
{
|
||||||
|
TakeFrame(1, frameInput);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 往前推进指定帧数量的Input
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="frameInput"></param>
|
||||||
|
public void TakeFrame(int addFrame, UInt64 frameInput)
|
||||||
|
{
|
||||||
|
if (addFrame < 0)
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
mCurrFrame += addFrame;
|
||||||
|
if (mCurrInput == frameInput)
|
||||||
|
return;
|
||||||
|
mCurrInput = frameInput;
|
||||||
|
|
||||||
|
wirteStep.FrameStartID = mCurrFrame;
|
||||||
|
wirteStep.InPut = mCurrInput;
|
||||||
|
dbgList.Add($"{mCurrFrame} | {mCurrInput}");
|
||||||
|
|
||||||
|
switch (mFormat)
|
||||||
|
{
|
||||||
|
case ReplayData.ReplayFormat.FM32IP64:
|
||||||
|
mBinaryWriter.Write(wirteStep.FrameStartID);
|
||||||
|
mBinaryWriter.Write(wirteStep.InPut);
|
||||||
|
break;
|
||||||
|
case ReplayData.ReplayFormat.FM32IP32:
|
||||||
|
mBinaryWriter.Write(BitConverter.GetBytes(wirteStep.All64Data), 0, 4 + 4);
|
||||||
|
break;
|
||||||
|
case ReplayData.ReplayFormat.FM32IP16:
|
||||||
|
mBinaryWriter.Write(BitConverter.GetBytes(wirteStep.All64Data), 0, 4 + 2);
|
||||||
|
break;
|
||||||
|
case ReplayData.ReplayFormat.FM32IPBYTE:
|
||||||
|
mBinaryWriter.Write(BitConverter.GetBytes(wirteStep.All64Data), 0, 4 + 1);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SaveData(string path, bool bWithDump = false, string dumppath = null)
|
||||||
|
{
|
||||||
|
ReplayData.GetStringByteData(mTitle, out byte[] titleData, out int titleLenghtWithEnd, TexEncoding);
|
||||||
|
ReplayData.GetStringByteData(mNote, out byte[] noteData, out int noteLenghtWithEnd, TexEncoding);
|
||||||
|
|
||||||
|
ReplayHandler handler = new ReplayHandler();
|
||||||
|
handler.Format = (int)this.mFormat;
|
||||||
|
handler.DataOffset = ReplayData.HandlerLenght;
|
||||||
|
handler.CreateTime = DateTimeOffset.UtcNow.ToUnixTimeSeconds();
|
||||||
|
handler.AllFrame = wirteStep.FrameStartID;
|
||||||
|
handler.SingleLenght = mSingleDataLenght;
|
||||||
|
|
||||||
|
using (FileStream fs = new FileStream(path, FileMode.Create))
|
||||||
|
{
|
||||||
|
using (BinaryWriter bw = new BinaryWriter(fs))
|
||||||
|
{
|
||||||
|
//写入Handler
|
||||||
|
bw.Write(ReplayData.GetHandlerData(handler));
|
||||||
|
//写入Data
|
||||||
|
bw.Write(mStream.ToArray());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (bWithDump)
|
||||||
|
{
|
||||||
|
List<string> temp = new List<string>();
|
||||||
|
temp.Add($"Format => {handler.Format}");
|
||||||
|
temp.Add($"DataOffset => {handler.DataOffset}");
|
||||||
|
temp.Add($"CreateTime => {handler.CreateTime}");
|
||||||
|
temp.Add($"AllFrame => {handler.AllFrame}");
|
||||||
|
temp.Add($"SingleLenght => {handler.SingleLenght}");
|
||||||
|
dbgList.InsertRange(0,temp);
|
||||||
|
File.WriteAllLines(dumppath, dbgList);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
mStream.Dispose();
|
||||||
|
mBinaryWriter.Dispose();
|
||||||
|
//TODO
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,11 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: dc53a3d9a3e1749438b6ad1cef7b39bc
|
||||||
|
MonoImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
serializedVersion: 2
|
||||||
|
defaultReferences: []
|
||||||
|
executionOrder: 0
|
||||||
|
icon: {instanceID: 0}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
@ -1,22 +0,0 @@
|
|||||||
fileFormatVersion: 2
|
|
||||||
guid: a811bde74b26b53498b4f6d872b09b6d
|
|
||||||
PluginImporter:
|
|
||||||
serializedVersion: 1
|
|
||||||
iconMap: {}
|
|
||||||
executionOrder: {}
|
|
||||||
isPreloaded: 0
|
|
||||||
platformData:
|
|
||||||
Any:
|
|
||||||
enabled: 1
|
|
||||||
settings: {}
|
|
||||||
Editor:
|
|
||||||
enabled: 0
|
|
||||||
settings:
|
|
||||||
DefaultValueInitialized: true
|
|
||||||
WindowsStoreApps:
|
|
||||||
enabled: 0
|
|
||||||
settings:
|
|
||||||
CPU: AnyCPU
|
|
||||||
userData:
|
|
||||||
assetBundleName:
|
|
||||||
assetBundleVariant:
|
|
@ -1,22 +0,0 @@
|
|||||||
fileFormatVersion: 2
|
|
||||||
guid: 45d5034162d6cf04dbe46da84fc7d074
|
|
||||||
PluginImporter:
|
|
||||||
serializedVersion: 1
|
|
||||||
iconMap: {}
|
|
||||||
executionOrder: {}
|
|
||||||
isPreloaded: 0
|
|
||||||
platformData:
|
|
||||||
Any:
|
|
||||||
enabled: 0
|
|
||||||
settings: {}
|
|
||||||
Editor:
|
|
||||||
enabled: 1
|
|
||||||
settings:
|
|
||||||
DefaultValueInitialized: true
|
|
||||||
WindowsStoreApps:
|
|
||||||
enabled: 0
|
|
||||||
settings:
|
|
||||||
CPU: AnyCPU
|
|
||||||
userData:
|
|
||||||
assetBundleName:
|
|
||||||
assetBundleVariant:
|
|
BIN
AxibugEmuOnline.Client/Assets/Plugins/MyNes.Standard2.dll
Normal file
BIN
AxibugEmuOnline.Client/Assets/Plugins/MyNes.Standard2.dll
Normal file
Binary file not shown.
@ -0,0 +1,86 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 1818bd4d6ed568f4f98c1750b011c967
|
||||||
|
PluginImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
serializedVersion: 2
|
||||||
|
iconMap: {}
|
||||||
|
executionOrder: {}
|
||||||
|
defineConstraints: []
|
||||||
|
isPreloaded: 0
|
||||||
|
isOverridable: 0
|
||||||
|
isExplicitlyReferenced: 0
|
||||||
|
validateReferences: 1
|
||||||
|
platformData:
|
||||||
|
- first:
|
||||||
|
: Any
|
||||||
|
second:
|
||||||
|
enabled: 0
|
||||||
|
settings:
|
||||||
|
Exclude Android: 0
|
||||||
|
Exclude Editor: 0
|
||||||
|
Exclude Linux64: 0
|
||||||
|
Exclude OSXUniversal: 0
|
||||||
|
Exclude Win: 0
|
||||||
|
Exclude Win64: 0
|
||||||
|
Exclude iOS: 0
|
||||||
|
- first:
|
||||||
|
Android: Android
|
||||||
|
second:
|
||||||
|
enabled: 1
|
||||||
|
settings:
|
||||||
|
CPU: ARMv7
|
||||||
|
- first:
|
||||||
|
Any:
|
||||||
|
second:
|
||||||
|
enabled: 1
|
||||||
|
settings: {}
|
||||||
|
- first:
|
||||||
|
Editor: Editor
|
||||||
|
second:
|
||||||
|
enabled: 1
|
||||||
|
settings:
|
||||||
|
CPU: AnyCPU
|
||||||
|
DefaultValueInitialized: true
|
||||||
|
OS: AnyOS
|
||||||
|
- first:
|
||||||
|
Standalone: Linux64
|
||||||
|
second:
|
||||||
|
enabled: 1
|
||||||
|
settings:
|
||||||
|
CPU: None
|
||||||
|
- first:
|
||||||
|
Standalone: OSXUniversal
|
||||||
|
second:
|
||||||
|
enabled: 1
|
||||||
|
settings:
|
||||||
|
CPU: None
|
||||||
|
- first:
|
||||||
|
Standalone: Win
|
||||||
|
second:
|
||||||
|
enabled: 1
|
||||||
|
settings:
|
||||||
|
CPU: x86
|
||||||
|
- first:
|
||||||
|
Standalone: Win64
|
||||||
|
second:
|
||||||
|
enabled: 1
|
||||||
|
settings:
|
||||||
|
CPU: x86_64
|
||||||
|
- first:
|
||||||
|
Windows Store Apps: WindowsStoreApps
|
||||||
|
second:
|
||||||
|
enabled: 0
|
||||||
|
settings:
|
||||||
|
CPU: AnyCPU
|
||||||
|
- first:
|
||||||
|
iPhone: iOS
|
||||||
|
second:
|
||||||
|
enabled: 1
|
||||||
|
settings:
|
||||||
|
AddToEmbeddedBinaries: false
|
||||||
|
CPU: AnyCPU
|
||||||
|
CompileFlags:
|
||||||
|
FrameworkDependencies:
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
1
AxibugEmuOnline.Client/Assets/Resources/BillingMode.json
Normal file
1
AxibugEmuOnline.Client/Assets/Resources/BillingMode.json
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"androidStore":"GooglePlay"}
|
@ -0,0 +1,7 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: e4ccda23241d6af42ae6d1dc84bf75cd
|
||||||
|
TextScriptImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
8
AxibugEmuOnline.Client/Assets/Resources/Roms.meta
Normal file
8
AxibugEmuOnline.Client/Assets/Resources/Roms.meta
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: d830a09fe661cf84cacc42badaf2b40a
|
||||||
|
folderAsset: yes
|
||||||
|
DefaultImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
BIN
AxibugEmuOnline.Client/Assets/Resources/Roms/tstd2.nes.bytes
Normal file
BIN
AxibugEmuOnline.Client/Assets/Resources/Roms/tstd2.nes.bytes
Normal file
Binary file not shown.
@ -0,0 +1,7 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 8699750fbb17aca46835f0748d2344d0
|
||||||
|
TextScriptImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
@ -9,7 +9,6 @@ namespace AxibugEmuOnline.Client.ClientCore
|
|||||||
public static class AppAxibugEmuOnline
|
public static class AppAxibugEmuOnline
|
||||||
{
|
{
|
||||||
public static string TokenStr;
|
public static string TokenStr;
|
||||||
public static long RID = -1;
|
|
||||||
public static string IP;
|
public static string IP;
|
||||||
public static int Port;
|
public static int Port;
|
||||||
public static LogManager log;
|
public static LogManager log;
|
||||||
|
@ -3,7 +3,8 @@
|
|||||||
"rootNamespace": "AxibugEmuOnline.Client",
|
"rootNamespace": "AxibugEmuOnline.Client",
|
||||||
"references": [
|
"references": [
|
||||||
"GUID:390a2c4058e5c304a87e8be70c84d80b",
|
"GUID:390a2c4058e5c304a87e8be70c84d80b",
|
||||||
"GUID:085dc26d74e6f994a924d401ea41a5a8"
|
"GUID:085dc26d74e6f994a924d401ea41a5a8",
|
||||||
|
"GUID:0a45db2096af23647aaafe5b70ccb4d7"
|
||||||
],
|
],
|
||||||
"includePlatforms": [],
|
"includePlatforms": [],
|
||||||
"excludePlatforms": [],
|
"excludePlatforms": [],
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
using System;
|
using System;
|
||||||
|
using System.IO;
|
||||||
|
using System.IO.Compression;
|
||||||
|
|
||||||
namespace AxibugEmuOnline.Client.Common
|
namespace AxibugEmuOnline.Client.Common
|
||||||
{
|
{
|
||||||
@ -18,5 +20,27 @@ namespace AxibugEmuOnline.Client.Common
|
|||||||
TimeSpan ts = dt - new DateTime(1970, 1, 1, 0, 0, 0, 0);
|
TimeSpan ts = dt - new DateTime(1970, 1, 1, 0, 0, 0, 0);
|
||||||
return Convert.ToInt64(ts.TotalSeconds);
|
return Convert.ToInt64(ts.TotalSeconds);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static byte[] CompressByteArray(byte[] bytesToCompress)
|
||||||
|
{
|
||||||
|
using (var compressedMemoryStream = new MemoryStream())
|
||||||
|
using (var gzipStream = new GZipStream(compressedMemoryStream, CompressionMode.Compress))
|
||||||
|
{
|
||||||
|
gzipStream.Write(bytesToCompress, 0, bytesToCompress.Length);
|
||||||
|
gzipStream.Close();
|
||||||
|
return compressedMemoryStream.ToArray();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static byte[] DecompressByteArray(byte[] compressedBytes)
|
||||||
|
{
|
||||||
|
using (var compressedMemoryStream = new MemoryStream(compressedBytes))
|
||||||
|
using (var gzipStream = new GZipStream(compressedMemoryStream, CompressionMode.Decompress))
|
||||||
|
using (var resultMemoryStream = new MemoryStream())
|
||||||
|
{
|
||||||
|
gzipStream.CopyTo(resultMemoryStream);
|
||||||
|
return resultMemoryStream.ToArray();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3,6 +3,39 @@
|
|||||||
public enum EEvent
|
public enum EEvent
|
||||||
{
|
{
|
||||||
// 添加你自己需要的事件类型
|
// 添加你自己需要的事件类型
|
||||||
OnChatMsg
|
OnChatMsg,
|
||||||
|
|
||||||
|
|
||||||
|
OnRoomListAllUpdate,//房间列表全量刷新
|
||||||
|
OnRoomListSingleUpdate,//房间列表中单个更新
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 我进入房间
|
||||||
|
/// </summary>
|
||||||
|
OnMineJoinRoom,
|
||||||
|
/// <summary>
|
||||||
|
/// 我离开房间
|
||||||
|
/// </summary>
|
||||||
|
OnMineLeavnRoom,
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 其他人进入房间
|
||||||
|
/// </summary>
|
||||||
|
OnOtherPlayerJoinRoom,
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 其他人离开房间
|
||||||
|
/// </summary>
|
||||||
|
OnOtherPlayerLeavnRoom,
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 服务器等待Step更新
|
||||||
|
/// </summary>
|
||||||
|
OnRoomWaitStepChange,
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 要求加载即时存档
|
||||||
|
/// </summary>
|
||||||
|
OnRoomNeedLoadRawData,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3,8 +3,6 @@ using AxibugEmuOnline.Client.Common;
|
|||||||
using AxibugEmuOnline.Client.Network;
|
using AxibugEmuOnline.Client.Network;
|
||||||
using AxibugProtobuf;
|
using AxibugProtobuf;
|
||||||
using Google.Protobuf;
|
using Google.Protobuf;
|
||||||
using System.IO;
|
|
||||||
using System.IO.Compression;
|
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
|
||||||
namespace AxibugEmuOnline.Client.Manager
|
namespace AxibugEmuOnline.Client.Manager
|
||||||
@ -23,7 +21,7 @@ namespace AxibugEmuOnline.Client.Manager
|
|||||||
|
|
||||||
public void SendScreen(byte[] RenderBuffer)
|
public void SendScreen(byte[] RenderBuffer)
|
||||||
{
|
{
|
||||||
byte[] comData = CompressByteArray(RenderBuffer);
|
byte[] comData = Helper.CompressByteArray(RenderBuffer);
|
||||||
_Protobuf_Screnn_Frame.FrameID = 0;
|
_Protobuf_Screnn_Frame.FrameID = 0;
|
||||||
_Protobuf_Screnn_Frame.RawBitmap = ByteString.CopyFrom(comData);
|
_Protobuf_Screnn_Frame.RawBitmap = ByteString.CopyFrom(comData);
|
||||||
AppAxibugEmuOnline.networkHelper.SendToServer((int)CommandID.CmdScreen, ProtoBufHelper.Serizlize(_Protobuf_Screnn_Frame));
|
AppAxibugEmuOnline.networkHelper.SendToServer((int)CommandID.CmdScreen, ProtoBufHelper.Serizlize(_Protobuf_Screnn_Frame));
|
||||||
@ -34,7 +32,7 @@ namespace AxibugEmuOnline.Client.Manager
|
|||||||
Protobuf_Screnn_Frame msg = ProtoBufHelper.DeSerizlize<Protobuf_Screnn_Frame>(reqData);
|
Protobuf_Screnn_Frame msg = ProtoBufHelper.DeSerizlize<Protobuf_Screnn_Frame>(reqData);
|
||||||
lock (_renderbuffer)
|
lock (_renderbuffer)
|
||||||
{
|
{
|
||||||
byte[] data = DecompressByteArray(msg.RawBitmap.ToArray());
|
byte[] data = Helper.DecompressByteArray(msg.RawBitmap.ToArray());
|
||||||
for (int i = 0; i < data.Length; i++)
|
for (int i = 0; i < data.Length; i++)
|
||||||
{
|
{
|
||||||
_renderbuffer[i] = _palette[data[i]];
|
_renderbuffer[i] = _palette[data[i]];
|
||||||
@ -42,26 +40,6 @@ namespace AxibugEmuOnline.Client.Manager
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static byte[] CompressByteArray(byte[] bytesToCompress)
|
|
||||||
{
|
|
||||||
using (var compressedMemoryStream = new MemoryStream())
|
|
||||||
using (var gzipStream = new GZipStream(compressedMemoryStream, CompressionMode.Compress))
|
|
||||||
{
|
|
||||||
gzipStream.Write(bytesToCompress, 0, bytesToCompress.Length);
|
|
||||||
gzipStream.Close();
|
|
||||||
return compressedMemoryStream.ToArray();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static byte[] DecompressByteArray(byte[] compressedBytes)
|
|
||||||
{
|
|
||||||
using (var compressedMemoryStream = new MemoryStream(compressedBytes))
|
|
||||||
using (var gzipStream = new GZipStream(compressedMemoryStream, CompressionMode.Decompress))
|
|
||||||
using (var resultMemoryStream = new MemoryStream())
|
|
||||||
{
|
|
||||||
gzipStream.CopyTo(resultMemoryStream);
|
|
||||||
return resultMemoryStream.ToArray();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
326
AxibugEmuOnline.Client/Assets/Script/Manager/AppRoom.cs
Normal file
326
AxibugEmuOnline.Client/Assets/Script/Manager/AppRoom.cs
Normal file
@ -0,0 +1,326 @@
|
|||||||
|
using AxibugEmuOnline.Client.ClientCore;
|
||||||
|
using AxibugEmuOnline.Client.Common;
|
||||||
|
using AxibugEmuOnline.Client.Event;
|
||||||
|
using AxibugEmuOnline.Client.Network;
|
||||||
|
using AxibugProtobuf;
|
||||||
|
using AxiReplay;
|
||||||
|
using Google.Protobuf;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using UnityEngine;
|
||||||
|
|
||||||
|
namespace AxibugEmuOnline.Client.Manager
|
||||||
|
{
|
||||||
|
public class AppRoom
|
||||||
|
{
|
||||||
|
public Protobuf_Room_MiniInfo mineRoomMiniInfo { get; private set; } = null;
|
||||||
|
public bool InRoom => mineRoomMiniInfo != null;
|
||||||
|
public bool IsHost => mineRoomMiniInfo?.HostPlayerUID == AppAxibugEmuOnline.user.userdata.UID;
|
||||||
|
public RoomGameState RoomState => mineRoomMiniInfo.GameState;
|
||||||
|
public int MinePlayerIdx => GetMinePlayerIndex();
|
||||||
|
public int WaitStep { get; private set; } = -1;
|
||||||
|
public byte[] RawData { get; private set; } = null;
|
||||||
|
public NetReplay netReplay { get; private set; }
|
||||||
|
|
||||||
|
|
||||||
|
Dictionary<int, Protobuf_Room_MiniInfo> dictRoomListID2Info = new Dictionary<int, Protobuf_Room_MiniInfo>();
|
||||||
|
static Protobuf_Room_List _Protobuf_Room_List = new Protobuf_Room_List();
|
||||||
|
static Protobuf_Room_Create _Protobuf_Room_Create = new Protobuf_Room_Create();
|
||||||
|
static Protobuf_Room_Join _Protobuf_Room_Join = new Protobuf_Room_Join();
|
||||||
|
static Protobuf_Room_Leave _Protobuf_Room_Leave = new Protobuf_Room_Leave();
|
||||||
|
static Protobuf_Room_Player_Ready _Protobuf_Room_Player_Ready = new Protobuf_Room_Player_Ready();
|
||||||
|
static Protobuf_Room_SinglePlayerInputData _Protobuf_Room_SinglePlayerInputData = new Protobuf_Room_SinglePlayerInputData();
|
||||||
|
public AppRoom()
|
||||||
|
{
|
||||||
|
NetMsg.Instance.RegNetMsgEvent((int)CommandID.CmdRoomList, RecvGetRoomList);
|
||||||
|
NetMsg.Instance.RegNetMsgEvent((int)CommandID.CmdRoomListUpdate, RecvGetRoomListUpdate);
|
||||||
|
NetMsg.Instance.RegNetMsgEvent((int)CommandID.CmdRoomCreate, RecvCreateRoom);
|
||||||
|
NetMsg.Instance.RegNetMsgEvent((int)CommandID.CmdRoomJoin, RecvJoinRoom);
|
||||||
|
NetMsg.Instance.RegNetMsgEvent((int)CommandID.CmdRoomLeave, RecvLeavnRoom);
|
||||||
|
NetMsg.Instance.RegNetMsgEvent((int)CommandID.CmdRoomMyRoomStateChanged, RecvRoomMyRoomStateChange);
|
||||||
|
NetMsg.Instance.RegNetMsgEvent((int)CommandID.CmdRoomWaitStep, RecvRoom_WaitStep);
|
||||||
|
NetMsg.Instance.RegNetMsgEvent((int)CommandID.CmdRoomHostPlayerUpdateStateRaw, RecvHostPlayer_UpdateStateRaw);
|
||||||
|
NetMsg.Instance.RegNetMsgEvent((int)CommandID.CmdRoomSynPlayerInput, RecvHostSyn_RoomFrameAllInputData);
|
||||||
|
}
|
||||||
|
|
||||||
|
#region 房间列表管理
|
||||||
|
void AddOrUpdateRoomList(Protobuf_Room_MiniInfo roomInfo)
|
||||||
|
{
|
||||||
|
dictRoomListID2Info[roomInfo.RoomID] = roomInfo;
|
||||||
|
}
|
||||||
|
bool RemoveRoomList(int roomId)
|
||||||
|
{
|
||||||
|
if (dictRoomListID2Info.ContainsKey(roomId))
|
||||||
|
{
|
||||||
|
dictRoomListID2Info.Remove(roomId);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
/// <summary>
|
||||||
|
/// 获取单个房间MiniInfo
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="roomId"></param>
|
||||||
|
/// <param name="MiniInfo"></param>
|
||||||
|
/// <returns></returns>
|
||||||
|
public bool GetRoomListMiniInfo(int roomId, out Protobuf_Room_MiniInfo MiniInfo)
|
||||||
|
{
|
||||||
|
if (dictRoomListID2Info.ContainsKey(roomId))
|
||||||
|
{
|
||||||
|
MiniInfo = dictRoomListID2Info[roomId];
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
MiniInfo = null;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
public List<Protobuf_Room_MiniInfo> GetRoomList()
|
||||||
|
{
|
||||||
|
List<Protobuf_Room_MiniInfo> result = new List<Protobuf_Room_MiniInfo>();
|
||||||
|
foreach (var item in dictRoomListID2Info)
|
||||||
|
{
|
||||||
|
result.Add(new Protobuf_Room_MiniInfo());
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region Replay
|
||||||
|
public void InitRePlay()
|
||||||
|
{
|
||||||
|
netReplay = new NetReplay();
|
||||||
|
}
|
||||||
|
public void ReleaseRePlay()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region 房间管理
|
||||||
|
int GetMinePlayerIndex()
|
||||||
|
{
|
||||||
|
if (mineRoomMiniInfo == null)
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
if (mineRoomMiniInfo.Player1UID == AppAxibugEmuOnline.user.userdata.UID)
|
||||||
|
return 0;
|
||||||
|
if (mineRoomMiniInfo.Player2UID == AppAxibugEmuOnline.user.userdata.UID)
|
||||||
|
return 1;
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
long[] GetRoom4Player()
|
||||||
|
{
|
||||||
|
if (mineRoomMiniInfo == null)
|
||||||
|
return null;
|
||||||
|
long[] result = new long[4];
|
||||||
|
|
||||||
|
if (mineRoomMiniInfo.Player1UID > 0)
|
||||||
|
result[0] = mineRoomMiniInfo.Player1UID;
|
||||||
|
if (mineRoomMiniInfo.Player2UID == AppAxibugEmuOnline.user.userdata.UID)
|
||||||
|
result[1] = mineRoomMiniInfo.Player2UID;
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 获取所有房间列表
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="ChatMsg"></param>
|
||||||
|
public void SendGetRoomList()
|
||||||
|
{
|
||||||
|
AppAxibugEmuOnline.log.Info("拉取房间列表");
|
||||||
|
AppAxibugEmuOnline.networkHelper.SendToServer((int)CommandID.CmdRoomList, ProtoBufHelper.Serizlize(_Protobuf_Room_List));
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 获取所有房间列表
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="reqData"></param>
|
||||||
|
void RecvGetRoomList(byte[] reqData)
|
||||||
|
{
|
||||||
|
AppAxibugEmuOnline.log.Info("取得完整房间列表");
|
||||||
|
Protobuf_Room_List_RESP msg = ProtoBufHelper.DeSerizlize<Protobuf_Room_List_RESP>(reqData);
|
||||||
|
for (int i = 0; i < msg.RoomMiniInfoList.Count; i++)
|
||||||
|
AddOrUpdateRoomList(msg.RoomMiniInfoList[i]);
|
||||||
|
EventSystem.Instance.PostEvent(EEvent.OnRoomListAllUpdate);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 获取单个列表更新
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="reqData"></param>
|
||||||
|
void RecvGetRoomListUpdate(byte[] reqData)
|
||||||
|
{
|
||||||
|
AppAxibugEmuOnline.log.Debug("单个房间状态更新");
|
||||||
|
Protobuf_Room_Update_RESP msg = ProtoBufHelper.DeSerizlize<Protobuf_Room_Update_RESP>(reqData);
|
||||||
|
AddOrUpdateRoomList(msg.RoomMiniInfo);
|
||||||
|
EventSystem.Instance.PostEvent(EEvent.OnRoomListSingleUpdate, msg.RoomMiniInfo.GameRomID);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 创建房间
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="GameRomID"></param>
|
||||||
|
/// <param name="JoinPlayerIdx"></param>
|
||||||
|
/// <param name="GameRomHash"></param>
|
||||||
|
public void SendCreateRoom(int GameRomID, int JoinPlayerIdx, string GameRomHash = null)
|
||||||
|
{
|
||||||
|
_Protobuf_Room_Create.JoinPlayerIdx = JoinPlayerIdx;
|
||||||
|
_Protobuf_Room_Create.GameRomID = GameRomID;
|
||||||
|
_Protobuf_Room_Create.GameRomHash = GameRomHash;
|
||||||
|
AppAxibugEmuOnline.log.Info($"创建房间");
|
||||||
|
AppAxibugEmuOnline.networkHelper.SendToServer((int)CommandID.CmdRoomCreate, ProtoBufHelper.Serizlize(_Protobuf_Room_Create));
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 创建房间成功
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="reqData"></param>
|
||||||
|
void RecvCreateRoom(byte[] reqData)
|
||||||
|
{
|
||||||
|
AppAxibugEmuOnline.log.Debug("创建房间成功");
|
||||||
|
Protobuf_Room_Create_RESP msg = ProtoBufHelper.DeSerizlize<Protobuf_Room_Create_RESP>(reqData);
|
||||||
|
mineRoomMiniInfo = msg.RoomMiniInfo;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 创建房间
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="GameRomID"></param>
|
||||||
|
/// <param name="JoinPlayerIdx"></param>
|
||||||
|
/// <param name="GameRomHash"></param>
|
||||||
|
public void SendJoinRoom(int RoomID, int JoinPlayerIdx)
|
||||||
|
{
|
||||||
|
_Protobuf_Room_Join.RoomID = RoomID;
|
||||||
|
_Protobuf_Room_Join.PlayerNum = JoinPlayerIdx;
|
||||||
|
AppAxibugEmuOnline.log.Info($"创建房间");
|
||||||
|
AppAxibugEmuOnline.networkHelper.SendToServer((int)CommandID.CmdRoomJoin, ProtoBufHelper.Serizlize(_Protobuf_Room_Join));
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 加入房间成功
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="reqData"></param>
|
||||||
|
void RecvJoinRoom(byte[] reqData)
|
||||||
|
{
|
||||||
|
AppAxibugEmuOnline.log.Debug("加入房间成功");
|
||||||
|
Protobuf_Room_Join_RESP msg = ProtoBufHelper.DeSerizlize<Protobuf_Room_Join_RESP>(reqData);
|
||||||
|
mineRoomMiniInfo = msg.RoomMiniInfo;
|
||||||
|
InitRePlay();
|
||||||
|
EventSystem.Instance.PostEvent(EEvent.OnMineJoinRoom);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 离开房间
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="RoomID"></param>
|
||||||
|
public void SendLeavnRoom(int RoomID)
|
||||||
|
{
|
||||||
|
_Protobuf_Room_Leave.RoomID = RoomID;
|
||||||
|
AppAxibugEmuOnline.log.Info($"创建房间");
|
||||||
|
AppAxibugEmuOnline.networkHelper.SendToServer((int)CommandID.CmdRoomLeave, ProtoBufHelper.Serizlize(_Protobuf_Room_Leave));
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 离开房间成功
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="reqData"></param>
|
||||||
|
void RecvLeavnRoom(byte[] reqData)
|
||||||
|
{
|
||||||
|
AppAxibugEmuOnline.log.Debug("加入房间成功");
|
||||||
|
Protobuf_Room_Leave_RESP msg = ProtoBufHelper.DeSerizlize<Protobuf_Room_Leave_RESP>(reqData);
|
||||||
|
ReleaseRePlay();
|
||||||
|
mineRoomMiniInfo = null;
|
||||||
|
EventSystem.Instance.PostEvent(EEvent.OnMineLeavnRoom);
|
||||||
|
}
|
||||||
|
|
||||||
|
void RecvRoomMyRoomStateChange(byte[] reqData)
|
||||||
|
{
|
||||||
|
Protobuf_Room_MyRoom_State_Change msg = ProtoBufHelper.DeSerizlize<Protobuf_Room_MyRoom_State_Change>(reqData);
|
||||||
|
long[] oldRoomPlayer = GetRoom4Player();
|
||||||
|
mineRoomMiniInfo = msg.RoomMiniInfo;
|
||||||
|
long[] newRoomPlayer = GetRoom4Player();
|
||||||
|
for (int i = 0; i < 4; i++)
|
||||||
|
{
|
||||||
|
long OldPlayer = oldRoomPlayer[i];
|
||||||
|
long NewPlayer = newRoomPlayer[i];
|
||||||
|
if (OldPlayer == NewPlayer)
|
||||||
|
continue;
|
||||||
|
//位置之前有人,但是离开了
|
||||||
|
if (OldPlayer > 0)
|
||||||
|
{
|
||||||
|
EventSystem.Instance.PostEvent(EEvent.OnOtherPlayerLeavnRoom, i, OldPlayer);
|
||||||
|
if (NewPlayer > 0)//而且害换了一个玩家
|
||||||
|
EventSystem.Instance.PostEvent(EEvent.OnOtherPlayerJoinRoom, i, NewPlayer);
|
||||||
|
}
|
||||||
|
else //之前没人
|
||||||
|
EventSystem.Instance.PostEvent(EEvent.OnOtherPlayerJoinRoom, i, NewPlayer);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 上报即时存档
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="RoomID"></param>
|
||||||
|
public void SendLeavnRoom(byte[] RawData)
|
||||||
|
{
|
||||||
|
//压缩
|
||||||
|
byte[] compressRawData = Helper.CompressByteArray(RawData);
|
||||||
|
Protobuf_Room_HostPlayer_UpdateStateRaw msg = new Protobuf_Room_HostPlayer_UpdateStateRaw()
|
||||||
|
{
|
||||||
|
LoadStateRaw = Google.Protobuf.ByteString.CopyFrom(compressRawData)
|
||||||
|
};
|
||||||
|
AppAxibugEmuOnline.log.Info($"上报即时存档数据 原数据大小:{RawData.Length},压缩后;{compressRawData.Length}");
|
||||||
|
AppAxibugEmuOnline.networkHelper.SendToServer((int)CommandID.CmdRoomHostPlayerUpdateStateRaw, ProtoBufHelper.Serizlize(msg));
|
||||||
|
}
|
||||||
|
|
||||||
|
void RecvRoom_WaitStep(byte[] reqData)
|
||||||
|
{
|
||||||
|
Protobuf_Room_WaitStep_RESP msg = ProtoBufHelper.DeSerizlize<Protobuf_Room_WaitStep_RESP>(reqData);
|
||||||
|
if (WaitStep != msg.WaitStep)
|
||||||
|
{
|
||||||
|
WaitStep = msg.WaitStep;
|
||||||
|
EventSystem.Instance.PostEvent(EEvent.OnRoomWaitStepChange, WaitStep);
|
||||||
|
if (WaitStep == 1)
|
||||||
|
{
|
||||||
|
byte[] decompressRawData = Helper.DecompressByteArray(msg.LoadStateRaw.ToByteArray());
|
||||||
|
AppAxibugEmuOnline.log.Info($"收到即时存档数据 解压后;{decompressRawData.Length}");
|
||||||
|
RawData = decompressRawData;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RecvHostPlayer_UpdateStateRaw(byte[] reqData)
|
||||||
|
{
|
||||||
|
Protobuf_Room_HostPlayer_UpdateStateRaw_RESP msg = ProtoBufHelper.DeSerizlize<Protobuf_Room_HostPlayer_UpdateStateRaw_RESP>(reqData);
|
||||||
|
AppAxibugEmuOnline.log.Info($"鸡翅孙当上报成功");
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 即时存档加载完毕
|
||||||
|
/// </summary>
|
||||||
|
public void SendRoomPlayerReady()
|
||||||
|
{
|
||||||
|
AppAxibugEmuOnline.log.Debug("上报准备完毕");
|
||||||
|
AppAxibugEmuOnline.networkHelper.SendToServer((int)CommandID.CmdRoomPlayerReady, ProtoBufHelper.Serizlize(_Protobuf_Room_Player_Ready));
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 同步上行
|
||||||
|
/// </summary>
|
||||||
|
public void SendRoomSingelPlayerInput(uint FrameID,uint InputData)
|
||||||
|
{
|
||||||
|
_Protobuf_Room_SinglePlayerInputData.FrameID = FrameID;
|
||||||
|
_Protobuf_Room_SinglePlayerInputData.InputData = InputData;
|
||||||
|
AppAxibugEmuOnline.networkHelper.SendToServer((int)CommandID.CmdRoomSingelPlayerInput, ProtoBufHelper.Serizlize(_Protobuf_Room_SinglePlayerInputData));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void RecvHostSyn_RoomFrameAllInputData(byte[] reqData)
|
||||||
|
{
|
||||||
|
Protobuf_Room_Syn_RoomFrameAllInputData msg = ProtoBufHelper.DeSerizlize<Protobuf_Room_Syn_RoomFrameAllInputData>(reqData);
|
||||||
|
netReplay.InData(new ReplayStep() { FrameStartID = (int)msg.FrameID, InPut = msg.InputData });
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
11
AxibugEmuOnline.Client/Assets/Script/Manager/AppRoom.cs.meta
Normal file
11
AxibugEmuOnline.Client/Assets/Script/Manager/AppRoom.cs.meta
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 32566452eb52f484d92619b539b1d70f
|
||||||
|
MonoImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
serializedVersion: 2
|
||||||
|
defaultReferences: []
|
||||||
|
executionOrder: 0
|
||||||
|
icon: {instanceID: 0}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user