public static void UpdateUnitList(this Trigger self) { ListComponent <long> deleteList = ListComponent <long> .Create(); DUnitComponent dUnitComponent = self.Domain.GetComponent <DUnitComponent>(); for (int i = 0; i < self.UnitList.List.Count; i++) { DUnit unit = dUnitComponent.Get(self.UnitList.List[i]); if (unit == null) { deleteList.List.Add(unit.Id); continue; } if (unit.GetComponent <UnitStateComponent>().UnitState == (int)UnitState.Death) { deleteList.List.Add(unit.Id); } } for (int i = 0; i < deleteList.List.Count; i++) { self.UnitList.List.Remove(deleteList.List[i]); } deleteList.List.Clear(); }
// 场景切换协程 public static async ETTask SceneChangeTo(Scene zoneScene, string sceneName, long sceneInstanceId) { // zoneScene.RemoveComponent<AIComponent>(); zoneScene.AddComponent <KeyCodeComponent>(); CurrentScenesComponent currentScenesComponent = zoneScene.GetComponent <CurrentScenesComponent>(); currentScenesComponent.Scene?.Dispose(); // 删除之前的CurrentScene,创建新的 Scene currentScene = SceneFactory.CreateCurrentScene(sceneInstanceId, zoneScene.Zone, sceneName, currentScenesComponent); currentScene.AddComponent <UnitComponent>(); currentScene.AddComponent <AOISceneComponent, int>(6); // 可以订阅这个事件中创建Loading界面 using (ListComponent <ETTask> tasks = ListComponent <ETTask> .Create()) { tasks.Add(WaitChangeScene(zoneScene, sceneName)); //等收到消息并且地图创建完成 tasks.Add(WaitCreateMyUnit(zoneScene)); // 等待CreateMyUnit的消息 await ETTaskHelper.WaitAll(tasks); } M2C_CreateMyUnit m2CCreateMyUnit = waitCreateMyUnit.Message; UnitFactory.Create(currentScene, m2CCreateMyUnit.Unit); // zoneScene.AddComponent<AIComponent,int>(1); await Game.EventSystem.PublishAsync(new EventType.SceneChangeFinish() { ZoneScene = zoneScene, CurrentScene = currentScene }); // 通知等待场景切换的协程 zoneScene.GetComponent <ObjectWait>().Notify(new WaitType.Wait_SceneChangeFinish()); }
/// <summary> /// 异步加载assetbundle, 加载ab包分两部分,第一部分是从硬盘加载,第二部分加载all assets。两者不能同时并发 /// </summary> public static async ETTask LoadBundleAsync(this ResourcesComponent self, string assetBundleName) { assetBundleName = assetBundleName.BundleNameToLower(); string[] dependencies = self.GetSortedDependencies(assetBundleName); //Log.Debug($"-----------dep load async start {assetBundleName} dep: {dependencies.ToList().ListToString()}"); using (ListComponent <ABInfo> abInfos = ListComponent <ABInfo> .Create()) { async ETTask LoadDependency(string dependency, List <ABInfo> abInfosList) { CoroutineLock coroutineLock = null; try { coroutineLock = await CoroutineLockComponent.Instance.Wait(CoroutineLockType.Resources, dependency.GetHashCode()); ABInfo abInfo = await self.LoadOneBundleAsync(dependency); if (abInfo == null || abInfo.RefCount > 1) { return; } abInfosList.Add(abInfo); } finally { coroutineLock?.Dispose(); } } // LoadFromFileAsync部分可以并发加载 using (ListComponent <ETTask> tasks = ListComponent <ETTask> .Create()) { foreach (string dependency in dependencies) { tasks.Add(LoadDependency(dependency, abInfos)); } await ETTaskHelper.WaitAll(tasks); // ab包从硬盘加载完成,可以再并发加载all assets tasks.Clear(); foreach (ABInfo abInfo in abInfos) { tasks.Add(self.LoadOneBundleAllAssets(abInfo)); } await ETTaskHelper.WaitAll(tasks); } } }
protected override async ETTask Run(Session session, M2C_PathfindingResult message) { Unit unit = session.DomainScene().CurrentScene().GetComponent <UnitComponent>().Get(message.Id); float speed = unit.GetComponent <NumericComponent>().GetAsFloat(NumericType.Speed); using (ListComponent <Vector3> list = ListComponent <Vector3> .Create()) { for (int i = 0; i < message.Xs.Count; ++i) { list.Add(new Vector3(message.Xs[i], message.Ys[i], message.Zs[i])); } await unit.GetComponent <MoveComponent>().MoveToAsync(list, speed); } }
public async ETTask Run(ModeContex contex, string content) { switch (content) { case ConsoleMode.CreateRobot: Log.Console("CreateRobot args error!"); break; default: CreateRobotArgs options = null; Parser.Default.ParseArguments <CreateRobotArgs>(content.Split(' ')) .WithNotParsed(error => throw new Exception($"CreateRobotArgs error!")) .WithParsed(o => { options = o; }); // 获取当前进程的RobotScene using (ListComponent <StartSceneConfig> thisProcessRobotScenes = ListComponent <StartSceneConfig> .Create()) { List <StartSceneConfig> robotSceneConfigs = StartSceneConfigCategory.Instance.Robots; foreach (StartSceneConfig robotSceneConfig in robotSceneConfigs) { if (robotSceneConfig.Process != Game.Options.Process) { continue; } thisProcessRobotScenes.Add(robotSceneConfig); } // 创建机器人 for (int i = 0; i < options.Num; ++i) { int index = i % thisProcessRobotScenes.Count; StartSceneConfig robotSceneConfig = thisProcessRobotScenes[index]; Scene robotScene = Game.Scene.Get(robotSceneConfig.Id); RobotManagerComponent robotManagerComponent = robotScene.GetComponent <RobotManagerComponent>(); Scene robot = await robotManagerComponent.NewRobot(Game.Options.Process * 10000 + i); robot.AddComponent <AIComponent, int>(1); Log.Console($"create robot {robot.Zone}"); await TimerComponent.Instance.WaitAsync(2000); } } break; } contex.Parent.RemoveComponent <ModeContex>(); await ETTask.CompletedTask; }
public static Unit Create(Scene currentScene, UnitInfo unitInfo) { UnitComponent unitComponent = currentScene.GetComponent <UnitComponent>(); Unit unit = unitComponent.AddChildWithId <Unit, int>(unitInfo.UnitId, unitInfo.ConfigId); unitComponent.Add(unit); unit.Position = new Vector3(unitInfo.X, unitInfo.Y, unitInfo.Z); unit.Forward = new Vector3(unitInfo.ForwardX, unitInfo.ForwardY, unitInfo.ForwardZ); NumericComponent numericComponent = unit.AddComponent <NumericComponent>(); for (int i = 0; i < unitInfo.Ks.Count; ++i) { numericComponent.Set(unitInfo.Ks[i], unitInfo.Vs[i]); } unit.AddComponent <MoveComponent>(); if (unitInfo.MoveInfo != null) { if (unitInfo.MoveInfo.X.Count > 0) { using (ListComponent <Vector3> list = ListComponent <Vector3> .Create()) { list.Add(unit.Position); for (int i = 0; i < unitInfo.MoveInfo.X.Count; ++i) { list.Add(new Vector3(unitInfo.MoveInfo.X[i], unitInfo.MoveInfo.Y[i], unitInfo.MoveInfo.Z[i])); } unit.MoveToAsync(list).Coroutine(); } } } unit.AddComponent <ObjectWait>(); unit.AddComponent <XunLuoPathComponent>(); Game.EventSystem.Publish(unit.DomainScene(), new EventType.AfterUnitCreate() { Unit = unit }); return(unit); }
protected override void Destroy(ResourcesLoaderComponent self) { async ETTask UnLoadAsync() { using (ListComponent <string> list = ListComponent <string> .Create()) { list.AddRange(self.LoadedResource); self.LoadedResource = null; if (TimerComponent.Instance == null) { return; } // 延迟5秒卸载包,因为包卸载是引用计数,5秒之内假如重新有逻辑加载了这个包,那么可以避免一次卸载跟加载 await TimerComponent.Instance.WaitAsync(5000); foreach (string abName in list) { CoroutineLock coroutineLock = null; try { coroutineLock = await CoroutineLockComponent.Instance.Wait(CoroutineLockType.ResourcesLoader, abName.GetHashCode(), 0); { if (ResourcesComponent.Instance == null) { return; } await ResourcesComponent.Instance.UnloadBundleAsync(abName); } } finally { coroutineLock?.Dispose(); } } } } UnLoadAsync().Coroutine(); }
// 可以多次调用,多次调用的话会取消上一次的协程 public static async ETTask FindPathMoveToAsync(this Unit unit, Vector3 target, ETCancellationToken cancellationToken = null) { float speed = unit.GetComponent <NumericComponent>().GetAsFloat(NumericType.Speed); if (speed < 0.01) { unit.SendStop(-1); return; } using var list = ListComponent <Vector3> .Create(); unit.GetComponent <PathfindingComponent>().Find(unit.Position, target, list); List <Vector3> path = list; if (path.Count < 2) { unit.SendStop(0); return; } // 广播寻路路径 M2C_PathfindingResult m2CPathfindingResult = new M2C_PathfindingResult(); m2CPathfindingResult.Id = unit.Id; for (int i = 0; i < list.Count; ++i) { Vector3 vector3 = list[i]; m2CPathfindingResult.Xs.Add(vector3.x); m2CPathfindingResult.Ys.Add(vector3.y); m2CPathfindingResult.Zs.Add(vector3.z); } MessageHelper.Broadcast(unit, m2CPathfindingResult); bool ret = await unit.GetComponent <MoveComponent>().MoveToAsync(path, speed); if (ret) // 如果返回false,说明被其它移动取消了,这时候不需要通知客户端stop { unit.SendStop(0); } }
private static void CheckConnectTimeout(this RouterComponent self, long timeNow) { // 检查连接过程超时 using (ListComponent <long> listComponent = ListComponent <long> .Create()) { foreach (var kv in self.ConnectIdNodes) { if (timeNow < kv.Value.LastRecvOuterTime + 10 * 1000) { continue; } listComponent.Add(kv.Value.Id); } foreach (long id in listComponent) { self.OnError(id, ErrorCore.ERR_KcpRouterConnectFail); } } // 外网消息超时就断开,内网因为会一直重发,没有重连之前内网连接一直存在,会导致router一直收到内网消息 using (ListComponent <long> listComponent = ListComponent <long> .Create()) { foreach (var kv in self.OuterNodes) { // 比session超时应该多10秒钟 if (timeNow < kv.Value.LastRecvOuterTime + ConstValue.SessionTimeoutTime + 10 * 1000) { continue; } listComponent.Add(kv.Value.Id); } foreach (long id in listComponent) { self.OnError(id, ErrorCore.ERR_KcpRouterTimeout); } } }
public async ETTask Run(RobotCase robotCase) { using ListComponent <Scene> robots = ListComponent <Scene> .Create(); // 创建了两个机器人,生命周期是RobotCase,RobotCase_FirstCase.Run执行结束,机器人就会删除 await robotCase.NewRobot(2, robots); foreach (Scene robotScene in robots) { M2C_TestRobotCase response = await robotScene.GetComponent <Client.SessionComponent>().Session.Call(new C2M_TestRobotCase() { N = robotScene.Zone }) as M2C_TestRobotCase; if (response.N != robotScene.Zone) { // 跟预期不一致就抛异常,外层会catch住在控制台上打印 throw new Exception($"robot case: {RobotCaseType.FirstCase} run fail!"); } } }
public static void Check(this ActorLocationSenderComponent self) { using (ListComponent <long> list = ListComponent <long> .Create()) { long timeNow = TimeHelper.ServerNow(); foreach ((long key, Entity value) in self.Children) { ActorLocationSender actorLocationMessageSender = (ActorLocationSender)value; if (timeNow > actorLocationMessageSender.LastSendOrRecvTime + ActorLocationSenderComponent.TIMEOUT_TIME) { list.Add(key); } } foreach (long id in list) { self.Remove(id); } } }
/// 计算结果,传入的Dictionary中必须包含所有信息// public float GetData(NumericComponent comp, NumericComponent other) { ListComponent <int> priorityList = ListComponent <int> .Create(); ListComponent <FormulaNode> tempList = ListComponent <FormulaNode> .Create(); for (int i = 0; i < formulaNodeList.Count; i++) { FormulaNode node = new FormulaNode(formulaNodeList[i].Key, formulaNodeList[i].Value, formulaNodeList[i].IsSelf); tempList.Add(node); } for (int i = 0; i < tempList.Count; i++) { if (!float.TryParse(tempList[i].Value, out _)) { if (NumericType.Map.TryGetValue(tempList[i].Value, out int type)) { if (tempList[i].IsSelf) { tempList[i].Value = comp.GetAsFloat(type).ToString(); } else if (other != null) { tempList[i].Value = other.GetAsFloat(type).ToString(); } else { tempList[i].Value = "0"; Log.Error("计算伤害未传入目标"); } } } if (tempList[i].Key != 0 && !priorityList.Contains(tempList[i].Key)) { priorityList.Add(tempList[i].Key); } } priorityList.Sort(); while (priorityList.Count > 0) { int currentpri = priorityList[priorityList.Count - 1]; bool hasfind = false; do { hasfind = false; for (int i = 0; i < tempList.Count && tempList.Count >= 3; i++) { if (tempList[i].Key == currentpri && GetPriority(tempList[i].Value) != 0) { float final = GetOperactorFinal(tempList[i - 1].Value, tempList[i].Value, tempList[i + 1].Value); var newformula = new FormulaNode(tempList[i - 1].Key, final.ToString()); tempList.RemoveRange(i - 1, 3); tempList.Insert(i - 1, newformula); hasfind = true; break; } } } while (hasfind); priorityList.RemoveAt(priorityList.Count - 1); priorityList.Sort(); } if (tempList.Count == 0) { #if UNITY_EDITOR // UnityEngine.Debug.LogError("FormulaString is Error string = "+ lastFormatString); #endif return(0); } string outstring = tempList[0].Value;// + formulaNodeList.Count.ToString(); float finalnum = 0; if (!float.TryParse(outstring, out finalnum)) { #if UNITY_EDITOR // UnityEngine.Debug.Log(outstring); #endif finalnum = 0; } priorityList.Dispose(); tempList.Dispose(); return(finalnum); }
public override void Awake(Trigger self, TriggerType type) { self.TriggerType = type; self.UnitList = ListComponent <long> .Create(); }
public static async ETTask Transfer(Unit unit, long sceneInstanceId, string sceneName) { // 通知客户端开始切场景 M2C_StartSceneChange m2CStartSceneChange = new M2C_StartSceneChange() { SceneInstanceId = sceneInstanceId, SceneName = sceneName }; MessageHelper.SendToClient(unit, m2CStartSceneChange); M2M_UnitTransferRequest request = new M2M_UnitTransferRequest(); ListComponent <int> Stack = ListComponent <int> .Create(); request.Unit = unit; Entity curEntity = unit; Stack.Add(-1); while (Stack.Count > 0) { var index = Stack[Stack.Count - 1]; if (index != -1) { curEntity = request.Entitys[index]; } Stack.RemoveAt(Stack.Count - 1); foreach (Entity entity in curEntity.Components.Values) { if (entity is ITransfer) { var childIndex = request.Entitys.Count; request.Entitys.Add(entity); Stack.Add(childIndex); request.Map.Add(new RecursiveEntitys { ChildIndex = childIndex, ParentIndex = index, IsChild = 0 }); } } foreach (Entity entity in curEntity.Children.Values) { if (entity is ITransfer) { var childIndex = request.Entitys.Count; request.Entitys.Add(entity); Stack.Add(childIndex); request.Map.Add(new RecursiveEntitys { ChildIndex = childIndex, ParentIndex = index, IsChild = 1 }); } } } Stack.Dispose(); // 删除Mailbox,让发给Unit的ActorLocation消息重发 unit.RemoveComponent <MailBoxComponent>(); // location加锁 long oldInstanceId = unit.InstanceId; await LocationProxyComponent.Instance.Lock(unit.Id, unit.InstanceId); M2M_UnitTransferResponse response = await ActorMessageSenderComponent.Instance.Call(sceneInstanceId, request) as M2M_UnitTransferResponse; await LocationProxyComponent.Instance.UnLock(unit.Id, oldInstanceId, response.NewInstanceId); unit.Dispose(); }