Ver Fonte

保存包

hexiaojie há 1 ano atrás
pai
commit
b47bb71cea
100 ficheiros alterados com 1833 adições e 0 exclusões
  1. 16 0
      Packages/cn.etetet.actorlocation/Ignore.ET.ActorLocation.asmdef
  2. 7 0
      Packages/cn.etetet.actorlocation/Ignore.ET.ActorLocation.asmdef.meta
  3. 30 0
      Packages/cn.etetet.actorlocation/LICENSE
  4. 7 0
      Packages/cn.etetet.actorlocation/LICENSE.meta
  5. 8 0
      Packages/cn.etetet.actorlocation/Proto.meta
  6. 82 0
      Packages/cn.etetet.actorlocation/Proto/ActorLocation_S_20100.proto
  7. 7 0
      Packages/cn.etetet.actorlocation/Proto/ActorLocation_S_20100.proto.meta
  8. 8 0
      Packages/cn.etetet.actorlocation/Scripts.meta
  9. 8 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix.meta
  10. 8 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server.meta
  11. 21 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/FiberInit_Location.cs
  12. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/FiberInit_Location.cs.meta
  13. 140 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/LocationOneTypeSystem.cs
  14. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/LocationOneTypeSystem.cs.meta
  15. 87 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/LocationProxyComponentSystem.cs
  16. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/LocationProxyComponentSystem.cs.meta
  17. 39 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MailBoxType_OrderedMessageHandler.cs
  18. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MailBoxType_OrderedMessageHandler.cs.meta
  19. 107 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationHandler.cs
  20. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationHandler.cs.meta
  21. 287 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationSenderComponentSystem.cs
  22. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationSenderComponentSystem.cs.meta
  23. 23 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationSenderSystem.cs
  24. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationSenderSystem.cs.meta
  25. 13 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectAddRequestHandler.cs
  26. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectAddRequestHandler.cs.meta
  27. 13 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectGetRequestHandler.cs
  28. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectGetRequestHandler.cs.meta
  29. 13 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectLockRequestHandler.cs
  30. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectLockRequestHandler.cs.meta
  31. 13 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectRemoveRequestHandler.cs
  32. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectRemoveRequestHandler.cs.meta
  33. 15 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectUnLockRequestHandler.cs
  34. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectUnLockRequestHandler.cs.meta
  35. 8 0
      Packages/cn.etetet.actorlocation/Scripts/Model.meta
  36. 8 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server.meta
  37. 9 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/ConsoleMode.cs
  38. 3 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/ConsoleMode.cs.meta
  39. 8 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/CoroutineLockType.cs
  40. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/CoroutineLockType.cs.meta
  41. 29 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/LocationComponent.cs
  42. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/LocationComponent.cs.meta
  43. 9 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/LocationProxyComponent.cs
  44. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/LocationProxyComponent.cs.meta
  45. 7 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/MailBoxType.cs
  46. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/MailBoxType.cs.meta
  47. 14 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/MessageLocationSender.cs
  48. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/MessageLocationSender.cs.meta
  49. 18 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/MessageLocationSenderOneType.cs
  50. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/MessageLocationSenderOneType.cs.meta
  51. 7 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/TimerInvokeType.cs
  52. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Server/TimerInvokeType.cs.meta
  53. 8 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Share.meta
  54. 1 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Share/AssemblyReference.asmref
  55. 7 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Share/AssemblyReference.asmref.meta
  56. 12 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Share/ErrorCode.cs
  57. 3 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Share/ErrorCode.cs.meta
  58. 7 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Share/PackageType.cs
  59. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Share/PackageType.cs.meta
  60. 7 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Share/SceneType.cs
  61. 11 0
      Packages/cn.etetet.actorlocation/Scripts/Model/Share/SceneType.cs.meta
  62. 24 0
      Packages/cn.etetet.actorlocation/package.json
  63. 7 0
      Packages/cn.etetet.actorlocation/package.json.meta
  64. 4 0
      Packages/cn.etetet.actorlocation/packagegit.json
  65. 7 0
      Packages/cn.etetet.actorlocation/packagegit.json.meta
  66. 8 0
      Packages/cn.etetet.ai/Excel.meta
  67. BIN
      Packages/cn.etetet.ai/Excel/AIConfig.xlsx
  68. 7 0
      Packages/cn.etetet.ai/Excel/AIConfig.xlsx.meta
  69. 16 0
      Packages/cn.etetet.ai/Ignore.ET.AI.asmdef
  70. 7 0
      Packages/cn.etetet.ai/Ignore.ET.AI.asmdef.meta
  71. 30 0
      Packages/cn.etetet.ai/LICENSE
  72. 7 0
      Packages/cn.etetet.ai/LICENSE.meta
  73. 8 0
      Packages/cn.etetet.ai/Scripts.meta
  74. 8 0
      Packages/cn.etetet.ai/Scripts/Hotfix.meta
  75. 8 0
      Packages/cn.etetet.ai/Scripts/Hotfix/Share.meta
  76. 93 0
      Packages/cn.etetet.ai/Scripts/Hotfix/Share/AIComponentSystem.cs
  77. 11 0
      Packages/cn.etetet.ai/Scripts/Hotfix/Share/AIComponentSystem.cs.meta
  78. 1 0
      Packages/cn.etetet.ai/Scripts/Hotfix/Share/AssemblyReference.asmref
  79. 7 0
      Packages/cn.etetet.ai/Scripts/Hotfix/Share/AssemblyReference.asmref.meta
  80. 8 0
      Packages/cn.etetet.ai/Scripts/Model.meta
  81. 8 0
      Packages/cn.etetet.ai/Scripts/Model/Share.meta
  82. 18 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AAIHandler.cs
  83. 11 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AAIHandler.cs.meta
  84. 15 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AIComponent.cs
  85. 11 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AIComponent.cs.meta
  86. 33 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AIConfig.cs
  87. 3 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AIConfig.cs.meta
  88. 32 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AIDispatcherComponent.cs
  89. 11 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AIDispatcherComponent.cs.meta
  90. 1 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AssemblyReference.asmref
  91. 7 0
      Packages/cn.etetet.ai/Scripts/Model/Share/AssemblyReference.asmref.meta
  92. 7 0
      Packages/cn.etetet.ai/Scripts/Model/Share/PackageType.cs
  93. 3 0
      Packages/cn.etetet.ai/Scripts/Model/Share/PackageType.cs.meta
  94. 7 0
      Packages/cn.etetet.ai/Scripts/Model/Share/TimerInvokeType.cs
  95. 3 0
      Packages/cn.etetet.ai/Scripts/Model/Share/TimerInvokeType.cs.meta
  96. 20 0
      Packages/cn.etetet.ai/package.json
  97. 7 0
      Packages/cn.etetet.ai/package.json.meta
  98. 4 0
      Packages/cn.etetet.ai/packagegit.json
  99. 7 0
      Packages/cn.etetet.ai/packagegit.json.meta
  100. 16 0
      Packages/cn.etetet.aoi/Ignore.ET.Aoi.asmdef

+ 16 - 0
Packages/cn.etetet.actorlocation/Ignore.ET.ActorLocation.asmdef

@@ -0,0 +1,16 @@
+{
+    "name": "Ignore.ET.ActorLocation",
+    "rootNamespace": "",
+    "references": [],
+    "includePlatforms": [],
+    "excludePlatforms": [],
+    "allowUnsafeCode": false,
+    "overrideReferences": false,
+    "precompiledReferences": [],
+    "autoReferenced": true,
+    "defineConstraints": [
+        "IGNORE"
+    ],
+    "versionDefines": [],
+    "noEngineReferences": false
+}

+ 7 - 0
Packages/cn.etetet.actorlocation/Ignore.ET.ActorLocation.asmdef.meta

@@ -0,0 +1,7 @@
+fileFormatVersion: 2
+guid: 4316cb3baa7123e40a4dfe87d3d447b3
+AssemblyDefinitionImporter:
+  externalObjects: {}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 30 - 0
Packages/cn.etetet.actorlocation/LICENSE

