diff options
| author | Matan Shukry <matanshukry@gmail.com> | 2021-01-23 17:44:47 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2021-01-23 16:44:47 +0100 |
| commit | e601c6d1f9b9743e92e9562abd9f2d24d9aaf175 (patch) | |
| tree | 426f250d99f071d2703c6c581ede5f0a2ed8b600 /src | |
| parent | 1d51013b71d46a2825519cdb85d7049109b226ae (diff) | |
Core/Spells: Implemented summoning a personal gameobject effect (#25917)
Diffstat (limited to 'src')
| -rw-r--r-- | src/server/game/Entities/GameObject/GameObject.cpp | 2 | ||||
| -rw-r--r-- | src/server/game/Entities/GameObject/GameObject.h | 5 | ||||
| -rw-r--r-- | src/server/game/Entities/Object/Object.cpp | 4 | ||||
| -rw-r--r-- | src/server/game/Miscellaneous/SharedDefines.h | 2 | ||||
| -rw-r--r-- | src/server/game/Spells/Spell.h | 1 | ||||
| -rw-r--r-- | src/server/game/Spells/SpellEffects.cpp | 51 | ||||
| -rw-r--r-- | src/server/game/Spells/SpellInfo.cpp | 2 |
7 files changed, 63 insertions, 4 deletions
diff --git a/src/server/game/Entities/GameObject/GameObject.cpp b/src/server/game/Entities/GameObject/GameObject.cpp index 4f2a19a2d72..ca4ff39e14e 100644 --- a/src/server/game/Entities/GameObject/GameObject.cpp +++ b/src/server/game/Entities/GameObject/GameObject.cpp @@ -107,7 +107,7 @@ QuaternionData QuaternionData::fromEulerAnglesZYX(float Z, float Y, float X) } GameObject::GameObject() : WorldObject(false), MapObject(), - m_model(nullptr), m_goValue(), m_AI(nullptr), m_respawnCompatibilityMode(false), _animKitId(0), _worldEffectID(0) + m_model(nullptr), m_goValue(), m_AI(nullptr), m_respawnCompatibilityMode(false), _animKitId(0), _worldEffectID(0), m_visibleByUnitOnly() { m_objectType |= TYPEMASK_GAMEOBJECT; m_objectTypeId = TYPEID_GAMEOBJECT; diff --git a/src/server/game/Entities/GameObject/GameObject.h b/src/server/game/Entities/GameObject/GameObject.h index d49a8363e51..faf4b8dec72 100644 --- a/src/server/game/Entities/GameObject/GameObject.h +++ b/src/server/game/Entities/GameObject/GameObject.h @@ -317,6 +317,10 @@ class TC_GAME_API GameObject : public WorldObject, public GridObject<GameObject> void AIM_Destroy(); bool AIM_Initialize(); + void SetVisibleByUnitOnly(ObjectGuid unit) { m_visibleByUnitOnly = unit; } + bool IsVisibleByUnitOnly() const { return !m_visibleByUnitOnly.IsEmpty(); } + ObjectGuid GetVisibleByUnitOnly() const { return m_visibleByUnitOnly; } + UF::UpdateField<UF::GameObjectData, 0, TYPEID_GAMEOBJECT> m_gameObjectData; protected: @@ -374,5 +378,6 @@ class TC_GAME_API GameObject : public WorldObject, public GridObject<GameObject> bool m_respawnCompatibilityMode; uint16 _animKitId; uint32 _worldEffectID; + ObjectGuid m_visibleByUnitOnly; }; #endif diff --git a/src/server/game/Entities/Object/Object.cpp b/src/server/game/Entities/Object/Object.cpp index 96992a698a5..7e9ce1fff40 100644 --- a/src/server/game/Entities/Object/Object.cpp +++ b/src/server/game/Entities/Object/Object.cpp @@ -1453,6 +1453,10 @@ bool WorldObject::CanSeeOrDetect(WorldObject const* obj, bool ignoreStealth, boo return false; } + if (GameObject const* go = obj->ToGameObject()) + if (go->IsVisibleByUnitOnly() && GetGUID() != go->GetVisibleByUnitOnly()) + return false; + if (!viewpoint) viewpoint = this; diff --git a/src/server/game/Miscellaneous/SharedDefines.h b/src/server/game/Miscellaneous/SharedDefines.h index 83b6372cc4b..e6243536357 100644 --- a/src/server/game/Miscellaneous/SharedDefines.h +++ b/src/server/game/Miscellaneous/SharedDefines.h @@ -1219,7 +1219,7 @@ enum SpellEffectName SPELL_EFFECT_ALLOW_CONTROL_PET = 168, // NYI SPELL_EFFECT_DESTROY_ITEM = 169, SPELL_EFFECT_UPDATE_ZONE_AURAS_AND_PHASES = 170, // NYI - SPELL_EFFECT_171 = 171, // Summons gamebject + SPELL_EFFECT_SUMMON_PERSONAL_GAMEOBJECT = 171, // Summons gamebject SPELL_EFFECT_RESURRECT_WITH_AURA = 172, SPELL_EFFECT_UNLOCK_GUILD_VAULT_TAB = 173, // Guild tab unlocked (guild perk) SPELL_EFFECT_APPLY_AURA_ON_PET = 174, // NYI diff --git a/src/server/game/Spells/Spell.h b/src/server/game/Spells/Spell.h index 11a196d2ed4..e9f609639cb 100644 --- a/src/server/game/Spells/Spell.h +++ b/src/server/game/Spells/Spell.h @@ -462,6 +462,7 @@ class TC_GAME_API Spell void EffectCastButtons(SpellEffIndex effIndex); void EffectRechargeItem(SpellEffIndex effIndex); void EffectGiveCurrency(SpellEffIndex effIndex); + void EffectSummonPersonalGameObject(SpellEffIndex effIndex); void EffectResurrectWithAura(SpellEffIndex effIndex); void EffectCreateAreaTrigger(SpellEffIndex effIndex); void EffectRemoveTalent(SpellEffIndex effIndex); diff --git a/src/server/game/Spells/SpellEffects.cpp b/src/server/game/Spells/SpellEffects.cpp index 7db4fc958d5..e373411b120 100644 --- a/src/server/game/Spells/SpellEffects.cpp +++ b/src/server/game/Spells/SpellEffects.cpp @@ -249,7 +249,7 @@ NonDefaultConstructible<pEffect> SpellEffects[TOTAL_SPELL_EFFECTS] = &Spell::EffectNULL, //168 SPELL_EFFECT_ALLOW_CONTROL_PET &Spell::EffectDestroyItem, //169 SPELL_EFFECT_DESTROY_ITEM &Spell::EffectUpdateZoneAurasAndPhases, //170 SPELL_EFFECT_UPDATE_ZONE_AURAS_AND_PHASES - &Spell::EffectNULL, //171 SPELL_EFFECT_171 + &Spell::EffectSummonPersonalGameObject, //171 SPELL_EFFECT_SUMMON_PERSONAL_GAMEOBJECT &Spell::EffectResurrectWithAura, //172 SPELL_EFFECT_RESURRECT_WITH_AURA &Spell::EffectUnlockGuildVaultTab, //173 SPELL_EFFECT_UNLOCK_GUILD_VAULT_TAB &Spell::EffectApplyAura, //174 SPELL_EFFECT_APPLY_AURA_ON_PET @@ -5427,6 +5427,55 @@ void Spell::EffectUnlockGuildVaultTab(SpellEffIndex /*effIndex*/) guild->HandleBuyBankTab(caster->GetSession(), damage - 1); // Bank tabs start at zero internally } +void Spell::EffectSummonPersonalGameObject(SpellEffIndex effIndex) +{ + if (effectHandleMode != SPELL_EFFECT_HANDLE_HIT) + return; + + uint32 goId = effectInfo->MiscValue; + if (!goId) + return; + + float x, y, z; + if (m_targets.HasDst()) + destTarget->GetPosition(x, y, z); + else + m_caster->GetClosePoint(x, y, z, DEFAULT_PLAYER_BOUNDING_RADIUS); + + Map* map = m_caster->GetMap(); + Position pos = Position(x, y, z, m_caster->GetOrientation()); + QuaternionData rot = QuaternionData::fromEulerAnglesZYX(m_caster->GetOrientation(), 0.f, 0.f); + GameObject* go = GameObject::CreateGameObject(goId, map, pos, rot, 255, GO_STATE_READY); + + if (!go) + { + TC_LOG_WARN("spells", "SpellEffect Failed to summon personal gameobject. SpellId %u, effect %u", m_spellInfo->Id, effIndex); + return; + } + + PhasingHandler::InheritPhaseShift(go, m_caster); + + int32 duration = m_spellInfo->CalcDuration(m_caster); + + go->SetRespawnTime(duration > 0 ? duration / IN_MILLISECONDS : 0); + go->SetSpellId(m_spellInfo->Id); + go->SetVisibleByUnitOnly(m_caster->GetGUID()); + + ExecuteLogEffectSummonObject(effIndex, go); + + map->AddToMap(go); + + if (GameObject* linkedTrap = go->GetLinkedTrap()) + { + PhasingHandler::InheritPhaseShift(linkedTrap, m_caster); + + linkedTrap->SetRespawnTime(duration > 0 ? duration / IN_MILLISECONDS : 0); + linkedTrap->SetSpellId(m_spellInfo->Id); + + ExecuteLogEffectSummonObject(effIndex, linkedTrap); + } +} + void Spell::EffectResurrectWithAura(SpellEffIndex effIndex) { if (effectHandleMode != SPELL_EFFECT_HANDLE_HIT_TARGET) diff --git a/src/server/game/Spells/SpellInfo.cpp b/src/server/game/Spells/SpellInfo.cpp index 4f98c6573c7..81a71a8df8c 100644 --- a/src/server/game/Spells/SpellInfo.cpp +++ b/src/server/game/Spells/SpellInfo.cpp @@ -962,7 +962,7 @@ SpellEffectInfo::StaticData SpellEffectInfo::_data[TOTAL_SPELL_EFFECTS] = {EFFECT_IMPLICIT_TARGET_EXPLICIT, TARGET_OBJECT_TYPE_UNIT}, // 168 SPELL_EFFECT_168 {EFFECT_IMPLICIT_TARGET_CASTER, TARGET_OBJECT_TYPE_UNIT}, // 169 SPELL_EFFECT_DESTROY_ITEM {EFFECT_IMPLICIT_TARGET_EXPLICIT, TARGET_OBJECT_TYPE_UNIT}, // 170 SPELL_EFFECT_170 - {EFFECT_IMPLICIT_TARGET_NONE, TARGET_OBJECT_TYPE_DEST}, // 171 SPELL_EFFECT_171 + {EFFECT_IMPLICIT_TARGET_NONE, TARGET_OBJECT_TYPE_DEST}, // 171 SPELL_EFFECT_SUMMON_PERSONAL_GAMEOBJECT {EFFECT_IMPLICIT_TARGET_EXPLICIT, TARGET_OBJECT_TYPE_UNIT}, // 172 SPELL_EFFECT_172 {EFFECT_IMPLICIT_TARGET_NONE, TARGET_OBJECT_TYPE_NONE}, // 173 SPELL_EFFECT_UNLOCK_GUILD_VAULT_TAB {EFFECT_IMPLICIT_TARGET_EXPLICIT, TARGET_OBJECT_TYPE_UNIT}, // 174 SPELL_EFFECT_174 |
