server-master/srcs/_plugins/WingsEmu.Plugins.BasicImplementation/Event/Npcs/NpcSummonEventHandler.cs
2026-02-10 18:21:30 +01:00

127 lines
No EOL
4.4 KiB
C#

using System;
using System.Threading;
using System.Threading.Tasks;
using PhoenixLib.Events;
using WingsEmu.Core.Extensions;
using WingsEmu.DTOs.Maps;
using WingsEmu.Game;
using WingsEmu.Game._enum;
using WingsEmu.Game.Battle.Managers;
using WingsEmu.Game.Entities;
using WingsEmu.Game.Entities.Event;
using WingsEmu.Game.Helpers.Damages;
using WingsEmu.Game.Managers.StaticData;
using WingsEmu.Game.Monster.Event;
using WingsEmu.Game.Npcs;
using WingsEmu.Game.Npcs.Event;
using WingsEmu.Game.Triggers;
using WingsEmu.Packets.Enums;
namespace WingsEmu.Plugins.BasicImplementations.Event.Npcs;
public class NpcSummonEventHandler : IAsyncEventProcessor<NpcSummonEvent>
{
private readonly INpcEntityFactory _npcEntityFactory;
private readonly INpcMonsterManager _npcMonsterManager;
private readonly IPhantomPositionManager _phantomPositionManager;
public NpcSummonEventHandler(INpcEntityFactory npcEntityFactory, INpcMonsterManager npcMonsterManager, IPhantomPositionManager phantomPositionManager)
{
_npcEntityFactory = npcEntityFactory;
_npcMonsterManager = npcMonsterManager;
_phantomPositionManager = phantomPositionManager;
}
public async Task HandleAsync(NpcSummonEvent e, CancellationToken cancellation)
{
foreach (ToSummon summon in e.Npcs)
{
var npcMonster = new MonsterData(_npcMonsterManager.GetNpc(summon.VNum));
INpcEntity mapNpc = _npcEntityFactory.CreateNpc(npcMonster, e.Map, npcAdditionalData: new NpcAdditionalData
{
CanMove = summon.IsMoving,
CanAttack = summon.IsHostile,
IsHostile = summon.IsHostile,
NpcDirection = summon.Direction,
NpcShouldRespawn = false,
FactionType = e.Map.HasMapFlag(MapFlags.ACT_4) ? FactionType.Angel : FactionType.Neutral // Just random Faction
});
mapNpc.Target = summon.Target;
if (summon.TriggerEvents != null)
{
foreach ((string key, IAsyncEvent asyncEvent, bool removeOnUse) in summon.TriggerEvents)
{
mapNpc.AddEvent(key, asyncEvent, removeOnUse);
}
}
Position? phantomPosition = e.MonsterId.HasValue ? _phantomPositionManager.GetPosition(e.MonsterId.Value) : null;
Position spawnCell = phantomPosition ?? summon.SpawnCell ?? e.Map.GetRandomPosition();
await mapNpc.EmitEventAsync(new MapJoinNpcEntityEvent(mapNpc, spawnCell.X, spawnCell.Y));
CheckBeriosPhantom(mapNpc);
if (!summon.RemoveTick)
{
continue;
}
mapNpc.NextTick = DateTime.UtcNow.AddSeconds(-1000);
mapNpc.NextAttackReady = DateTime.UtcNow.AddSeconds(-1000);
}
}
private void CheckBeriosPhantom(INpcEntity mapNpc)
{
switch ((MonsterVnum)mapNpc.MonsterVNum)
{
case MonsterVnum.EMERALD_SHADOW_PHANTOM:
mapNpc.AddEvent(BattleTriggers.OnDeath, new MonsterSummonEvent(mapNpc.MapInstance, Lists.Create(new ToSummon
{
VNum = (short)MonsterVnum.EMERALD_PHANTOM,
SpawnCell = mapNpc.Position,
IsMoving = true,
IsHostile = true
}))
{
NpcId = mapNpc.UniqueId
}, true);
break;
case MonsterVnum.SAPPHIRE_SHADOW_PHANTOM:
mapNpc.AddEvent(BattleTriggers.OnDeath, new MonsterSummonEvent(mapNpc.MapInstance, Lists.Create(new ToSummon
{
VNum = (short)MonsterVnum.SAPPHIRE_PHANTOM,
SpawnCell = mapNpc.Position,
IsMoving = true,
IsHostile = true
}))
{
NpcId = mapNpc.UniqueId
}, true);
break;
case MonsterVnum.RUBY_SHADOW_PHANTOM:
mapNpc.AddEvent(BattleTriggers.OnDeath, new MonsterSummonEvent(mapNpc.MapInstance, Lists.Create(new ToSummon
{
VNum = (short)MonsterVnum.RUBY_PHANTOM,
SpawnCell = mapNpc.Position,
IsMoving = true,
IsHostile = true
}))
{
NpcId = mapNpc.UniqueId
}, true);
break;
}
}
}