@@ -0,0 +1,30 @@
+ET License
+
+1. 该ET版本版权属于广州市一踢互联网科技有限公司所有。  
+2. 该ET版本可以任意修改代码,或者在ET基础上添加代码,但是仅限于自己或者自己任职的公司使用,不得传播给他人,私下传播ET修改版或者基于ET开发的代码都是违反ET License的行为  
+3. 自行修改的代码或者在ET基础上添加的代码,如果要分享给他人使用,必须以Package的形式放到ET的Package仓库中,具体请咨询广州市一踢互联网科技有限公司的唐海,QQ:80081771  
+4. 该版本可以用于开发任何商业项目。在项目上线运营之前必须主动通知广州市一踢互联网科技有限公司上线项目的名称,上线项目的公司等信息。广州市一踢互联网科技有限公司不会泄露这些信息,仅仅作为统计使用,如果需要公布,则会获得上线项目公司的许可  
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+

+ 7 - 0
Packages/cn.etetet.actorlocation/LICENSE.meta

@@ -0,0 +1,7 @@
+fileFormatVersion: 2
+guid: 02de30c85d9e7544ab621e9d2678a6bc
+DefaultImporter:
+  externalObjects: {}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 8 - 0
Packages/cn.etetet.actorlocation/Proto.meta

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

+ 82 - 0
Packages/cn.etetet.actorlocation/Proto/ActorLocation_S_20100.proto

@@ -0,0 +1,82 @@
+
+syntax = "proto3";
+
+package ET;
+
+// ResponseType ObjectAddResponse
+message ObjectAddRequest // IRequest
+{
+	int32 RpcId = 1;
+	int32 Type = 2;
+	int64 Key = 3;
+	ActorId ActorId = 4;
+}
+
+message ObjectAddResponse // IResponse
+{
+	int32 RpcId = 1;
+	int32 Error = 2;
+	string Message = 3;
+}
+
+// ResponseType ObjectLockResponse
+message ObjectLockRequest // IRequest
+{
+	int32 RpcId = 1;
+	int32 Type = 2;
+	int64 Key = 3;
+	ActorId ActorId = 4;
+	int32 Time = 5;
+}
+message ObjectLockResponse // IResponse
+{
+	int32 RpcId = 1;
+	int32 Error = 2;
+	string Message = 3;
+}
+
+// ResponseType ObjectUnLockResponse
+message ObjectUnLockRequest // IRequest
+{
+	int32 RpcId = 1;
+	int32 Type = 2;
+	int64 Key = 3;
+	ActorId OldActorId = 4;
+	ActorId NewActorId = 5;
+}
+message ObjectUnLockResponse // IResponse
+{
+	int32 RpcId = 1;
+	int32 Error = 2;
+	string Message = 3;
+}
+
+// ResponseType ObjectRemoveResponse
+message ObjectRemoveRequest // IRequest
+{
+	int32 RpcId = 1;
+	int32 Type = 2;
+	int64 Key = 3;
+}
+message ObjectRemoveResponse // IResponse
+{
+	int32 RpcId = 1;
+	int32 Error = 2;
+	string Message = 3;
+}
+
+// ResponseType ObjectGetResponse
+message ObjectGetRequest // IRequest
+{
+	int32 RpcId = 1;
+	int32 Type = 2;
+	int64 Key = 3;
+}
+message ObjectGetResponse // IResponse
+{
+	int32 RpcId = 1;
+	int32 Error = 2;
+	string Message = 3;
+	int32 Type = 4;
+	ActorId ActorId = 5;
+}

+ 7 - 0
Packages/cn.etetet.actorlocation/Proto/ActorLocation_S_20100.proto.meta

@@ -0,0 +1,7 @@
+fileFormatVersion: 2
+guid: 8d4f74e2f9836e24a9b732da07844c9e
+DefaultImporter:
+  externalObjects: {}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 8 - 0
Packages/cn.etetet.actorlocation/Scripts.meta

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

+ 8 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix.meta

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

+ 8 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server.meta

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

+ 21 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/FiberInit_Location.cs

