From 2b7b0b0db12697d3b9da2701b4824b4ffe1aad37 Mon Sep 17 00:00:00 2001 From: Shauren Date: Sat, 18 Jun 2022 19:05:57 +0200 Subject: [PATCH] Core/Scripts: Begin unifying triggering gameevents (not the game_event db stuff) --- .../game/Entities/GameObject/GameObject.cpp | 34 ++++-------- .../game/Entities/GameObject/GameObject.h | 2 - src/server/game/Entities/Object/Object.cpp | 17 ++++-- src/server/game/Entities/Object/Object.h | 1 + .../game/Entities/Transport/Transport.cpp | 4 +- src/server/game/Events/GameEventSender.cpp | 52 +++++++++++++++++++ src/server/game/Events/GameEventSender.h | 30 +++++++++++ .../FlightPathMovementGenerator.cpp | 3 +- src/server/game/Spells/SpellEffects.cpp | 10 ++-- 9 files changed, 111 insertions(+), 42 deletions(-) create mode 100644 src/server/game/Events/GameEventSender.cpp create mode 100644 src/server/game/Events/GameEventSender.h diff --git a/src/server/game/Entities/GameObject/GameObject.cpp b/src/server/game/Entities/GameObject/GameObject.cpp index 9cf04c8463..f7c9f3fe14 100644 --- a/src/server/game/Entities/GameObject/GameObject.cpp +++ b/src/server/game/Entities/GameObject/GameObject.cpp @@ -22,6 +22,7 @@ #include "CreatureAISelector.h" #include "DatabaseEnv.h" #include "GameObjectAI.h" +#include "GameEventSender.h" #include "GameObjectModel.h" #include "GameTime.h" #include "GossipDef.h" @@ -1670,8 +1671,7 @@ void GameObject::Use(Unit* user) if (info->goober.eventId) { TC_LOG_DEBUG("maps.script", "Goober ScriptStart id %u for GO entry %u (GUID %u).", info->goober.eventId, GetEntry(), GetSpawnId()); - GetMap()->ScriptsStart(sEventScripts, info->goober.eventId, player, this); - EventInform(info->goober.eventId, user); + GameEvents::Trigger(info->goober.eventId, player, this); } // possible quest objective for active quests @@ -1728,10 +1728,7 @@ void GameObject::Use(Unit* user) player->SendCinematicStart(info->camera.cinematicId); if (info->camera.eventID) - { - GetMap()->ScriptsStart(sEventScripts, info->camera.eventID, player, this); - EventInform(info->camera.eventID, user); - } + GameEvents::Trigger(info->camera.eventID, player, this); return; } @@ -2210,22 +2207,6 @@ bool GameObject::IsInRange(float x, float y, float z, float radius) const && dz < info->GeoBoxMax.Z + radius && dz > info->GeoBoxMin.Z - radius; } -void GameObject::EventInform(uint32 eventId, WorldObject* invoker /*= nullptr*/) -{ - if (!eventId) - return; - - if (AI()) - AI()->EventInform(eventId); - - if (GetZoneScript()) - GetZoneScript()->ProcessEvent(this, eventId); - - if (BattlegroundMap* bgMap = GetMap()->ToBattlegroundMap()) - if (bgMap->GetBG()) - bgMap->GetBG()->ProcessEvent(this, eventId, invoker); -} - uint32 GameObject::GetScriptId() const { if (GameObjectData const* gameObjectData = GetGameObjectData()) @@ -2375,7 +2356,8 @@ void GameObject::SetDestructibleState(GameObjectDestructibleState state, Player* break; case GO_DESTRUCTIBLE_DAMAGED: { - EventInform(m_goInfo->building.damagedEvent, eventInvoker); + if (GetGOInfo()->building.damagedEvent) + GameEvents::Trigger(GetGOInfo()->building.damagedEvent, eventInvoker, this); AI()->Damaged(eventInvoker, m_goInfo->building.damageEvent); RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_DESTROYED); @@ -2400,7 +2382,8 @@ void GameObject::SetDestructibleState(GameObjectDestructibleState state, Player* } case GO_DESTRUCTIBLE_DESTROYED: { - EventInform(m_goInfo->building.destroyedEvent, eventInvoker); + if (GetGOInfo()->building.destroyedEvent) + GameEvents::Trigger(GetGOInfo()->building.destroyedEvent, eventInvoker, this); AI()->Destroyed(eventInvoker, m_goInfo->building.destroyedEvent); if (eventInvoker) @@ -2426,7 +2409,8 @@ void GameObject::SetDestructibleState(GameObjectDestructibleState state, Player* } case GO_DESTRUCTIBLE_REBUILDING: { - EventInform(m_goInfo->building.rebuildingEvent, eventInvoker); + if (GetGOInfo()->building.rebuildingEvent) + GameEvents::Trigger(GetGOInfo()->building.rebuildingEvent, eventInvoker, this); RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_DAMAGED | GO_FLAG_DESTROYED); uint32 modelId = m_goInfo->displayId; diff --git a/src/server/game/Entities/GameObject/GameObject.h b/src/server/game/Entities/GameObject/GameObject.h index afe49e8fc6..4ea646e0a1 100644 --- a/src/server/game/Entities/GameObject/GameObject.h +++ b/src/server/game/Entities/GameObject/GameObject.h @@ -260,8 +260,6 @@ class TC_GAME_API GameObject : public WorldObject, public GridObject return GO_DESTRUCTIBLE_INTACT; } - void EventInform(uint32 eventId, WorldObject* invoker = nullptr); - // There's many places not ready for dynamic spawns. This allows them to live on for now. void SetRespawnCompatibilityMode(bool mode = true) { m_respawnCompatibilityMode = mode; } bool GetRespawnCompatibilityMode() { return m_respawnCompatibilityMode; } diff --git a/src/server/game/Entities/Object/Object.cpp b/src/server/game/Entities/Object/Object.cpp index b9d12828a5..8306af553c 100644 --- a/src/server/game/Entities/Object/Object.cpp +++ b/src/server/game/Entities/Object/Object.cpp @@ -2166,22 +2166,29 @@ void Map::SummonCreatureGroup(uint8 group, std::list* list /*= null list->push_back(summon); } -void WorldObject::SetZoneScript() +ZoneScript* WorldObject::FindZoneScript() const { if (Map* map = FindMap()) { - if (map->IsDungeon()) - m_zoneScript = (ZoneScript*)((InstanceMap*)map)->GetInstanceScript(); + if (InstanceMap* instanceMap = map->ToInstanceMap()) + return reinterpret_cast(instanceMap->GetInstanceScript()); else if (!map->IsBattlegroundOrArena()) { if (Battlefield* bf = sBattlefieldMgr->GetBattlefieldToZoneId(GetZoneId())) - m_zoneScript = bf; + return bf; else - m_zoneScript = sOutdoorPvPMgr->GetZoneScript(GetZoneId()); + return sOutdoorPvPMgr->GetZoneScript(GetZoneId()); } } + return nullptr; } +void WorldObject::SetZoneScript() +{ + m_zoneScript = FindZoneScript(); +} + + void WorldObject::ClearZoneScript() { m_zoneScript = nullptr; diff --git a/src/server/game/Entities/Object/Object.h b/src/server/game/Entities/Object/Object.h index 19c71d60f8..4af128b7cc 100644 --- a/src/server/game/Entities/Object/Object.h +++ b/src/server/game/Entities/Object/Object.h @@ -401,6 +401,7 @@ class TC_GAME_API WorldObject : public Object, public WorldLocation void SetZoneScript(); void ClearZoneScript(); + ZoneScript* FindZoneScript() const; ZoneScript* GetZoneScript() const { return m_zoneScript; } TempSummon* SummonCreature(uint32 entry, Position const& pos, TempSummonType despawnType = TEMPSUMMON_MANUAL_DESPAWN, uint32 despawnTime = 0, uint32 vehId = 0, ObjectGuid privateObjectOwner = ObjectGuid::Empty); diff --git a/src/server/game/Entities/Transport/Transport.cpp b/src/server/game/Entities/Transport/Transport.cpp index aa4198fe64..5481bc5c2d 100644 --- a/src/server/game/Entities/Transport/Transport.cpp +++ b/src/server/game/Entities/Transport/Transport.cpp @@ -18,6 +18,7 @@ #include "Transport.h" #include "CellImpl.h" #include "Common.h" +#include "GameEventSender.h" #include "DBCStores.h" #include "GameObjectAI.h" #include "Log.h" @@ -748,8 +749,7 @@ void Transport::DoEventIfAny(KeyFrame const& node, bool departure) if (uint32 eventid = departure ? node.Node->DepartureEventID : node.Node->ArrivalEventID) { TC_LOG_DEBUG("maps.script", "Taxi %s event %u of node %u of %s path", departure ? "departure" : "arrival", eventid, node.Node->NodeIndex, GetName().c_str()); - GetMap()->ScriptsStart(sEventScripts, eventid, this, this); - EventInform(eventid); + GameEvents::Trigger(eventid, this, this); } } diff --git a/src/server/game/Events/GameEventSender.cpp b/src/server/game/Events/GameEventSender.cpp new file mode 100644 index 0000000000..a454ce547a --- /dev/null +++ b/src/server/game/Events/GameEventSender.cpp @@ -0,0 +1,52 @@ +/* + * This file is part of the TrinityCore Project. See AUTHORS file for Copyright information + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see . + */ + +#include "GameEventSender.h" +#include "Battleground.h" +#include "GameObject.h" +#include "GameObjectAI.h" +#include "InstanceScript.h" +#include "Map.h" +#include "ObjectMgr.h" +#include "Util.h" + +void GameEvents::Trigger(uint32 gameEventId, WorldObject* source, WorldObject* target) +{ + ASSERT(source || target, "At least one of [source] or [target] must be provided"); + + WorldObject* refForMapAndZoneScript = Coalesce(source, target); + + ZoneScript* zoneScript = refForMapAndZoneScript->GetZoneScript(); + if (!zoneScript && refForMapAndZoneScript->IsPlayer()) + zoneScript = refForMapAndZoneScript->FindZoneScript(); + + if (zoneScript) + zoneScript->ProcessEvent(target, gameEventId, source); + + Map* map = refForMapAndZoneScript->GetMap(); + if (target) + { + if (GameObject* goTarget = target->ToGameObject()) + if (GameObjectAI* goAI = goTarget->AI()) + goAI->EventInform(gameEventId); + + if (BattlegroundMap* bgMap = map->ToBattlegroundMap()) + bgMap->GetBG()->ProcessEvent(target, gameEventId, source); + } + + map->ScriptsStart(sEventScripts, gameEventId, source, target); +} diff --git a/src/server/game/Events/GameEventSender.h b/src/server/game/Events/GameEventSender.h new file mode 100644 index 0000000000..ed2650d2c0 --- /dev/null +++ b/src/server/game/Events/GameEventSender.h @@ -0,0 +1,30 @@ +/* + * This file is part of the TrinityCore Project. See AUTHORS file for Copyright information + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see . + */ + +#ifndef GameEventSender_h__ +#define GameEventSender_h__ + +#include "Define.h" + +class WorldObject; + +namespace GameEvents +{ + TC_GAME_API void Trigger(uint32 gameEventId, WorldObject* source, WorldObject* target); +} + +#endif // GameEventSender_h__ diff --git a/src/server/game/Movement/MovementGenerators/FlightPathMovementGenerator.cpp b/src/server/game/Movement/MovementGenerators/FlightPathMovementGenerator.cpp index e1ee696307..9ef20b48d8 100644 --- a/src/server/game/Movement/MovementGenerators/FlightPathMovementGenerator.cpp +++ b/src/server/game/Movement/MovementGenerators/FlightPathMovementGenerator.cpp @@ -17,6 +17,7 @@ #include "FlightPathMovementGenerator.h" #include "DBCStores.h" +#include "GameEventSender.h" #include "Log.h" #include "MapManager.h" #include "MoveSpline.h" @@ -219,7 +220,7 @@ void FlightPathMovementGenerator::DoEventIfAny(Player* player, TaxiPathNodeEntry if (uint32 eventid = departure ? node->DepartureEventID : node->ArrivalEventID) { TC_LOG_DEBUG("maps.script", "Taxi %s event %u of node %u of path %u for player %s", departure ? "departure" : "arrival", eventid, node->NodeIndex, node->PathID, player->GetName().c_str()); - player->GetMap()->ScriptsStart(sEventScripts, eventid, player, player); + GameEvents::Trigger(eventid, player, player); } } diff --git a/src/server/game/Spells/SpellEffects.cpp b/src/server/game/Spells/SpellEffects.cpp index af7af3e8a1..41db5ef481 100644 --- a/src/server/game/Spells/SpellEffects.cpp +++ b/src/server/game/Spells/SpellEffects.cpp @@ -26,6 +26,7 @@ #include "DatabaseEnv.h" #include "DynamicObject.h" #include "Formulas.h" +#include "GameEventSender.h" #include "GameObject.h" #include "GameObjectAI.h" #include "GameClient.h" @@ -1035,12 +1036,7 @@ void Spell::EffectSendEvent(SpellEffIndex effIndex) TC_LOG_DEBUG("spells", "Spell ScriptStart %u for spellid %u in EffectSendEvent ", m_spellInfo->Effects[effIndex].MiscValue, m_spellInfo->Id); - if (ZoneScript* zoneScript = m_caster->GetZoneScript()) - zoneScript->ProcessEvent(target, m_spellInfo->Effects[effIndex].MiscValue); - else if (InstanceScript* instanceScript = m_caster->GetInstanceScript()) // needed in case Player is the caster - instanceScript->ProcessEvent(target, m_spellInfo->Effects[effIndex].MiscValue); - - m_caster->GetMap()->ScriptsStart(sEventScripts, m_spellInfo->Effects[effIndex].MiscValue, m_caster, target); + GameEvents::Trigger(m_spellInfo->Effects[effIndex].MiscValue, m_caster, target); } void Spell::EffectPowerBurn(SpellEffIndex effIndex) @@ -1591,7 +1587,7 @@ void Spell::SendLoot(ObjectGuid guid, LootType loottype) if (gameObjTarget->GetGOInfo()->chest.eventId) { TC_LOG_DEBUG("spells", "Chest ScriptStart id %u for GO %u", gameObjTarget->GetGOInfo()->chest.eventId, gameObjTarget->GetSpawnId()); - player->GetMap()->ScriptsStart(sEventScripts, gameObjTarget->GetGOInfo()->chest.eventId, player, gameObjTarget); + GameEvents::Trigger(gameObjTarget->GetGOInfo()->chest.eventId, player, gameObjTarget); } // triggering linked GO