feat 客户端

This commit is contained in:
2025-12-17 09:56:43 +08:00
parent d602a16b15
commit 65bd1e5477
30 changed files with 2272 additions and 243 deletions

Binary file not shown.

View File

@@ -0,0 +1,33 @@
fileFormatVersion: 2
guid: 4e701241228a3ab428b568d7a9eb7e22
PluginImporter:
externalObjects: {}
serializedVersion: 2
iconMap: {}
executionOrder: {}
defineConstraints: []
isPreloaded: 0
isOverridable: 0
isExplicitlyReferenced: 0
validateReferences: 1
platformData:
- first:
Any:
second:
enabled: 1
settings: {}
- first:
Editor: Editor
second:
enabled: 0
settings:
DefaultValueInitialized: true
- first:
Windows Store Apps: WindowsStoreApps
second:
enabled: 0
settings:
CPU: AnyCPU
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,33 @@
fileFormatVersion: 2
guid: 07325f6d60fc46f4cbce792ec9cedfb3
PluginImporter:
externalObjects: {}
serializedVersion: 2
iconMap: {}
executionOrder: {}
defineConstraints: []
isPreloaded: 0
isOverridable: 0
isExplicitlyReferenced: 0
validateReferences: 1
platformData:
- first:
Any:
second:
enabled: 1
settings: {}
- first:
Editor: Editor
second:
enabled: 0
settings:
DefaultValueInitialized: true
- first:
Windows Store Apps: WindowsStoreApps
second:
enabled: 0
settings:
CPU: AnyCPU
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 30e44c1fde61af34abfe4b0bb668f7ce
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: e8dab7c23228fa447b7c4f66f7d1ec77
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,177 @@
%YAML 1.1
%TAG !u! tag:unity3d.com,2011:
--- !u!1 &2084311658768222122
GameObject:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
serializedVersion: 6
m_Component:
- component: {fileID: 7414835070702525908}
- component: {fileID: 7093731443316182106}
- component: {fileID: 6228951757656075159}
- component: {fileID: 8667308135367594039}
- component: {fileID: -2296976507622875492}
- component: {fileID: 3176206830247056507}
m_Layer: 0
m_Name: Player
m_TagString: Untagged
m_Icon: {fileID: 0}
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!4 &7414835070702525908
Transform:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 2084311658768222122}
serializedVersion: 2
m_LocalRotation: {x: 0, y: 0, z: 0, w: 1}
m_LocalPosition: {x: 0, y: 0, z: 0}
m_LocalScale: {x: 1, y: 1, z: 1}
m_ConstrainProportionsScale: 0
m_Children: []
m_Father: {fileID: 0}
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
--- !u!212 &7093731443316182106
SpriteRenderer:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 2084311658768222122}
m_Enabled: 1
m_CastShadows: 0
m_ReceiveShadows: 0
m_DynamicOccludee: 1
m_StaticShadowCaster: 0
m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 0
m_RayTraceProcedural: 0
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:
- {fileID: 10754, guid: 0000000000000000f000000000000000, type: 0}
m_StaticBatchInfo:
firstSubMesh: 0
subMeshCount: 0
m_StaticBatchRoot: {fileID: 0}
m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 0
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0
m_StitchLightmapSeams: 1
m_SelectedEditorRenderState: 0
m_MinimumChartSize: 4
m_AutoUVMaxDistance: 0.5
m_AutoUVMaxAngle: 89
m_LightmapParameters: {fileID: 0}
m_SortingLayerID: 0
m_SortingLayer: 0
m_SortingOrder: 2
m_Sprite: {fileID: -2413806693520163455, guid: a86470a33a6bf42c4b3595704624658b, type: 3}
m_Color: {r: 1, g: 1, b: 1, a: 1}
m_FlipX: 0
m_FlipY: 0
m_DrawMode: 0
m_Size: {x: 1, y: 1}
m_AdaptiveModeThreshold: 0.5
m_SpriteTileMode: 0
m_WasSpriteAssigned: 1
m_MaskInteraction: 0
m_SpriteSortPoint: 0
--- !u!50 &6228951757656075159
Rigidbody2D:
serializedVersion: 4
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 2084311658768222122}
m_BodyType: 0
m_Simulated: 1
m_UseFullKinematicContacts: 0
m_UseAutoMass: 0
m_Mass: 1
m_LinearDrag: 0
m_AngularDrag: 0.05
m_GravityScale: 0
m_Material: {fileID: 0}
m_IncludeLayers:
serializedVersion: 2
m_Bits: 0
m_ExcludeLayers:
serializedVersion: 2
m_Bits: 0
m_Interpolate: 0
m_SleepingMode: 1
m_CollisionDetection: 0
m_Constraints: 0
--- !u!58 &8667308135367594039
CircleCollider2D:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 2084311658768222122}
m_Enabled: 1
m_Density: 1
m_Material: {fileID: 0}
m_IncludeLayers:
serializedVersion: 2
m_Bits: 0
m_ExcludeLayers:
serializedVersion: 2
m_Bits: 0
m_LayerOverridePriority: 0
m_ForceSendLayers:
serializedVersion: 2
m_Bits: 4294967295
m_ForceReceiveLayers:
serializedVersion: 2
m_Bits: 4294967295
m_ContactCaptureLayers:
serializedVersion: 2
m_Bits: 4294967295
m_CallbackLayers:
serializedVersion: 2
m_Bits: 4294967295
m_IsTrigger: 0
m_UsedByEffector: 0
m_UsedByComposite: 0
m_Offset: {x: 0, y: 0}
serializedVersion: 2
m_Radius: 0.5
--- !u!114 &-2296976507622875492
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 2084311658768222122}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: e8262c63fb4770549befe57c9245251c, type: 3}
m_Name:
m_EditorClassIdentifier:
--- !u!114 &3176206830247056507
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 2084311658768222122}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: b2fb6c5cc8234d1f853f94a89472348c, type: 3}
m_Name:
m_EditorClassIdentifier:
uid: 0

