using GlobalClassLib; using ONDServer.Map; using ONDServer.Net; using PacketLib; namespace ONDServer.Enemies; public class NekoEnemy : Enemy { public override string Name{ get; } = "Neko"; public override EnemyType Type{ get; } = EnemyType.NEKO; public override bool BlocksTile{ get; set; } = true; public bool Aggressive = false; public ServerPlayer? Target{ get; set; } private readonly RoamingPathfinder pathfinder; public NekoEnemy(int difficulty) : base(difficulty, 4000) { pathfinder = new RoamingPathfinder(this, 1){AdditionalTileFilter = t => Aggressive || t.Owner == null || !t.Lit}; } public override void Spawn(MapTile location) { base.Spawn(location); MovementOpportunity.Start(); pathfinder.TakenPath.Add(Location!); Server.SendUpdateToAll([GameEvent.ENEMY_SPAWN(Type, Id, Difficulty, Location!.Id)]); } public override void Reset() { MapTile[] resetLocations = new[]{MapManager.Get(7), MapManager.Get(12), MapManager.Get(17)}.Where(t => EnemyManager.GetByLocation(t).Length == 0).ToArray(); Location = resetLocations[new Random().Next(resetLocations.Length)]; pathfinder.TakenPath.Clear(); pathfinder.TakenPath.Add(Location); Aggressive = false; Target = Server.OtherPlayer(Target!); Server.SendUpdateToAll([GameEvent.ENEMY_RESET(Id, Location.Id)]); } public override void Update() { base.Update(); if(Location == null) return; if (Location.Owner != null && Location.Lit && !Aggressive){ Aggressive = true; Server.SendUpdateToAll([GameEvent.NEKO_ANGERED(Location.Owner.State.Pid, Id)]); } if (Target == null){ if (Server.P1.State.Power > Server.P2.State.Power){ Target = Server.P2; } else if (Server.P1.State.Power < Server.P2.State.Power){ Target = Server.P1; } else{ if (GameLogic.PhaseCounter > 1){ Target = Server.Players[new Random().Next(2)]; SetDifficulty(8); } } } bool succeed = MovementOpportunity.CheckAndRoll(); if (Target != null && (succeed || (Aggressive && GameLogic.NSecondUpdate))){ Pathfinder.Decision decision = pathfinder.DecideNext(MapManager.Get(Target.State.OfficeTileId)); switch (decision.type){ case Pathfinder.Decision.MoveType: if (Location.GetConnector(decision.nextTile!)!.Type == ConnectorType.VENT){ Server.SendUpdateToAll([GameEvent.VENT_USED()]); } Location = decision.nextTile!; Server.SendUpdateToAll([GameEvent.ENEMY_MOVEMENT(Id, Location.Id)]); Console.WriteLine($"Enemy {Type} ({Name}) moving to {Location.IdAsString})"); break; case Pathfinder.Decision.AttackType: Attack(decision.attackTarget!); break; case Pathfinder.Decision.ResetType: Reset(); break; case Pathfinder.Decision.WaitType: Aggressive = false; break; } } } }