private AShip SearchClosestShip(AShip ship, QuadTree quadTree, float range) { var possibleCollisions = new List <AShip>(); quadTree.Retrieve(possibleCollisions, ship); AShip nearestShip = null; foreach (var potentialEnemyShip in possibleCollisions) { //only add ships that are new var rangeCircle = new CircleF(ship.Position, range); //scan radius if (rangeCircle.Contains(potentialEnemyShip.Position) && potentialEnemyShip.Owned && potentialEnemyShip.Hp >= 0) { if (nearestShip == null) { nearestShip = potentialEnemyShip; } else if (Vector2.Distance(nearestShip.Position, ship.Position) > Vector2.Distance(potentialEnemyShip.Position, ship.Position)) { nearestShip = potentialEnemyShip; } } } return(nearestShip); }
// Очистка группы public void Clear() { foreach (Ship AShip in Ships) { AShip.ShowPath(false); } LastPlanet = null; Ships.Clear(); Planets.Clear(); DoSetGroup(); }
public Coord(AShip ship) { Hit = false; Ship = ship; }
/// <summary> /// Check for possible actions for the Fleets and single Ships controled by the AI. /// </summary> public void Update(GameTime gameTime, QuadTree quadTree) { //FisherShips var counter = mAiFisherShipList.Count; for (var i = 0; i < counter; i++) { var fShip = mAiFisherShipList[i]; if (!fShip.Moving) { if (mFishingMovingDelay <= 0) { var randomNumber = new Random(); //moving to a random position in the Map var x = randomNumber.Next(0, 5760); var y = randomNumber.Next(0, 5760); fShip.Move(PathFinder.CalculatePath(fShip.Position, new Vector2(x, y), false)); mFishingMovingDelay = 8; } else { mFishingMovingDelay -= gameTime.ElapsedGameTime.TotalSeconds; } } if (!fShip.Owned && fShip.Hp > 0) { continue; } mAiFisherShipList.RemoveAt(i); counter--; fShip.HealthBar = null; fShip.CrewBar = null; if (fShip.Owned ) { Game1.mEventScreen.mEventManager.UpdateStatTotal("Ships Hijacked", 1); } } //TradingShips counter = mAiTradingShipList.Count; for (var i = 0; i < counter; i++) { var tShip = mAiTradingShipList[i]; if (!tShip.Moving) { if (mTradingMovingDelay <= 0) { var randomNumber = new Random(); var number = randomNumber.Next(0, IslandManager.IslandCount); var destination = new Vector2(IslandManager.Islands[IslandManager.mIslandNames[number]].X + randomNumber.Next(20, 50), IslandManager.Islands[IslandManager.mIslandNames[number]].Y + randomNumber.Next(20, 50)); if (Vector2.Distance(destination, tShip.Position) > 100 && Game1.mMapScreen.mGridMap.GetCell(destination).IsWalkable && !Game1.mMapScreen.mGridMap.GetCell(destination).Occupied) { tShip.Move(PathFinder.CalculatePath(tShip.Position, destination, false)); mTradingMovingDelay = 5; } } else { mTradingMovingDelay -= gameTime.ElapsedGameTime.TotalSeconds; } } if (tShip.Hp < tShip.MaxHp) //shoot back { if (!mDefendingShipList.Contains(tShip)) { tShip.Defend(tShip.ShipPath); mDefendingShipList.Add(tShip); } if (tShip.Hp <= 40) //fleeing { tShip.TargetShip = null; tShip.Move(tShip.ShipPath); tShip.CurrentBState = TradingShip.ShipBattleState.Idle; mDefendingShipList.Remove(tShip); } } if (!tShip.Owned && tShip.Hp > 0) { continue; } mAiTradingShipList.RemoveAt(i); counter--; if (tShip.Owned) { tShip.CrewBar = null; tShip.HealthBar = null; Game1.mEventScreen.mEventManager.UpdateStatTotal("Ships Hijacked", 1); var random = new Random(); if (random.Next(0, 4) == 1)// 25% dropchance { RessourceManager.AddRessource("mapParts", 1); } } } //BattleShips counter = mAiBattleShipsList.Count; for (var i = 0; i < counter; i++) { var bShip = mAiBattleShipsList[i]; if (bShip.CurrentBState == BattleShip.ShipBattleState.Idle) { if (!bShip.Moving) { if (mBattleMovingDelay <= 0) { //moving to a random position in the Map var randomNumber = new Random(); var x = randomNumber.Next(0, 5760); var y = randomNumber.Next(0, 5760); bShip.Move(PathFinder.CalculatePath(bShip.Position, new Vector2(x, y), false)); mBattleMovingDelay = 3; } else { mBattleMovingDelay -= gameTime.ElapsedGameTime.TotalSeconds; } } //scan for possible enemies in reach and attack them if they aren't to powefull var possibleCollisions = new List <AShip>(); var enemyShipsCount = 0; quadTree.Retrieve(possibleCollisions, bShip); if (possibleCollisions.Count > 0) { AShip nearestShip = null; for (var index = 0; index < possibleCollisions.Count; index++) { var rangeCircle = new CircleF(bShip.Position, 500f); //scan radius if (rangeCircle.Contains(possibleCollisions[index].Position) && possibleCollisions[index].Owned && possibleCollisions[index].Hp >= 0) { if (nearestShip == null) { nearestShip = possibleCollisions[index]; } enemyShipsCount++; //save the nearest Ship if (Vector2.Distance(bShip.Position, possibleCollisions[index].Position) < Vector2.Distance(bShip.Position, nearestShip.Position)) { nearestShip = possibleCollisions[index]; } } } //only attack up to 3 ships if (enemyShipsCount > 0 && enemyShipsCount <= 3 && nearestShip != null) { var random = new Random(); var number = random.Next(0, 2); if ((number == 1) && nearestShip.EnterAttackValue - 8 < bShip.EnterAttackValue) { bShip.Move(PathFinder.CalculatePath(bShip.Position, nearestShip.Position, false)); bShip.Enter(nearestShip); mEnteringShipList.Add(bShip); } else { bShip.Move(PathFinder.CalculatePath(bShip.Position, nearestShip.Position, false)); bShip.Attack(nearestShip); mAttackingShipList.Add(bShip); } } else if (enemyShipsCount > 3) { bShip.CurrentBState = BattleShip.ShipBattleState.Defending; mDefendingShipList.Add(bShip); } } } if (!bShip.Owned && bShip.Hp > 0) { continue; } mAiBattleShipsList.RemoveAt(i); counter--; bShip.CrewBar = null; bShip.HealthBar = null; if (!Game1.mMapScreen.mTechDemo && bShip.Owned) { Game1.mEventScreen.mEventManager.UpdateStatTotal("Ships Hijacked", 1); var random = new Random(); if (random.Next(0, 3) == 1)// 33% dropchance { RessourceManager.AddRessource("mapParts", 1); } } } //Fleets counter = mAiFleetList.Count; for (var t = 0; t < counter; t++) { var fleet = mAiFleetList[t]; //check if the ships are still in the fleet var bCounter = fleet.BattleShips.Count; for (var i = 0; i < bCounter; i++) { if (!(fleet.BattleShips[i].Hp <= 0) && !fleet.BattleShips[i].Owned) { continue; } fleet.BattleShips.RemoveAt(i); bCounter--; } var tCounter = fleet.TradingShips.Count; for (var i = 0; i < tCounter; i++) { if (!(fleet.TradingShips[i].Hp <= 0) && !fleet.TradingShips[i].Owned) { continue; } fleet.TradingShips.RemoveAt(i); tCounter--; } //ceck if fleets are whiped out if (fleet.FleetCount() <= 0) { mAiFleetList.Remove(fleet); counter--; } if (!fleet.InBattle) { //search for enemies when not in Battle var possibleCollisions = new List <AShip>(); var toAttack = new List <AShip>(); quadTree.Retrieve(possibleCollisions, fleet.FlagShip); //check if the ships are enemies and in range foreach (var potentialEnemyShip in possibleCollisions) { var rangeCircle = new CircleF(fleet.FlagShip.Position, 600f); //scan radius if (rangeCircle.Contains(potentialEnemyShip.Position) && potentialEnemyShip.Owned && potentialEnemyShip.Hp >= 0) { toAttack.Add(potentialEnemyShip); } } //if there are any enemies, attack them if (toAttack.Count > 0) { fleet.Attack(toAttack); } //random movement. Determines with the Flagship if the fleet is moving. if (!fleet.FlagShip.Moving && !fleet.Defending) { if (mBattleMovingDelay <= 0) { //moving to a random position in the Map var randomNumber = new Random(); var x = randomNumber.Next(0, 5760); var y = randomNumber.Next(0, 5760); fleet.Move(new Vector2(x, y)); mBattleMovingDelay = 3; } else { mBattleMovingDelay -= gameTime.ElapsedGameTime.TotalSeconds; } } } else//when in battle { //check if own ships were entered for (int i = 0; i < fleet.BattleShips.Count; i++) { if (fleet.BattleShips[i].Owned) { fleet.MarkedShips.Add(fleet.BattleShips[i]); fleet.BattleShips.RemoveAt(i); } } //check if own ships were entered for (int i = 0; i < fleet.TradingShips.Count; i++) { if (fleet.TradingShips[i].Owned) { fleet.MarkedShips.Add(fleet.TradingShips[i]); fleet.TradingShips.RemoveAt(i); } } //check if the marked ships still exist and the distance var kCounter = fleet.MarkedShips.Count; for (var i = 0; i < kCounter; i++) { if (fleet.MarkedShips[i].Hp <= 0 || !fleet.MarkedShips[i].Owned || Vector2.Distance(fleet.MarkedShips[i].Position, fleet.FlagShip.Position) > 600) { fleet.MarkedShips.RemoveAt(i); kCounter--; i--; } } fleet.UpdateBattle(); //check for enemies var possibleCollisions = new List <AShip>(); var toAttack = new List <AShip>(); quadTree.Retrieve(possibleCollisions, fleet.FlagShip); foreach (var potentialEnemyShip in possibleCollisions) { //only add ships that are new var rangeCircle = new CircleF(fleet.FlagShip.Position, 700f); //scan radius if (!fleet.MarkedShips.Contains(potentialEnemyShip) && rangeCircle.Contains(potentialEnemyShip.Position) && potentialEnemyShip.Owned && potentialEnemyShip.Hp >= 0) { toAttack.Add(potentialEnemyShip); } } if (toAttack.Count > 0) { fleet.MarkedShips.AddRange(toAttack); } //if there is no enemy left, the fleet will stop battling if (fleet.MarkedShips.Count <= 0) { fleet.InBattle = false; fleet.StopBattle(); } } } //GhostShip if (GhostShip != null) { if (GhostShip.CurrentBState == GhostShip.ShipBattleState.Idle) { //check if there are any enemyShips nearby var enemyShips = new List <AShip>(); var possibleCollisions = new List <AShip>(); quadTree.Retrieve(possibleCollisions, GhostShip); foreach (var potentialEnemyShip in possibleCollisions) { //only add ships that are new var rangeCircle = new CircleF(GhostShip.Position, 600f); //scan radius if (!GhostShip.TargetShips.Contains(potentialEnemyShip) && rangeCircle.Contains(potentialEnemyShip.Position) && potentialEnemyShip.Owned && potentialEnemyShip.Hp >= 0) { enemyShips.Add(potentialEnemyShip); } } if (enemyShips.Count > 0) { GhostShip.Attack(enemyShips); } //move to the island if not already next to it. if (Vector2.Distance(GhostShip.Position, GhostShip.TreasureIslandPosition) >= 200 && !GhostShip.Moving) { GhostShip.Move(PathFinder.CalculatePath(GhostShip.Position, GhostShip.TreasureIslandPosition, true)); } } else if (GhostShip.CurrentBState == GhostShip.ShipBattleState.Attacking) { GhostShip.Update(gameTime); //check if there are any new enemyShips nearby var possibleCollisions = new List <AShip>(); quadTree.Retrieve(possibleCollisions, GhostShip); foreach (var potentialEnemyShip in possibleCollisions) { //only add ships that are new var rangeCircle = new CircleF(GhostShip.Position, 600f); //scan radius if (!GhostShip.TargetShips.Contains(potentialEnemyShip) && rangeCircle.Contains(potentialEnemyShip.Position) && potentialEnemyShip.Owned && potentialEnemyShip.Hp >= 0) { GhostShip.TargetShips.Add(potentialEnemyShip); } } //moving mGhostMovementDelay -= gameTime.ElapsedGameTime.TotalSeconds; if (mGhostMovementDelay <= 0 && GhostShip.NearestTarget != null) { Vector2 movementTarget; if (Vector2.Distance(GhostShip.NearestTarget.Position, GhostShip.Position) <= 120) { if (GhostShip.MoveRight) { movementTarget = GhostShip.Position + (Vector2.Normalize(GhostShip.Position - GhostShip.NearestTarget.Position).PerpendicularCounterClockwise() * 100f); GhostShip.MoveRight = false; } else { movementTarget = GhostShip.Position + (Vector2.Normalize(GhostShip.Position - GhostShip.NearestTarget.Position).PerpendicularClockwise() * 100f); GhostShip.MoveRight = true; } mGhostMovementDelay = 1.5; } else { movementTarget = GhostShip.NearestTarget.Position + Vector2.Normalize(GhostShip.Position - GhostShip.NearestTarget.Position) * 20f; mGhostMovementDelay = 1; } GhostShip.Move(PathFinder.CalculatePath(GhostShip.Position, movementTarget, true)); } } if (GhostShip.Hp <= 0) { GhostShip.DropLoot(); mAllShipList.Remove(GhostShip); GhostShip = null; } } else { //spawn ships if necessary RespawnShips(); } if (Octopus != null) { //search for enemies if (Octopus.CurrentBState == Octopus.ShipBattleState.Idle) { /* * var possibleCollisions = new List<AShip>(); * quadTree.Retrieve(possibleCollisions, Octopus); * AShip nearestShip = null; * foreach (var potentialEnemyShip in possibleCollisions) * { * //only add ships that are new * * var rangeCircle = new CircleF(Octopus.Position, 400f); //scan radius * if (rangeCircle.Contains(potentialEnemyShip.Position) && potentialEnemyShip.Owned && * potentialEnemyShip.Hp >= 0) * { * if (nearestShip == null) * { * nearestShip = potentialEnemyShip; * } * else if (Vector2.Distance(nearestShip.Position, Octopus.Position) > Vector2.Distance(potentialEnemyShip.Position, Octopus.Position)) * { * nearestShip = potentialEnemyShip; * } * } * }*/ var nearestShip = SearchClosestShip(Octopus, quadTree, 400f);//testing if (nearestShip != null) { Octopus.Enter(nearestShip);//attack the closest enemy } //move back to original position if (Vector2.Distance(Octopus.Position, Octopus.HousingPosition) >= 200 && !Octopus.Moving) { Octopus.Move(PathFinder.CalculatePath(Octopus.Position, Octopus.HousingPosition, true)); } } else if (Octopus.CurrentBState == Octopus.ShipBattleState.Entering) { Octopus.Update(gameTime); mOctopusChasingDelay -= gameTime.ElapsedGameTime.TotalSeconds; if (Octopus.TargetShip != null && Vector2.Distance(Octopus.Position, Octopus.TargetShip.Position) >= 70 && mOctopusChasingDelay <= 0) { mOctopusChasingDelay = 2; Octopus.Move(PathFinder.CalculatePath(Octopus.Position, Octopus.TargetShip.Position, true)); } } if (Octopus.Hp <= 0) { Octopus.DropLoot(); mAllShipList.Remove(Octopus); Octopus = null; } } if (Dragon != null) { Dragon.Update(gameTime, quadTree);//special Updates for the dragon.. Dragon.UpdateDragonMovement(gameTime); //check if the Dragoon is fighting or not if (Dragon.CurrentBState == Dragon.ShipBattleState.Idle) { if (!Dragon.Moving) { //moving to a random position in the Map var randomNumber = new Random(); var x = randomNumber.Next(0, 5760); var y = randomNumber.Next(0, 5760); Dragon.MoveDragon(new Vector2(x, y)); } /* * var possibleCollisions = new List<AShip>(); * quadTree.Retrieve(possibleCollisions, Dragon); * AShip nearestShip = null; * foreach (var potentialEnemyShip in possibleCollisions) * { * //only add ships that are new * var rangeCircle = new CircleF(Octopus.Position, 200f); //scan radius * if (rangeCircle.Contains(potentialEnemyShip.Position) && potentialEnemyShip.Owned && * potentialEnemyShip.Hp >= 0) * { * if (nearestShip == null) * { * nearestShip = potentialEnemyShip; * } * else if (Vector2.Distance(nearestShip.Position, Octopus.Position) > Vector2.Distance(potentialEnemyShip.Position, Octopus.Position)) * { * nearestShip = potentialEnemyShip; * } * } * }*/ var nearestShip = SearchClosestShip(Dragon, quadTree, 200f); if (nearestShip != null) { Dragon.Attack(nearestShip); //attack the closest enemy } } else if (Dragon.CurrentBState == Dragon.ShipBattleState.Attacking) { //Chasing if (Dragon.TargetShip != null && Vector2.Distance(Dragon.Position, Dragon.TargetShip.Position) >= 70) { Dragon.MoveDragon(Dragon.TargetShip.Position); } } if (Dragon.Hp <= 0) { Dragon.DropLoot(); mAllShipList.Remove(Dragon); Dragon = null; } } }