View File

@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: e051488d35d18a146b594bce989a21f1
PrefabImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -122,168 +122,6 @@ NavMeshSettings:
debug:
m_Flags: 0
m_NavMeshData: {fileID: 0}
--- !u!1 &42881342
GameObject:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
serializedVersion: 6
m_Component:
- component: {fileID: 42881344}
- component: {fileID: 42881343}
- component: {fileID: 42881345}
- component: {fileID: 42881347}
- component: {fileID: 42881346}
m_Layer: 0
m_Name: Player
m_TagString: Untagged
m_Icon: {fileID: 0}
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!212 &42881343
SpriteRenderer:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 42881342}
m_Enabled: 1
m_CastShadows: 0
m_ReceiveShadows: 0
m_DynamicOccludee: 1
m_StaticShadowCaster: 0
m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 0
m_RayTraceProcedural: 0
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:
- {fileID: 10754, guid: 0000000000000000f000000000000000, type: 0}
m_StaticBatchInfo:
firstSubMesh: 0
subMeshCount: 0
m_StaticBatchRoot: {fileID: 0}
m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 0
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0
m_StitchLightmapSeams: 1
m_SelectedEditorRenderState: 0
m_MinimumChartSize: 4
m_AutoUVMaxDistance: 0.5
m_AutoUVMaxAngle: 89
m_LightmapParameters: {fileID: 0}
m_SortingLayerID: 0
m_SortingLayer: 0
m_SortingOrder: 2
m_Sprite: {fileID: -2413806693520163455, guid: a86470a33a6bf42c4b3595704624658b, type: 3}
m_Color: {r: 1, g: 1, b: 1, a: 1}
m_FlipX: 0
m_FlipY: 0
m_DrawMode: 0
m_Size: {x: 1, y: 1}
m_AdaptiveModeThreshold: 0.5
m_SpriteTileMode: 0
m_WasSpriteAssigned: 1
m_MaskInteraction: 0
m_SpriteSortPoint: 0
--- !u!4 &42881344
Transform:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 42881342}
serializedVersion: 2
m_LocalRotation: {x: 0, y: 0, z: 0, w: 1}
m_LocalPosition: {x: 0, y: 0, z: 0}
m_LocalScale: {x: 1, y: 1, z: 1}
m_ConstrainProportionsScale: 0
m_Children: []
m_Father: {fileID: 0}
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
--- !u!114 &42881345
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 42881342}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: e8262c63fb4770549befe57c9245251c, type: 3}
m_Name:
m_EditorClassIdentifier:
moveSpeed: 5
--- !u!58 &42881346
CircleCollider2D:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 42881342}
m_Enabled: 1
m_Density: 1
m_Material: {fileID: 0}
m_IncludeLayers:
serializedVersion: 2
m_Bits: 0
m_ExcludeLayers:
serializedVersion: 2
m_Bits: 0
m_LayerOverridePriority: 0
m_ForceSendLayers:
serializedVersion: 2
m_Bits: 4294967295
m_ForceReceiveLayers:
serializedVersion: 2
m_Bits: 4294967295
m_ContactCaptureLayers:
serializedVersion: 2
m_Bits: 4294967295
m_CallbackLayers:
serializedVersion: 2
m_Bits: 4294967295
m_IsTrigger: 0
m_UsedByEffector: 0
m_UsedByComposite: 0
m_Offset: {x: 0, y: 0}
serializedVersion: 2
m_Radius: 0.5
--- !u!50 &42881347
Rigidbody2D:
serializedVersion: 4
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 42881342}
m_BodyType: 0
m_Simulated: 1
m_UseFullKinematicContacts: 0
m_UseAutoMass: 0
m_Mass: 1
m_LinearDrag: 0
m_AngularDrag: 0.05
m_GravityScale: 0
m_Material: {fileID: 0}
m_IncludeLayers:
serializedVersion: 2
m_Bits: 0
m_ExcludeLayers:
serializedVersion: 2
m_Bits: 0
m_Interpolate: 0
m_SleepingMode: 1
m_CollisionDetection: 0
m_Constraints: 0
--- !u!1 &340097764
GameObject:
m_ObjectHideFlags: 0
@@ -885,6 +723,37 @@ Transform:
- {fileID: 340097765}
m_Father: {fileID: 0}
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
--- !u!1 &1738608076
GameObject:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
serializedVersion: 6
m_Component:
- component: {fileID: 1738608077}
m_Layer: 0
m_Name: PlayerScene
m_TagString: Untagged
m_Icon: {fileID: 0}
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!4 &1738608077
Transform:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1738608076}
serializedVersion: 2
m_LocalRotation: {x: 0, y: 0, z: 0, w: 1}
m_LocalPosition: {x: 0, y: 0, z: 0}
m_LocalScale: {x: 1, y: 1, z: 1}
m_ConstrainProportionsScale: 0
m_Children: []
m_Father: {fileID: 0}
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
--- !u!1 &1943777364
GameObject:
m_ObjectHideFlags: 0
@@ -1024,7 +893,9 @@ GameObject:
serializedVersion: 6
m_Component:
- component: {fileID: 1996456070}
- component: {fileID: 1996456069}
- component: {fileID: 1996456072}
- component: {fileID: 1996456071}
- component: {fileID: 1996456073}
m_Layer: 0
m_Name: Manager
m_TagString: Untagged
@@ -1032,18 +903,6 @@ GameObject:
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!114 &1996456069
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1996456068}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 978b6860fdd772442ba87da5c3024a0d, type: 3}
m_Name:
m_EditorClassIdentifier:
--- !u!4 &1996456070
Transform:
m_ObjectHideFlags: 0
@@ -1059,6 +918,44 @@ Transform:
m_Children: []
m_Father: {fileID: 0}
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
--- !u!114 &1996456071
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1996456068}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: afc9630f7f1a49b5b0e8b13bffa9b4ea, type: 3}
m_Name:
m_EditorClassIdentifier:
--- !u!114 &1996456072
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1996456068}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: d6b127b9486a4f07acfbdcc29fc7d2a5, type: 3}
m_Name:
m_EditorClassIdentifier:
--- !u!114 &1996456073
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1996456068}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 5228fd1670b3455a9900c17b9c1899e6, type: 3}
m_Name:
m_EditorClassIdentifier:
playerPrefab: {fileID: 2084311658768222122, guid: e051488d35d18a146b594bce989a21f1, type: 3}
playerScene: {fileID: 1738608077}
--- !u!1660057539 &9223372036854775807
SceneRoots:
m_ObjectHideFlags: 0
@@ -1066,5 +963,5 @@ SceneRoots:
- {fileID: 519420032}
- {fileID: 933894492}
- {fileID: 1433534646}
- {fileID: 42881344}
- {fileID: 1738608077}
- {fileID: 1996456070}