@@ -0,0 +1,21 @@
+using System.Net;
+
+namespace ET.Server
+{
+    [Invoke(SceneType.Location)]
+    public class FiberInit_Location: AInvokeHandler<FiberInit, ETTask>
+    {
+        public override async ETTask Handle(FiberInit fiberInit)
+        {
+            Scene root = fiberInit.Fiber.Root;
+            root.AddComponent<MailBoxComponent, int>(MailBoxType.UnOrderedMessage);
+            root.AddComponent<TimerComponent>();
+            root.AddComponent<CoroutineLockComponent>();
+            root.AddComponent<ProcessInnerSender>();
+            root.AddComponent<MessageSender>();
+            root.AddComponent<LocationManagerComoponent>();
+
+            await ETTask.CompletedTask;
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/FiberInit_Location.cs.meta

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

+ 140 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/LocationOneTypeSystem.cs

@@ -0,0 +1,140 @@
+using System;
+
+namespace ET.Server
+{
+    [EntitySystemOf(typeof(LockInfo))]
+    [FriendOf(typeof(LockInfo))]
+    public static partial class LockInfoSystem
+    {
+        [EntitySystem]
+        private static void Awake(this LockInfo self, ActorId lockActorId, CoroutineLock coroutineLock)
+        {
+            self.CoroutineLock = coroutineLock;
+            self.LockActorId = lockActorId;
+        }
+        
+        [EntitySystem]
+        private static void Destroy(this LockInfo self)
+        {
+            self.CoroutineLock.Dispose();
+            self.LockActorId = default;
+        }
+    }
+    
+
+    [EntitySystemOf(typeof(LocationOneType))]
+    [FriendOf(typeof(LocationOneType))]
+    [FriendOf(typeof(LockInfo))]
+    public static partial class LocationOneTypeSystem
+    {
+        [EntitySystem]
+        private static void Awake(this LocationOneType self)
+        {
+        }
+        
+        public static async ETTask Add(this LocationOneType self, long key, ActorId instanceId)
+        {
+            long coroutineLockType = (self.Id << 32) | CoroutineLockType.Location;
+            using (await self.Root().GetComponent<CoroutineLockComponent>().Wait(coroutineLockType, key))
+            {
+                self.locations[key] = instanceId;
+                Log.Info($"location add key: {key} instanceId: {instanceId}");
+            }
+        }
+
+        public static async ETTask Remove(this LocationOneType self, long key)
+        {
+            long coroutineLockType = (self.Id << 32) | CoroutineLockType.Location;
+            using (await self.Root().GetComponent<CoroutineLockComponent>().Wait(coroutineLockType, key))
+            {
+                self.locations.Remove(key);
+                Log.Info($"location remove key: {key}");
+            }
+        }
+
+        public static async ETTask Lock(this LocationOneType self, long key, ActorId actorId, int time = 0)
+        {
+            long coroutineLockType = (self.Id << 32) | CoroutineLockType.Location;
+            CoroutineLock coroutineLock = await self.Root().GetComponent<CoroutineLockComponent>().Wait(coroutineLockType, key);
+
+            LockInfo lockInfo = self.AddChild<LockInfo, ActorId, CoroutineLock>(actorId, coroutineLock);
+            self.lockInfos.Add(key, lockInfo);
+
+            Log.Info($"location lock key: {key} instanceId: {actorId}");
+
+            if (time > 0)
+            {
+                async ETTask TimeWaitAsync()
+                {
+                    long lockInfoInstanceId = lockInfo.InstanceId;
+                    await self.Root().GetComponent<TimerComponent>().WaitAsync(time);
+                    if (lockInfo.InstanceId != lockInfoInstanceId)
+                    {
+                        return;
+                    }
+                    Log.Info($"location timeout unlock key: {key} instanceId: {actorId} newInstanceId: {actorId}");
+                    self.UnLock(key, actorId, actorId);
+                }
+                TimeWaitAsync().NoContext();
+            }
+        }
+
+        public static void UnLock(this LocationOneType self, long key, ActorId oldActorId, ActorId newInstanceId)
+        {
+            if (!self.lockInfos.TryGetValue(key, out EntityRef<LockInfo> lockInfoRef))
+            {
+                Log.Error($"location unlock not found key: {key} {oldActorId}");
+                return;
+            }
+
+            LockInfo lockInfo = lockInfoRef;
+            if (oldActorId != lockInfo.LockActorId)
+            {
+                Log.Error($"location unlock oldInstanceId is different: {key} {oldActorId}");
+                return;
+            }
+
+            Log.Info($"location unlock key: {key} instanceId: {oldActorId} newInstanceId: {newInstanceId}");
+
+            self.locations[key] = newInstanceId;
+
+            self.lockInfos.Remove(key);
+
+            // 解锁
+            lockInfo.Dispose();
+        }
+
+        public static async ETTask<ActorId> Get(this LocationOneType self, long key)
+        {
+            long coroutineLockType = (self.Id << 32) | CoroutineLockType.Location;
+            using (await self.Root().GetComponent<CoroutineLockComponent>().Wait(coroutineLockType, key))
+            {
+                self.locations.TryGetValue(key, out ActorId actorId);
+                Log.Info($"location get key: {key} actorId: {actorId}");
+                return actorId;
+            }
+        }
+    }
+
+    [EntitySystemOf(typeof(LocationManagerComoponent))]
+    [FriendOf(typeof(LocationManagerComoponent))]
+    public static partial class LocationComoponentSystem
+    {
+        [EntitySystem]
+        private static void Awake(this LocationManagerComoponent self)
+        {
+        }
+        
+        public static LocationOneType Get(this LocationManagerComoponent self, int locationType)
+        {
+            LocationOneType locationOneType = self.GetChild<LocationOneType>(locationType);
+            if (locationOneType != null)
+            {
+                return locationOneType;
+            }
+            locationOneType = self.AddChildWithId<LocationOneType>(locationType);
+            return locationOneType;
+        }
+
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/LocationOneTypeSystem.cs.meta

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

+ 87 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/LocationProxyComponentSystem.cs

@@ -0,0 +1,87 @@
+using System;
+using System.Collections.Generic;
+
+namespace ET.Server
+{
+    public static partial class LocationProxyComponentSystem
+    {
+        private static ActorId GetLocationSceneId(this LocationProxyComponent self, long key)
+        {
+            List<StartSceneConfig> locationConfigs = StartSceneConfigCategory.Instance.GetBySceneType(self.Zone(), SceneType.Location);
+            return locationConfigs[(int)(key % locationConfigs.Count)].ActorId;
+        }
+
+        public static async ETTask Add(this LocationProxyComponent self, int type, long key, ActorId actorId)
+        {
+            Fiber fiber = self.Fiber();
+            Log.Info($"location proxy add {key}, {actorId} {TimeInfo.Instance.ServerNow()}");
+            ObjectAddRequest objectAddRequest = ObjectAddRequest.Create();
+            objectAddRequest.Type = type;
+            objectAddRequest.Key = key;
+            objectAddRequest.ActorId = actorId;
+            await fiber.Root.GetComponent<MessageSender>().Call(self.GetLocationSceneId(key), objectAddRequest);
+        }
+
+        public static async ETTask Lock(this LocationProxyComponent self, int type, long key, ActorId actorId, int time = 60000)
+        {
+            Fiber fiber = self.Fiber();
+            Log.Info($"location proxy lock {key}, {actorId} {TimeInfo.Instance.ServerNow()}");
+
+            ObjectLockRequest objectLockRequest = ObjectLockRequest.Create();
+            objectLockRequest.Type = type;
+            objectLockRequest.Key = key;
+            objectLockRequest.ActorId = actorId;
+            objectLockRequest.Time = time;
+            await fiber.Root.GetComponent<MessageSender>().Call(self.GetLocationSceneId(key), objectLockRequest);
+        }
+
+        public static async ETTask UnLock(this LocationProxyComponent self, int type, long key, ActorId oldActorId, ActorId newActorId)
+        {
+            Fiber fiber = self.Fiber();
+            Log.Info($"location proxy unlock {key}, {newActorId} {TimeInfo.Instance.ServerNow()}");
+            ObjectUnLockRequest objectUnLockRequest = ObjectUnLockRequest.Create();
+            objectUnLockRequest.Type = type;
+            objectUnLockRequest.Key = key;
+            objectUnLockRequest.OldActorId = oldActorId;
+            objectUnLockRequest.NewActorId = newActorId;
+            await fiber.Root.GetComponent<MessageSender>().Call(self.GetLocationSceneId(key), objectUnLockRequest);
+        }
+
+        public static async ETTask Remove(this LocationProxyComponent self, int type, long key)
+        {
+            Fiber fiber = self.Fiber();
+            Log.Info($"location proxy remove {key}, {TimeInfo.Instance.ServerNow()}");
+
+            ObjectRemoveRequest objectRemoveRequest = ObjectRemoveRequest.Create();
+            objectRemoveRequest.Type = type;
+            objectRemoveRequest.Key = key;
+            await fiber.Root.GetComponent<MessageSender>().Call(self.GetLocationSceneId(key), objectRemoveRequest);
+        }
+
+        public static async ETTask<ActorId> Get(this LocationProxyComponent self, int type, long key)
+        {
+            if (key == 0)
+            {
+                throw new Exception($"get location key 0");
+            }
+
+            // location server配置到共享区,一个大战区可以配置N多个location server,这里暂时为1
+            ObjectGetRequest objectGetRequest = ObjectGetRequest.Create();
+            objectGetRequest.Type = type;
+            objectGetRequest.Key = key;
+            ObjectGetResponse response =
+                    (ObjectGetResponse) await self.Root().GetComponent<MessageSender>().Call(self.GetLocationSceneId(key), objectGetRequest);
+            return response.ActorId;
+        }
+
+        public static async ETTask AddLocation(this Entity self, int type)
+        {
+            await self.Root().GetComponent<LocationProxyComponent>().Add(type, self.Id, self.GetActorId());
+        }
+
+        public static async ETTask RemoveLocation(this Entity self, int type)
+        {
+            await self.Root().GetComponent<LocationProxyComponent>().Remove(type, self.Id);
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/LocationProxyComponentSystem.cs.meta

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

+ 39 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MailBoxType_OrderedMessageHandler.cs

@@ -0,0 +1,39 @@
+namespace ET
+{
+    [Invoke(MailBoxType.OrderedMessage)]
+    public class MailBoxType_OrderedMessageHandler: AInvokeHandler<MailBoxInvoker>
+    {
+        public override void Handle(MailBoxInvoker args)
+        {
+            HandleInner(args).NoContext();
+        }
+
+        private static async ETTask HandleInner(MailBoxInvoker args)
+        {
+            MailBoxComponent mailBoxComponent = args.MailBoxComponent;
+            
+            MessageObject messageObject = args.MessageObject;
+
+            Fiber fiber = mailBoxComponent.Fiber();
+            if (fiber.IsDisposed)
+            {
+                return;
+            }
+
+            long instanceId = mailBoxComponent.InstanceId;
+            using (await fiber.Root.GetComponent<CoroutineLockComponent>().Wait(CoroutineLockType.Mailbox, mailBoxComponent.ParentInstanceId))
+            {
+                if (mailBoxComponent.InstanceId != instanceId)
+                {
+                    if (messageObject is IRequest request)
+                    {
+                        IResponse resp = MessageHelper.CreateResponse(request.GetType(), request.RpcId, ErrorCode.ERR_NotFoundActor);
+                        mailBoxComponent.Root().GetComponent<ProcessInnerSender>().Reply(args.FromAddress, resp);
+                    }
+                    return;
+                }
+                await MessageDispatcher.Instance.Handle(mailBoxComponent.Parent, args.FromAddress, messageObject);
+            }
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MailBoxType_OrderedMessageHandler.cs.meta

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

+ 107 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationHandler.cs

@@ -0,0 +1,107 @@
+using System;
+
+namespace ET.Server
+{
+    public abstract class MessageLocationHandler<E, Message>: HandlerObject, IMHandler where E : Entity where Message : class, ILocationMessage
+    {
+        protected abstract ETTask Run(E entity, Message message);
+
+        public async ETTask Handle(Entity entity, Address fromAddress, MessageObject actorMessage)
+        {
+            Fiber fiber = entity.Fiber();
+            if (actorMessage is not Message message)
+            {
+                Log.Error($"消息类型转换错误: {actorMessage.GetType().FullName} to {typeof (Message).Name}");
+                return;
+            }
+
+            if (entity is not E e)
+            {
+                Log.Error($"Actor类型转换错误: {entity.GetType().FullName} to {typeof (E).FullName} --{typeof (Message).FullName}");
+                return;
+            }
+            
+            MessageResponse response = ObjectPool.Fetch<MessageResponse>();
+            response.RpcId = message.RpcId;
+            fiber.Root.GetComponent<ProcessInnerSender>().Reply(fromAddress, response);
+
+            await this.Run(e, message);
+        }
+
+        public Type GetRequestType()
+        {
+            return typeof (Message);
+        }
+
+        public Type GetResponseType()
+        {
+            return typeof (MessageResponse);
+        }
+    }
+    
+    
+    
+    public abstract class MessageLocationHandler<E, Request, Response>: HandlerObject, IMHandler where E : Entity where Request : MessageObject, ILocationRequest where Response : MessageObject, ILocationResponse
+    {
+        protected abstract ETTask Run(E unit, Request request, Response response);
+
+        public async ETTask Handle(Entity entity, Address fromAddress, MessageObject actorMessage)
+        {
+            try
+            {
+                Fiber fiber = entity.Fiber();
+                if (actorMessage is not Request request)
+                {
+                    Log.Error($"消息类型转换错误: {actorMessage.GetType().FullName} to {typeof (Request).Name}");
+                    return;
+                }
+
+                if (entity is not E ee)
+                {
+                    Log.Error($"Actor类型转换错误: {entity.GetType().FullName} to {typeof (E).FullName} --{typeof (Request).FullName}");
+                    return;
+                }
+
+                int rpcId = request.RpcId;
+                Response response = ObjectPool.Fetch<Response>();
+                try
+                {
+                    await this.Run(ee, request, response);
+                }
+                catch (RpcException exception)
+                {
+                    response.Error = exception.Error;
+                    response.Message = exception.ToString();
+                }
+                catch (Exception exception)
+                {
+                    response.Error = ErrorCode.ERR_RpcFail;
+                    response.Message = exception.ToString();
+                }
+                response.RpcId = rpcId;
+                
+                // 这里是为了保证response消息在handler消息处理完成之后发出,
+                // 因为MessageLocationSenderComponentSystem里面的Send方法有可能需要从location获取actorid
+                // 这样会导致send实际上进入了新的协程,从而response却先发送出去了
+                using (await fiber.Root.GetComponent<CoroutineLockComponent>().Wait(CoroutineLockType.MessageLocationSender, entity.Id))
+                {
+                    fiber.Root.GetComponent<ProcessInnerSender>().Reply(fromAddress, response);
+                }
+            }
+            catch (Exception e)
+            {
+                throw new Exception($"解释消息失败: {actorMessage.GetType().FullName}", e);
+            }
+        }
+
+        public Type GetRequestType()
+        {
+            return typeof (Request);
+        }
+
+        public Type GetResponseType()
+        {
+            return typeof (Response);
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationHandler.cs.meta

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

+ 287 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationSenderComponentSystem.cs

@@ -0,0 +1,287 @@
+using System;
+using System.IO;
+using MongoDB.Bson;
+
+namespace ET.Server
+{
+    [EntitySystemOf(typeof(MessageLocationSenderOneType))]
+    [FriendOf(typeof(MessageLocationSenderOneType))]
+    [FriendOf(typeof(MessageLocationSender))]
+    public static partial class MessageLocationSenderComponentSystem
+    {
+        [Invoke(TimerInvokeType.MessageLocationSenderChecker)]
+        public class MessageLocationSenderChecker: ATimer<MessageLocationSenderOneType>
+        {
+            protected override void Run(MessageLocationSenderOneType self)
+            {
+                try
+                {
+                    self.Check();
+                }
+                catch (Exception e)
+                {
+                    Log.Error($"move timer error: {self.Id}\n{e}");
+                }
+            }
+        }
+    
+        [EntitySystem]
+        private static void Awake(this MessageLocationSenderOneType self)
+        {
+            // 每10s扫描一次过期的actorproxy进行回收,过期时间是2分钟
+            // 可能由于bug或者进程挂掉,导致ActorLocationSender发送的消息没有确认,结果无法自动删除,每一分钟清理一次这种ActorLocationSender
+            self.CheckTimer = self.Root().GetComponent<TimerComponent>().NewRepeatedTimer(10 * 1000, TimerInvokeType.MessageLocationSenderChecker, self);
+        }
+        
+        [EntitySystem]
+        private static void Destroy(this MessageLocationSenderOneType self)
+        {
+            self.Root().GetComponent<TimerComponent>()?.Remove(ref self.CheckTimer);
+        }
+
+        private static void Check(this MessageLocationSenderOneType self)
+        {
+            using ListComponent<long> list = ListComponent<long>.Create();
+            
+            long timeNow = TimeInfo.Instance.ServerNow();
+            foreach ((long key, Entity value) in self.Children)
+            {
+                MessageLocationSender messageLocationMessageSender = (MessageLocationSender) value;
+
+                if (timeNow > messageLocationMessageSender.LastSendOrRecvTime + MessageLocationSenderOneType.TIMEOUT_TIME)
+                {
+                    list.Add(key);
+                }
+            }
+
+            foreach (long id in list)
+            {
+                self.Remove(id);
+            }
+        }
+
+        private static MessageLocationSender GetOrCreate(this MessageLocationSenderOneType self, long id)
+        {
+            if (id == 0)
+            {
+                throw new Exception($"actor id is 0");
+            }
+
+            if (self.Children.TryGetValue(id, out Entity actorLocationSender))
+            {
+                return (MessageLocationSender) actorLocationSender;
+            }
+
+            actorLocationSender = self.AddChildWithId<MessageLocationSender>(id);
+            return (MessageLocationSender) actorLocationSender;
+        }
+
+        // 有需要主动删除actorMessageSender的需求,比如断线重连,玩家登录了不同的Gate,这时候需要通知map删掉之前的actorMessageSender
+        // 然后重新创建新的,重新请求新的ActorId
+        public static void Remove(this MessageLocationSenderOneType self, long id)
+        {
+            if (!self.Children.TryGetValue(id, out Entity actorMessageSender))
+            {
+                return;
+            }
+
+            actorMessageSender.Dispose();
+        }
+        
+        // 发给不会改变位置的actorlocation用这个,这种actor消息不会阻塞发送队列,性能更高
+        // 发送过去找不到actor不会重试,用此方法,你得保证actor提前注册好了location
+        public static void Send(this MessageLocationSenderOneType self, long entityId, IMessage message)
+        {
+            self.SendInner(entityId, message).NoContext();
+        }
+        
+        private static async ETTask SendInner(this MessageLocationSenderOneType self, long entityId, IMessage message)
+        {
+            MessageLocationSender messageLocationSender = self.GetOrCreate(entityId);
+
+            Scene root = self.Root();
+            
+            long instanceId = messageLocationSender.InstanceId;
+            
+            using (await root.GetComponent<CoroutineLockComponent>().Wait(CoroutineLockType.MessageLocationSender, entityId))
+            {
+                if (messageLocationSender.InstanceId != instanceId)
+                {
+                    throw new RpcException(ErrorCode.ERR_MessageTimeout, $"{message}");
+                }
+                
+                if (messageLocationSender.ActorId == default)
+                {
+                    messageLocationSender.ActorId = await root.GetComponent<LocationProxyComponent>().Get((int)self.Id, messageLocationSender.Id);
+                    if (messageLocationSender.InstanceId != instanceId)
+                    {
+                        throw new RpcException(ErrorCode.ERR_ActorLocationSenderTimeout2, $"{message}");
+                    }
+                }
+                
+                messageLocationSender.LastSendOrRecvTime = TimeInfo.Instance.ServerNow();
+                root.GetComponent<MessageSender>().Send(messageLocationSender.ActorId, message);
+            }
+        }
+
+        // 发给不会改变位置的actorlocation用这个,这种actor消息不会阻塞发送队列,性能更高,发送过去找不到actor不会重试
+        // 发送过去找不到actor不会重试,用此方法,你得保证actor提前注册好了location
+        public static async ETTask<IResponse> Call(this MessageLocationSenderOneType self, long entityId, IRequest request)
+        {
+            MessageLocationSender messageLocationSender = self.GetOrCreate(entityId);
+
+            Scene root = self.Root();
+            
+            long instanceId = messageLocationSender.InstanceId;
+            
+            using (await root.GetComponent<CoroutineLockComponent>().Wait(CoroutineLockType.MessageLocationSender, entityId))
+            {
+                if (messageLocationSender.InstanceId != instanceId)
+                {
+                    throw new RpcException(ErrorCode.ERR_MessageTimeout, $"{request}");
+                }
+
+                if (messageLocationSender.ActorId == default)
+                {
+                    messageLocationSender.ActorId = await root.GetComponent<LocationProxyComponent>().Get((int)self.Id, messageLocationSender.Id);
+                    if (messageLocationSender.InstanceId != instanceId)
+                    {
+                        throw new RpcException(ErrorCode.ERR_ActorLocationSenderTimeout2, $"{request}");
+                    }
+                }
+            }
+
+            messageLocationSender.LastSendOrRecvTime = TimeInfo.Instance.ServerNow();
+            return await root.GetComponent<MessageSender>().Call(messageLocationSender.ActorId, request);
+        }
+
+        public static void Send(this MessageLocationSenderOneType self, long entityId, ILocationMessage message)
+        {
+            self.Call(entityId, message).NoContext();
+        }
+
+        public static async ETTask<IResponse> Call(this MessageLocationSenderOneType self, long entityId, ILocationRequest iRequest)
+        {
+            MessageLocationSender messageLocationSender = self.GetOrCreate(entityId);
+
+            Scene root = self.Root();
+            Type iRequestType = iRequest.GetType();
+            long actorLocationSenderInstanceId = messageLocationSender.InstanceId;
+            using (await root.GetComponent<CoroutineLockComponent>().Wait(CoroutineLockType.MessageLocationSender, entityId))
+            {
+                if (messageLocationSender.InstanceId != actorLocationSenderInstanceId)
+                {
+                    throw new RpcException(ErrorCode.ERR_NotFoundActor, $"{iRequest}");
+                }
+
+                try
+                {
+                    return await self.CallInner(messageLocationSender, iRequest);
+                }
+                catch (RpcException)
+                {
+                    self.Remove(messageLocationSender.Id);
+                    throw;
+                }
+                catch (Exception e)
+                {
+                    self.Remove(messageLocationSender.Id);
+                    throw new Exception($"{iRequestType.FullName}", e);
+                }
+            }
+        }
+
+        private static async ETTask<IResponse> CallInner(this MessageLocationSenderOneType self, MessageLocationSender messageLocationSender, IRequest iRequest)
+        {
+            int failTimes = 0;
+            long instanceId = messageLocationSender.InstanceId;
+            messageLocationSender.LastSendOrRecvTime = TimeInfo.Instance.ServerNow();
+            
+            Scene root = self.Root();
+
+            Type requestType = iRequest.GetType();
+            while (true)
+            {
+                if (messageLocationSender.ActorId == default)
+                {
+                    messageLocationSender.ActorId = await root.GetComponent<LocationProxyComponent>().Get((int)self.Id, messageLocationSender.Id);
+                    if (messageLocationSender.InstanceId != instanceId)
+                    {
+                        throw new RpcException(ErrorCode.ERR_ActorLocationSenderTimeout2, $"{iRequest}");
+                    }
+                }
+
+                if (messageLocationSender.ActorId == default)
+                {
+                    return MessageHelper.CreateResponse(requestType, 0, ErrorCode.ERR_NotFoundActor);
+                }
+                IResponse response = await root.GetComponent<MessageSender>().Call(messageLocationSender.ActorId, iRequest, needException: false);
+                
+                if (messageLocationSender.InstanceId != instanceId)
+                {
+                    throw new RpcException(ErrorCode.ERR_ActorLocationSenderTimeout3, $"{requestType.FullName}");
+                }
+                
+                switch (response.Error)
+                {
+                    case ErrorCode.ERR_NotFoundActor:
+                    {
+                        // 如果没找到Actor,重试
+                        ++failTimes;
+                        if (failTimes > 20)
+                        {
+                            Log.Debug($"actor send message fail, actorid: {messageLocationSender.Id} {requestType.FullName}");
+                            
+                            // 这里删除actor,后面等待发送的消息会判断InstanceId,InstanceId不一致返回ERR_NotFoundActor
+                            self.Remove(messageLocationSender.Id);
+                            return response;
+                        }
+
+                        // 等待0.5s再发送
+                        await root.GetComponent<TimerComponent>().WaitAsync(500);
+                        if (messageLocationSender.InstanceId != instanceId)
+                        {
+                            throw new RpcException(ErrorCode.ERR_ActorLocationSenderTimeout4, $"{requestType.FullName}");
+                        }
+
+                        messageLocationSender.ActorId = default;
+                        continue;
+                    }
+                    case ErrorCode.ERR_MessageTimeout:
+                    {
+                        throw new RpcException(response.Error, $"{requestType.FullName}");
+                    }
+                }
+
+                if (ErrorCode.IsRpcNeedThrowException(response.Error))
+                {
+                    throw new RpcException(response.Error, $"Message: {response.Message} Request: {requestType.FullName}");
+                }
+
+                return response;
+            }
+        }
+    }
+
+    [EntitySystemOf(typeof(MessageLocationSenderComponent))]
+    [FriendOf(typeof (MessageLocationSenderComponent))]
+    public static partial class MessageLocationSenderManagerComponentSystem
+    {
+        [EntitySystem]
+        private static void Awake(this MessageLocationSenderComponent self)
+        {
+        }
+        
+        public static MessageLocationSenderOneType Get(this MessageLocationSenderComponent self, int locationType)
+        {
+            MessageLocationSenderOneType messageLocationSenderOneType = self.GetChild<MessageLocationSenderOneType>(locationType);
+            if (messageLocationSenderOneType != null)
+            {
+                return messageLocationSenderOneType;
+            }
+
+            messageLocationSenderOneType = self.AddChildWithId<MessageLocationSenderOneType>(locationType);
+            return messageLocationSenderOneType;
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationSenderComponentSystem.cs.meta

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

+ 23 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationSenderSystem.cs

@@ -0,0 +1,23 @@
+using System;
+
+namespace ET.Server
+{
+    [EntitySystemOf(typeof(MessageLocationSender))]
+    public static partial class MessageLocationSenderSystem
+    {
+        [EntitySystem]
+        private static void Awake(this MessageLocationSender self)
+        {
+            self.LastSendOrRecvTime = TimeInfo.Instance.ServerNow();
+            self.ActorId = default;
+        }
+        
+        [EntitySystem]
+        private static void Destroy(this MessageLocationSender self)
+        {
+            Log.Debug($"actor location remove: {self.Id}");
+            self.LastSendOrRecvTime = 0;
+            self.ActorId = default;
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/MessageLocationSenderSystem.cs.meta

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

+ 13 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectAddRequestHandler.cs

@@ -0,0 +1,13 @@
+using System;
+
+namespace ET.Server
+{
+    [MessageHandler(SceneType.Location)]
+    public class ObjectAddRequestHandler: MessageHandler<Scene, ObjectAddRequest, ObjectAddResponse>
+    {
+        protected override async ETTask Run(Scene scene, ObjectAddRequest request, ObjectAddResponse response)
+        {
+            await scene.GetComponent<LocationManagerComoponent>().Get(request.Type).Add(request.Key, request.ActorId);
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectAddRequestHandler.cs.meta

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

+ 13 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectGetRequestHandler.cs

@@ -0,0 +1,13 @@
+using System;
+
+namespace ET.Server
+{
+    [MessageHandler(SceneType.Location)]
+    public class ObjectGetRequestHandler: MessageHandler<Scene, ObjectGetRequest, ObjectGetResponse>
+    {
+        protected override async ETTask Run(Scene scene, ObjectGetRequest request, ObjectGetResponse response)
+        {
+            response.ActorId = await scene.GetComponent<LocationManagerComoponent>().Get(request.Type).Get(request.Key);
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectGetRequestHandler.cs.meta

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

+ 13 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectLockRequestHandler.cs

@@ -0,0 +1,13 @@
+using System;
+
+namespace ET.Server
+{
+    [MessageHandler(SceneType.Location)]
+    public class ObjectLockRequestHandler: MessageHandler<Scene, ObjectLockRequest, ObjectLockResponse>
+    {
+        protected override async ETTask Run(Scene scene, ObjectLockRequest request, ObjectLockResponse response)
+        {
+            await scene.GetComponent<LocationManagerComoponent>().Get(request.Type).Lock(request.Key, request.ActorId, request.Time);
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectLockRequestHandler.cs.meta

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

+ 13 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectRemoveRequestHandler.cs

@@ -0,0 +1,13 @@
+using System;
+
+namespace ET.Server
+{
+    [MessageHandler(SceneType.Location)]
+    public class ObjectRemoveRequestHandler: MessageHandler<Scene, ObjectRemoveRequest, ObjectRemoveResponse>
+    {
+        protected override async ETTask Run(Scene scene, ObjectRemoveRequest request, ObjectRemoveResponse response)
+        {
+            await scene.GetComponent<LocationManagerComoponent>().Get(request.Type).Remove(request.Key);
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectRemoveRequestHandler.cs.meta

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

+ 15 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectUnLockRequestHandler.cs

@@ -0,0 +1,15 @@
+using System;
+
+namespace ET.Server
+{
+    [MessageHandler(SceneType.Location)]
+    public class ObjectUnLockRequestHandler: MessageHandler<Scene, ObjectUnLockRequest, ObjectUnLockResponse>
+    {
+        protected override async ETTask Run(Scene scene, ObjectUnLockRequest request, ObjectUnLockResponse response)
+        {
+            scene.GetComponent<LocationManagerComoponent>().Get(request.Type).UnLock(request.Key, request.OldActorId, request.NewActorId);
+
+            await ETTask.CompletedTask;
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Hotfix/Server/ObjectUnLockRequestHandler.cs.meta

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

+ 8 - 0
Packages/cn.etetet.actorlocation/Scripts/Model.meta

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

+ 8 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server.meta

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

+ 9 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/ConsoleMode.cs

@@ -0,0 +1,9 @@
+namespace ET.Server
+{
+    public static partial class ConsoleMode
+    {
+        public const string CreateDB = "CreateDB";
+        public const string DropDB = "DropDB";
+        public const string UpdateDB = "UpdateDB";
+    }
+}

+ 3 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/ConsoleMode.cs.meta

@@ -0,0 +1,3 @@
+fileFormatVersion: 2
+guid: 534bba05cb454353be3d6f549c5f06d0
+timeCreated: 1726125479

+ 8 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/CoroutineLockType.cs

@@ -0,0 +1,8 @@
+namespace ET
+{
+    public static partial class CoroutineLockType
+    {
+        public const int Location = PackageType.ActorLocation * 1000 + 1;                  // location进程上使用
+        public const int MessageLocationSender = PackageType.ActorLocation * 1000 + 2;       // MessageLocationSender中队列消息 
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/CoroutineLockType.cs.meta

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

+ 29 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/LocationComponent.cs

@@ -0,0 +1,29 @@
+using System.Collections.Generic;
+
+namespace ET.Server
+{
+    [ChildOf(typeof(LocationOneType))]
+    public class LockInfo: Entity, IAwake<ActorId, CoroutineLock>, IDestroy
+    {
+        public ActorId LockActorId;
+
+        public CoroutineLock CoroutineLock
+        {
+            get;
+            set;
+        }
+    }
+
+    [ChildOf(typeof(LocationManagerComoponent))]
+    public class LocationOneType: Entity, IAwake
+    {
+        public readonly Dictionary<long, ActorId> locations = new();
+
+        public readonly Dictionary<long, EntityRef<LockInfo>> lockInfos = new();
+    }
+
+    [ComponentOf(typeof(Scene))]
+    public class LocationManagerComoponent: Entity, IAwake
+    {
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/LocationComponent.cs.meta

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

+ 9 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/LocationProxyComponent.cs

@@ -0,0 +1,9 @@
+using System;
+
+namespace ET.Server
+{
+    [ComponentOf(typeof(Scene))]
+    public class LocationProxyComponent: Entity, IAwake
+    {
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/LocationProxyComponent.cs.meta

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

+ 7 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/MailBoxType.cs

@@ -0,0 +1,7 @@
+namespace ET
+{
+    public static partial class MailBoxType
+    {
+        public const int OrderedMessage = PackageType.ActorLocation * 1000 + 1;
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/MailBoxType.cs.meta

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

+ 14 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/MessageLocationSender.cs

@@ -0,0 +1,14 @@
+using System.IO;
+
+namespace ET.Server
+{
+    // 知道对方的Id,使用这个类发actor消息
+    [ChildOf(typeof(MessageLocationSenderOneType))]
+    public class MessageLocationSender: Entity, IAwake, IDestroy
+    {
+        public ActorId ActorId;
+
+        // 最近接收或者发送消息的时间
+        public long LastSendOrRecvTime;
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/MessageLocationSender.cs.meta

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

+ 18 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/MessageLocationSenderOneType.cs

@@ -0,0 +1,18 @@
+namespace ET.Server
+{
+    
+    [ChildOf(typeof(MessageLocationSenderComponent))]
+    public class MessageLocationSenderOneType: Entity, IAwake, IDestroy
+    {
+        public const long TIMEOUT_TIME = 60 * 1000;
+
+        public long CheckTimer;
+    }
+    
+    
+    [ComponentOf(typeof(Scene))]
+    public class MessageLocationSenderComponent: Entity, IAwake
+    {
+        public long CheckTimer;
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/MessageLocationSenderOneType.cs.meta

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

+ 7 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/TimerInvokeType.cs

@@ -0,0 +1,7 @@
+namespace ET
+{
+    public static partial class TimerInvokeType
+    {
+        public const int MessageLocationSenderChecker = PackageType.ActorLocation * 1000 + 2;
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Server/TimerInvokeType.cs.meta

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

+ 8 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Share.meta

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

+ 1 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Share/AssemblyReference.asmref

@@ -0,0 +1 @@
+{ "reference": "ET.Model" }

+ 7 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Share/AssemblyReference.asmref.meta

@@ -0,0 +1,7 @@
+fileFormatVersion: 2
+guid: 4172620a36971f342a2de85a04bc19b7
+AssemblyDefinitionReferenceImporter:
+  externalObjects: {}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 12 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Share/ErrorCode.cs

@@ -0,0 +1,12 @@
+namespace ET
+{
+    public static partial class ErrorCode
+    {
+        public const int ERR_NotFoundActor = ERR_WithException + PackageType.ActorLocation * 1000 + 1;
+        public const int ERR_RpcFail = ERR_WithException + PackageType.ActorLocation * 1000 + 2;
+        public const int ERR_MessageTimeout = ERR_WithException + PackageType.ActorLocation * 1000 + 3;
+        public const int ERR_ActorLocationSenderTimeout2 = ERR_WithException + PackageType.ActorLocation * 1000 + 4;
+        public const int ERR_ActorLocationSenderTimeout3 = ERR_WithException + PackageType.ActorLocation * 1000 + 5;
+        public const int ERR_ActorLocationSenderTimeout4 = ERR_WithException + PackageType.ActorLocation * 1000 + 6;
+    }
+}

+ 3 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Share/ErrorCode.cs.meta

@@ -0,0 +1,3 @@
+fileFormatVersion: 2
+guid: 2fe4ac67491f40adae1a415fce601590
+timeCreated: 1726650947

+ 7 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Share/PackageType.cs

@@ -0,0 +1,7 @@
+namespace ET
+{
+    public static partial class PackageType
+    {
+        public const int ActorLocation = 3;
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Share/PackageType.cs.meta

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

+ 7 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Share/SceneType.cs

@@ -0,0 +1,7 @@
+namespace ET
+{
+    public static partial class SceneType
+    {
+        public const int Location = PackageType.ActorLocation * 1000 + 1;
+    }
+}

+ 11 - 0
Packages/cn.etetet.actorlocation/Scripts/Model/Share/SceneType.cs.meta

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

+ 24 - 0
Packages/cn.etetet.actorlocation/package.json

@@ -0,0 +1,24 @@
+{
+  "name": "cn.etetet.actorlocation",
+  "displayName": "ET.ActorLocation",
+  "version": "2.0.1",
+  "unity": "2022.3",
+  "description": "实现了actor location机制",
+  "author": {
+    "name": "tanghai",
+    "url": "https://github.com/egametang/ET"
+  },
+  "repository": {
+    "type": "git",
+    "url": "https://github.com/egametang/ET"
+  },
+  "relatedPackages": {},
+  "dependencies": {
+    "cn.etetet.core": "2.0.0",
+    "cn.etetet.netinner": "2.0.1",
+    "cn.etetet.startconfig": "2.0.1"
+  },
+  "publishConfig": {
+    "registry": "https://npm.pkg.github.com/@ET-Packages"
+  }
+}

+ 7 - 0
Packages/cn.etetet.actorlocation/package.json.meta

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

+ 4 - 0
Packages/cn.etetet.actorlocation/packagegit.json

@@ -0,0 +1,4 @@
+{
+"Id": 3,
+"Name": "ActorLocation"
+}

+ 7 - 0
Packages/cn.etetet.actorlocation/packagegit.json.meta

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

+ 8 - 0
Packages/cn.etetet.ai/Excel.meta

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

BIN
Packages/cn.etetet.ai/Excel/AIConfig.xlsx


+ 7 - 0
Packages/cn.etetet.ai/Excel/AIConfig.xlsx.meta

@@ -0,0 +1,7 @@
+fileFormatVersion: 2
+guid: 909a1917a36de4a448e1437eca80f016
+DefaultImporter:
+  externalObjects: {}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 16 - 0
Packages/cn.etetet.ai/Ignore.ET.AI.asmdef

@@ -0,0 +1,16 @@
+{
+    "name": "Ignore.ET.AI",
+    "rootNamespace": "",
+    "references": [],
+    "includePlatforms": [],
+    "excludePlatforms": [],
+    "allowUnsafeCode": false,
+    "overrideReferences": false,
+    "precompiledReferences": [],
+    "autoReferenced": true,
+    "defineConstraints": [
+        "IGNORE"
+    ],
+    "versionDefines": [],
+    "noEngineReferences": false
+}

+ 7 - 0
Packages/cn.etetet.ai/Ignore.ET.AI.asmdef.meta

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

+ 30 - 0
Packages/cn.etetet.ai/LICENSE

@@ -0,0 +1,30 @@
+ET License
+
+1. 该ET版本版权属于广州市一踢互联网科技有限公司所有。  
+2. 该ET版本可以任意修改代码,或者在ET基础上添加代码,但是仅限于自己或者自己任职的公司使用,不得传播给他人,私下传播ET修改版或者基于ET开发的代码都是违反ET License的行为  
+3. 自行修改的代码或者在ET基础上添加的代码,如果要分享给他人使用,必须以Package的形式放到ET的Package仓库中,具体请咨询广州市一踢互联网科技有限公司的唐海,QQ:80081771  
+4. 该版本可以用于开发任何商业项目。在项目上线运营之前必须主动通知广州市一踢互联网科技有限公司上线项目的名称,上线项目的公司等信息。广州市一踢互联网科技有限公司不会泄露这些信息,仅仅作为统计使用,如果需要公布,则会获得上线项目公司的许可  
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+

+ 7 - 0
Packages/cn.etetet.ai/LICENSE.meta

@@ -0,0 +1,7 @@
+fileFormatVersion: 2
+guid: 221edd9c45a2df24b99faaf9408b913b
+DefaultImporter:
+  externalObjects: {}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 8 - 0
Packages/cn.etetet.ai/Scripts.meta

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

+ 8 - 0
Packages/cn.etetet.ai/Scripts/Hotfix.meta

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

+ 8 - 0
Packages/cn.etetet.ai/Scripts/Hotfix/Share.meta

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

+ 93 - 0
Packages/cn.etetet.ai/Scripts/Hotfix/Share/AIComponentSystem.cs

@@ -0,0 +1,93 @@
+using System;
+
+namespace ET
+{
+    [EntitySystemOf(typeof(AIComponent))]
+    [FriendOf(typeof(AIComponent))]
+    [FriendOf(typeof(AIDispatcherComponent))]
+    public static partial class AIComponentSystem
+    {
+        [Invoke(TimerInvokeType.AITimer)]
+        public class AITimer: ATimer<AIComponent>
+        {
+            protected override void Run(AIComponent self)
+            {
+                try
+                {
+                    self.Check();
+                }
+                catch (Exception e)
+                {
+                    Log.Error($"move timer error: {self.Id}\n{e}");
+                }
+            }
+        }
+    
+        [EntitySystem]
+        private static void Awake(this AIComponent self, int aiConfigId)
+        {
+            self.AIConfigId = aiConfigId;
+            self.Timer = self.Root().GetComponent<TimerComponent>().NewRepeatedTimer(1000, TimerInvokeType.AITimer, self);
+        }
+
+        [EntitySystem]
+        private static void Destroy(this AIComponent self)
+        {
+            self.Root().GetComponent<TimerComponent>()?.Remove(ref self.Timer);
+            self.CancellationToken?.Cancel();
+            self.CancellationToken = null;
+            self.Current = 0;
+        }
+
+        private static void Check(this AIComponent self)
+        {
+            Fiber fiber = self.Fiber();
+            if (self.Parent == null)
+            {
+                fiber.Root.GetComponent<TimerComponent>().Remove(ref self.Timer);
+                return;
+            }
+
+            var oneAI = AIConfigCategory.Instance.AIConfigs[self.AIConfigId];
+
+            foreach (AIConfig aiConfig in oneAI.Values)
+            {
+
+                AAIHandler aaiHandler = AIDispatcherComponent.Instance.Get(aiConfig.Name);
+
+                if (aaiHandler == null)
+                {
+                    Log.Error($"not found aihandler: {aiConfig.Name}");
+                    continue;
+                }
+
+                int ret = aaiHandler.Check(self, aiConfig);
+                if (ret != 0)
+                {
+                    continue;
+                }
+
+                if (self.Current == aiConfig.Id)
+                {
+                    break;
+                }
+
+                self.Cancel(); // 取消之前的行为
+                ETCancellationToken cancellationToken = new();
+                self.CancellationToken = cancellationToken;
+                self.Current = aiConfig.Id;
+
+                aaiHandler.Execute(self, aiConfig).WithContext(cancellationToken);
+                return;
+            }
+            
+        }
+
+        private static void Cancel(this AIComponent self)
+        {
+            self.CancellationToken?.Cancel();
+            self.Current = 0;
+            self.CancellationToken = null;
+        }
+    }
+} 

+ 11 - 0
Packages/cn.etetet.ai/Scripts/Hotfix/Share/AIComponentSystem.cs.meta

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

+ 1 - 0
Packages/cn.etetet.ai/Scripts/Hotfix/Share/AssemblyReference.asmref

@@ -0,0 +1 @@
+{ "reference": "ET.Hotfix" }

+ 7 - 0
Packages/cn.etetet.ai/Scripts/Hotfix/Share/AssemblyReference.asmref.meta

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

+ 8 - 0
Packages/cn.etetet.ai/Scripts/Model.meta

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

+ 8 - 0
Packages/cn.etetet.ai/Scripts/Model/Share.meta

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

+ 18 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AAIHandler.cs

@@ -0,0 +1,18 @@
+using System;
+
+namespace ET
+{
+    public class AIHandlerAttribute: BaseAttribute
+    {
+    }
+    
+    [AIHandler]
+    public abstract class AAIHandler: HandlerObject
+    {
+        // 检查是否满足条件
+        public abstract int Check(AIComponent aiComponent, AIConfig aiConfig);
+
+        // 协程编写必须可以取消
+        public abstract ETTask Execute(AIComponent aiComponent, AIConfig aiConfig);
+    }
+}

+ 11 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AAIHandler.cs.meta

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

+ 15 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AIComponent.cs

@@ -0,0 +1,15 @@
+namespace ET
+{
+    // 客户端挂在ClientScene上,服务端挂在Unit上
+    [ComponentOf(typeof(Scene))]
+    public class AIComponent: Entity, IAwake<int>, IDestroy
+    {
+        public int AIConfigId;
+        
+        public ETCancellationToken CancellationToken;
+
+        public long Timer;
+
+        public int Current;
+    }
+}

+ 11 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AIComponent.cs.meta

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

+ 33 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AIConfig.cs

@@ -0,0 +1,33 @@
+using System.Collections.Generic;
+using System.ComponentModel;
+using MongoDB.Bson;
+using MongoDB.Bson.Serialization.Attributes;
+
+namespace ET
+{
+	public partial class AIConfigCategory
+	{
+		[BsonIgnore]
+		public Dictionary<int, SortedDictionary<int, AIConfig>> AIConfigs = new Dictionary<int, SortedDictionary<int, AIConfig>>();
+
+		public SortedDictionary<int, AIConfig> GetAI(int aiConfigId)
+		{
+			return this.AIConfigs[aiConfigId];
+		}
+
+		public override void EndInit()
+		{
+			foreach (var kv in this.GetAll())
+			{
+				SortedDictionary<int, AIConfig> aiNodeConfig;
+				if (!this.AIConfigs.TryGetValue(kv.Value.AIConfigId, out aiNodeConfig))
+				{
+					aiNodeConfig = new SortedDictionary<int, AIConfig>();
+					this.AIConfigs.Add(kv.Value.AIConfigId, aiNodeConfig);
+				}
+				
+				aiNodeConfig.Add(kv.Key, kv.Value);
+			}
+		}
+	}
+}

+ 3 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AIConfig.cs.meta

@@ -0,0 +1,3 @@
+fileFormatVersion: 2
+guid: 25d0d959fb88483281a52c776ccde0ce
+timeCreated: 1722790259

+ 32 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AIDispatcherComponent.cs

@@ -0,0 +1,32 @@
+using System;
+using System.Collections.Generic;
+
+namespace ET
+{
+    [CodeProcess]
+    public class AIDispatcherComponent: Singleton<AIDispatcherComponent>, ISingletonAwake
+    {
+        private readonly Dictionary<string, AAIHandler> aiHandlers = new();
+        
+        public void Awake()
+        {
+            var types = CodeTypes.Instance.GetTypes(typeof (AIHandlerAttribute));
+            foreach (Type type in types)
+            {
+                AAIHandler aaiHandler = Activator.CreateInstance(type) as AAIHandler;
+                if (aaiHandler == null)
+                {
+                    Log.Error($"robot ai is not AAIHandler: {type.Name}");
+                    continue;
+                }
+                this.aiHandlers.Add(type.Name, aaiHandler);
+            }
+        }
+
+        public AAIHandler Get(string key)
+        {
+            this.aiHandlers.TryGetValue(key, out var aaiHandler);
+            return aaiHandler;
+        }
+    }
+}

+ 11 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AIDispatcherComponent.cs.meta

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

+ 1 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AssemblyReference.asmref

@@ -0,0 +1 @@
+{ "reference": "ET.Model" }

+ 7 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/AssemblyReference.asmref.meta

@@ -0,0 +1,7 @@
+fileFormatVersion: 2
+guid: 4aa31fd5e1051eb45bc32b74f4c0acf9
+AssemblyDefinitionReferenceImporter:
+  externalObjects: {}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 7 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/PackageType.cs

@@ -0,0 +1,7 @@
+namespace ET
+{
+    public static partial class PackageType
+    {
+        public const int AI = 31;
+    }
+}

+ 3 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/PackageType.cs.meta

@@ -0,0 +1,3 @@
+fileFormatVersion: 2
+guid: 958ca32c195c40b8aace24c25b9e1fed
+timeCreated: 1722790135

+ 7 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/TimerInvokeType.cs

@@ -0,0 +1,7 @@
+namespace ET
+{
+    public static partial class TimerInvokeType
+    {
+        public const int AITimer = PackageType.AI * 1000 + 1;
+    }
+}

+ 3 - 0
Packages/cn.etetet.ai/Scripts/Model/Share/TimerInvokeType.cs.meta

@@ -0,0 +1,3 @@
+fileFormatVersion: 2
+guid: 378b571e462e46c8abc2aba46c1ba1c3
+timeCreated: 1722790095

+ 20 - 0
Packages/cn.etetet.ai/package.json

@@ -0,0 +1,20 @@
+{
+  "name": "cn.etetet.ai",
+  "displayName": "ET.AI",
+  "version": "2.0.0",
+  "unity": "2022.3",
+  "description": "行为机模块,用来写ai非常方便",
+  "author": {
+    "name": "tanghai",
+    "url": "https://github.com/egametang/ET"
+  },
+  "repository": {
+    "type": "git",
+    "url": "https://github.com/egametang/ET"
+  },
+  "relatedPackages": {},
+  "publishConfig": {
+    "registry": "https://npm.pkg.github.com/@ET-Packages"
+  },
+  "dependencies": {}
+}

+ 7 - 0
Packages/cn.etetet.ai/package.json.meta

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

+ 4 - 0
Packages/cn.etetet.ai/packagegit.json

@@ -0,0 +1,4 @@
+{
+"Id": 32,
+"Name": "AI"
+}

+ 7 - 0
Packages/cn.etetet.ai/packagegit.json.meta

@@ -0,0 +1,7 @@
+fileFormatVersion: 2
+guid: 3c97b98ef7a085343b9787d04db0030d
+TextScriptImporter:
+  externalObjects: {}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 16 - 0
Packages/cn.etetet.aoi/Ignore.ET.Aoi.asmdef

@@ -0,0 +1,16 @@
+{
+    "name": "Ignore.ET.Aoi",
+    "rootNamespace": "",
+    "references": [],
+    "includePlatforms": [],
+    "excludePlatforms": [],
+    "allowUnsafeCode": false,
+    "overrideReferences": false,
+    "precompiledReferences": [],
+    "autoReferenced": true,
+    "defineConstraints": [
+        "IGNORE"
+    ],
+    "versionDefines": [],
+    "noEngineReferences": false
+}

Alguns ficheiros não foram mostrados porque muitos ficheiros mudaram neste diff