private void SetLocations() { if (DefensiveLocation == null) { DefensiveLocation = ProxyLocationService.GetCliffProxyLocation(); TargetLocation = TargetingData.EnemyMainBasePoint; var angle = Math.Atan2(TargetLocation.Y - DefensiveLocation.Y, DefensiveLocation.X - TargetLocation.X); var x = -6 * Math.Cos(angle); var y = -6 * Math.Sin(angle); LoadingLocation = new Point2D { X = DefensiveLocation.X + (float)x, Y = DefensiveLocation.Y - (float)y }; LoadingLocationHeight = MapDataService.MapHeight(LoadingLocation); var loadingVector = new Vector2(LoadingLocation.X, LoadingLocation.Y); DropArea = AreaService.GetTargetArea(TargetLocation); var dropVector = DropArea.OrderBy(p => Vector2.DistanceSquared(new Vector2(p.X, p.Y), loadingVector)).First(); x = -2 * Math.Cos(angle); y = -2 * Math.Sin(angle); DropLocation = new Point2D { X = dropVector.X + (float)x, Y = dropVector.Y - (float)y }; DropLocationHeight = MapDataService.MapHeight(DropLocation); InsideBaseDistanceSquared = Vector2.DistanceSquared(new Vector2(LoadingLocation.X, LoadingLocation.Y), new Vector2(TargetLocation.X, TargetLocation.Y)); } DebugService.DrawSphere(new Point { X = LoadingLocation.X, Y = LoadingLocation.Y, Z = 12 }, 3, new Color { R = 0, G = 0, B = 255 }); DebugService.DrawSphere(new Point { X = DropLocation.X, Y = DropLocation.Y, Z = 12 }, 3, new Color { R = 0, G = 255, B = 0 }); }
public Point2D FindPylonPlacement(Point2D reference, float maxDistance, float minimumMineralProximinity = 2, bool requireSameHeight = false, WallOffType wallOffType = WallOffType.None) { var x = reference.X; var y = reference.Y; var radius = 1f; // start at 12 o'clock then rotate around 12 times, increase radius by 1 until it's more than maxDistance while (radius < maxDistance / 2.0) { var fullCircle = Math.PI * 2; var sliceSize = fullCircle / (8.0 + radius); var angle = 0.0; while (angle + (sliceSize / 2) < fullCircle) { var point = new Point2D { X = x + (float)(radius * Math.Cos(angle)), Y = y + (float)(radius * Math.Sin(angle)) }; //DebugService.DrawSphere(new Point { X = point.X, Y = point.Y, Z = 12 }); //if (!BuildingService.AreaBuildable(point.X, point.Y, 1.25f)) //{ // DebugService.DrawSphere(new Point { X = point.X, Y = point.Y, Z = 12 }, 1, new Color { R = 255, G = 0, B = 0 }); //} //else if (BuildingService.Blocked(point.X, point.Y, 1.25f, .1f)) //{ // DebugService.DrawSphere(new Point { X = point.X, Y = point.Y, Z = 12 }, 1, new Color { R = 255, G = 255, B = 0 }); //} //else if (BuildingService.HasCreep(point.X, point.Y, 1.5f)) //{ // DebugService.DrawSphere(new Point { X = point.X, Y = point.Y, Z = 12 }, 1, new Color { R = 255, G = 255, B = 255 }); //} //else //{ // DebugService.DrawSphere(new Point { X = point.X, Y = point.Y, Z = 12 }, 1, new Color { R = 0, G = 255, B = 0 }); //} if (BuildingService.AreaBuildable(point.X, point.Y, 1.25f) && (minimumMineralProximinity == 0 || !BuildingService.BlocksResourceCenter(point.X, point.Y, 1.25f)) && !BuildingService.Blocked(point.X, point.Y, 1.25f, .1f) && !BuildingService.HasCreep(point.X, point.Y, 1.5f) && (!requireSameHeight || MapDataService.MapHeight(point) == MapDataService.MapHeight(reference))) { var mineralFields = ActiveUnitData.NeutralUnits.Where(u => SharkyUnitData.MineralFieldTypes.Contains((UnitTypes)u.Value.Unit.UnitType) || SharkyUnitData.GasGeyserTypes.Contains((UnitTypes)u.Value.Unit.UnitType)); var squared = (1 + minimumMineralProximinity + .5) * (1 + minimumMineralProximinity + .5); var nexusDistanceSquared = 16f; if (minimumMineralProximinity == 0) { nexusDistanceSquared = 0; } var nexusClashes = ActiveUnitData.SelfUnits.Where(u => (u.Value.Unit.UnitType == (uint)UnitTypes.PROTOSS_NEXUS || u.Value.Unit.UnitType == (uint)UnitTypes.PROTOSS_PYLON) && Vector2.DistanceSquared(u.Value.Position, new Vector2(point.X, point.Y)) < squared + nexusDistanceSquared); if (nexusClashes.Count() == 0) { var clashes = mineralFields.Where(u => Vector2.DistanceSquared(u.Value.Position, new Vector2(point.X, point.Y)) < squared); if (clashes.Count() == 0) { if (Vector2.DistanceSquared(new Vector2(reference.X, reference.Y), new Vector2(point.X, point.Y)) <= maxDistance * maxDistance) { DebugService.DrawSphere(new Point { X = point.X, Y = point.Y, Z = 12 }); return(point); } } } } angle += sliceSize; } radius += 1; } return(null); }
bool NavigateToSupportUnit(UnitCommander commander, Point2D target, int frame, out List <SC2APIProtocol.Action> action) { if (MapDataService.PathWalkable(commander.UnitCalculation.Unit.Pos)) // if it is in unplaceable terrain, can't unload { if (commander.UnitCalculation.Unit.Shield + commander.UnitCalculation.Unit.Health < 50 || commander.UnitCalculation.EnemiesInRangeOf.Count > 0) // if warp prism dying or enemies nearby unload { action = commander.Order(frame, Abilities.UNLOADALLAT_WARPPRISM, null, commander.UnitCalculation.Unit.Tag); return(true); } foreach (var passenger in commander.UnitCalculation.Unit.Passengers) { var passengerUnit = ActiveUnitData.Commanders[passenger.Tag].UnitCalculation.Unit; var unit = ActiveUnitData.Commanders[passenger.Tag].UnitCalculation; foreach (var enemyAttack in commander.UnitCalculation.NearbyEnemies) { if (DamageService.CanDamage(unit, enemyAttack) && InRange(commander.UnitCalculation.Position, enemyAttack.Position, unit.Range + passengerUnit.Radius + enemyAttack.Unit.Radius) && MapDataService.MapHeight(commander.UnitCalculation.Unit.Pos) == MapDataService.MapHeight(enemyAttack.Unit.Pos)) { if (!enemyAttack.UnitClassifications.Contains(UnitClassification.ArmyUnit) && !InRange(commander.UnitCalculation.Position, enemyAttack.Position, 2 + passengerUnit.Radius + enemyAttack.Unit.Radius)) { continue; } // if an enemy is in range drop the unit //action = commander.Order(frame, Abilities.UNLOADALLAT_WARPPRISM, null, commander.UnitCalculation.Unit.Tag); // TODO: dropping a specific unit not working, can only drop all, change it if they ever fix the api action = commander.UnloadSpecificUnit(frame, Abilities.UNLOADUNIT_WARPPRISM, passenger.Tag); return(true); } } } if (InRange(new Vector2(target.X, target.Y), commander.UnitCalculation.Position, 3)) // if made it to the target just drop { action = commander.Order(frame, Abilities.UNLOADALLAT_WARPPRISM, null, commander.UnitCalculation.Unit.Tag); return(true); } } if (commander.UnitCalculation.Unit.CargoSpaceMax > commander.UnitCalculation.Unit.CargoSpaceTaken && commander.UnitCalculation.Unit.Shield + commander.UnitCalculation.Unit.Health > 50) // find more units to load { var friendly = commander.UnitCalculation.NearbyAllies.Where(u => !u.Unit.IsFlying && u.Unit.BuildProgress == 1 && u.UnitClassifications.Contains(UnitClassification.ArmyUnit) && !commander.UnitCalculation.Unit.Passengers.Any(p => p.Tag == u.Unit.Tag) && commander.UnitCalculation.Unit.CargoSpaceMax - commander.UnitCalculation.Unit.CargoSpaceTaken >= UnitDataService.CargoSize((UnitTypes)u.Unit.UnitType) && u.EnemiesInRange.Count == 0 && u.EnemiesInRangeOf.Count == 0).OrderBy(u => Vector2.DistanceSquared(commander.UnitCalculation.Position, u.Position)).FirstOrDefault(); if (friendly != null) { action = commander.Order(frame, Abilities.LOAD, null, friendly.Unit.Tag); return(true); } } action = commander.Order(frame, Abilities.MOVE, target); return(true); }