View File

@@ -1,58 +0,0 @@
using UnityEngine;
using NativeWebSocket;
public class Connection : MonoBehaviour
{
WebSocket websocket;
async void Start()
{
websocket = new WebSocket("ws://localhost:8501?token=1");
websocket.OnOpen += () => { Debug.Log("Connection open!"); };
websocket.OnError += (e) => { Debug.Log("Error! " + e); };
websocket.OnClose += (e) => { Debug.Log("Connection closed!"); };
websocket.OnMessage += (bytes) =>
{
Debug.Log("OnMessage!");
Debug.Log(bytes);
// getting the message as a string
// var message = System.Text.Encoding.UTF8.GetString(bytes);
// Debug.Log("OnMessage! " + message);
};
// Keep sending messages at every 0.3s
// InvokeRepeating("SendWebSocketMessage", 0.0f, 0.3f);
// waiting for messages
await websocket.Connect();
}
void Update()
{
#if !UNITY_WEBGL || UNITY_EDITOR
websocket.DispatchMessageQueue();
#endif
}
async void SendWebSocketMessage()
{
if (websocket.State == WebSocketState.Open)
{
// Sending bytes
await websocket.Send(new byte[] { 10, 20, 30 });
// Sending plain text
await websocket.SendText("plain text message");
}
}
private async void OnApplicationQuit()
{
await websocket.Close();
}
}

