public void MoveEx(Player me, World world, Game game, Move move, RewindClient.RewindClient rewindClient) { GlobalHelper.World = world; GlobalHelper.Move = move; GlobalHelper.Game = game; GlobalHelper.Me = me; GlobalHelper.Enemy = world.GetOpponentPlayer(); var enemy = GlobalHelper.Enemy; LazyClusters = new Lazy <List <List <DbScanHelper.Point> > >(() => { var enemyPoints = UnitHelper.UnitsEnemy.Select(x => new DbScanHelper.Point(x.X, x.Y, x.Type, x.Durability)).ToList(); List <List <DbScanHelper.Point> > clusters = DbScanHelper.GetClusters(enemyPoints, 15, 1); return(clusters); }); UpdateVehiclesStates(me, world, game, rewindClient); FacilityHelper.UpdateFacilitiesStates(); #if DEBUG UnitHelper.DrawAllUnits(); DbScanHelper.DrawClusters(LazyClusters.Value); FacilityHelper.DrawFacilities(); NuclearStrikeHelper.DrawNuclearStrikes(me, enemy, game, rewindClient); #endif if (world.TickIndex == 0) { PrepareUnits(); } if (QueueHelper.Queue.Count > 0) { if (!GlobalHelper.MoveAllowed) { return; } var task = QueueHelper.Queue.Dequeue(); task.Execute(); return; } var nucStrikeProcessed = NuclearStrikeHelper.ProcessEnemyNuclearStrikeDodge(GlobalHelper.MoveAllowed); if (nucStrikeProcessed) { return; } var selectedUnits = UnitHelper.UnitsAlly.Where(x => x.Groups.Contains(GroupHelper.CurrentGroup.Id)).ToArray(); if (selectedUnits.Length == 0) { if (GlobalHelper.MoveAllowed) { GroupHelper.SelectNextGroup(); return; } return; } if (GlobalHelper.MoveAllowed && ConfigurationHelper.EnableNuclearStrike) { if (me.NextNuclearStrikeTickIndex > 0) { var isNucleatorInGroup = selectedUnits.Select(x => x.Id).Contains(me.NextNuclearStrikeVehicleId); if (isNucleatorInGroup) { var nucleator = selectedUnits.FirstOrDefault(x => x.Id == me.NextNuclearStrikeVehicleId); if (nucleator != null) { ActionHelper.StopMove(); return; } } } if (me.RemainingNuclearStrikeCooldownTicks <= 0) { //var unit = UnitHelper.UnitsAlly.First(); //var vr = GetVisionRangeByWeather(unit); //var maxRange = // UnitHelper.UnitsAlly // .Where(x => PotentialFieldsHelper.GetDistanceTo(x.X, x.Y, unit.X, unit.Y) < vr) // .Max(x => PotentialFieldsHelper.GetDistanceTo(x.X, x.Y, unit.X, unit.Y)); //var targetUnit = // UnitHelper.UnitsAlly.First(x => PotentialFieldsHelper.GetDistanceTo(x.X, x.Y, unit.X, unit.Y) == maxRange); //ActionHelper.NuclearStrike(unit.Id, targetUnit.X, targetUnit.Y); //return; var hasTargetToNuclearAttack = NuclearStrikeHelper.HasTargetToNuclearAttack(selectedUnits); if (hasTargetToNuclearAttack.Success) { //Остановимся для выстрела ActionHelper.StopMove(); var selectedUnit = hasTargetToNuclearAttack.SelectedUnitRes; var enemyUnit = hasTargetToNuclearAttack.EnemyRes; QueueHelper.Queue.Enqueue(new NuclearStrike(selectedUnit.Id, enemyUnit.X, enemyUnit.Y)); return; } } } var size = PotentialFieldsHelper.PpSize; PotentialFieldsHelper.Clear(); var applyNuclearStrikePower = me.RemainingNuclearStrikeCooldownTicks <= 0 && ConfigurationHelper.EnableNuclearStrike; PotentialFieldsHelper.AppendEnemyPower(LazyClusters.Value, applyNuclearStrikePower); PotentialFieldsHelper.ApplyHealPower(); PotentialFieldsHelper.ApplyFacilitiesPower(); PotentialFieldsHelper.AppendAllyUnitsToDodge(selectedUnits); PotentialFieldsHelper.Normalize(); for (int i = 0; i < size; i++) { for (int j = 0; j < size; j++) { var color = PotentialFieldsHelper.GetColorFromValue(PotentialFieldsHelper.PotentialFields[i, j]); rewindClient.Rectangle(i * size, j * size, (i + 1) * size, (j + 1) * size, color); } } if (GlobalHelper.MoveAllowed) { var currentSelectedGroup = GroupHelper.CurrentGroup; //Если на предыдущем ходу текущая группа уже двигалась, передадим управление след группе if (currentSelectedGroup.Moved) { var isSelectSuccess = GroupHelper.SelectNextGroup(); if (isSelectSuccess) { currentSelectedGroup.Moved = false; return; } } if (currentSelectedGroup.MovesCount > 0 && currentSelectedGroup.MovesCount % ConfigurationHelper.MovesCoutToScale == 0) { new ScaleCurrentGroupToCenterTask().Execute(); } else { var cx = selectedUnits.Sum(x => x.X) / selectedUnits.Length; var cy = selectedUnits.Sum(x => x.Y) / selectedUnits.Length; var nextPpPoint = PotentialFieldsHelper.Get_PP_PointToMove(cx, cy, 3); var quartCellLength = PotentialFieldsHelper.PpSize * 0.25; var nextPpPointX = nextPpPoint.X * size + size / 2d; var nextPpPointY = nextPpPoint.Y * size + size / 2d; //Если достаточно подойти к цели, отдадим управление дргому отряду if (PotentialFieldsHelper.GetDistanceTo(nextPpPointX, nextPpPointY, cx, cy) < quartCellLength) { var isSelectSuccess = GroupHelper.SelectNextGroup(); if (isSelectSuccess) { currentSelectedGroup.Moved = false; return; } } var vx = nextPpPointX - cx; var vy = nextPpPointY - cy; #if DEBUG rewindClient.Line(cx, cy, nextPpPointX, nextPpPointY, Color.Black); #endif ActionHelper.Move(vx, vy); } currentSelectedGroup.Moved = true; currentSelectedGroup.MovesCount++; return; } return; }