View File

@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: f8939796ed96d754dad0824d88e97473
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,64 @@
using System.Collections.Generic;
using Google.Protobuf;
using UnityEngine;
public class PlayerManager : MonoBehaviour
{
public GameObject playerPrefab;
public Transform playerScene;
private Dictionary<int, PlayerMove> _players = new();
public static PlayerManager Instance { get; private set; }
private void Awake()
{
if (Instance != null)
{
Destroy(gameObject);
return;
}
Instance = this;
}
private void Start()
{
SocketMessageManager.Instance.Subscribe(MessageID.EnterInstance, OnEnterInstance);
SocketMessageManager.Instance.Subscribe(MessageID.Position, OnPosition);
SocketManager.Instance.Connect();
}
private GameObject AddPlayer(PositionInfo info)
{
var player = Instantiate(playerPrefab, playerScene);
player.GetComponent<PlayerInfo>().uid = info.UID;
var move = player.GetComponent<PlayerMove>();
move.SetPosition(info.X, info.Y);
_players.Add(info.UID, move);
return player;
}
private void OnEnterInstance(ByteString msg)
{
var enterInstance = S2C_EnterInstance.Parser.ParseFrom(msg);
var player = AddPlayer(enterInstance.Info);
player.AddComponent<PlayerControl>();
}
private void OnPosition(ByteString msg)
{
var position = S2C_Position.Parser.ParseFrom(msg);
foreach (var info in position.Info)
{
if (!_players.ContainsKey(info.UID))
{
AddPlayer(info);
}
else
{
_players[info.UID].SetPosition(info.X, info.Y);
}
}
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: 5228fd1670b3455a9900c17b9c1899e6
timeCreated: 1765791557

View File

@@ -0,0 +1,70 @@
using Google.Protobuf;
using NativeWebSocket;
using UnityEngine;
public class SocketManager : MonoBehaviour
{
private WebSocket _ws;
public static SocketManager Instance { get; private set; }
private void Awake()
{
if (Instance != null)
{
Destroy(gameObject);
return;
}
Instance = this;
}
public async void Connect()
{
_ws = new WebSocket($"wss://www.hlsq.asia/ws/?token={Random.Range(1, 1000)}");
_ws.OnOpen += () =>
{
Debug.Log("Connection open!");
SendMessage(MessageID.EnterInstance, new C2S_EnterInstance
{
InstanceID = 1
});
};
_ws.OnError += (e) => { Debug.Log("Error! " + e); };
_ws.OnClose += (e) => { Debug.Log("Connection closed!"); };
_ws.OnMessage += (bytes) =>
{
var message = Message.Parser.ParseFrom(bytes);
Debug.Log("OnMessage: " + message.ID);
SocketMessageManager.Instance.TriggerEvent(message.ID, message.Payload);
};
await _ws.Connect();
}
public void SendMessage(MessageID id, IMessage msg)
{
var m = new Message
{
ID = id,
Payload = ByteString.CopyFrom(msg.ToByteArray())
};
_ws.Send(m.ToByteArray());
}
private void Update()
{
#if !UNITY_WEBGL || UNITY_EDITOR
_ws?.DispatchMessageQueue();
#endif
}
private async void OnApplicationQuit()
{
await _ws.Close();
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: d6b127b9486a4f07acfbdcc29fc7d2a5
timeCreated: 1765791343

View File

@@ -0,0 +1,55 @@
using System;
using System.Collections.Generic;
using Google.Protobuf;
using UnityEngine;
public class SocketMessageManager : MonoBehaviour
{
// 使用字典存储
private Dictionary<MessageID, Action<ByteString>> _eventDictionary;
public static SocketMessageManager Instance { get; private set; }
private void Awake()
{
if (Instance != null)
{
Destroy(gameObject);
return;
}
Instance = this;
_eventDictionary = new Dictionary<MessageID, Action<ByteString>>();
}
// 订阅事件
public void Subscribe(MessageID messageID, Action<ByteString> listener)
{
if (_eventDictionary.ContainsKey(messageID))
{
_eventDictionary[messageID] += listener;
}
else
{
_eventDictionary[messageID] = listener;
}
}
// 取消订阅
public void Unsubscribe(MessageID messageID, Action<ByteString> listener)
{
if (_eventDictionary.ContainsKey(messageID))
{
_eventDictionary[messageID] -= listener;
}
}
// 触发事件
public void TriggerEvent(MessageID messageID, ByteString data = null)
{
if (_eventDictionary.ContainsKey(messageID))
{
_eventDictionary[messageID]?.Invoke(data);
}
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: afc9630f7f1a49b5b0e8b13bffa9b4ea
timeCreated: 1765791087

View File

@@ -0,0 +1,42 @@
using UnityEngine;
// 玩家控制,只有当前玩家能控制自己角色
public class PlayerControl : MonoBehaviour
{
private const float SendRate = 1f; // 1秒至少发送一次
private float _lastSendTime;
private Vector2 _lastSentDirection = Vector2.zero;
private void Update()
{
var input = new Vector2(
Input.GetAxisRaw("Horizontal"),
Input.GetAxisRaw("Vertical")
);
var currentDir = input == Vector2.zero ? Vector2.zero : input.normalized;
if (Time.time >= _lastSendTime + 1f / SendRate)
{
SendMoveInput(currentDir);
}
else if (currentDir != _lastSentDirection)
{
SendMoveInput(currentDir);
}
}
private void SendMoveInput(Vector2 direction)
{
Debug.Log($"SendMoveInput {direction} {transform.GetComponent<PlayerInfo>().uid}");
_lastSentDirection = direction;
_lastSendTime = Time.time;
SocketManager.Instance.SendMessage(MessageID.Action, new C2S_Action
{
// Sequence = SocketManager.Instance.Sequence,
// Timestamp = (long)(Time.time * 1000),
Action = ActionID.Move,
DirX = (int)(direction.x * 100),
DirY = (int)(direction.y * 100)
});
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: d7c83e290b104d08836d805dd0733f69
timeCreated: 1765872496

View File

@@ -0,0 +1,6 @@
using UnityEngine;
public class PlayerInfo : MonoBehaviour
{
[HideInInspector] public int uid;
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: b2fb6c5cc8234d1f853f94a89472348c
timeCreated: 1765858911

View File

@@ -1,14 +1,23 @@
using UnityEngine;
// 控制玩家移动
public class PlayerMove : MonoBehaviour
{
public float moveSpeed = 5f; // 移动速度
private Vector3 _targetPosition;
private const float SmoothSpeed = 10f;
private void Start()
{
_targetPosition = transform.position;
}
private void Update()
{
var moveX = Input.GetAxis("Horizontal") * moveSpeed * Time.deltaTime;
var moveY = Input.GetAxis("Vertical") * moveSpeed * Time.deltaTime;
transform.position = Vector3.Lerp(transform.position, _targetPosition, SmoothSpeed * Time.deltaTime);
}
transform.Translate(moveX, moveY, 0);
public void SetPosition(float x, float y)
{
_targetPosition = new Vector3(x / 100, y / 100, 0f);
}
}

View File

@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 616d927c0d69413d84be47b97ebda7b4
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

File diff suppressed because it is too large Load Diff

View File

@@ -1,5 +1,5 @@
fileFormatVersion: 2
guid: 978b6860fdd772442ba87da5c3024a0d
guid: 7ca822f0a057b8c42b38e4605c0482d0
MonoImporter:
externalObjects: {}
serializedVersion: 2

View File

@@ -0,0 +1,290 @@
// <auto-generated>
// Generated by the protocol buffer compiler. DO NOT EDIT!
// source: define.proto
// </auto-generated>
#pragma warning disable 1591, 0612, 3021, 8981
#region Designer generated code
using pb = global::Google.Protobuf;
using pbc = global::Google.Protobuf.Collections;
using pbr = global::Google.Protobuf.Reflection;
using scg = global::System.Collections.Generic;
/// <summary>Holder for reflection information generated from define.proto</summary>
public static partial class DefineReflection {
#region Descriptor
/// <summary>File descriptor for define.proto</summary>
public static pbr::FileDescriptor Descriptor {
get { return descriptor; }
}
private static pbr::FileDescriptor descriptor;
static DefineReflection() {
byte[] descriptorData = global::System.Convert.FromBase64String(
string.Concat(
"CgxkZWZpbmUucHJvdG8aD3NjX2NvbW1vbi5wcm90byIyCgdNZXNzYWdlEhYK",
"AklEGAEgASgOMgouTWVzc2FnZUlEEg8KB1BheWxvYWQYAiABKAwqcgoJTWVz",
"c2FnZUlEEhYKEk1FU1NBR0VfSURfSU5WQUxJRBAAEh0KGU1FU1NBR0VfSURf",
"RU5URVJfSU5TVEFOQ0UQARIVChFNRVNTQUdFX0lEX0FDVElPThACEhcKE01F",
"U1NBR0VfSURfUE9TSVRJT04QA0IXWhVjb21tb24vcHJvdG8vc2Mvc2NfcGJi",
"BnByb3RvMw=="));
descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData,
new pbr::FileDescriptor[] { global::ScCommonReflection.Descriptor, },
new pbr::GeneratedClrTypeInfo(new[] {typeof(global::MessageID), }, null, new pbr::GeneratedClrTypeInfo[] {
new pbr::GeneratedClrTypeInfo(typeof(global::Message), global::Message.Parser, new[]{ "ID", "Payload" }, null, null, null, null)
}));
}
#endregion
}
#region Enums
public enum MessageID {
[pbr::OriginalName("MESSAGE_ID_INVALID")] Invalid = 0,
/// <summary>
/// 进入副本
/// </summary>
[pbr::OriginalName("MESSAGE_ID_ENTER_INSTANCE")] EnterInstance = 1,
/// <summary>
/// 指令
/// </summary>
[pbr::OriginalName("MESSAGE_ID_ACTION")] Action = 2,
/// <summary>
/// 位置更新
/// </summary>
[pbr::OriginalName("MESSAGE_ID_POSITION")] Position = 3,
}
#endregion
#region Messages
[global::System.Diagnostics.DebuggerDisplayAttribute("{ToString(),nq}")]
public sealed partial class Message : pb::IMessage<Message>
#if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE
, pb::IBufferMessage
#endif
{
private static readonly pb::MessageParser<Message> _parser = new pb::MessageParser<Message>(() => new Message());
private pb::UnknownFieldSet _unknownFields;
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public static pb::MessageParser<Message> Parser { get { return _parser; } }
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public static pbr::MessageDescriptor Descriptor {
get { return global::DefineReflection.Descriptor.MessageTypes[0]; }
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
pbr::MessageDescriptor pb::IMessage.Descriptor {
get { return Descriptor; }
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public Message() {
OnConstruction();
}
partial void OnConstruction();
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public Message(Message other) : this() {
iD_ = other.iD_;
payload_ = other.payload_;
_unknownFields = pb::UnknownFieldSet.Clone(other._unknownFields);
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public Message Clone() {
return new Message(this);
}
/// <summary>Field number for the "ID" field.</summary>
public const int IDFieldNumber = 1;
private global::MessageID iD_ = global::MessageID.Invalid;
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public global::MessageID ID {
get { return iD_; }
set {
iD_ = value;
}
}
/// <summary>Field number for the "Payload" field.</summary>
public const int PayloadFieldNumber = 2;
private pb::ByteString payload_ = pb::ByteString.Empty;
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public pb::ByteString Payload {
get { return payload_; }
set {
payload_ = pb::ProtoPreconditions.CheckNotNull(value, "value");
}
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public override bool Equals(object other) {
return Equals(other as Message);
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public bool Equals(Message other) {
if (ReferenceEquals(other, null)) {
return false;
}
if (ReferenceEquals(other, this)) {
return true;
}
if (ID != other.ID) return false;
if (Payload != other.Payload) return false;
return Equals(_unknownFields, other._unknownFields);
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public override int GetHashCode() {
int hash = 1;
if (ID != global::MessageID.Invalid) hash ^= ID.GetHashCode();
if (Payload.Length != 0) hash ^= Payload.GetHashCode();
if (_unknownFields != null) {
hash ^= _unknownFields.GetHashCode();
}
return hash;
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public override string ToString() {
return pb::JsonFormatter.ToDiagnosticString(this);
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public void WriteTo(pb::CodedOutputStream output) {
#if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE
output.WriteRawMessage(this);
#else
if (ID != global::MessageID.Invalid) {
output.WriteRawTag(8);
output.WriteEnum((int) ID);
}
if (Payload.Length != 0) {
output.WriteRawTag(18);
output.WriteBytes(Payload);
}
if (_unknownFields != null) {
_unknownFields.WriteTo(output);
}
#endif
}
#if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
void pb::IBufferMessage.InternalWriteTo(ref pb::WriteContext output) {
if (ID != global::MessageID.Invalid) {
output.WriteRawTag(8);
output.WriteEnum((int) ID);
}
if (Payload.Length != 0) {
output.WriteRawTag(18);
output.WriteBytes(Payload);
}
if (_unknownFields != null) {
_unknownFields.WriteTo(ref output);
}
}
#endif
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public int CalculateSize() {
int size = 0;
if (ID != global::MessageID.Invalid) {
size += 1 + pb::CodedOutputStream.ComputeEnumSize((int) ID);
}
if (Payload.Length != 0) {
size += 1 + pb::CodedOutputStream.ComputeBytesSize(Payload);
}
if (_unknownFields != null) {
size += _unknownFields.CalculateSize();
}
return size;
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public void MergeFrom(Message other) {
if (other == null) {
return;
}
if (other.ID != global::MessageID.Invalid) {
ID = other.ID;
}
if (other.Payload.Length != 0) {
Payload = other.Payload;
}
_unknownFields = pb::UnknownFieldSet.MergeFrom(_unknownFields, other._unknownFields);
}
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
public void MergeFrom(pb::CodedInputStream input) {
#if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE
input.ReadRawMessage(this);
#else
uint tag;
while ((tag = input.ReadTag()) != 0) {
switch(tag) {
default:
_unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, input);
break;
case 8: {
ID = (global::MessageID) input.ReadEnum();
break;
}
case 18: {
Payload = input.ReadBytes();
break;
}
}
}
#endif
}
#if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
[global::System.CodeDom.Compiler.GeneratedCode("protoc", null)]
void pb::IBufferMessage.InternalMergeFrom(ref pb::ParseContext input) {
uint tag;
while ((tag = input.ReadTag()) != 0) {
switch(tag) {
default:
_unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, ref input);
break;
case 8: {
ID = (global::MessageID) input.ReadEnum();
break;
}
case 18: {
Payload = input.ReadBytes();
break;
}
}
}
}
#endif
}
#endregion
#endregion Designer generated code

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: d4e8c64e79289b744a0ea4b3a8386ab9
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,35 @@
// <auto-generated>
// Generated by the protocol buffer compiler. DO NOT EDIT!
// source: sc_common.proto
// </auto-generated>
#pragma warning disable 1591, 0612, 3021, 8981
#region Designer generated code
using pb = global::Google.Protobuf;
using pbc = global::Google.Protobuf.Collections;
using pbr = global::Google.Protobuf.Reflection;
using scg = global::System.Collections.Generic;
/// <summary>Holder for reflection information generated from sc_common.proto</summary>
public static partial class ScCommonReflection {
#region Descriptor
/// <summary>File descriptor for sc_common.proto</summary>
public static pbr::FileDescriptor Descriptor {
get { return descriptor; }
}
private static pbr::FileDescriptor descriptor;
static ScCommonReflection() {
byte[] descriptorData = global::System.Convert.FromBase64String(
string.Concat(
"Cg9zY19jb21tb24ucHJvdG9CG1oZY29tbW9uL3Byb3RvL3NjL3NjX2NvbW1v",
"bmIGcHJvdG8z"));
descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData,
new pbr::FileDescriptor[] { },
new pbr::GeneratedClrTypeInfo(null, null, null));
}
#endregion
}
#endregion Designer generated code

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 2858039bb822fe74a92883426174f776
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -44,8 +44,8 @@ PlayerSettings:
m_HolographicTrackingLossScreen: {fileID: 0}
defaultScreenWidth: 1920
defaultScreenHeight: 1080
defaultScreenWidthWeb: 960
defaultScreenHeightWeb: 600
defaultScreenWidthWeb: 1920
defaultScreenHeightWeb: 1080
m_StereoRenderingPath: 0
m_ActiveColorSpace: 1
unsupportedMSAAFallback: 0
@@ -79,7 +79,7 @@ PlayerSettings:
androidAutoRotationBehavior: 1
defaultIsNativeResolution: 1
macRetinaSupport: 1
runInBackground: 0
runInBackground: 1
captureSingleScreen: 0
muteOtherAudioSources: 0
Prepare IOS For Recording: 0
@@ -590,7 +590,7 @@ PlayerSettings:
webGLTemplate: APPLICATION:Default
webGLAnalyzeBuildSize: 0
webGLUseEmbeddedResources: 0
webGLCompressionFormat: 0
webGLCompressionFormat: 2
webGLWasmArithmeticExceptions: 0
webGLLinkerTarget: 1
webGLThreadsSupport: 0