TrinityCore
Loading...
Searching...
No Matches
SpellEffects.cpp
Go to the documentation of this file.
1/*
2 * This file is part of the TrinityCore Project. See AUTHORS file for Copyright information
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms of the GNU General Public License as published by the
6 * Free Software Foundation; either version 2 of the License, or (at your
7 * option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12 * more details.
13 *
14 * You should have received a copy of the GNU General Public License along
15 * with this program. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18#include "Spell.h"
19#include "AccountMgr.h"
20#include "Battleground.h"
21#include "CellImpl.h"
22#include "Common.h"
23#include "Creature.h"
24#include "CreatureAI.h"
25#include "DatabaseEnv.h"
26#include "DynamicObject.h"
27#include "Formulas.h"
28#include "GameObject.h"
29#include "GameObjectAI.h"
30#include "GossipDef.h"
31#include "GridNotifiers.h"
32#include "InstanceScript.h"
33#include "Item.h"
34#include "Language.h"
35#include "Log.h"
36#include "LootMgr.h"
37#include "MiscPackets.h"
38#include "MotionMaster.h"
39#include "ObjectAccessor.h"
40#include "ObjectMgr.h"
41#include "Opcodes.h"
42#include "OutdoorPvPMgr.h"
43#include "PathGenerator.h"
44#include "Pet.h"
45#include "Player.h"
46#include "ReputationMgr.h"
47#include "ScriptMgr.h"
48#include "SkillExtraItems.h"
49#include "SharedDefines.h"
50#include "SocialMgr.h"
51#include "SpellAuraEffects.h"
52#include "SpellAuras.h"
53#include "SpellHistory.h"
54#include "SpellMgr.h"
55#include "TemporarySummon.h"
56#include "Totem.h"
57#include "UpdateMask.h"
58#include "Unit.h"
59#include "Util.h"
60#include "World.h"
61#include "WorldPacket.h"
62#include "WorldSession.h"
63
65{
67 &Spell::EffectInstaKill, // 1 SPELL_EFFECT_INSTAKILL
68 &Spell::EffectSchoolDMG, // 2 SPELL_EFFECT_SCHOOL_DAMAGE
69 &Spell::EffectDummy, // 3 SPELL_EFFECT_DUMMY
70 &Spell::EffectUnused, // 4 SPELL_EFFECT_PORTAL_TELEPORT unused
71 &Spell::EffectTeleportUnits, // 5 SPELL_EFFECT_TELEPORT_UNITS
72 &Spell::EffectApplyAura, // 6 SPELL_EFFECT_APPLY_AURA
73 &Spell::EffectEnvironmentalDMG, // 7 SPELL_EFFECT_ENVIRONMENTAL_DAMAGE
74 &Spell::EffectPowerDrain, // 8 SPELL_EFFECT_POWER_DRAIN
75 &Spell::EffectHealthLeech, // 9 SPELL_EFFECT_HEALTH_LEECH
76 &Spell::EffectHeal, // 10 SPELL_EFFECT_HEAL
77 &Spell::EffectBind, // 11 SPELL_EFFECT_BIND
78 &Spell::EffectNULL, // 12 SPELL_EFFECT_PORTAL
79 &Spell::EffectUnused, // 13 SPELL_EFFECT_RITUAL_BASE unused
80 &Spell::EffectUnused, // 14 SPELL_EFFECT_RITUAL_SPECIALIZE unused
81 &Spell::EffectUnused, // 15 SPELL_EFFECT_RITUAL_ACTIVATE_PORTAL unused
82 &Spell::EffectQuestComplete, // 16 SPELL_EFFECT_QUEST_COMPLETE
83 &Spell::EffectWeaponDmg, // 17 SPELL_EFFECT_WEAPON_DAMAGE_NOSCHOOL
84 &Spell::EffectResurrect, // 18 SPELL_EFFECT_RESURRECT
85 &Spell::EffectAddExtraAttacks, // 19 SPELL_EFFECT_ADD_EXTRA_ATTACKS
86 &Spell::EffectUnused, // 20 SPELL_EFFECT_DODGE one spell: Dodge
87 &Spell::EffectUnused, // 21 SPELL_EFFECT_EVADE one spell: Evade (DND)
88 &Spell::EffectParry, // 22 SPELL_EFFECT_PARRY
89 &Spell::EffectBlock, // 23 SPELL_EFFECT_BLOCK one spell: Block
90 &Spell::EffectCreateItem, // 24 SPELL_EFFECT_CREATE_ITEM
91 &Spell::EffectUnused, // 25 SPELL_EFFECT_WEAPON
92 &Spell::EffectUnused, // 26 SPELL_EFFECT_DEFENSE one spell: Defense
93 &Spell::EffectPersistentAA, // 27 SPELL_EFFECT_PERSISTENT_AREA_AURA
94 &Spell::EffectSummonType, // 28 SPELL_EFFECT_SUMMON
95 &Spell::EffectLeap, // 29 SPELL_EFFECT_LEAP
96 &Spell::EffectEnergize, // 30 SPELL_EFFECT_ENERGIZE
97 &Spell::EffectWeaponDmg, // 31 SPELL_EFFECT_WEAPON_PERCENT_DAMAGE
98 &Spell::EffectTriggerMissileSpell, // 32 SPELL_EFFECT_TRIGGER_MISSILE
99 &Spell::EffectOpenLock, // 33 SPELL_EFFECT_OPEN_LOCK
100 &Spell::EffectSummonChangeItem, // 34 SPELL_EFFECT_SUMMON_CHANGE_ITEM
101 &Spell::EffectUnused, // 35 SPELL_EFFECT_APPLY_AREA_AURA_PARTY
102 &Spell::EffectLearnSpell, // 36 SPELL_EFFECT_LEARN_SPELL
103 &Spell::EffectUnused, // 37 SPELL_EFFECT_SPELL_DEFENSE one spell: SPELLDEFENSE (DND)
104 &Spell::EffectDispel, // 38 SPELL_EFFECT_DISPEL
105 &Spell::EffectUnused, // 39 SPELL_EFFECT_LANGUAGE
106 &Spell::EffectDualWield, // 40 SPELL_EFFECT_DUAL_WIELD
107 &Spell::EffectJump, // 41 SPELL_EFFECT_JUMP
108 &Spell::EffectJumpDest, // 42 SPELL_EFFECT_JUMP_DEST
109 &Spell::EffectTeleUnitsFaceCaster, // 43 SPELL_EFFECT_TELEPORT_UNITS_FACE_CASTER
110 &Spell::EffectLearnSkill, // 44 SPELL_EFFECT_SKILL_STEP
111 &Spell::EffectAddHonor, // 45 SPELL_EFFECT_ADD_HONOR honor/pvp related
112 &Spell::EffectUnused, // 46 SPELL_EFFECT_SPAWN clientside, unit appears as if it was just spawned
113 &Spell::EffectTradeSkill, // 47 SPELL_EFFECT_TRADE_SKILL
114 &Spell::EffectUnused, // 48 SPELL_EFFECT_STEALTH one spell: Base Stealth
115 &Spell::EffectUnused, // 49 SPELL_EFFECT_DETECT one spell: Detect
116 &Spell::EffectTransmitted, // 50 SPELL_EFFECT_TRANS_DOOR
117 &Spell::EffectUnused, // 51 SPELL_EFFECT_FORCE_CRITICAL_HIT unused
118 &Spell::EffectUnused, // 52 SPELL_EFFECT_GUARANTEE_HIT one spell: zzOLDCritical Shot
119 &Spell::EffectEnchantItemPerm, // 53 SPELL_EFFECT_ENCHANT_ITEM
120 &Spell::EffectEnchantItemTmp, // 54 SPELL_EFFECT_ENCHANT_ITEM_TEMPORARY
121 &Spell::EffectTameCreature, // 55 SPELL_EFFECT_TAMECREATURE
122 &Spell::EffectSummonPet, // 56 SPELL_EFFECT_SUMMON_PET
123 &Spell::EffectLearnPetSpell, // 57 SPELL_EFFECT_LEARN_PET_SPELL
124 &Spell::EffectWeaponDmg, // 58 SPELL_EFFECT_WEAPON_DAMAGE
125 &Spell::EffectCreateRandomItem, // 59 SPELL_EFFECT_CREATE_RANDOM_ITEM create item base at spell specific loot
126 &Spell::EffectProficiency, // 60 SPELL_EFFECT_PROFICIENCY
127 &Spell::EffectSendEvent, // 61 SPELL_EFFECT_SEND_EVENT
128 &Spell::EffectPowerBurn, // 62 SPELL_EFFECT_POWER_BURN
129 &Spell::EffectThreat, // 63 SPELL_EFFECT_THREAT
130 &Spell::EffectTriggerSpell, // 64 SPELL_EFFECT_TRIGGER_SPELL
131 &Spell::EffectUnused, // 65 SPELL_EFFECT_APPLY_AREA_AURA_RAID
132 &Spell::EffectRechargeManaGem, // 66 SPELL_EFFECT_CREATE_MANA_GEM (possibly recharge it, misc - is item ID)
133 &Spell::EffectHealMaxHealth, // 67 SPELL_EFFECT_HEAL_MAX_HEALTH
134 &Spell::EffectInterruptCast, // 68 SPELL_EFFECT_INTERRUPT_CAST
135 &Spell::EffectDistract, // 69 SPELL_EFFECT_DISTRACT
136 &Spell::EffectPull, // 70 SPELL_EFFECT_PULL one spell: Distract Move
137 &Spell::EffectPickPocket, // 71 SPELL_EFFECT_PICKPOCKET
138 &Spell::EffectAddFarsight, // 72 SPELL_EFFECT_ADD_FARSIGHT
139 &Spell::EffectUntrainTalents, // 73 SPELL_EFFECT_UNTRAIN_TALENTS
140 &Spell::EffectApplyGlyph, // 74 SPELL_EFFECT_APPLY_GLYPH
141 &Spell::EffectHealMechanical, // 75 SPELL_EFFECT_HEAL_MECHANICAL one spell: Mechanical Patch Kit
142 &Spell::EffectSummonObjectWild, // 76 SPELL_EFFECT_SUMMON_OBJECT_WILD
143 &Spell::EffectScriptEffect, // 77 SPELL_EFFECT_SCRIPT_EFFECT
144 &Spell::EffectUnused, // 78 SPELL_EFFECT_ATTACK
145 &Spell::EffectSanctuary, // 79 SPELL_EFFECT_SANCTUARY
146 &Spell::EffectAddComboPoints, // 80 SPELL_EFFECT_ADD_COMBO_POINTS
147 &Spell::EffectUnused, // 81 SPELL_EFFECT_CREATE_HOUSE one spell: Create House (TEST)
148 &Spell::EffectNULL, // 82 SPELL_EFFECT_BIND_SIGHT
149 &Spell::EffectDuel, // 83 SPELL_EFFECT_DUEL
150 &Spell::EffectStuck, // 84 SPELL_EFFECT_STUCK
151 &Spell::EffectSummonPlayer, // 85 SPELL_EFFECT_SUMMON_PLAYER
152 &Spell::EffectActivateObject, // 86 SPELL_EFFECT_ACTIVATE_OBJECT
153 &Spell::EffectGameObjectDamage, // 87 SPELL_EFFECT_GAMEOBJECT_DAMAGE
154 &Spell::EffectGameObjectRepair, // 88 SPELL_EFFECT_GAMEOBJECT_REPAIR
155 &Spell::EffectGameObjectSetDestructionState, // 89 SPELL_EFFECT_GAMEOBJECT_SET_DESTRUCTION_STATE
156 &Spell::EffectKillCreditPersonal, // 90 SPELL_EFFECT_KILL_CREDIT Kill credit but only for single person
157 &Spell::EffectUnused, // 91 SPELL_EFFECT_THREAT_ALL one spell: zzOLDBrainwash
158 &Spell::EffectEnchantHeldItem, // 92 SPELL_EFFECT_ENCHANT_HELD_ITEM
159 &Spell::EffectForceDeselect, // 93 SPELL_EFFECT_FORCE_DESELECT
160 &Spell::EffectSelfResurrect, // 94 SPELL_EFFECT_SELF_RESURRECT
161 &Spell::EffectSkinning, // 95 SPELL_EFFECT_SKINNING
162 &Spell::EffectCharge, // 96 SPELL_EFFECT_CHARGE
163 &Spell::EffectCastButtons, // 97 SPELL_EFFECT_CAST_BUTTON (totem bar since 3.2.2a)
164 &Spell::EffectKnockBack, // 98 SPELL_EFFECT_KNOCK_BACK
165 &Spell::EffectDisEnchant, // 99 SPELL_EFFECT_DISENCHANT
166 &Spell::EffectInebriate, //100 SPELL_EFFECT_INEBRIATE
167 &Spell::EffectFeedPet, //101 SPELL_EFFECT_FEED_PET
168 &Spell::EffectDismissPet, //102 SPELL_EFFECT_DISMISS_PET
169 &Spell::EffectReputation, //103 SPELL_EFFECT_REPUTATION
170 &Spell::EffectSummonObject, //104 SPELL_EFFECT_SUMMON_OBJECT_SLOT1
171 &Spell::EffectSummonObject, //105 SPELL_EFFECT_SUMMON_OBJECT_SLOT2
172 &Spell::EffectSummonObject, //106 SPELL_EFFECT_SUMMON_OBJECT_SLOT3
173 &Spell::EffectSummonObject, //107 SPELL_EFFECT_SUMMON_OBJECT_SLOT4
174 &Spell::EffectDispelMechanic, //108 SPELL_EFFECT_DISPEL_MECHANIC
175 &Spell::EffectResurrectPet, //109 SPELL_EFFECT_RESURRECT_PET
176 &Spell::EffectDestroyAllTotems, //110 SPELL_EFFECT_DESTROY_ALL_TOTEMS
177 &Spell::EffectDurabilityDamage, //111 SPELL_EFFECT_DURABILITY_DAMAGE
178 &Spell::EffectUnused, //112 SPELL_EFFECT_112
179 &Spell::EffectResurrectNew, //113 SPELL_EFFECT_RESURRECT_NEW
180 &Spell::EffectTaunt, //114 SPELL_EFFECT_ATTACK_ME
181 &Spell::EffectDurabilityDamagePCT, //115 SPELL_EFFECT_DURABILITY_DAMAGE_PCT
182 &Spell::EffectSkinPlayerCorpse, //116 SPELL_EFFECT_SKIN_PLAYER_CORPSE one spell: Remove Insignia, bg usage, required special corpse flags...
183 &Spell::EffectSpiritHeal, //117 SPELL_EFFECT_SPIRIT_HEAL one spell: Spirit Heal
184 &Spell::EffectSkill, //118 SPELL_EFFECT_SKILL professions and more
185 &Spell::EffectUnused, //119 SPELL_EFFECT_APPLY_AREA_AURA_PET
186 &Spell::EffectUnused, //120 SPELL_EFFECT_TELEPORT_GRAVEYARD one spell: Graveyard Teleport Test
187 &Spell::EffectWeaponDmg, //121 SPELL_EFFECT_NORMALIZED_WEAPON_DMG
188 &Spell::EffectUnused, //122 SPELL_EFFECT_122 unused
189 &Spell::EffectSendTaxi, //123 SPELL_EFFECT_SEND_TAXI taxi/flight related (misc value is taxi path id)
190 &Spell::EffectPullTowards, //124 SPELL_EFFECT_PULL_TOWARDS
191 &Spell::EffectModifyThreatPercent, //125 SPELL_EFFECT_MODIFY_THREAT_PERCENT
192 &Spell::EffectStealBeneficialBuff, //126 SPELL_EFFECT_STEAL_BENEFICIAL_BUFF spell steal effect?
193 &Spell::EffectProspecting, //127 SPELL_EFFECT_PROSPECTING Prospecting spell
194 &Spell::EffectUnused, //128 SPELL_EFFECT_APPLY_AREA_AURA_FRIEND
195 &Spell::EffectUnused, //129 SPELL_EFFECT_APPLY_AREA_AURA_ENEMY
196 &Spell::EffectRedirectThreat, //130 SPELL_EFFECT_REDIRECT_THREAT
197 &Spell::EffectPlaySound, //131 SPELL_EFFECT_PLAY_SOUND sound id in misc value (SoundEntries.dbc)
198 &Spell::EffectPlayMusic, //132 SPELL_EFFECT_PLAY_MUSIC sound id in misc value (SoundEntries.dbc)
199 &Spell::EffectUnlearnSpecialization, //133 SPELL_EFFECT_UNLEARN_SPECIALIZATION unlearn profession specialization
200 &Spell::EffectKillCredit, //134 SPELL_EFFECT_KILL_CREDIT misc value is creature entry
201 &Spell::EffectNULL, //135 SPELL_EFFECT_CALL_PET
202 &Spell::EffectHealPct, //136 SPELL_EFFECT_HEAL_PCT
203 &Spell::EffectEnergizePct, //137 SPELL_EFFECT_ENERGIZE_PCT
204 &Spell::EffectLeapBack, //138 SPELL_EFFECT_LEAP_BACK Leap back
205 &Spell::EffectQuestClear, //139 SPELL_EFFECT_CLEAR_QUEST Reset quest status (miscValue - quest ID)
206 &Spell::EffectForceCast, //140 SPELL_EFFECT_FORCE_CAST
207 &Spell::EffectForceCast, //141 SPELL_EFFECT_FORCE_CAST_WITH_VALUE
208 &Spell::EffectTriggerSpell, //142 SPELL_EFFECT_TRIGGER_SPELL_WITH_VALUE
209 &Spell::EffectUnused, //143 SPELL_EFFECT_APPLY_AREA_AURA_OWNER
210 &Spell::EffectKnockBack, //144 SPELL_EFFECT_KNOCK_BACK_DEST
211 &Spell::EffectPullTowardsDest, //145 SPELL_EFFECT_PULL_TOWARDS_DEST Black Hole Effect
212 &Spell::EffectActivateRune, //146 SPELL_EFFECT_ACTIVATE_RUNE
213 &Spell::EffectQuestFail, //147 SPELL_EFFECT_QUEST_FAIL quest fail
214 &Spell::EffectTriggerMissileSpell, //148 SPELL_EFFECT_TRIGGER_MISSILE_SPELL_WITH_VALUE
215 &Spell::EffectChargeDest, //149 SPELL_EFFECT_CHARGE_DEST
216 &Spell::EffectQuestStart, //150 SPELL_EFFECT_QUEST_START
217 &Spell::EffectTriggerRitualOfSummoning, //151 SPELL_EFFECT_TRIGGER_SPELL_2
218 &Spell::EffectSummonRaFFriend, //152 SPELL_EFFECT_SUMMON_RAF_FRIEND summon Refer-a-Friend
219 &Spell::EffectCreateTamedPet, //153 SPELL_EFFECT_CREATE_TAMED_PET misc value is creature entry
220 &Spell::EffectDiscoverTaxi, //154 SPELL_EFFECT_DISCOVER_TAXI
221 &Spell::EffectTitanGrip, //155 SPELL_EFFECT_TITAN_GRIP Allows you to equip two-handed axes, maces and swords in one hand, but you attack $49152s1% slower than normal.
222 &Spell::EffectEnchantItemPrismatic, //156 SPELL_EFFECT_ENCHANT_ITEM_PRISMATIC
223 &Spell::EffectCreateItem2, //157 SPELL_EFFECT_CREATE_ITEM_2 create item or create item template and replace by some randon spell loot item
224 &Spell::EffectMilling, //158 SPELL_EFFECT_MILLING milling
225 &Spell::EffectRenamePet, //159 SPELL_EFFECT_ALLOW_RENAME_PET allow rename pet once again
226 &Spell::EffectForceCast, //160 SPELL_EFFECT_FORCE_CAST_2
227 &Spell::EffectSpecCount, //161 SPELL_EFFECT_TALENT_SPEC_COUNT second talent spec (learn/revert)
228 &Spell::EffectActivateSpec, //162 SPELL_EFFECT_TALENT_SPEC_SELECT activate primary/secondary spec
229 &Spell::EffectNULL, //163 unused
230 &Spell::EffectRemoveAura, //164 SPELL_EFFECT_REMOVE_AURA
231};
232
234{
235 TC_LOG_DEBUG("spells", "WORLD: Spell Effect DUMMY");
236}
237
239{
240 // NOT USED BY ANY SPELL OR USELESS OR IMPLEMENTED IN DIFFERENT WAY IN TRINITY
241}
242
244{
246 return;
247
248 if (!m_corpseTarget && !unitTarget)
249 return;
250
251 Player* player = nullptr;
252
253 if (m_corpseTarget)
255 else if (unitTarget)
256 player = unitTarget->ToPlayer();
257
258 if (!player || player->IsAlive() || !player->IsInWorld())
259 return;
260
261 if (player->IsResurrectRequested()) // already have one active request
262 return;
263
264 uint32 health = damage;
267 player->SetResurrectRequestData(m_caster, health, mana, 0);
268 SendResurrectRequest(player);
269}
270
272{
274 return;
275
276 if (!unitTarget || !unitTarget->IsAlive())
277 return;
278
281 return;
282
283 if (m_caster == unitTarget) // prevent interrupt message
284 finish();
285
287 data << m_caster->GetGUID();
288 data << unitTarget->GetGUID();
289 data << uint32(m_spellInfo->Id);
290 m_caster->SendMessageToSet(&data, true);
291
293}
294
296{
298 return;
299
300 if (!unitTarget || !unitTarget->IsAlive())
301 return;
302
303 // CalcAbsorbResist already in Player::EnvironmentalDamage
306 else
307 {
308 Unit* unitCaster = GetUnitCasterForEffectHandlers();
310 Unit::CalcAbsorbResist(damageInfo);
311
313 log.damage = damageInfo.GetDamage();
314 log.absorb = damageInfo.GetAbsorb();
315 log.resist = damageInfo.GetResist();
316
317 if (unitCaster)
318 unitCaster->SendSpellNonMeleeDamageLog(&log);
319 }
320}
321
323{
325 return;
326
327 if (unitTarget && unitTarget->IsAlive())
328 {
329 bool apply_direct_bonus = true;
330 Unit* unitCaster = GetUnitCasterForEffectHandlers();
332 {
334 {
335 // Meteor like spells (divided damage to targets)
337 {
338 // divide to all targets
340 damage /= count;
341 }
342
343 break;
344 }
346 {
347 if (!unitCaster)
348 break;
349
350 // Shield Slam
351 if ((m_spellInfo->SpellFamilyFlags[1] & 0x200) && m_spellInfo->GetCategory() == 1209)
352 {
353 uint8 level = unitCaster->GetLevel();
354 uint32 block_value = unitCaster->GetShieldBlockValue(uint32(float(level) * 24.5f), uint32(float(level) * 34.5f));
355 damage += int32(unitCaster->ApplyEffectModifiers(m_spellInfo, effectInfo->EffectIndex, float(block_value)));
356 }
357 // Victory Rush
358 else if (m_spellInfo->SpellFamilyFlags[1] & 0x100)
360 // Shockwave
361 else if (m_spellInfo->Id == 46968)
362 {
364 if (pct > 0)
366 break;
367 }
368 break;
369 }
371 {
372 if (!unitCaster)
373 break;
374
375 // Incinerate Rank 1 & 2
376 if ((m_spellInfo->SpellFamilyFlags[1] & 0x000040) && m_spellInfo->SpellIconID == 2128)
377 {
378 // Incinerate does more dmg (dmg*0.25) if the target have Immolate debuff.
379 // Check aura state for speed but aura state set not only for Immolate spell
381 {
383 damage += damage / 4;
384 }
385 }
386 // Conflagrate - consumes Immolate or Shadowflame
388 {
389 AuraEffect const* aura = nullptr; // found req. aura for damage calculation
390
392 for (Unit::AuraEffectList::const_iterator i = mPeriodic.begin(); i != mPeriodic.end(); ++i)
393 {
394 // for caster applied auras only
395 if ((*i)->GetSpellInfo()->SpellFamilyName != SPELLFAMILY_WARLOCK ||
396 (*i)->GetCasterGUID() != unitCaster->GetGUID())
397 continue;
398
399 // Immolate
400 if ((*i)->GetSpellInfo()->SpellFamilyFlags[0] & 0x4)
401 {
402 aura = *i; // it selected always if exist
403 break;
404 }
405
406 // Shadowflame
407 if ((*i)->GetSpellInfo()->SpellFamilyFlags[2] & 0x00000002)
408 aura = *i; // remember but wait possible Immolate as primary priority
409 }
410
411 // found Immolate or Shadowflame
412 if (aura)
413 {
414 // Calculate damage of Immolate/Shadowflame tick
415 int32 pdamage = aura->GetAmount();
416
417 // And multiply by amount of ticks to get damage potential
418 pdamage *= aura->GetSpellInfo()->GetMaxTicks();
419
421 damage += CalculatePct(pdamage, pct_dir);
422
424 int32 const dotBasePoints = CalculatePct(pdamage, pct_dot);
425
428
429 // Glyph of Conflagrate
430 if (!unitCaster->HasAura(56235))
431 unitTarget->RemoveAurasDueToSpell(aura->GetId(), unitCaster->GetGUID());
432
433 break;
434 }
435 }
436 // Shadow Bite
437 else if (m_spellInfo->SpellFamilyFlags[1] & 0x400000)
438 {
439 if (unitCaster->GetTypeId() == TYPEID_UNIT && unitCaster->IsPet())
440 {
441 if (Player* owner = unitCaster->GetOwner()->ToPlayer())
442 {
443 if (AuraEffect* aurEff = owner->GetAuraEffect(SPELL_AURA_ADD_FLAT_MODIFIER, SPELLFAMILY_WARLOCK, 214, 0))
444 {
445 int32 bp0 = aurEff->GetId() == 54037 ? 4 : 8;
448 unitCaster->CastSpell(nullptr, 54425, args);
449 }
450 }
451 }
452 }
453 break;
454 }
456 {
457 if (!unitCaster)
458 break;
459
460 // Improved Mind Blast (Mind Blast in shadow form bonus)
461 if (unitCaster->GetShapeshiftForm() == FORM_SHADOW && (m_spellInfo->SpellFamilyFlags[0] & 0x00002000))
462 {
464 for (Unit::AuraEffectList::const_iterator i = ImprMindBlast.begin(); i != ImprMindBlast.end(); ++i)
465 {
466 if ((*i)->GetSpellInfo()->SpellFamilyName == SPELLFAMILY_PRIEST &&
467 ((*i)->GetSpellInfo()->SpellIconID == 95))
468 {
469 // Mind Trauma
470 int32 const chance = (*i)->GetSpellInfo()->GetEffect(EFFECT_1).CalcValue(unitCaster);
471 if (roll_chance_i(chance))
472 unitCaster->CastSpell(unitTarget, 48301, true);
473 break;
474 }
475 }
476 }
477 break;
478 }
480 {
481 if (!unitCaster)
482 break;
483
484 // Ferocious Bite
485 if (unitCaster->GetTypeId() == TYPEID_PLAYER && (m_spellInfo->SpellFamilyFlags[0] & 0x000800000) && m_spellInfo->SpellVisual[0] == 6587)
486 {
487 // converts each extra point of energy into ($f1+$AP/410) additional damage
488 float ap = unitCaster->GetTotalAttackPowerValue(BASE_ATTACK);
489 float multiple = ap / 410 + effectInfo->ChainAmplitude;
490 int32 energy = -(unitCaster->ModifyPower(POWER_ENERGY, -30));
491 damage += int32(energy * multiple);
492 damage += int32(CalculatePct(unitCaster->ToPlayer()->GetComboPoints() * ap, 7));
493 }
494 // Wrath
495 else if (m_spellInfo->SpellFamilyFlags[0] & 0x00000001)
496 {
497 // Improved Insect Swarm
498 if (AuraEffect const* aurEff = unitCaster->GetDummyAuraEffect(SPELLFAMILY_DRUID, 1771, 0))
500 AddPct(damage, aurEff->GetAmount());
501 }
502 break;
503 }
505 {
506 if (!unitCaster)
507 break;
508
509 // Envenom
510 if (m_spellInfo->SpellFamilyFlags[1] & 0x00000008)
511 {
512 if (Player* player = unitCaster->ToPlayer())
513 {
514 // consume from stack dozes not more that have combo-points
515 if (uint32 combo = player->GetComboPoints())
516 {
517 // Lookup for Deadly poison (only attacker applied)
518 if (AuraEffect const* aurEff = unitTarget->GetAuraEffect(SPELL_AURA_PERIODIC_DAMAGE, SPELLFAMILY_ROGUE, 0x00010000, 0, 0, unitCaster->GetGUID()))
519 {
520 // count consumed deadly poison doses at target
521 bool needConsume = true;
522 uint32 spellId = aurEff->GetId();
523
524 uint32 doses = aurEff->GetBase()->GetStackAmount();
525 if (doses > combo)
526 doses = combo;
527
528 // Master Poisoner
529 Unit::AuraEffectList const& auraList = player->GetAuraEffectsByType(SPELL_AURA_MOD_AURA_DURATION_BY_DISPEL_NOT_STACK);
530 for (Unit::AuraEffectList::const_iterator iter = auraList.begin(); iter != auraList.end(); ++iter)
531 {
532 if ((*iter)->GetSpellInfo()->SpellFamilyName == SPELLFAMILY_ROGUE && (*iter)->GetSpellInfo()->SpellIconID == 1960)
533 {
534 uint32 chance = (*iter)->GetSpellInfo()->GetEffect(EFFECT_2).CalcValue(unitCaster);
535
536 if (chance && roll_chance_i(chance))
537 needConsume = false;
538
539 break;
540 }
541 }
542
543 if (needConsume)
544 for (uint32 i = 0; i < doses; ++i)
545 unitTarget->RemoveAuraFromStack(spellId, unitCaster->GetGUID());
546
547 damage *= doses;
548 damage += int32(player->GetTotalAttackPowerValue(BASE_ATTACK) * 0.09f * combo);
549 }
550
551 // Eviscerate and Envenom Bonus Damage (item set effect)
552 if (unitCaster->HasAura(37169))
553 damage += combo * 40;
554 }
555 }
556 }
557 // Eviscerate
558 else if (m_spellInfo->SpellFamilyFlags[0] & 0x00020000)
559 {
560 if (Player* player = unitCaster->ToPlayer())
561 {
562 if (uint32 combo = player->GetComboPoints())
563 {
564 float ap = unitCaster->GetTotalAttackPowerValue(BASE_ATTACK);
565 damage += std::lroundf(ap * combo * 0.07f);
566
567 // Eviscerate and Envenom Bonus Damage (item set effect)
568 if (unitCaster->HasAura(37169))
569 damage += combo*40;
570 }
571 }
572 }
573 break;
574 }
576 {
577 if (!unitCaster)
578 break;
579
580 //Gore
581 if (m_spellInfo->SpellIconID == 1578)
582 {
583 if (unitCaster->HasAura(57627)) // Charge 6 sec post-affect
584 damage *= 2;
585 }
586 // Steady Shot
587 else if (m_spellInfo->SpellFamilyFlags[1] & 0x1)
588 {
589 bool found = false;
590 // check dazed affect
592 for (Unit::AuraEffectList::const_iterator iter = decSpeedList.begin(); iter != decSpeedList.end(); ++iter)
593 {
594 if ((*iter)->GetSpellInfo()->SpellIconID == 15 && (*iter)->GetSpellInfo()->Dispel == 0)
595 {
596 found = true;
597 break;
598 }
599 }
600
602 if (found)
604
605 if (Player* caster = unitCaster->ToPlayer())
606 {
607 // Add Ammo and Weapon damage plus RAP * 0.1
608 float dmg_min = 0.f;
609 float dmg_max = 0.f;
610 for (uint8 i = 0; i < MAX_ITEM_PROTO_DAMAGES; ++i)
611 {
612 dmg_min += caster->GetWeaponDamageRange(RANGED_ATTACK, MINDAMAGE, i);
613 dmg_max += caster->GetWeaponDamageRange(RANGED_ATTACK, MAXDAMAGE, i);
614 }
615
616 if (dmg_max == 0.0f && dmg_min > dmg_max)
617 damage += int32(dmg_min);
618 else
619 damage += irand(int32(dmg_min), int32(dmg_max));
620 damage += int32(caster->GetAmmoDPS() * caster->GetAttackTime(RANGED_ATTACK) * 0.001f);
621 }
622 }
623 break;
624 }
626 {
627 if (!unitCaster)
628 break;
629
630 // Hammer of the Righteous
631 if (m_spellInfo->SpellFamilyFlags[1] & 0x00040000)
632 {
633 float minTotal = 0.f;
634 float maxTotal = 0.f;
635
636 float tmpMin, tmpMax;
637 for (uint8 i = 0; i < MAX_ITEM_PROTO_DAMAGES; ++i)
638 {
639 unitCaster->CalculateMinMaxDamage(BASE_ATTACK, false, false, tmpMin, tmpMax, i);
640 minTotal += tmpMin;
641 maxTotal += tmpMax;
642 }
643
644 float average = (minTotal + maxTotal) / 2;
645 // Add main hand dps * effect[2] amount
647 damage += count * int32(average * float(IN_MILLISECONDS)) / unitCaster->GetAttackTime(BASE_ATTACK);
648 break;
649 }
650 // Shield of Righteousness
651 if (m_spellInfo->SpellFamilyFlags[EFFECT_1] & 0x100000)
652 {
653 uint8 level = unitCaster->GetLevel();
654 uint32 block_value = unitCaster->GetShieldBlockValue(uint32(float(level) * 29.5f), uint32(float(level) * 39.5f));
656 break;
657 }
658 break;
659 }
661 {
662 if (!unitCaster)
663 break;
664
665 // Blood Boil - bonus for diseased targets
666 if (m_spellInfo->SpellFamilyFlags[0] & 0x00040000)
667 {
669 {
670 damage += m_damage / 2;
671 damage += int32(unitCaster->GetTotalAttackPowerValue(BASE_ATTACK) * 0.035f);
672 }
673 }
674 break;
675 }
676 }
677
678 if (unitCaster && apply_direct_bonus)
679 {
682 }
683
684 m_damage += damage;
685 }
686}
687
689{
691 return;
692
694 return;
695
696 // pet auras
698 {
699 if (PetAura const* petSpell = sSpellMgr->GetPetAura(m_spellInfo->Id, effectInfo->EffectIndex))
700 {
701 m_caster->ToPlayer()->AddPetAura(petSpell);
702 return;
703 }
704 }
705}
706
708{
711 return;
712
713 uint32 triggered_spell_id = effectInfo->TriggerSpell;
714
718 {
719 Unit* unitCaster = GetUnitCasterForEffectHandlers();
720 // special cases
721 switch (triggered_spell_id)
722 {
723 // Mirror Image
724 case 58832:
725 {
726 if (!unitCaster)
727 break;
728
729 // Glyph of Mirror Image
730 if (unitCaster->HasAura(63093))
731 unitCaster->CastSpell(nullptr, 65047, true); // Mirror Image
732 break;
733 }
734 // Demonic Empowerment -- succubus
735 case 54437:
736 {
740
741 // Cast Lesser Invisibility
742 unitTarget->CastSpell(unitTarget, 7870, true);
743 return;
744 }
745 // Brittle Armor - (need add max stack of 24575 Brittle Armor)
746 case 29284:
747 {
748 // Brittle Armor
749 SpellInfo const* spell = sSpellMgr->GetSpellInfo(24575);
750 if (!spell)
751 return;
752
753 for (uint32 j = 0; j < spell->StackAmount; ++j)
754 m_caster->CastSpell(unitTarget, spell->Id, true);
755 return;
756 }
757 // Mercurial Shield - (need add max stack of 26464 Mercurial Shield)
758 case 29286:
759 {
760 // Mercurial Shield
761 SpellInfo const* spell = sSpellMgr->GetSpellInfo(26464);
762 if (!spell)
763 return;
764
765 for (uint32 j = 0; j < spell->StackAmount; ++j)
766 m_caster->CastSpell(unitTarget, spell->Id, true);
767 return;
768 }
769 }
770 }
771
772 if (triggered_spell_id == 0)
773 {
774 TC_LOG_WARN("spells.effect.nospell", "Spell::EffectTriggerSpell: Spell {} [EffectIndex: {}] does not have triggered spell.", m_spellInfo->Id, uint32(effectInfo->EffectIndex));
775 return;
776 }
777
778 // normal case
779 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(triggered_spell_id);
780 if (!spellInfo)
781 {
782 TC_LOG_ERROR("spells.effect.nospell", "Spell::EffectTriggerSpell spell {} tried to trigger unknown spell {}", m_spellInfo->Id, triggered_spell_id);
783 return;
784 }
785
786 SpellCastTargets targets;
788 {
790 return;
791 targets.SetUnitTarget(unitTarget);
792 }
793 else //if (effectHandleMode == SPELL_EFFECT_HANDLE_LAUNCH)
794 {
796 return;
797
799 targets.SetDst(m_targets);
800
801 if (Unit* target = m_targets.GetUnitTarget())
802 targets.SetUnitTarget(target);
803 else
804 {
805 if (Unit* unit = m_caster->ToUnit())
806 targets.SetUnitTarget(unit);
807 else if (GameObject* go = m_caster->ToGameObject())
808 targets.SetGOTarget(go);
809 }
810 }
811
813 // set basepoints for trigger with value effect
815 for (uint32 i = 0; i < MAX_SPELL_EFFECTS; ++i)
817
818 // original caster guid only for GO cast
819 m_caster->CastSpell(std::move(targets), spellInfo->Id, args);
820}
821
823{
826 return;
827
828 uint32 triggered_spell_id = effectInfo->TriggerSpell;
829 if (triggered_spell_id == 0)
830 {
831 TC_LOG_WARN("spells.effect.nospell", "Spell::EffectTriggerMissileSpell: Spell {} [EffectIndex: {}] does not have triggered spell.", m_spellInfo->Id, uint32(effectInfo->EffectIndex));
832 return;
833 }
834
835 // normal case
836 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(triggered_spell_id);
837 if (!spellInfo)
838 {
839 TC_LOG_ERROR("spells.effect.nospell", "Spell::EffectTriggerMissileSpell spell {} tried to trigger unknown spell {}.", m_spellInfo->Id, triggered_spell_id);
840 return;
841 }
842
843 SpellCastTargets targets;
845 {
847 return;
848 targets.SetUnitTarget(unitTarget);
849 }
850 else //if (effectHandleMode == SPELL_EFFECT_HANDLE_HIT)
851 {
853 return;
854
856 targets.SetDst(m_targets);
857
858 if (Unit* unit = m_caster->ToUnit())
859 targets.SetUnitTarget(unit);
860 else if (GameObject* go = m_caster->ToGameObject())
861 targets.SetGOTarget(go);
862 }
863
865 // set basepoints for trigger with value effect
867 for (uint32 i = 0; i < MAX_SPELL_EFFECTS; ++i)
869
870 // original caster guid only for GO cast
871 m_caster->CastSpell(std::move(targets), spellInfo->Id, args);
872}
873
875{
877 return;
878
879 if (!unitTarget)
880 return;
881
882 uint32 triggered_spell_id = effectInfo->TriggerSpell;
883 if (triggered_spell_id == 0)
884 {
885 TC_LOG_WARN("spells.effect.nospell", "Spell::EffectForceCast: Spell {} [EffectIndex: {}] does not have triggered spell.", m_spellInfo->Id, uint32(effectInfo->EffectIndex));
886 return;
887 }
888
889 // normal case
890 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(triggered_spell_id);
891
892 if (!spellInfo)
893 {
894 TC_LOG_ERROR("spells.effect.nospell", "Spell::EffectForceCast of spell {}: triggering unknown spell id {}.", m_spellInfo->Id, triggered_spell_id);
895 return;
896 }
897
899 {
900 switch (m_spellInfo->Id)
901 {
902 case 52588: // Skeletal Gryphon Escape
903 case 48598: // Ride Flamebringer Cue
905 break;
906 case 52463: // Hide In Mine Car
907 case 52349: // Overtake
908 {
911 unitTarget->CastSpell(unitTarget, spellInfo->Id, args);
912 return;
913 }
914 }
915 }
916
917 switch (spellInfo->Id)
918 {
919 case 72298: // Malleable Goo Summon
921 return;
922 }
923
926 for (uint32 i = 0; i < MAX_SPELL_EFFECTS; ++i)
928
929 unitTarget->CastSpell(m_caster, spellInfo->Id, args);
930}
931
933{
935 return;
936
937 uint32 triggered_spell_id = effectInfo->TriggerSpell;
938 if (triggered_spell_id == 0)
939 {
940 TC_LOG_WARN("spells.effect.nospell", "Spell::EffectTriggerRitualOfSummoning: Spell {} [EffectIndex: {}] does not have triggered spell.", m_spellInfo->Id, uint32(effectInfo->EffectIndex));
941 return;
942 }
943
944 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(triggered_spell_id);
945
946 if (!spellInfo)
947 {
948 TC_LOG_ERROR("spells.effect.nospell", "EffectTriggerRitualOfSummoning of spell {}: triggering unknown spell id {}.", m_spellInfo->Id, triggered_spell_id);
949 return;
950 }
951
952 finish();
953
954 m_caster->CastSpell(nullptr, spellInfo->Id, false);
955}
956
957void Spell::CalculateJumpSpeeds(SpellEffectInfo const& spellEffectInfo, float dist, float& speedXY, float& speedZ)
958{
959 Unit* unitCaster = GetUnitCasterForEffectHandlers();
960 ASSERT(unitCaster);
961 float runSpeed = unitCaster->IsControlledByPlayer() ? playerBaseMoveSpeed[MOVE_RUN] : baseMoveSpeed[MOVE_RUN];
962 if (Creature* creature = unitCaster->ToCreature())
963 runSpeed *= creature->GetCreatureTemplate()->speed_run;
964
965 float multiplier = spellEffectInfo.Amplitude;
966 if (multiplier <= 0.0f)
967 multiplier = 1.0f;
968
969 speedXY = std::min(runSpeed * 3.0f * multiplier, std::max(28.0f, unitCaster->GetSpeed(MOVE_RUN) * 4.0f));
970
971 float duration = dist / speedXY;
972 float durationSqr = duration * duration;
973 float minHeight = spellEffectInfo.MiscValue ? spellEffectInfo.MiscValue / 10.0f : 0.5f; // Lower bound is blizzlike
974 float maxHeight = spellEffectInfo.MiscValueB ? spellEffectInfo.MiscValueB / 10.0f : 1000.0f; // Upper bound is unknown
975 float height;
976 if (durationSqr < minHeight * 8 / Movement::gravity)
977 height = minHeight;
978 else if (durationSqr > maxHeight * 8 / Movement::gravity)
979 height = maxHeight;
980 else
981 height = Movement::gravity * durationSqr / 8;
982
983 speedZ = std::sqrt(2 * Movement::gravity * height);
984}
985
987{
989 return;
990
991 Unit* unitCaster = GetUnitCasterForEffectHandlers();
992 if (!unitCaster)
993 return;
994
995 if (unitCaster->IsInFlight())
996 return;
997
998 if (!unitTarget)
999 return;
1000
1001 float speedXY, speedZ;
1002 CalculateJumpSpeeds(*effectInfo, unitCaster->GetExactDist2d(unitTarget), speedXY, speedZ);
1003 unitCaster->GetMotionMaster()->MoveJump(*unitTarget, speedXY, speedZ, EVENT_JUMP, false);
1004}
1005
1007{
1009 return;
1010
1011 Unit* unitCaster = GetUnitCasterForEffectHandlers();
1012 if (!unitCaster)
1013 return;
1014
1015 if (unitCaster->IsInFlight())
1016 return;
1017
1018 if (!m_targets.HasDst())
1019 return;
1020
1021 float speedXY, speedZ;
1022 CalculateJumpSpeeds(*effectInfo, unitCaster->GetExactDist2d(destTarget), speedXY, speedZ);
1023 unitCaster->GetMotionMaster()->MoveJump(*destTarget, speedXY, speedZ, EVENT_JUMP, !m_targets.GetObjectTargetGUID().IsEmpty());
1024}
1025
1027{
1029 return;
1030
1031 if (!unitTarget || unitTarget->IsInFlight())
1032 return;
1033
1034 // If not exist data for dest location - return
1035 if (!m_targets.HasDst())
1036 {
1037 TC_LOG_ERROR("spells", "Spell::EffectTeleportUnits - does not have a destination for spellId {}.", m_spellInfo->Id);
1038 return;
1039 }
1040
1041 // Init dest coordinates
1042 WorldLocation targetDest(*destTarget);
1043 if (targetDest.GetMapId() == MAPID_INVALID)
1044 targetDest.m_mapId = unitTarget->GetMapId();
1045
1046 if (!targetDest.GetOrientation() && m_targets.GetUnitTarget())
1048
1049 if (targetDest.GetMapId() == unitTarget->GetMapId())
1051 else if (unitTarget->GetTypeId() == TYPEID_PLAYER)
1053 else
1054 {
1055 TC_LOG_ERROR("spells", "Spell::EffectTeleportUnits - spellId {} attempted to teleport creature to a different map.", m_spellInfo->Id);
1056 return;
1057 }
1058}
1059
1061{
1063 return;
1064
1065 if (!_spellAura || !unitTarget)
1066 return;
1067
1068 // register target/effect on aura
1070 if (!aurApp)
1072 else
1073 aurApp->UpdateApplyEffectMask(aurApp->GetEffectsToApply() | 1 << effectInfo->EffectIndex, false);
1074}
1075
1077{
1079 return;
1080
1082 return;
1083
1084 Player* player = unitTarget->ToPlayer();
1085 uint32 spellToUnlearn = effectInfo->TriggerSpell;
1086
1087 player->RemoveSpell(spellToUnlearn);
1088
1089 TC_LOG_DEBUG("spells", "Spell: Player {} has unlearned spell {} from Npc {}", player->GetGUID().ToString(), spellToUnlearn, m_caster->GetGUID().ToString());
1090}
1091
1093{
1095 return;
1096
1098 return;
1099
1100 Powers powerType = Powers(effectInfo->MiscValue);
1101 if (!unitTarget || !unitTarget->IsAlive() || (unitTarget->GetPowerType() != powerType && powerType != POWER_HAPPINESS) || damage < 0)
1102 return;
1103
1104 Unit* unitCaster = GetUnitCasterForEffectHandlers();
1105 // add spell damage bonus
1106 if (unitCaster)
1107 {
1110 }
1111
1112 // resilience reduce mana draining effect at spell crit damage reduction (added in 2.4)
1113 int32 power = damage;
1114 if (powerType == POWER_MANA)
1115 power -= unitTarget->GetSpellCritDamageReduction(power);
1116
1117 int32 newDamage = -(unitTarget->ModifyPower(powerType, -int32(power)));
1118
1119 // Don't restore from self drain
1120 float gainMultiplier = 0.f;
1121 if (unitCaster && unitCaster != unitTarget)
1122 {
1123 gainMultiplier = effectInfo->CalcValueMultiplier(unitCaster, this);
1124 int32 const gain = int32(newDamage * gainMultiplier);
1125
1126 unitCaster->EnergizeBySpell(unitCaster, m_spellInfo, gain, powerType);
1127 }
1128 ExecuteLogEffectTakeTargetPower(effectInfo->EffectIndex, unitTarget, powerType, newDamage, gainMultiplier);
1129}
1130
1132{
1133 // we do not handle a flag dropping or clicking on flag in battleground by sendevent system
1136 return;
1137
1138 WorldObject* target = nullptr;
1139
1140 // call events for object target if present
1142 {
1143 if (unitTarget)
1144 target = unitTarget;
1145 else if (gameObjTarget)
1146 target = gameObjTarget;
1147 else if (m_corpseTarget)
1148 target = m_corpseTarget;
1149 }
1150 else // if (effectHandleMode == SPELL_EFFECT_HANDLE_HIT)
1151 {
1152 // let's prevent executing effect handler twice in case when spell effect is capable of targeting an object
1153 // this check was requested by scripters, but it has some downsides:
1154 // now it's impossible to script (using sEventScripts) a cast which misses all targets
1155 // or to have an ability to script the moment spell hits dest (in a case when there are object targets present)
1157 return;
1158 // some spells have no target entries in dbc and they use focus target
1159 if (focusObject)
1160 target = focusObject;
1162 }
1163
1164 TC_LOG_DEBUG("spells", "Spell ScriptStart {} for spellid {} in EffectSendEvent ", effectInfo->MiscValue, m_spellInfo->Id);
1165
1166 if (ZoneScript* zoneScript = m_caster->GetZoneScript())
1167 zoneScript->ProcessEvent(target, effectInfo->MiscValue);
1168 else if (InstanceScript* instanceScript = m_caster->GetInstanceScript()) // needed in case Player is the caster
1169 instanceScript->ProcessEvent(target, effectInfo->MiscValue);
1170
1172}
1173
1175{
1177 return;
1178
1180 return;
1181
1182 Powers powerType = Powers(effectInfo->MiscValue);
1183 if (!unitTarget || !unitTarget->IsAlive() || unitTarget->GetPowerType() != powerType || damage < 0)
1184 return;
1185
1186 Unit* unitCaster = GetUnitCasterForEffectHandlers();
1187
1188 // burn x% of target's mana, up to maximum of 2x% of caster's mana (Mana Burn)
1190 if (unitCaster && m_spellInfo->Id == 8129)
1191 {
1192 int32 maxDamage = int32(CalculatePct(unitCaster->GetMaxPower(powerType), damage * 2));
1194 damage = std::min(damage, maxDamage);
1195 }
1196
1197 int32 power = damage;
1198 // resilience reduce mana draining effect at spell crit damage reduction (added in 2.4)
1199 if (powerType == POWER_MANA)
1200 power -= unitTarget->GetSpellCritDamageReduction(power);
1201
1202 int32 newDamage = -(unitTarget->ModifyPower(powerType, -power));
1203
1204 // NO - Not a typo - EffectPowerBurn uses effect value multiplier - not effect damage multiplier
1205 float dmgMultiplier = effectInfo->CalcValueMultiplier(unitCaster, this);
1206
1207 // add log data before multiplication (need power amount, not damage)
1209
1210 newDamage = int32(newDamage * dmgMultiplier);
1211
1212 m_damage += newDamage;
1213}
1214
1216{
1218 return;
1219
1220 if (!unitTarget || !unitTarget->IsAlive() || damage < 0)
1221 return;
1222
1223 Unit* unitCaster = GetUnitCasterForEffectHandlers();
1224
1225 // Skip if m_originalCaster not available
1226 if (!unitCaster)
1227 return;
1228
1229 int32 addhealth = damage;
1230
1231 // Vessel of the Naaru (Vial of the Sunwell trinket)
1233 if (m_spellInfo->Id == 45064)
1234 {
1235 // Amount of heal - depends from stacked Holy Energy
1236 int32 damageAmount = 0;
1237 if (AuraEffect const* aurEff = unitCaster->GetAuraEffect(45062, 0))
1238 {
1239 damageAmount += aurEff->GetAmount();
1240 unitCaster->RemoveAurasDueToSpell(45062);
1241 }
1242
1243 addhealth += damageAmount;
1244 }
1245 // Swiftmend - consumes Regrowth or Rejuvenation
1247 {
1249 // find most short by duration
1250 AuraEffect* targetAura = nullptr;
1251 for (Unit::AuraEffectList::const_iterator i = RejorRegr.begin(); i != RejorRegr.end(); ++i)
1252 {
1253 if ((*i)->GetSpellInfo()->SpellFamilyName == SPELLFAMILY_DRUID
1254 && (*i)->GetSpellInfo()->SpellFamilyFlags[0] & 0x50)
1255 {
1256 if (!targetAura || (*i)->GetBase()->GetDuration() < targetAura->GetBase()->GetDuration())
1257 targetAura = *i;
1258 }
1259 }
1260
1261 if (!targetAura)
1262 {
1263 TC_LOG_ERROR("spells", "Target ({}) has the aurastate AURA_STATE_SWIFTMEND, but no matching aura.", unitTarget->GetGUID().ToString());
1264 return;
1265 }
1266
1267 int32 tickheal = targetAura->GetAmount();
1268 unitTarget->SpellHealingBonusTaken(unitCaster, targetAura->GetSpellInfo(), tickheal, DOT);
1269
1270 int32 tickcount = 0;
1271 // Rejuvenation
1272 if (targetAura->GetSpellInfo()->SpellFamilyFlags[0] & 0x10)
1273 tickcount = 4;
1274 // Regrowth
1275 else // if (targetAura->GetSpellInfo()->SpellFamilyFlags[0] & 0x40)
1276 tickcount = 6;
1277
1278 addhealth += tickheal * tickcount;
1279
1280 // Glyph of Swiftmend
1281 if (!unitCaster->HasAura(54824))
1282 unitTarget->RemoveAura(targetAura->GetId(), targetAura->GetCasterGUID());
1283 }
1284 // Death Pact - return pct of max health to caster
1286 addhealth = unitCaster->SpellHealingBonusDone(unitTarget, m_spellInfo, int32(unitCaster->CountPctFromMaxHealth(damage)), HEAL, *effectInfo, { });
1287 else
1288 addhealth = unitCaster->SpellHealingBonusDone(unitTarget, m_spellInfo, addhealth, HEAL, *effectInfo, { });
1289
1290 addhealth = unitTarget->SpellHealingBonusTaken(unitCaster, m_spellInfo, addhealth, HEAL);
1291
1292 // Remove Grievious bite if fully healed
1293 if (unitTarget->HasAura(48920) && (unitTarget->GetHealth() + addhealth >= unitTarget->GetMaxHealth()))
1294 unitTarget->RemoveAura(48920);
1295
1296 m_healing += addhealth;
1297}
1298
1300{
1302 return;
1303
1304 if (!unitTarget || !unitTarget->IsAlive() || damage < 0)
1305 return;
1306
1308 if (Unit* unitCaster = GetUnitCasterForEffectHandlers())
1309 {
1310 heal = unitCaster->SpellHealingBonusDone(unitTarget, m_spellInfo, heal, HEAL, *effectInfo, { });
1311 heal = unitTarget->SpellHealingBonusTaken(unitCaster, m_spellInfo, heal, HEAL);
1312 }
1313
1314 m_healing += heal;
1315}
1316
1318{
1320 return;
1321
1322 if (!unitTarget || !unitTarget->IsAlive() || damage < 0)
1323 return;
1324
1325 uint32 heal = damage;
1326 if (Unit* unitCaster = GetUnitCasterForEffectHandlers())
1327 {
1328 heal = unitCaster->SpellHealingBonusDone(unitTarget, m_spellInfo, heal, HEAL, *effectInfo, { });
1329 heal = unitTarget->SpellHealingBonusTaken(unitCaster, m_spellInfo, heal, HEAL);
1330 }
1331
1332 m_healing += heal;
1333}
1334
1336{
1338 return;
1339
1340 if (!unitTarget || !unitTarget->IsAlive() || damage < 0)
1341 return;
1342
1343 Unit* unitCaster = GetUnitCasterForEffectHandlers();
1344 if (unitCaster)
1345 {
1348 }
1349
1350 TC_LOG_DEBUG("spells", "HealthLeech :{}", damage);
1351
1352 float healMultiplier = effectInfo->CalcValueMultiplier(unitCaster, this);
1353
1354 m_damage += damage;
1355
1357 Unit::CalcAbsorbResist(damageInfo);
1358 uint32 const absorb = damageInfo.GetAbsorb();
1359 damage -= absorb;
1360
1361 // get max possible damage, don't count overkill for heal
1362 uint32 healthGain = uint32(-unitTarget->GetHealthGain(-damage) * healMultiplier);
1363
1364 if (unitCaster && unitCaster->IsAlive())
1365 {
1366 healthGain = unitCaster->SpellHealingBonusDone(unitCaster, m_spellInfo, healthGain, HEAL, *effectInfo, { });
1367 healthGain = unitCaster->SpellHealingBonusTaken(unitCaster, m_spellInfo, healthGain, HEAL);
1368
1369 HealInfo healInfo(unitCaster, unitCaster, healthGain, m_spellInfo, m_spellSchoolMask);
1370 unitCaster->HealBySpell(healInfo);
1371 }
1372}
1373
1375{
1377 return;
1378
1379 Player* player = unitTarget->ToPlayer();
1380
1381 uint32 newitemid = itemId;
1382 ItemTemplate const* pProto = sObjectMgr->GetItemTemplate(newitemid);
1383 if (!pProto)
1384 {
1385 player->SendEquipError(EQUIP_ERR_ITEM_NOT_FOUND, nullptr, nullptr);
1386 return;
1387 }
1388
1389 // bg reward have some special in code work
1390 uint32 bgType = 0;
1391 switch (m_spellInfo->Id)
1392 {
1395 bgType = BATTLEGROUND_AV;
1396 break;
1399 bgType = BATTLEGROUND_WS;
1400 break;
1403 bgType = BATTLEGROUND_AB;
1404 break;
1405 default:
1406 break;
1407 }
1408
1409 uint32 num_to_add = damage;
1410
1411 if (num_to_add < 1)
1412 num_to_add = 1;
1413 if (num_to_add > pProto->GetMaxStackSize())
1414 num_to_add = pProto->GetMaxStackSize();
1415
1416 /* == gem perfection handling == */
1417
1418 // the chance of getting a perfect result
1419 float perfectCreateChance = 0.0f;
1420 // the resulting perfect item if successful
1421 uint32 perfectItemType = itemId;
1422 // get perfection capability and chance
1423 if (CanCreatePerfectItem(player, m_spellInfo->Id, perfectCreateChance, perfectItemType))
1424 if (roll_chance_f(perfectCreateChance)) // if the roll succeeds...
1425 newitemid = perfectItemType; // the perfect item replaces the regular one
1426
1427 /* == gem perfection handling over == */
1428
1429 /* == profession specialization handling == */
1430
1431 // init items_count to 1, since 1 item will be created regardless of specialization
1432 int items_count=1;
1433 // the chance to create additional items
1434 float additionalCreateChance=0.0f;
1435 // the maximum number of created additional items
1436 uint8 additionalMaxNum=0;
1437 // get the chance and maximum number for creating extra items
1438 if (CanCreateExtraItems(player, m_spellInfo->Id, additionalCreateChance, additionalMaxNum))
1439 // roll with this chance till we roll not to create or we create the max num
1440 while (roll_chance_f(additionalCreateChance) && items_count <= additionalMaxNum)
1441 ++items_count;
1442
1443 // really will be created more items
1444 num_to_add *= items_count;
1445
1446 /* == profession specialization handling over == */
1447
1448 // can the player store the new item?
1449 ItemPosCountVec dest;
1450 uint32 no_space = 0;
1451 InventoryResult msg = player->CanStoreNewItem(NULL_BAG, NULL_SLOT, dest, newitemid, num_to_add, &no_space);
1452 if (msg != EQUIP_ERR_OK)
1453 {
1454 // convert to possible store amount
1455 if (msg == EQUIP_ERR_INV_FULL || msg == EQUIP_ERR_ITEM_MAX_COUNT)
1456 num_to_add -= no_space;
1457 else
1458 {
1459 // if not created by another reason from full inventory or unique items amount limitation
1460 player->SendEquipError(msg, nullptr, nullptr, newitemid);
1461 return;
1462 }
1463 }
1464
1465 if (num_to_add)
1466 {
1467 // create the new item and store it
1468 Item* pItem = player->StoreNewItem(dest, newitemid, true, GenerateItemRandomPropertyId(newitemid));
1469
1470 // was it successful? return error if not
1471 if (!pItem)
1472 {
1473 player->SendEquipError(EQUIP_ERR_ITEM_NOT_FOUND, nullptr, nullptr);
1474 return;
1475 }
1476
1477 // set the "Crafted by ..." property of the item
1478 if (pItem->GetTemplate()->HasSignature())
1479 pItem->SetCreator(player->GetGUID());
1480
1481 // send info to the client
1482 player->SendNewItem(pItem, num_to_add, true, bgType == 0);
1483
1484 // we succeeded in creating at least one item, so a levelup is possible
1485 if (bgType == 0)
1487 }
1488
1489/*
1490 // for battleground marks send by mail if not add all expected
1491 if (no_space > 0 && bgType)
1492 {
1493 if (Battleground* bg = sBattlegroundMgr->GetBattlegroundTemplate(BattlegroundTypeId(bgType)))
1494 bg->SendRewardMarkByMail(player, newitemid, no_space);
1495 }
1496*/
1497}
1498
1507
1509{
1511 return;
1512
1514 return;
1515
1516 Player* player = unitTarget->ToPlayer();
1517
1518 // Pick a random item from spell_loot_template
1520 {
1521 player->AutoStoreLoot(m_spellInfo->Id, LootTemplates_Spell, false, true);
1523 }
1524 else // If there's no random loot entries for this spell, pick the item associated with this spell
1525 {
1526 uint32 item_id = effectInfo->ItemType;
1527
1528 if (item_id)
1529 DoCreateItem(item_id);
1530 }
1531
1533}
1534
1536{
1538 return;
1539
1541 return;
1542 Player* player = unitTarget->ToPlayer();
1543
1544 // create some random items
1547}
1548
1550{
1552 return;
1553
1554 Unit* unitCaster = GetUnitCasterForEffectHandlers();
1555 if (!unitCaster)
1556 return;
1557
1558 // Caster not in world, might be spell triggered from aura removal
1559 if (!unitCaster->IsInWorld())
1560 return;
1561
1562 // only handle at last effect
1563 for (size_t i = effectInfo->EffectIndex + 1; i < m_spellInfo->GetEffects().size(); ++i)
1565 return;
1566
1568
1569 float radius = 0.0f;
1570 for (size_t i = 0; i <= effectInfo->EffectIndex; ++i)
1571 {
1572 SpellEffectInfo const& spellEffectInfo = m_spellInfo->GetEffect(SpellEffIndex(i));
1573 if (spellEffectInfo.IsEffect(SPELL_EFFECT_PERSISTENT_AREA_AURA))
1574 radius = std::max(radius, spellEffectInfo.CalcRadius(unitCaster));
1575 }
1576
1577 DynamicObject* dynObj = new DynamicObject(false);
1579 {
1580 delete dynObj;
1581 return;
1582 }
1583
1584 AuraCreateInfo createInfo(m_spellInfo, MAX_EFFECT_MASK, dynObj);
1585 createInfo
1586 .SetCaster(unitCaster)
1588
1589 if (Aura* aura = Aura::TryCreate(createInfo))
1590 {
1591 _dynObjAura = aura->ToDynObjAura();
1593 }
1594 else
1595 return;
1596
1598 for (size_t i = 0; i < m_spellInfo->GetEffects().size(); ++i)
1601}
1602
1604{
1606 return;
1607
1608 Unit* unitCaster = GetUnitCasterForEffectHandlers();
1609 if (!unitCaster || !unitTarget)
1610 return;
1611
1612 if (!unitTarget->IsAlive())
1613 return;
1614
1616 return;
1617
1621 return;
1622
1623 if (unitTarget->GetMaxPower(power) == 0)
1624 return;
1625
1626 // Some level depends spells
1628 int32 level_multiplier = 0;
1629 int32 level_diff = 0;
1630 switch (m_spellInfo->Id)
1631 {
1632 case 9512: // Restore Energy
1633 level_diff = unitCaster->GetLevel() - 40;
1634 level_multiplier = 2;
1635 break;
1636 case 24571: // Blood Fury
1637 level_diff = unitCaster->GetLevel() - 60;
1638 level_multiplier = 10;
1639 break;
1640 case 24532: // Burst of Energy
1641 level_diff = unitCaster->GetLevel() - 60;
1642 level_multiplier = 4;
1643 break;
1644 case 31930: // Judgements of the Wise
1645 case 63375: // Improved Stormstrike
1646 case 68082: // Glyph of Seal of Command
1648 break;
1649 case 48542: // Revitalize
1651 break;
1652 case 67490: // Runic Mana Injector (mana gain increased by 25% for engineers - 3.2.0 patch change)
1653 {
1654 if (Player* player = unitCaster->ToPlayer())
1655 if (player->HasSkill(SKILL_ENGINEERING))
1656 AddPct(damage, 25);
1657 break;
1658 }
1659 case 71132: // Glyph of Shadow Word: Pain
1660 damage = int32(CalculatePct(unitTarget->GetCreateMana(), 1)); // set 1 as value, missing in dbc
1661 break;
1662 default:
1663 break;
1664 }
1665
1666 if (level_diff > 0)
1667 damage -= level_multiplier * level_diff;
1668
1669 if (damage < 0)
1670 return;
1671
1672 unitCaster->EnergizeBySpell(unitTarget, m_spellInfo, damage, power);
1673}
1674
1676{
1678 return;
1679
1680 Unit* unitCaster = GetUnitCasterForEffectHandlers();
1681 if (!unitCaster || !unitTarget)
1682 return;
1683
1684 if (!unitTarget->IsAlive())
1685 return;
1686
1688 return;
1689
1691
1693 return;
1694
1695 uint32 maxPower = unitTarget->GetMaxPower(power);
1696 if (!maxPower)
1697 return;
1698
1699 uint32 const gain = CalculatePct(maxPower, damage);
1700 unitCaster->EnergizeBySpell(unitTarget, m_spellInfo, gain, power);
1701}
1702
1704{
1705 Player* player = m_caster->ToPlayer();
1706 if (!player)
1707 return;
1708
1709 if (gameObjTarget)
1710 {
1711 // Players shouldn't be able to loot gameobjects that are currently despawned
1712 if (!gameObjTarget->isSpawned() && !player->IsGameMaster())
1713 {
1714 TC_LOG_ERROR("entities.player.cheat", "Possible hacking attempt: Player {} {} tried to loot a gameobject {} which is on respawn timer without being in GM mode!",
1715 player->GetName(), player->GetGUID().ToString(), gameObjTarget->GetGUID().ToString());
1716 return;
1717 }
1718 // special case, already has GossipHello inside so return and avoid calling twice
1720 {
1721 gameObjTarget->Use(player);
1722 return;
1723 }
1724
1725 player->PlayerTalkClass->ClearMenus();
1726 if (gameObjTarget->AI()->OnGossipHello(player))
1727 return;
1728
1729 switch (gameObjTarget->GetGoType())
1730 {
1733 gameObjTarget->UseDoorOrButton(0, false, player);
1734 return;
1735
1739 return;
1740
1742 // triggering linked GO
1744 gameObjTarget->TriggeringLinkedGameObject(trapEntry, player);
1745 return;
1746
1750 {
1751 TC_LOG_DEBUG("spells", "Chest ScriptStart id {} for GO {}", gameObjTarget->GetGOInfo()->chest.eventId, gameObjTarget->GetSpawnId());
1753 }
1754
1755 // triggering linked GO
1756 if (uint32 trapEntry = gameObjTarget->GetGOInfo()->chest.linkedTrapId)
1757 gameObjTarget->TriggeringLinkedGameObject(trapEntry, player);
1758
1759 // Don't return, let loots been taken
1760 break;
1761 default:
1762 break;
1763 }
1764 }
1765
1766 // Send loot
1767 player->SendLoot(guid, loottype);
1768}
1769
1771{
1773 return;
1774
1776 {
1777 TC_LOG_DEBUG("spells", "WORLD: Open Lock - No Player Caster!");
1778 return;
1779 }
1780
1781 Player* player = m_caster->ToPlayer();
1782
1783 uint32 lockId = 0;
1784 ObjectGuid guid;
1785
1786 // Get lockId
1787 if (gameObjTarget)
1788 {
1789 GameObjectTemplate const* goInfo = gameObjTarget->GetGOInfo();
1790
1791 if (goInfo->CannotBeUsedUnderImmunity() && player->HasUnitFlag(UNIT_FLAG_IMMUNE))
1792 return;
1793
1794 // Arathi Basin banner opening. /// @todo Verify correctness of this check
1795 if ((goInfo->type == GAMEOBJECT_TYPE_BUTTON && goInfo->button.noDamageImmune) ||
1796 (goInfo->type == GAMEOBJECT_TYPE_GOOBER && goInfo->goober.losOK))
1797 {
1798 //CanUseBattlegroundObject() already called in CheckCast()
1799 // in battleground check
1800 if (Battleground* bg = player->GetBattleground())
1801 {
1802 bg->EventPlayerClickedOnFlag(player, gameObjTarget);
1803 return;
1804 }
1805 }
1806 else if (goInfo->type == GAMEOBJECT_TYPE_FLAGSTAND)
1807 {
1808 //CanUseBattlegroundObject() already called in CheckCast()
1809 // in battleground check
1810 if (Battleground* bg = player->GetBattleground())
1811 {
1812 if (bg->GetTypeID(true) == BATTLEGROUND_EY)
1813 bg->EventPlayerClickedOnFlag(player, gameObjTarget);
1814 return;
1815 }
1816 }
1818 {
1820 return;
1821 }
1823 // handle outdoor pvp object opening, return true if go was registered for handling
1824 // these objects must have been spawned by outdoorpvp!
1825 else if (gameObjTarget->GetGOInfo()->type == GAMEOBJECT_TYPE_GOOBER && sOutdoorPvPMgr->HandleOpenGo(player, gameObjTarget))
1826 return;
1827 lockId = goInfo->GetLockId();
1828 guid = gameObjTarget->GetGUID();
1829 }
1830 else if (itemTarget)
1831 {
1832 lockId = itemTarget->GetTemplate()->GetLockID();
1833 guid = itemTarget->GetGUID();
1834 }
1835 else
1836 {
1837 TC_LOG_DEBUG("spells", "WORLD: Open Lock - No GameObject/Item Target!");
1838 return;
1839 }
1840
1841 SkillType skillId = SKILL_NONE;
1842 int32 reqSkillValue = 0;
1843 int32 skillValue;
1844
1845 SpellCastResult res = CanOpenLock(*effectInfo, lockId, skillId, reqSkillValue, skillValue);
1846 if (res != SPELL_CAST_OK)
1847 {
1848 SendCastResult(res);
1849 return;
1850 }
1851
1852 if (gameObjTarget)
1853 SendLoot(guid, LOOT_SKINNING);
1854 else if (itemTarget)
1855 {
1858 }
1859
1860 // not allow use skill grow at item base open
1861 if (!m_CastItem && skillId != SKILL_NONE)
1862 {
1863 // update skill if really known
1864 if (uint32 pureSkillValue = player->GetPureSkillValue(skillId))
1865 {
1866 if (gameObjTarget)
1867 {
1868 // Allow one skill-up until respawned
1869 if (!gameObjTarget->IsInSkillupList(player->GetGUID()))
1870 {
1871 player->UpdateGatherSkill(skillId, pureSkillValue, reqSkillValue);
1873 }
1874 }
1875 else if (itemTarget)
1876 {
1877 // Do one skill-up
1878 player->UpdateGatherSkill(skillId, pureSkillValue, reqSkillValue);
1879 }
1880 }
1881 }
1883}
1884
1886{
1888 return;
1889
1891 return;
1892
1893 Player* player = m_caster->ToPlayer();
1894
1895 // applied only to using item
1896 if (!m_CastItem)
1897 return;
1898
1899 // ... only to item in own inventory/bank/equip_slot
1900 if (m_CastItem->GetOwnerGUID() != player->GetGUID())
1901 return;
1902
1903 uint32 newitemid = effectInfo->ItemType;
1904 if (!newitemid)
1905 return;
1906
1907 uint16 pos = m_CastItem->GetPos();
1908
1909 Item* pNewItem = Item::CreateItem(newitemid, 1, player);
1910 if (!pNewItem)
1911 return;
1912
1916
1918 {
1920 player->DurabilityLoss(pNewItem, lossPercent);
1921 }
1922
1923 if (player->IsInventoryPos(pos))
1924 {
1925 ItemPosCountVec dest;
1926 InventoryResult msg = player->CanStoreItem(m_CastItem->GetBagSlot(), m_CastItem->GetSlot(), dest, pNewItem, true);
1927 if (msg == EQUIP_ERR_OK)
1928 {
1929 player->DestroyItem(m_CastItem->GetBagSlot(), m_CastItem->GetSlot(), true);
1930
1931 // prevent crash at access and unexpected charges counting with item update queue corrupt
1933 m_targets.SetItemTarget(nullptr);
1934
1935 m_CastItem = nullptr;
1937 m_castItemEntry = 0;
1938
1939 player->StoreItem(dest, pNewItem, true);
1940 player->SendNewItem(pNewItem, 1, true, false);
1941 player->ItemAddedQuestCheck(newitemid, 1);
1942 return;
1943 }
1944 }
1945 else if (player->IsBankPos(pos))
1946 {
1947 ItemPosCountVec dest;
1948 if (player->CanBankItem(m_CastItem->GetBagSlot(), m_CastItem->GetSlot(), dest, pNewItem, true) == EQUIP_ERR_OK)
1949 {
1950 player->DestroyItem(m_CastItem->GetBagSlot(), m_CastItem->GetSlot(), true);
1951
1952 // prevent crash at access and unexpected charges counting with item update queue corrupt
1954 m_targets.SetItemTarget(nullptr);
1955
1956 m_CastItem = nullptr;
1958 m_castItemEntry = 0;
1959
1960 player->BankItem(dest, pNewItem, true);
1961 return;
1962 }
1963 }
1964 else if (player->IsEquipmentPos(pos))
1965 {
1966 uint16 dest;
1967
1968 player->DestroyItem(m_CastItem->GetBagSlot(), m_CastItem->GetSlot(), true);
1969
1970 InventoryResult msg = player->CanEquipItem(m_CastItem->GetSlot(), dest, pNewItem, true);
1971
1972 if (msg == EQUIP_ERR_OK || msg == EQUIP_ERR_CLIENT_LOCKED_OUT)
1973 {
1975
1976 // prevent crash at access and unexpected charges counting with item update queue corrupt
1978 m_targets.SetItemTarget(nullptr);
1979
1980 m_CastItem = nullptr;
1982 m_castItemEntry = 0;
1983
1984 player->EquipItem(dest, pNewItem, true);
1985 player->AutoUnequipOffhandIfNeed();
1986 player->SendNewItem(pNewItem, 1, true, false);
1987 player->ItemAddedQuestCheck(newitemid, 1);
1988 return;
1989 }
1990 }
1991
1992 // fail
1993 delete pNewItem;
1994}
1995
1997{
1999 return;
2000
2002 return;
2003 Player* p_target = m_caster->ToPlayer();
2004
2006 if (m_spellInfo->EquippedItemClass == ITEM_CLASS_WEAPON && !(p_target->GetWeaponProficiency() & subClassMask))
2007 {
2008 p_target->AddWeaponProficiency(subClassMask);
2010 }
2011 if (m_spellInfo->EquippedItemClass == ITEM_CLASS_ARMOR && !(p_target->GetArmorProficiency() & subClassMask))
2012 {
2013 p_target->AddArmorProficiency(subClassMask);
2015 }
2016}
2017
2019{
2021 return;
2022
2023 uint32 entry = effectInfo->MiscValue;
2024 if (!entry)
2025 return;
2026
2027 SummonPropertiesEntry const* properties = sSummonPropertiesStore.LookupEntry(effectInfo->MiscValueB);
2028 if (!properties)
2029 {
2030 TC_LOG_ERROR("spells", "EffectSummonType: Unhandled summon type {}.", effectInfo->MiscValueB);
2031 return;
2032 }
2033
2034 WorldObject* caster = m_caster;
2035 if (m_originalCaster)
2036 caster = m_originalCaster;
2037
2038 ObjectGuid privateObjectOwner;
2039 if (properties->Flags & SUMMON_PROP_FLAG_PERSONAL_SPAWN)
2041 int32 duration = m_spellInfo->GetDuration();
2042 if (Player* modOwner = caster->GetSpellModOwner())
2043 modOwner->ApplySpellMod(m_spellInfo->Id, SPELLMOD_DURATION, duration);
2044
2045 Unit* unitCaster = GetUnitCasterForEffectHandlers();
2046
2047 TempSummon* summon = nullptr;
2048
2049 // determine how many units should be summoned
2050 uint32 numSummons;
2051
2052 // some spells need to summon many units, for those spells number of summons is stored in effect value
2053 // however so far noone found a generic check to find all of those (there's no related data in summonproperties.dbc
2054 // and in spell attributes, possibly we need to add a table for those)
2055 // so here's a list of MiscValueB values, which is currently most generic check
2056 switch (properties->ID)
2057 {
2058 case 64:
2059 case 61:
2060 case 1101:
2061 case 66:
2062 case 648:
2063 case 2301:
2064 case 1061:
2065 case 1261:
2066 case 629:
2067 case 181:
2068 case 715:
2069 case 1562:
2070 case 833:
2071 case 1161:
2072 case 713:
2073 numSummons = (damage > 0) ? damage : 1;
2074 break;
2075 default:
2076 numSummons = 1;
2077 break;
2078 }
2079
2080 switch (properties->Control)
2081 {
2085 {
2086 if (properties->Flags & 512)
2087 {
2088 SummonGuardian(*effectInfo, entry, properties, numSummons);
2089 break;
2090 }
2091
2092 switch (properties->Title)
2093 {
2094 case SUMMON_TYPE_PET:
2097 case SUMMON_TYPE_MINION:
2098 SummonGuardian(*effectInfo, entry, properties, numSummons);
2099 break;
2100 // Summons a vehicle, but doesn't force anyone to enter it (see SUMMON_CATEGORY_VEHICLE)
2104 {
2105 if (!unitCaster)
2106 return;
2107
2108 summon = unitCaster->GetMap()->SummonCreature(entry, *destTarget, properties, duration, unitCaster, m_spellInfo->Id);
2109 break;
2110 }
2111 case SUMMON_TYPE_TOTEM:
2112 {
2113 if (!unitCaster)
2114 return;
2115
2116 summon = unitCaster->GetMap()->SummonCreature(entry, *destTarget, properties, duration, unitCaster, m_spellInfo->Id, 0, privateObjectOwner);
2117 if (!summon || !summon->IsTotem())
2118 return;
2119
2120 // Mana Tide Totem
2121 if (m_spellInfo->Id == 16190)
2122 damage = unitCaster->CountPctFromMaxHealth(10);
2123
2124 if (damage) // if not spell info, DB values used
2125 {
2126 summon->SetMaxHealth(damage);
2127 summon->SetHealth(damage);
2128 }
2129 break;
2130 }
2132 {
2133 if (!unitCaster)
2134 return;
2135
2136 summon = unitCaster->GetMap()->SummonCreature(entry, *destTarget, properties, duration, unitCaster, m_spellInfo->Id, 0, privateObjectOwner);
2137 if (!summon || !summon->HasUnitTypeMask(UNIT_MASK_MINION))
2138 return;
2139
2140 summon->SelectLevel(); // some summoned creaters have different from 1 DB data for level/hp
2142 summon->SetImmuneToAll(true);
2143 break;
2144 }
2145 default:
2146 {
2147 float radius = effectInfo->CalcRadius();
2148
2149 TempSummonType summonType = (duration == 0) ? TEMPSUMMON_DEAD_DESPAWN : TEMPSUMMON_TIMED_DESPAWN;
2150
2151 for (uint32 count = 0; count < numSummons; ++count)
2152 {
2153 Position pos;
2154 if (count == 0)
2155 pos = *destTarget;
2156 else
2157 // randomize position for multiple summons
2158 pos = caster->GetRandomPoint(*destTarget, radius);
2159
2160 summon = caster->SummonCreature(entry, pos, summonType, Milliseconds(duration), 0, m_spellInfo->Id, privateObjectOwner);
2161 if (!summon)
2162 continue;
2163
2164 if (properties->Control == SUMMON_CATEGORY_ALLY)
2165 {
2166 summon->SetOwnerGUID(caster->GetGUID());
2167 summon->SetFaction(caster->GetFaction());
2168 }
2169
2171 }
2172 return;
2173 }
2174 }
2175 break;
2176 }
2178 SummonGuardian(*effectInfo, entry, properties, numSummons);
2179 break;
2181 {
2182 if (!unitCaster)
2183 return;
2184
2185 summon = unitCaster->GetMap()->SummonCreature(entry, *destTarget, properties, duration, unitCaster, m_spellInfo->Id, 0, privateObjectOwner);
2186 break;
2187 }
2189 {
2190 if (!unitCaster)
2191 return;
2192
2193 // Summoning spells (usually triggered by npc_spellclick) that spawn a vehicle and that cause the clicker
2194 // to cast a ride vehicle spell on the summoned unit.
2195 summon = unitCaster->GetMap()->SummonCreature(entry, *destTarget, properties, duration, unitCaster, m_spellInfo->Id);
2196 if (!summon || !summon->IsVehicle())
2197 return;
2198
2199 // The spell that this effect will trigger. It has SPELL_AURA_CONTROL_VEHICLE
2201 int32 basePoints = effectInfo->CalcValue();
2202 if (basePoints > MAX_VEHICLE_SEATS)
2203 {
2204 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(basePoints);
2205 if (spellInfo && spellInfo->HasAura(SPELL_AURA_CONTROL_VEHICLE))
2206 spellId = spellInfo->Id;
2207 }
2208
2210
2211 // if we have small value, it indicates seat position
2212 if (basePoints > 0 && basePoints < MAX_VEHICLE_SEATS)
2213 args.AddSpellMod(SPELLVALUE_BASE_POINT0, basePoints);
2214
2215 unitCaster->CastSpell(summon, spellId, args);
2216
2217 uint32 faction = properties->Faction;
2218 if (!faction)
2219 faction = unitCaster->GetFaction();
2220
2221 summon->SetFaction(faction);
2222 break;
2223 }
2224 }
2225
2226 if (summon)
2227 {
2228 summon->SetCreatorGUID(caster->GetGUID());
2230 }
2231}
2232
2234{
2236 return;
2237
2238 if (!unitTarget)
2239 return;
2240
2242 {
2243 if (unitTarget->ToPet())
2245 return;
2246 }
2247
2248 Player* player = unitTarget->ToPlayer();
2249
2251 {
2252 for (ItemEffect const& itemEffect : m_CastItem->GetTemplate()->Effects)
2253 {
2254 if (itemEffect.TriggerType != ITEM_SPELLTRIGGER_LEARN_SPELL_ID)
2255 continue;
2256
2257 player->LearnSpell(itemEffect.SpellID, false);
2258 }
2259 }
2260
2262 {
2263 player->LearnSpell(effectInfo->TriggerSpell, false);
2264 TC_LOG_DEBUG("spells", "Spell: Player {} has learned spell {} from Npc {}", player->GetGUID().ToString(), effectInfo->TriggerSpell, m_caster->GetGUID().ToString());
2265 }
2266}
2267
2269{
2271 return;
2272
2273 if (!unitTarget)
2274 return;
2275
2276 // Create dispel mask by dispel type
2277 uint32 dispel_type = effectInfo->MiscValue;
2278 uint32 dispelMask = SpellInfo::GetDispelMask(DispelType(dispel_type));
2279
2280 DispelChargesList dispelList;
2282 if (dispelList.empty())
2283 return;
2284
2285 size_t remaining = dispelList.size();
2286
2287 // Ok if exist some buffs for dispel try dispel it
2288 uint32 failCount = 0;
2289 DispelChargesList successList;
2290 successList.reserve(damage);
2291
2292 WorldPacket dataFail(SMSG_DISPEL_FAILED, 8 + 8 + 4 + 4 + damage * 4);
2293 // dispel N = damage buffs (or while exist buffs for dispel)
2294 for (int32 count = 0; count < damage && remaining > 0;)
2295 {
2296 // Random select buff for dispel
2297 auto itr = dispelList.begin();
2298 std::advance(itr, urand(0, remaining - 1));
2299
2300 if (itr->RollDispel())
2301 {
2302 auto successItr = std::find_if(successList.begin(), successList.end(), [&itr](DispelableAura& dispelAura) -> bool
2303 {
2304 if (dispelAura.GetAura()->GetId() == itr->GetAura()->GetId() && dispelAura.GetAura()->GetCaster() == itr->GetAura()->GetCaster())
2305 return true;
2306
2307 return false;
2308 });
2309
2310 if (successItr == successList.end())
2311 successList.emplace_back(itr->GetAura(), 0, 1);
2312 else
2313 successItr->IncrementCharges();
2314
2315 if (!itr->DecrementCharge())
2316 {
2317 --remaining;
2318 std::swap(*itr, dispelList[remaining]);
2319 }
2320 }
2321 else
2322 {
2323 if (!failCount)
2324 {
2325 // Failed to dispell
2326 dataFail << m_caster->GetGUID(); // Caster GUID
2327 dataFail << unitTarget->GetGUID(); // Victim GUID
2328 dataFail << uint32(m_spellInfo->Id); // dispel spell id
2329 }
2330 ++failCount;
2331 dataFail << uint32(itr->GetAura()->GetId()); // Spell Id
2332 }
2333 ++count;
2334 }
2335
2336 if (failCount)
2337 m_caster->SendMessageToSet(&dataFail, true);
2338
2339 if (successList.empty())
2340 return;
2341
2342 WorldPacket dataSuccess(SMSG_SPELLDISPELLOG, 8 + 8 + 4 + 1 + 4 + successList.size() * 5);
2343 // Send packet header
2344 dataSuccess << unitTarget->GetPackGUID(); // Victim GUID
2345 dataSuccess << m_caster->GetPackGUID(); // Caster GUID
2346 dataSuccess << uint32(m_spellInfo->Id); // dispel spell id
2347 dataSuccess << uint8(0); // not used
2348 dataSuccess << uint32(successList.size()); // count
2349 for (DispelChargesList::iterator itr = successList.begin(); itr != successList.end(); ++itr)
2350 {
2351 // Send dispelled spell info
2352 dataSuccess << uint32(itr->GetAura()->GetId()); // Spell Id
2353 dataSuccess << uint8(0); // 0 - dispelled !=0 cleansed
2354 unitTarget->RemoveAurasDueToSpellByDispel(itr->GetAura()->GetId(), m_spellInfo->Id, itr->GetAura()->GetCasterGUID(), m_caster, itr->GetDispelCharges());
2355 }
2356 m_caster->SendMessageToSet(&dataSuccess, true);
2357
2359}
2360
2362{
2364 return;
2365
2367}
2368
2370{
2372 EffectNULL();
2373}
2374
2376{
2378 return;
2379
2380 // Check for possible target
2381 if (!unitTarget || unitTarget->IsEngaged())
2382 return;
2383
2384 // target must be OK to do this
2386 return;
2387
2389}
2390
2392{
2394 return;
2395
2397 return;
2398
2399 // victim must be creature and attackable
2401 return;
2402
2403 // victim have to be alive and humanoid or undead
2406}
2407
2409{
2411 return;
2412
2413 Player* player = m_caster->ToPlayer();
2414 if (!player)
2415 return;
2416
2417 float radius = effectInfo->CalcRadius();
2418 int32 duration = m_spellInfo->GetDuration();
2419 // Caster not in world, might be spell triggered from aura removal
2420 if (!player->IsInWorld())
2421 return;
2422
2423 DynamicObject* dynObj = new DynamicObject(true);
2425 {
2426 delete dynObj;
2427 return;
2428 }
2429
2430 dynObj->SetDuration(duration);
2431 dynObj->SetCasterViewpoint();
2432}
2433
2435{
2437 return;
2438
2439 if (!unitTarget->IsPlayer())
2440 return;
2441
2442 Player* playerTarget = unitTarget->ToPlayer();
2443 playerTarget->SendRespecWipeConfirm(m_caster->GetGUID(), playerTarget->GetNextResetTalentsCost());
2444}
2445
2460
2462{
2464 return;
2465
2467 return;
2468
2469 if (damage < 0)
2470 return;
2471
2472 uint32 skillid = effectInfo->MiscValue;
2474 if (!rcEntry)
2475 return;
2476
2477 SkillTiersEntry const* tier = sSkillTiersStore.LookupEntry(rcEntry->SkillTierID);
2478 if (!tier)
2479 return;
2480
2481 uint16 skillval = unitTarget->ToPlayer()->GetPureSkillValue(skillid);
2482 unitTarget->ToPlayer()->SetSkill(skillid, effectInfo->CalcValue(), std::max<uint16>(skillval, 1), tier->Value[damage - 1]);
2483}
2484
2486{
2488 return;
2489
2491 return;
2492
2493 // not scale value for item based reward (/10 value expected)
2494 if (m_CastItem)
2495 {
2496 unitTarget->ToPlayer()->RewardHonor(nullptr, 1, damage/10);
2497 TC_LOG_DEBUG("spells", "SpellEffect::AddHonor (spell_id {}) rewards {} honor points (item {}) for player {}", m_spellInfo->Id, damage/10, m_CastItem->GetEntry(), unitTarget->ToPlayer()->GetGUID().ToString());
2498 return;
2499 }
2500
2501 // do not allow to add too many honor for player (50 * 21) = 1040 at level 70, or (50 * 31) = 1550 at level 80
2502 if (damage <= 50)
2503 {
2505 unitTarget->ToPlayer()->RewardHonor(nullptr, 1, honor_reward);
2506 TC_LOG_DEBUG("spells", "SpellEffect::AddHonor (spell_id {}) rewards {} honor points (scale) to player {}", m_spellInfo->Id, honor_reward, unitTarget->ToPlayer()->GetGUID().ToString());
2507 }
2508 else
2509 {
2510 //maybe we have correct honor_gain in damage already
2511 unitTarget->ToPlayer()->RewardHonor(nullptr, 1, damage);
2512 TC_LOG_DEBUG("spells", "SpellEffect::AddHonor (spell_id {}) rewards {} honor points (non scale) for player {}", m_spellInfo->Id, damage, unitTarget->ToPlayer()->GetGUID().ToString());
2513 }
2514}
2515
2517{
2519 return;
2520
2522 return;
2523 // uint32 skillid = effectInfo->MiscValue;
2524 // uint16 skillmax = unitTarget->ToPlayer()->(skillid);
2525 // m_caster->ToPlayer()->SetSkill(skillid, skillval?skillval:1, skillmax+75);
2526}
2527
2529{
2531 return;
2532
2533 if (!itemTarget)
2534 return;
2535
2536 Player* player = m_caster->ToPlayer();
2537 if (!player)
2538 return;
2539
2540 // Handle vellums
2542 {
2543 // destroy one vellum from stack
2544 uint32 count = 1;
2545 player->DestroyItemCount(itemTarget, count, true);
2546 unitTarget = player;
2547 // and add a scroll
2549 itemTarget = nullptr;
2550 m_targets.SetItemTarget(nullptr);
2551 }
2552 else
2553 {
2554 // do not increase skill if vellum used
2557
2558 uint32 enchant_id = effectInfo->MiscValue;
2559 if (!enchant_id)
2560 return;
2561
2562 SpellItemEnchantmentEntry const* pEnchant = sSpellItemEnchantmentStore.LookupEntry(enchant_id);
2563 if (!pEnchant)
2564 return;
2565
2566 // item can be in trade slot and have owner diff. from caster
2567 Player* item_owner = itemTarget->GetOwner();
2568 if (!item_owner)
2569 return;
2570
2571 if (item_owner != player && player->GetSession()->HasPermission(rbac::RBAC_PERM_LOG_GM_TRADE))
2572 {
2573 sLog->OutCommand(player->GetSession()->GetAccountId(), "GM {} (Account: {}) enchanting(perm): {} (Entry: {}) for player: {} (Account: {})",
2574 player->GetName(), player->GetSession()->GetAccountId(),
2575 itemTarget->GetNameForLocaleIdx(sWorld->GetDefaultDbcLocale()), itemTarget->GetEntry(),
2576 item_owner->GetName(), item_owner->GetSession()->GetAccountId());
2577 }
2578
2579 // remove old enchanting before applying new if equipped
2581
2583
2584 // add new enchanting if equipped
2586
2587 item_owner->RemoveTradeableItem(itemTarget);
2589 }
2590}
2591
2593{
2595 return;
2596
2597 if (!itemTarget)
2598 return;
2599
2600 Player* player = m_caster->ToPlayer();
2601 if (!player)
2602 return;
2603
2604 uint32 enchantId = effectInfo->MiscValue;
2605 if (!enchantId)
2606 return;
2607
2608 SpellItemEnchantmentEntry const* enchant = sSpellItemEnchantmentStore.LookupEntry(enchantId);
2609 if (!enchant)
2610 return;
2611
2612 // support only enchantings with add socket in this slot
2613 {
2614 bool add_socket = false;
2615 for (uint8 i = 0; i < MAX_ITEM_ENCHANTMENT_EFFECTS; ++i)
2616 {
2618 {
2619 add_socket = true;
2620 break;
2621 }
2622 }
2623 if (!add_socket)
2624 {
2625 TC_LOG_ERROR("spells", "Spell::EffectEnchantItemPrismatic: attempt to apply the enchant spell {} with SPELL_EFFECT_ENCHANT_ITEM_PRISMATIC ({}), but without ITEM_ENCHANTMENT_TYPE_PRISMATIC_SOCKET ({}), not supported yet.",
2627 return;
2628 }
2629 }
2630
2631 // item can be in trade slot and have owner diff. from caster
2632 Player* item_owner = itemTarget->GetOwner();
2633 if (!item_owner)
2634 return;
2635
2636 if (item_owner != player && player->GetSession()->HasPermission(rbac::RBAC_PERM_LOG_GM_TRADE))
2637 {
2638 sLog->OutCommand(player->GetSession()->GetAccountId(), "GM {} (Account: {}) enchanting(perm): {} (Entry: {}) for player: {} (Account: {})",
2639 player->GetName(), player->GetSession()->GetAccountId(),
2640 itemTarget->GetNameForLocaleIdx(sWorld->GetDefaultDbcLocale()), itemTarget->GetEntry(),
2641 item_owner->GetName(), item_owner->GetSession()->GetAccountId());
2642 }
2643
2644 // remove old enchanting before applying new if equipped
2646
2648
2649 // add new enchanting if equipped
2651
2652 item_owner->RemoveTradeableItem(itemTarget);
2654}
2655
2657{
2659 return;
2660
2661 Player* player = m_caster->ToPlayer();
2662 if (!player)
2663 return;
2664
2665 // Rockbiter Weapon apply to both weapon
2666 if (!itemTarget)
2667 return;
2669 {
2670 uint32 spell_id = 0;
2671
2672 // enchanting spell selected by calculated damage-per-sec stored in Effect[1] base value
2673 // Note: damage calculated (correctly) with rounding int32(float(v)) but
2674 // RW enchantments applied damage int32(float(v)+0.5), this create 0..1 difference sometime
2675 switch (damage)
2676 {
2677 // Rank 1
2678 case 2: spell_id = 36744; break; // 0% [ 7% == 2, 14% == 2, 20% == 2]
2679 // Rank 2
2680 case 4: spell_id = 36753; break; // 0% [ 7% == 4, 14% == 4]
2681 case 5: spell_id = 36751; break; // 20%
2682 // Rank 3
2683 case 6: spell_id = 36754; break; // 0% [ 7% == 6, 14% == 6]
2684 case 7: spell_id = 36755; break; // 20%
2685 // Rank 4
2686 case 9: spell_id = 36761; break; // 0% [ 7% == 6]
2687 case 10: spell_id = 36758; break; // 14%
2688 case 11: spell_id = 36760; break; // 20%
2689 default:
2690 TC_LOG_ERROR("spells", "Spell::EffectEnchantItemTmp: Damage {} not handled in S'RW.", damage);
2691 return;
2692 }
2693
2694 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spell_id);
2695 if (!spellInfo)
2696 {
2697 TC_LOG_ERROR("spells", "Spell::EffectEnchantItemTmp: unknown spell id {}", spell_id);
2698 return;
2699
2700 }
2701
2702 for (int j = BASE_ATTACK; j <= OFF_ATTACK; ++j)
2703 {
2704 if (Item* item = player->GetWeaponForAttack(WeaponAttackType(j)))
2705 {
2706 if (item->IsFitToSpellRequirements(m_spellInfo))
2707 {
2708 Spell* spell = new Spell(m_caster, spellInfo, TRIGGERED_FULL_MASK);
2709 SpellCastTargets targets;
2710 targets.SetItemTarget(item);
2711 spell->prepare(targets);
2712 }
2713 }
2714 }
2715 return;
2716 }
2717
2718 uint32 enchant_id = effectInfo->MiscValue;
2719
2720 if (!enchant_id)
2721 {
2722 TC_LOG_ERROR("spells", "Spell {} Effect {} (SPELL_EFFECT_ENCHANT_ITEM_TEMPORARY) has enchanting id 0.", m_spellInfo->Id, uint32(effectInfo->EffectIndex));
2723 return;
2724 }
2725
2726 SpellItemEnchantmentEntry const* pEnchant = sSpellItemEnchantmentStore.LookupEntry(enchant_id);
2727 if (!pEnchant)
2728 {
2729 TC_LOG_ERROR("spells", "Spell {} Effect {} (SPELL_EFFECT_ENCHANT_ITEM_TEMPORARY) has a non-existing enchanting id {} ", m_spellInfo->Id, uint32(effectInfo->EffectIndex), enchant_id);
2730 return;
2731 }
2732
2733 // select enchantment duration
2734 uint32 duration;
2735
2736 // rogue family enchantments exception by duration
2737 if (m_spellInfo->Id == 38615)
2738 duration = 1800; // 30 mins
2739 // other rogue family enchantments always 1 hour (some have spell damage=0, but some have wrong data in EffBasePoints)
2741 duration = 3600; // 1 hour
2742 // shaman family enchantments
2744 duration = 1800; // 30 mins
2745 // other cases with this SpellVisual already selected
2746 else if (m_spellInfo->SpellVisual[0] == 215)
2747 duration = 1800; // 30 mins
2748 // some fishing pole bonuses except Glow Worm which lasts full hour
2749 else if (m_spellInfo->SpellVisual[0] == 563 && m_spellInfo->Id != 64401)
2750 duration = 600; // 10 mins
2751 // shaman rockbiter enchantments
2752 else if (m_spellInfo->SpellVisual[0] == 0)
2753 duration = 1800; // 30 mins
2754 else if (m_spellInfo->Id == 29702)
2755 duration = 300; // 5 mins
2756 else if (m_spellInfo->Id == 37360)
2757 duration = 300; // 5 mins
2758 // default case
2759 else
2760 duration = 3600; // 1 hour
2761
2762 // item can be in trade slot and have owner diff. from caster
2763 Player* item_owner = itemTarget->GetOwner();
2764 if (!item_owner)
2765 return;
2766
2767 if (item_owner != player && player->GetSession()->HasPermission(rbac::RBAC_PERM_LOG_GM_TRADE))
2768 {
2769 sLog->OutCommand(player->GetSession()->GetAccountId(), "GM {} (Account: {}) enchanting(temp): {} (Entry: {}) for player: {} (Account: {})",
2770 player->GetName(), player->GetSession()->GetAccountId(),
2771 itemTarget->GetNameForLocaleIdx(sWorld->GetDefaultDbcLocale()), itemTarget->GetEntry(),
2772 item_owner->GetName(), item_owner->GetSession()->GetAccountId());
2773 }
2774
2775 // remove old enchanting before applying new if equipped
2777
2778 itemTarget->SetEnchantment(TEMP_ENCHANTMENT_SLOT, enchant_id, duration * 1000, 0, m_caster->GetGUID());
2779
2780 // add new enchanting if equipped
2782}
2783
2785{
2787 return;
2788
2789 Unit* unitCaster = GetUnitCasterForEffectHandlers();
2790 if (!unitCaster || !unitCaster->GetPetGUID().IsEmpty())
2791 return;
2792
2793 if (!unitTarget)
2794 return;
2795
2797 return;
2798
2799 Creature* creatureTarget = unitTarget->ToCreature();
2800
2801 if (creatureTarget->IsPet())
2802 return;
2803
2804 if (unitCaster->GetClass() != CLASS_HUNTER)
2805 return;
2806
2807 // cast finish successfully
2808 //SendChannelUpdate(0);
2809 finish();
2810
2811 Pet* pet = unitCaster->CreateTamedPetFrom(creatureTarget, m_spellInfo->Id);
2812 if (!pet) // in very specific state like near world end/etc.
2813 return;
2814
2815 // "kill" original creature
2816 creatureTarget->DespawnOrUnsummon();
2817
2818 uint8 level = (creatureTarget->GetLevel() < (unitCaster->GetLevel() - 5)) ? (unitCaster->GetLevel() - 5) : creatureTarget->GetLevel();
2819
2820 // prepare visual effect for levelup
2821 pet->SetUInt32Value(UNIT_FIELD_LEVEL, level - 1);
2822
2823 // add to world
2824 pet->GetMap()->AddToMap(pet->ToCreature());
2825
2826 // visual effect for levelup
2827 pet->SetUInt32Value(UNIT_FIELD_LEVEL, level);
2828
2829 // caster have pet now
2830 unitCaster->SetMinion(pet, true);
2831
2832 pet->InitTalentForLevel();
2833
2834 if (unitCaster->GetTypeId() == TYPEID_PLAYER)
2835 {
2837 unitCaster->ToPlayer()->PetSpellInitialize();
2838 }
2839}
2840
2842{
2844 return;
2845
2846 Player* owner = nullptr;
2847 if (Unit* unitCaster = GetUnitCasterForEffectHandlers())
2848 {
2849 owner = unitCaster->ToPlayer();
2850 if (!owner && unitCaster->IsTotem())
2851 owner = unitCaster->GetCharmerOrOwnerPlayerOrPlayerItself();
2852 }
2853
2854 uint32 petentry = effectInfo->MiscValue;
2855
2856 if (!owner)
2857 {
2858 SummonPropertiesEntry const* properties = sSummonPropertiesStore.LookupEntry(67);
2859 if (properties)
2860 SummonGuardian(*effectInfo, petentry, properties, 1);
2861 return;
2862 }
2863
2864 Pet* OldSummon = owner->GetPet();
2865
2866 // if pet requested type already exist
2867 if (OldSummon)
2868 {
2869 if (petentry == 0 || OldSummon->GetEntry() == petentry)
2870 {
2871 // pet in corpse state can't be summoned
2872 if (OldSummon->isDead())
2873 return;
2874
2875 ASSERT(OldSummon->GetMap() == owner->GetMap());
2876
2877 //OldSummon->GetMap()->Remove(OldSummon->ToCreature(), false);
2878
2879 float px, py, pz;
2880 owner->GetClosePoint(px, py, pz, OldSummon->GetCombatReach());
2881
2882 OldSummon->NearTeleportTo(px, py, pz, OldSummon->GetOrientation());
2883 //OldSummon->Relocate(px, py, pz, OldSummon->GetOrientation());
2884 //OldSummon->SetMap(owner->GetMap());
2885 //owner->GetMap()->Add(OldSummon->ToCreature());
2886 if (OldSummon->getPetType() == SUMMON_PET)
2887 {
2888 OldSummon->SetHealth(OldSummon->GetMaxHealth());
2889 OldSummon->SetPower(OldSummon->GetPowerType(), OldSummon->GetMaxPower(OldSummon->GetPowerType()));
2890 OldSummon->GetSpellHistory()->ResetAllCooldowns();
2891 }
2892
2893 if (owner->GetTypeId() == TYPEID_PLAYER && OldSummon->isControlled())
2894 owner->ToPlayer()->PetSpellInitialize();
2895
2896 return;
2897 }
2898
2899 if (owner->GetTypeId() == TYPEID_PLAYER)
2900 owner->ToPlayer()->RemovePet(OldSummon, PET_SAVE_NOT_IN_SLOT, false);
2901 else
2902 return;
2903 }
2904
2905 float x, y, z;
2906 owner->GetClosePoint(x, y, z, owner->GetCombatReach());
2907 Pet* pet = owner->SummonPet(petentry, x, y, z, owner->GetOrientation(), SUMMON_PET, 0);
2908 if (!pet)
2909 return;
2910
2911 if (m_caster->GetTypeId() == TYPEID_UNIT)
2912 {
2913 if (m_caster->ToCreature()->IsTotem())
2915 else
2917 }
2918
2920
2921 // generate new name for summon pet
2922 std::string new_name = sObjectMgr->GeneratePetName(petentry);
2923 if (!new_name.empty())
2924 pet->SetName(new_name);
2925
2927}
2928
2930{
2932 return;
2933
2934 if (!unitTarget)
2935 return;
2936
2937 if (unitTarget->ToPlayer())
2938 {
2940 return;
2941 }
2942 Pet* pet = unitTarget->ToPet();
2943 if (!pet)
2944 return;
2945
2946 SpellInfo const* learn_spellproto = sSpellMgr->GetSpellInfo(effectInfo->TriggerSpell);
2947 if (!learn_spellproto)
2948 return;
2949
2950 pet->learnSpell(learn_spellproto->Id);
2952 pet->GetOwner()->PetSpellInitialize();
2953}
2954
2956{
2958 return;
2959
2960 Unit* unitCaster = GetUnitCasterForEffectHandlers();
2961 if (!unitCaster)
2962 return;
2963
2964 // this effect use before aura Taunt apply for prevent taunt already attacking target
2965 // for spell as marked "non effective at already attacking target"
2966 if (!unitTarget || unitTarget->IsTotem())
2967 {
2969 return;
2970 }
2971
2972 // Hand of Reckoning can hit some entities that can't have a threat list (including players' pets)
2973 if (m_spellInfo->Id == 62124)
2974 if (unitTarget->GetTypeId() != TYPEID_PLAYER && unitTarget->GetTarget() != unitCaster->GetGUID())
2975 unitCaster->CastSpell(unitTarget, 67485, true);
2976
2978 {
2980 return;
2981 }
2982
2984 if (mgr.GetCurrentVictim() == unitCaster)
2985 {
2987 return;
2988 }
2989
2990 if (!mgr.IsThreatListEmpty())
2991 // Set threat equal to highest threat currently on target
2992 mgr.MatchUnitThreatToHighestThreat(unitCaster);
2993}
2994
2996{
2998 return;
2999
3000 Unit* unitCaster = GetUnitCasterForEffectHandlers();
3001 if (!unitCaster)
3002 return;
3003
3004 if (!unitTarget || !unitTarget->IsAlive())
3005 return;
3006
3007 // multiple weapon dmg effect workaround
3008 // execute only the last weapon damage
3009 // and handle all effects at once
3010 for (size_t j = effectInfo->EffectIndex + 1; j < m_spellInfo->GetEffects().size(); ++j)
3011 {
3013 {
3018 return; // we must calculate only at last weapon effect
3019 default:
3020 break;
3021 }
3022 }
3023
3024 // some spell specific modifiers
3025 float totalDamagePercentMod = 1.0f; // applied to final bonus+weapon damage
3026 int32 fixed_bonus = 0;
3027 int32 spell_bonus = 0; // bonus specific for spell
3028
3030 {
3032 {
3033 // Devastate (player ones)
3034 if (m_spellInfo->SpellFamilyFlags[1] & 0x40)
3035 {
3036 unitCaster->CastSpell(unitTarget, 58567, true);
3037 // 58388 - Glyph of Devastate dummy aura.
3038 if (unitCaster->HasAura(58388))
3039 unitCaster->CastSpell(unitTarget, 58567, true);
3040
3041 if (Aura* aur = unitTarget->GetAura(58567, unitCaster->GetGUID()))
3042 fixed_bonus += (aur->GetStackAmount() - 1) * CalculateDamage(m_spellInfo->GetEffect(EFFECT_2)); // subtract 1 so fixed bonus is not applied twice
3043 }
3044 else if (m_spellInfo->SpellFamilyFlags[0] & 0x8000000) // Mocking Blow
3045 {
3047 {
3048 m_damage = 0;
3049 return;
3050 }
3051 }
3052 break;
3053 }
3054 case SPELLFAMILY_ROGUE:
3055 {
3056 // Fan of Knives, Hemorrhage, Ghostly Strike
3057 if ((m_spellInfo->SpellFamilyFlags[1] & 0x40000)
3058 || (m_spellInfo->SpellFamilyFlags[0] & 0x6000000))
3059 {
3060 // Hemorrhage
3061 if (m_spellInfo->SpellFamilyFlags[0] & 0x2000000)
3063
3064 // 50% more damage with daggers
3065 if (unitCaster->GetTypeId() == TYPEID_PLAYER)
3066 if (Item* item = unitCaster->ToPlayer()->GetWeaponForAttack(m_attackType, true))
3067 if (item->GetTemplate()->GetSubClass() == ITEM_SUBCLASS_WEAPON_DAGGER)
3068 totalDamagePercentMod *= 1.5f;
3069 }
3070 // Mutilate (for each hand)
3071 else if (m_spellInfo->SpellFamilyFlags[1] & 0x6)
3072 {
3073 bool found = false;
3074 // fast check
3076 found = true;
3077 // full aura scan
3078 else
3079 {
3081 for (Unit::AuraApplicationMap::const_iterator itr = auras.begin(); itr != auras.end(); ++itr)
3082 {
3083 if (itr->second->GetBase()->GetSpellInfo()->Dispel == DISPEL_POISON)
3084 {
3085 found = true;
3086 break;
3087 }
3088 }
3089 }
3090
3091 if (found)
3092 totalDamagePercentMod *= 1.2f; // 120% if poisoned
3093 }
3094 break;
3095 }
3097 {
3098 // Seal of Command Unleashed
3099 if (m_spellInfo->Id == 20467)
3100 {
3101 spell_bonus += int32(0.08f * unitCaster->GetTotalAttackPowerValue(BASE_ATTACK));
3102 spell_bonus += int32(0.13f * unitCaster->SpellBaseDamageBonusDone(m_spellInfo->GetSchoolMask()));
3103 }
3104 break;
3105 }
3106 case SPELLFAMILY_SHAMAN:
3107 {
3108 // Skyshatter Harness item set bonus
3109 // Stormstrike
3110 if (AuraEffect* aurEff = unitCaster->IsScriptOverriden(m_spellInfo, 5634))
3111 unitCaster->CastSpell(nullptr, 38430, aurEff);
3112 break;
3113 }
3114 case SPELLFAMILY_DRUID:
3115 {
3116 // Mangle (Cat): CP
3117 if (m_spellInfo->SpellFamilyFlags[1] & 0x400)
3119
3120 // Shred, Maul - Rend and Tear
3122 {
3123 if (AuraEffect const* rendAndTear = unitCaster->GetDummyAuraEffect(SPELLFAMILY_DRUID, 2859, 0))
3124 AddPct(totalDamagePercentMod, rendAndTear->GetAmount());
3125 }
3126 break;
3127 }
3128 case SPELLFAMILY_HUNTER:
3129 {
3130 // Kill Shot - bonus damage from Ranged Attack Power
3131 if (m_spellInfo->SpellFamilyFlags[1] & 0x800000)
3132 spell_bonus += int32(0.4f * unitCaster->GetTotalAttackPowerValue(RANGED_ATTACK));
3133 break;
3134 }
3136 {
3137 // Plague Strike
3138 if (m_spellInfo->SpellFamilyFlags[0] & 0x1)
3139 {
3140 // Glyph of Plague Strike
3141 if (AuraEffect const* aurEff = unitCaster->GetAuraEffect(58657, EFFECT_0))
3142 AddPct(totalDamagePercentMod, aurEff->GetAmount());
3143 break;
3144 }
3145 // Blood Strike
3146 if (m_spellInfo->SpellFamilyFlags[0] & 0x400000)
3147 {
3148 float bonusPct = m_spellInfo->GetEffect(EFFECT_2).CalcValue() * unitTarget->GetDiseasesByCaster(unitCaster->GetGUID()) / 2.0f;
3149 // Death Knight T8 Melee 4P Bonus
3150 if (AuraEffect const* aurEff = unitCaster->GetAuraEffect(64736, EFFECT_0))
3151 AddPct(bonusPct, aurEff->GetAmount());
3152 AddPct(totalDamagePercentMod, bonusPct);
3153
3154 // Glyph of Blood Strike
3155 if (unitCaster->GetAuraEffect(59332, EFFECT_0))
3157 AddPct(totalDamagePercentMod, 20);
3158 break;
3159 }
3160 // Death Strike
3161 if (m_spellInfo->SpellFamilyFlags[0] & 0x10)
3162 {
3163 // Glyph of Death Strike
3164 if (AuraEffect const* aurEff = unitCaster->GetAuraEffect(59336, EFFECT_0))
3165 if (uint32 runic = std::min<uint32>(unitCaster->GetPower(POWER_RUNIC_POWER), aurEff->GetSpellInfo()->GetEffect(EFFECT_1).CalcValue()))
3166 AddPct(totalDamagePercentMod, runic);
3167 break;
3168 }
3169 // Obliterate (12.5% more damage per disease)
3170 if (m_spellInfo->SpellFamilyFlags[1] & 0x20000)
3171 {
3172 bool consumeDiseases = true;
3173 // Annihilation
3174 if (AuraEffect const* aurEff = unitCaster->GetDummyAuraEffect(SPELLFAMILY_DEATHKNIGHT, 2710, EFFECT_0))
3175 // Do not consume diseases if roll sucesses
3176 if (roll_chance_i(aurEff->GetAmount()))
3177 consumeDiseases = false;
3178
3179 float bonusPct = m_spellInfo->GetEffect(EFFECT_2).CalcValue() * unitTarget->GetDiseasesByCaster(unitCaster->GetGUID(), consumeDiseases) / 2.0f;
3180 // Death Knight T8 Melee 4P Bonus
3181 if (AuraEffect const* aurEff = unitCaster->GetAuraEffect(64736, EFFECT_0))
3182 AddPct(bonusPct, aurEff->GetAmount());
3183 AddPct(totalDamagePercentMod, bonusPct);
3184 break;
3185 }
3186 // Blood-Caked Strike - Blood-Caked Blade
3187 if (m_spellInfo->SpellIconID == 1736)
3188 {
3189 AddPct(totalDamagePercentMod, unitTarget->GetDiseasesByCaster(unitCaster->GetGUID()) * 50.0f);
3190 break;
3191 }
3192 // Heart Strike
3193 if (m_spellInfo->SpellFamilyFlags[0] & 0x1000000)
3194 {
3195 float bonusPct = m_spellInfo->GetEffect(EFFECT_2).CalcValue() * unitTarget->GetDiseasesByCaster(unitCaster->GetGUID());
3196 // Death Knight T8 Melee 4P Bonus
3197 if (AuraEffect const* aurEff = unitCaster->GetAuraEffect(64736, EFFECT_0))
3198 AddPct(bonusPct, aurEff->GetAmount());
3199
3200 AddPct(totalDamagePercentMod, bonusPct);
3201 break;
3202 }
3203 break;
3204 }
3205 }
3206
3207 bool normalized = false;
3208 float weaponDamagePercentMod = 1.0f;
3209 for (SpellEffectInfo const& spellEffectInfo : m_spellInfo->GetEffects())
3210 {
3211 switch (spellEffectInfo.Effect)
3212 {
3215 fixed_bonus += CalculateDamage(spellEffectInfo);
3216 break;
3218 fixed_bonus += CalculateDamage(spellEffectInfo);
3219 normalized = true;
3220 break;
3222 ApplyPct(weaponDamagePercentMod, CalculateDamage(spellEffectInfo));
3223 break;
3224 default:
3225 break; // not weapon damage effect, just skip
3226 }
3227 }
3228
3229 // if (addPctMods) { percent mods are added in Unit::CalculateDamage } else { percent mods are added in Unit::MeleeDamageBonusDone }
3230 // this distinction is neccessary to properly inform the client about his autoattack damage values from Script_UnitDamage
3232 if (addPctMods)
3233 {
3234 UnitMods unitMod;
3235 switch (m_attackType)
3236 {
3237 default:
3238 case BASE_ATTACK: unitMod = UNIT_MOD_DAMAGE_MAINHAND; break;
3239 case OFF_ATTACK: unitMod = UNIT_MOD_DAMAGE_OFFHAND; break;
3240 case RANGED_ATTACK: unitMod = UNIT_MOD_DAMAGE_RANGED; break;
3241 }
3242
3243 float weapon_total_pct = unitCaster->GetPctModifierValue(unitMod, TOTAL_PCT);
3244 if (fixed_bonus)
3245 fixed_bonus = int32(fixed_bonus * weapon_total_pct);
3246 if (spell_bonus)
3247 spell_bonus = int32(spell_bonus * weapon_total_pct);
3248 }
3249
3250 int32 weaponDamage = unitCaster->CalculateDamage(m_attackType, normalized, addPctMods);
3251
3252 // Sequence is important
3253 for (SpellEffectInfo const& spellEffectInfo : m_spellInfo->GetEffects())
3254 {
3255 // We assume that a spell have at most one fixed_bonus
3256 // and at most one weaponDamagePercentMod
3257 switch (spellEffectInfo.Effect)
3258 {
3262 weaponDamage += fixed_bonus;
3263 break;
3265 weaponDamage = int32(weaponDamage * weaponDamagePercentMod);
3266 break;
3267 default:
3268 break; // not weapon damage effect, just skip
3269 }
3270 }
3271
3272 weaponDamage += spell_bonus;
3273 weaponDamage = int32(weaponDamage * totalDamagePercentMod);
3274
3275 // apply spellmod to Done damage
3276 if (Player* modOwner = unitCaster->GetSpellModOwner())
3277 modOwner->ApplySpellMod(m_spellInfo->Id, SPELLMOD_DAMAGE, weaponDamage);
3278
3279 // prevent negative damage
3280 weaponDamage = std::max(weaponDamage, 0);
3281
3282 // Add melee damage bonuses (also check for negative)
3283 weaponDamage = unitCaster->MeleeDamageBonusDone(unitTarget, weaponDamage, m_attackType, m_spellInfo);
3284 m_damage += unitTarget->MeleeDamageBonusTaken(unitCaster, weaponDamage, m_attackType, m_spellInfo);
3285}
3286
3288{
3290 return;
3291
3292 Unit* unitCaster = GetUnitCasterForEffectHandlers();
3293 if (!unitCaster || !unitCaster->IsAlive())
3294 return;
3295
3296 if (!unitTarget)
3297 return;
3298
3300 return;
3301
3302 unitTarget->GetThreatManager().AddThreat(unitCaster, float(damage), m_spellInfo, true);
3303}
3304
3306{
3308 return;
3309
3310 Unit* unitCaster = GetUnitCasterForEffectHandlers();
3311 if (!unitCaster)
3312 return;
3313
3314 if (!unitTarget || !unitTarget->IsAlive())
3315 return;
3316
3317 int32 addhealth = 0;
3318
3319 // damage == 0 - heal for caster max health
3320 if (damage == 0)
3321 addhealth = unitCaster->GetMaxHealth();
3322 else
3323 addhealth = unitTarget->GetMaxHealth() - unitTarget->GetHealth();
3324
3325 m_healing += addhealth;
3326}
3327
3329{
3331 return;
3332
3333 if (!unitTarget || !unitTarget->IsAlive())
3334 return;
3335
3337 // also exist case: apply cooldown to interrupted cast only and to all spells
3338 // there is no CURRENT_AUTOREPEAT_SPELL spells that can be interrupted
3340 {
3342 {
3343 SpellInfo const* curSpellInfo = spell->m_spellInfo;
3344 // check if we can interrupt spell
3345 if ((spell->getState() == SPELL_STATE_CASTING
3346 || (spell->getState() == SPELL_STATE_PREPARING && spell->GetCastTime() > 0.0f))
3350 {
3351 if (Unit* unitCaster = GetUnitCasterForEffectHandlers())
3352 {
3353 int32 duration = m_spellInfo->GetDuration();
3361 }
3364 }
3365 }
3366 }
3367}
3368
3370{
3372 return;
3373
3374 uint32 gameobject_id = effectInfo->MiscValue;
3375
3376 GameObject* pGameObj = new GameObject();
3377
3378 WorldObject* target = focusObject;
3379 if (!target)
3380 target = m_caster;
3381
3382 float x, y, z;
3383 if (m_targets.HasDst())
3384 destTarget->GetPosition(x, y, z);
3385 else
3387
3388 Map* map = target->GetMap();
3389
3391 if (!pGameObj->Create(map->GenerateLowGuid<HighGuid::GameObject>(), gameobject_id, map, m_caster->GetPhaseMask(), Position(x, y, z, target->GetOrientation()), rot, 255, GO_STATE_READY))
3392 {
3393 delete pGameObj;
3394 return;
3395 }
3396
3397 int32 duration = m_spellInfo->GetDuration();
3398
3399 pGameObj->SetRespawnTime(duration > 0 ? duration/IN_MILLISECONDS : 0);
3400 pGameObj->SetSpellId(m_spellInfo->Id);
3401
3403
3404 // Wild object not have owner and check clickable by players
3405 map->AddToMap(pGameObj);
3406
3407 if (pGameObj->GetGoType() == GAMEOBJECT_TYPE_FLAGDROP)
3408 if (Player* player = m_caster->ToPlayer())
3409 if (Battleground* bg = player->GetBattleground())
3410 bg->SetDroppedFlagGUID(pGameObj->GetGUID(), player->GetTeam() == ALLIANCE ? TEAM_HORDE: TEAM_ALLIANCE);
3411
3412 if (GameObject* linkedTrap = pGameObj->GetLinkedTrap())
3413 {
3414 linkedTrap->SetRespawnTime(duration > 0 ? duration / IN_MILLISECONDS : 0);
3415 linkedTrap->SetSpellId(m_spellInfo->Id);
3416
3418 }
3419}
3420
3422{
3424 return;
3425
3426 Unit* unitCaster = GetUnitCasterForEffectHandlers();
3427
3431 {
3433 {
3434 switch (m_spellInfo->Id)
3435 {
3436 // Shadow Flame (All script effects, not just end ones to prevent player from dodging the last triggered spell)
3437 case 22539:
3438 case 22972:
3439 case 22975:
3440 case 22976:
3441 case 22977:
3442 case 22978:
3443 case 22979:
3444 case 22980:
3445 case 22981:
3446 case 22982:
3447 case 22983:
3448 case 22984:
3449 case 22985:
3450 {
3451 if (!unitTarget || !unitTarget->IsAlive())
3452 return;
3453
3454 // Onyxia Scale Cloak
3455 if (unitTarget->HasAura(22683))
3456 return;
3457
3458 // Shadow Flame
3459 m_caster->CastSpell(unitTarget, 22682, true);
3460 return;
3461 }
3462 // Mug Transformation
3463 case 41931:
3464 {
3466 return;
3467
3468 uint8 bag = 19;
3469 uint8 slot = 0;
3470 Item* item = nullptr;
3471
3472 while (bag) // 256 = 0 due to var type
3473 {
3474 item = m_caster->ToPlayer()->GetItemByPos(bag, slot);
3475 if (item && item->GetEntry() == 38587)
3476 break;
3477
3478 ++slot;
3479 if (slot == 39)
3480 {
3481 slot = 0;
3482 ++bag;
3483 }
3484 }
3485 if (bag)
3486 {
3487 if (m_caster->ToPlayer()->GetItemByPos(bag, slot)->GetCount() == 1) m_caster->ToPlayer()->RemoveItem(bag, slot, true);
3488 else m_caster->ToPlayer()->GetItemByPos(bag, slot)->SetCount(m_caster->ToPlayer()->GetItemByPos(bag, slot)->GetCount()-1);
3489 // Spell 42518 (Braufest - Gratisprobe des Braufest herstellen)
3490 m_caster->CastSpell(m_caster, 42518, true);
3491 return;
3492 }
3493 break;
3494 }
3495 // Brutallus - Burn
3496 case 45141:
3497 case 45151:
3498 {
3499 //Workaround for Range ... should be global for every ScriptEffect
3500 float radius = effectInfo->CalcRadius();
3502 unitTarget->CastSpell(unitTarget, 46394, true);
3503
3504 break;
3505 }
3506 // Summon Ghouls On Scarlet Crusade
3507 case 51904:
3508 {
3509 if (!m_targets.HasDst())
3510 return;
3511
3512 float radius = effectInfo->CalcRadius();
3513 for (uint8 i = 0; i < 15; ++i)
3514 m_caster->CastSpell(m_caster->GetRandomPoint(*destTarget, radius), 54522, true);
3515 break;
3516 }
3517 case 52173: // Coyote Spirit Despawn
3518 case 60243: // Blood Parrot Despawn
3521 return;
3522 case 57347: // Retrieving (Wintergrasp RP-GG pickup spell)
3523 {
3525 return;
3526
3528
3529 return;
3530 }
3531 case 57349: // Drop RP-GG (Wintergrasp RP-GG at death drop spell)
3532 {
3534 return;
3535
3536 // Delete item from inventory at death
3538
3539 return;
3540 }
3541 case 62482: // Grab Crate
3542 {
3543 if (!unitCaster)
3544 return;
3545
3546 if (unitTarget)
3547 {
3548 if (Unit* seat = unitCaster->GetVehicleBase())
3549 {
3550 if (Unit* parent = seat->GetVehicleBase())
3551 {
3553 unitCaster->CastSpell(parent, 62496, true);
3555 }
3556 }
3557 }
3558 return;
3559 }
3560 }
3561 break;
3562 }
3563 }
3564}
3565
3567{
3569 return;
3570
3571 if (!unitTarget)
3572 return;
3573
3575 {
3576 // stop all pve combat for players outside dungeons, suppress pvp combat
3577 unitTarget->CombatStop(false, false);
3578 }
3579 else
3580 {
3581 // in dungeons (or for nonplayers), reset this unit on all enemies' threat lists
3582 for (auto const& pair : unitTarget->GetThreatManager().GetThreatenedByMeList())
3583 pair.second->ScaleThreat(0.0f);
3584 }
3585
3586 // makes spells cast before this time fizzle
3588}
3589
3591{
3593 return;
3594
3595 if (!unitTarget)
3596 return;
3597
3598 if (damage <= 0)
3599 return;
3600
3602}
3603
3605{
3607 return;
3608
3610 return;
3611
3612 Player* caster = m_caster->ToPlayer();
3613 Player* target = unitTarget->ToPlayer();
3614
3615 // caster or target already have requested duel
3616 if (caster->duel || target->duel || !target->GetSocial() || target->GetSocial()->HasIgnore(caster->GetGUID()))
3617 return;
3618
3619 // Players can only fight a duel in zones with this flag
3620 AreaTableEntry const* casterAreaEntry = sAreaTableStore.LookupEntry(caster->GetAreaId());
3621 if (casterAreaEntry && !(casterAreaEntry->Flags & AREA_FLAG_ALLOW_DUELS))
3622 {
3623 SendCastResult(SPELL_FAILED_NO_DUELING); // Dueling isn't allowed here
3624 return;
3625 }
3626
3627 AreaTableEntry const* targetAreaEntry = sAreaTableStore.LookupEntry(target->GetAreaId());
3628 if (targetAreaEntry && !(targetAreaEntry->Flags & AREA_FLAG_ALLOW_DUELS))
3629 {
3630 SendCastResult(SPELL_FAILED_NO_DUELING); // Dueling isn't allowed here
3631 return;
3632 }
3633
3634 //CREATE DUEL FLAG OBJECT
3635 GameObject* pGameObj = new GameObject;
3636
3637 uint32 gameobject_id = effectInfo->MiscValue;
3638
3639 Position const pos =
3640 {
3641 caster->GetPositionX() + (unitTarget->GetPositionX() - caster->GetPositionX()) / 2,
3642 caster->GetPositionY() + (unitTarget->GetPositionY() - caster->GetPositionY()) / 2,
3643 caster->GetPositionZ(),
3644 caster->GetOrientation()
3645 };
3646
3647 Map* map = caster->GetMap();
3649 if (!pGameObj->Create(map->GenerateLowGuid<HighGuid::GameObject>(), gameobject_id, map, caster->GetPhaseMask(), pos, rot, 0, GO_STATE_READY))
3650 {
3651 delete pGameObj;
3652 return;
3653 }
3654
3655 pGameObj->SetFaction(caster->GetFaction());
3656 pGameObj->SetLevel(caster->GetLevel() + 1);
3657 int32 duration = m_spellInfo->GetDuration();
3658 pGameObj->SetRespawnTime(duration > 0 ? duration/IN_MILLISECONDS : 0);
3659 pGameObj->SetSpellId(m_spellInfo->Id);
3660
3662
3663 caster->AddGameObject(pGameObj);
3664 map->AddToMap(pGameObj);
3665 //END
3666
3667 // Send request
3668 WorldPacket data(SMSG_DUEL_REQUESTED, 8 + 8);
3669 data << pGameObj->GetGUID();
3670 data << caster->GetGUID();
3671 caster->SendDirectMessage(&data);
3672 target->SendDirectMessage(&data);
3673
3674 // create duel-info
3675 bool isMounted = (GetSpellInfo()->Id == 62875);
3676 caster->duel = std::make_unique<DuelInfo>(target, caster, isMounted);
3677 target->duel = std::make_unique<DuelInfo>(caster, caster, isMounted);
3678
3679 caster->SetGuidValue(PLAYER_DUEL_ARBITER, pGameObj->GetGUID());
3680 target->SetGuidValue(PLAYER_DUEL_ARBITER, pGameObj->GetGUID());
3681
3682 sScriptMgr->OnPlayerDuelRequest(target, caster);
3683}
3684
3686{
3688 return;
3689
3690 if (!sWorld->getBoolConfig(CONFIG_CAST_UNSTUCK))
3691 return;
3692
3693 Player* player = m_caster->ToPlayer();
3694 if (!player)
3695 return;
3696
3697 TC_LOG_DEBUG("spells", "Spell Effect: Stuck");
3698 TC_LOG_DEBUG("spells", "Player {} {} used the auto-unstuck feature at map {} ({}, {}, {}).", player->GetName(), player->GetGUID().ToString(), player->GetMapId(), player->GetPositionX(), player->GetPositionY(), player->GetPositionZ());
3699
3700 if (player->IsInFlight())
3701 return;
3702
3703 // if player is dead - teleport to graveyard
3704 if (!player->IsAlive())
3705 {
3707 return;
3708
3709 // player is in corpse
3711 player->BuildPlayerRepop();
3712 player->RepopAtGraveyard();
3713 return;
3714 }
3715
3716 // no hearthstone in bag or on cooldown
3717 Item* hearthStone = player->GetItemByEntry(6948 /*Hearthstone*/);
3718 if (!hearthStone || player->GetSpellHistory()->HasCooldown(8690 /*Spell Hearthstone*/))
3719 {
3720 float o = rand_norm() * 2 * M_PI;
3721 Position pos = *player;
3722 player->MovePositionToFirstCollision(pos, 5.0f, o);
3723 player->NearTeleportTo(pos.GetPositionX(), pos.GetPositionY(), pos.GetPositionZ(), player->GetOrientation());
3724 return;
3725 }
3726
3727 // we have hearthstone not on cooldown, just use it
3729}
3730
3732{
3733 // workaround - this effect should not use target map
3735 return;
3736
3737 Unit* unitCaster = GetUnitCasterForEffectHandlers();
3738 if (!unitCaster)
3739 return;
3740
3742 return;
3743
3745}
3746
3759
3761{
3763 return;
3764
3765 if (m_misc.GlyphSlot >= MAX_GLYPH_SLOT_INDEX)
3766 return;
3767
3768 Player* player = m_caster->ToPlayer();
3769 if (!player)
3770 return;
3771
3772 // glyph sockets level requirement
3773 uint8 minLevel = 0;
3774 switch (m_misc.GlyphSlot)
3775 {
3776 case 0:
3777 case 1: minLevel = 15; break;
3778 case 2: minLevel = 50; break;
3779 case 3: minLevel = 30; break;
3780 case 4: minLevel = 70; break;
3781 case 5: minLevel = 80; break;
3782 }
3783 if (minLevel && player->GetLevel() < minLevel)
3784 {
3786 return;
3787 }
3788
3789 // apply new one
3790 if (uint32 newGlyph = effectInfo->MiscValue)
3791 {
3792 if (GlyphPropertiesEntry const* newGlyphProperties = sGlyphPropertiesStore.LookupEntry(newGlyph))
3793 {
3794 if (GlyphSlotEntry const* newGlyphSlot = sGlyphSlotStore.LookupEntry(player->GetGlyphSlot(m_misc.GlyphSlot)))
3795 {
3796 if (newGlyphProperties->GlyphSlotFlags != newGlyphSlot->Type)
3797 {
3799 return; // glyph slot mismatch
3800 }
3801 }
3802
3803 // remove old glyph
3804 if (uint32 oldGlyph = player->GetGlyph(player->GetActiveTalentGroup(), m_misc.GlyphSlot))
3805 {
3806 if (GlyphPropertiesEntry const* oldGlyphProperties = sGlyphPropertiesStore.LookupEntry(oldGlyph))
3807 {
3808 player->RemoveAurasDueToSpell(oldGlyphProperties->SpellID);
3809 player->SetGlyph(m_misc.GlyphSlot, 0);
3810 }
3811 }
3812
3813 player->CastSpell(player, newGlyphProperties->SpellID, true);
3814 player->SetGlyph(m_misc.GlyphSlot, newGlyph);
3815 player->SendTalentsInfoData(false);
3816 }
3817 }
3818}
3819
3821{
3823 return;
3824
3825 // this is only item spell effect applied to main-hand weapon of target player (players in area)
3827 return;
3828
3829 Player* item_owner = unitTarget->ToPlayer();
3831
3832 if (!item)
3833 return;
3834
3835 // must be equipped
3836 if (!item->IsEquipped())
3837 return;
3838
3839 if (effectInfo->MiscValue)
3840 {
3841 uint32 enchant_id = effectInfo->MiscValue;
3842 int32 duration = m_spellInfo->GetDuration(); // Try duration index first ..
3843 if (!duration)
3844 duration = damage;//+1; // Base points after ..
3845 if (!duration)
3846 duration = 10 * IN_MILLISECONDS; // 10 seconds for enchants which don't have listed duration
3847
3848 if (m_spellInfo->Id == 14792) // Venomhide Poison
3849 duration = 5 * MINUTE * IN_MILLISECONDS;
3850
3851 SpellItemEnchantmentEntry const* pEnchant = sSpellItemEnchantmentStore.LookupEntry(enchant_id);
3852 if (!pEnchant)
3853 return;
3854
3855 // Always go to temp enchantment slot
3857
3858 // Enchantment will not be applied if a different one already exists
3859 if (item->GetEnchantmentId(slot) && item->GetEnchantmentId(slot) != enchant_id)
3860 return;
3861
3862 // Apply the temporary enchantment
3863 item->SetEnchantment(slot, enchant_id, duration, 0, m_caster->GetGUID());
3864 item_owner->ApplyEnchantment(item, slot, true);
3865 }
3866}
3867
3869{
3871 return;
3872
3874 return;
3875
3876 if (Player* caster = m_caster->ToPlayer())
3877 {
3878 caster->UpdateCraftSkill(m_spellInfo->Id);
3879 caster->SendLoot(itemTarget->GetGUID(), LOOT_DISENCHANTING);
3880 }
3881
3882 // item will be removed at disenchanting end
3883}
3884
3886{
3888 return;
3889
3890 if (!unitTarget || !unitTarget->IsPlayer())
3891 return;
3892
3893 Player* player = unitTarget->ToPlayer();
3894 uint8 currentDrunk = player->GetDrunkValue();
3895 int32 drunkMod = damage;
3896
3897 if (drunkMod == 0)
3898 return;
3899
3900 // drunkMod may contain values that are guaranteed to cause uint8 overflow/underflow (examples: 29690, 46874)
3901 // In addition, we would not want currentDrunk to become more than 100.
3902 // So before adding the values, let's check that everything is fine.
3903 if (drunkMod > static_cast<int32>(100 - currentDrunk))
3904 currentDrunk = 100;
3905 else if (drunkMod < static_cast<int32>(0 - currentDrunk))
3906 currentDrunk = 0;
3907 else
3908 currentDrunk += drunkMod; // Due to previous checks we can be sure that currentDrunk will not go beyond [0-100] range.
3909
3910 player->SetDrunkValue(currentDrunk, m_CastItem ? m_CastItem->GetEntry() : 0);
3911
3912 if (currentDrunk == 100 && drunkMod > 0 && roll_chance_i(25))
3913 player->CastSpell(player, 67468, false); // Drunken Vomit
3914}
3915
3917{
3919 return;
3920
3921 Player* player = m_caster->ToPlayer();
3922 if (!player)
3923 return;
3924
3925 Item* foodItem = itemTarget;
3926 if (!foodItem)
3927 return;
3928
3929 Pet* pet = player->GetPet();
3930 if (!pet)
3931 return;
3932
3933 if (!pet->IsAlive())
3934 return;
3935
3936 int32 benefit = pet->GetCurrentFoodBenefitLevel(foodItem->GetTemplate()->GetBaseItemLevel());
3937 if (benefit <= 0)
3938 return;
3939
3941
3942 uint32 count = 1;
3943 player->DestroyItemCount(foodItem, count, true);
3945
3947 args.AddSpellMod(SPELLVALUE_BASE_POINT0, benefit);
3949}
3950
3952{
3954 return;
3955
3956 if (!unitTarget || !unitTarget->IsPet())
3957 return;
3958
3959 Pet* pet = unitTarget->ToPet();
3960
3963}
3964
3966{
3968 return;
3969
3970 Unit* unitCaster = GetUnitCasterForEffectHandlers();
3971 if (!unitCaster)
3972 return;
3973
3974 uint32 go_id = effectInfo->MiscValue;
3976
3977 ObjectGuid guid = unitCaster->m_ObjectSlot[slot];
3978 if (!guid.IsEmpty())
3979 {
3980 if (GameObject* obj = unitCaster->GetMap()->GetGameObject(guid))
3981 {
3982 // Recast case - null spell id to make auras not be removed on object remove from world
3983 if (m_spellInfo->Id == obj->GetSpellId())
3984 obj->SetSpellId(0);
3985 unitCaster->RemoveGameObject(obj, true);
3986 }
3987 unitCaster->m_ObjectSlot[slot].Clear();
3988 }
3989
3990 GameObject* go = new GameObject();
3991 float x, y, z;
3992 // If dest location if present
3993 if (m_targets.HasDst())
3994 destTarget->GetPosition(x, y, z);
3995 // Summon in random point all other units if location present
3996 else
3997 unitCaster->GetClosePoint(x, y, z, DEFAULT_PLAYER_BOUNDING_RADIUS);
3998
3999 Map* map = unitCaster->GetMap();
4001 if (!go->Create(map->GenerateLowGuid<HighGuid::GameObject>(), go_id, map, unitCaster->GetPhaseMask(), Position(x, y, z, unitCaster->GetOrientation()), rot, 255, GO_STATE_READY))
4002 {
4003 delete go;
4004 return;
4005 }
4006
4007 go->SetFaction(unitCaster->GetFaction());
4008 go->SetLevel(unitCaster->GetLevel());
4009 int32 duration = m_spellInfo->GetDuration();
4010 go->SetRespawnTime(duration > 0 ? duration / IN_MILLISECONDS : 0);
4012 unitCaster->AddGameObject(go);
4013
4015
4016 map->AddToMap(go);
4017
4018 unitCaster->m_ObjectSlot[slot] = go->GetGUID();
4019}
4020
4022{
4024 return;
4025
4026 if (!m_corpseTarget && !unitTarget)
4027 return;
4028
4029 Player* player = nullptr;
4030
4031 if (m_corpseTarget)
4033 else if (unitTarget)
4034 player = unitTarget->ToPlayer();
4035
4036 if (!player || player->IsAlive() || !player->IsInWorld())
4037 return;
4038
4039 if (player->IsResurrectRequested()) // already have one active request
4040 return;
4041
4042 uint32 health = player->CountPctFromMaxHealth(damage);
4044
4046
4047 player->SetResurrectRequestData(m_caster, health, mana, 0);
4048 SendResurrectRequest(player);
4049}
4050
4063
4065{
4067 return;
4068
4070 m_caster->ToPlayer()->SetCanParry(true);
4071}
4072
4074{
4076 return;
4077
4079 m_caster->ToPlayer()->SetCanBlock(true);
4080}
4081
4083{
4085 return;
4086
4087 if (!unitTarget || unitTarget->IsInFlight())
4088 return;
4089
4090 if (!m_targets.HasDst())
4091 return;
4092
4095}
4096
4098{
4100 return;
4101
4103 return;
4104
4105 Player* player = unitTarget->ToPlayer();
4106
4107 int32 repChange = damage;
4108
4109 uint32 factionId = effectInfo->MiscValue;
4110
4111 FactionEntry const* factionEntry = sFactionStore.LookupEntry(factionId);
4112 if (!factionEntry)
4113 return;
4114
4115 repChange = player->CalculateReputationGain(REPUTATION_SOURCE_SPELL, 0, repChange, factionId);
4116
4117 player->GetReputationMgr().ModifyReputation(factionEntry, repChange);
4118}
4119
4121{
4123 return;
4124
4126 return;
4127 Player* player = unitTarget->ToPlayer();
4128
4129 uint32 questId = effectInfo->MiscValue;
4130 if (questId)
4131 {
4132 Quest const* quest = sObjectMgr->GetQuestTemplate(questId);
4133 if (!quest)
4134 return;
4135
4136 uint16 logSlot = player->FindQuestSlot(questId);
4137 if (logSlot < MAX_QUEST_LOG_SIZE)
4138 player->AreaExploredOrEventHappens(questId);
4139 else if (quest->HasFlag(QUEST_FLAGS_TRACKING)) // Check if the quest is used as a serverside flag.
4140 player->SetRewardedQuest(questId); // If so, set status to rewarded without broadcasting it to client.
4141 }
4142}
4143
4145{
4147 return;
4148
4149 Unit* unitCaster = GetUnitCasterForEffectHandlers();
4150 if (!unitCaster)
4151 return;
4152
4153 float dist = unitCaster->GetVisibilityRange();
4154
4155 // clear focus
4156 WorldPacket data(SMSG_BREAK_TARGET, unitCaster->GetPackGUID().size());
4157 data << unitCaster->GetPackGUID();
4158 Trinity::MessageDistDelivererToHostile notifierBreak(unitCaster, &data, dist);
4159 Cell::VisitWorldObjects(unitCaster, notifierBreak, dist);
4160
4161 // and selection
4163 data << unitCaster->GetGUID();
4164 Trinity::MessageDistDelivererToHostile notifierClear(unitCaster, &data, dist);
4165 Cell::VisitWorldObjects(unitCaster, notifierClear, dist);
4166
4167 // we should also force pets to remove us from current target
4168 Unit::AttackerSet attackerSet;
4169 for (Unit::AttackerSet::const_iterator itr = unitCaster->getAttackers().begin(); itr != unitCaster->getAttackers().end(); ++itr)
4170 if ((*itr)->GetTypeId() == TYPEID_UNIT && !(*itr)->CanHaveThreatList())
4171 attackerSet.insert(*itr);
4172
4173 for (Unit::AttackerSet::const_iterator itr = attackerSet.begin(); itr != attackerSet.end(); ++itr)
4174 (*itr)->AttackStop();
4175}
4176
4178{
4180 return;
4181
4182 Player* player = m_caster->ToPlayer();
4183 if (!player || !player->IsInWorld() || player->IsAlive())
4184 return;
4185
4186 uint32 health = 0;
4187 uint32 mana = 0;
4188
4189 // flat case
4190 if (damage < 0)
4191 {
4192 health = uint32(-damage);
4193 mana = effectInfo->MiscValue;
4194 }
4195 // percent case
4196 else
4197 {
4198 health = player->CountPctFromMaxHealth(damage);
4199 if (player->GetMaxPower(POWER_MANA) > 0)
4200 mana = CalculatePct(player->GetMaxPower(POWER_MANA), damage);
4201 }
4202
4203 player->ResurrectPlayer(0.0f);
4204
4205 player->SetHealth(health);
4206 player->SetPower(POWER_MANA, mana);
4207 player->SetPower(POWER_RAGE, 0);
4208 player->SetPower(POWER_ENERGY, player->GetMaxPower(POWER_ENERGY));
4209
4210 player->SpawnCorpseBones();
4211}
4212
4214{
4216 return;
4217
4219 return;
4220
4221 Player* player = m_caster->ToPlayer();
4222 if (!player)
4223 return;
4224
4225 Creature* creature = unitTarget->ToCreature();
4226 int32 targetLevel = creature->GetLevel();
4227
4228 uint32 skill = creature->GetCreatureTemplate()->GetRequiredLootSkill();
4229
4232 player->SendLoot(creature->GetGUID(), LOOT_SKINNING);
4233
4234 int32 const reqValue = targetLevel < 10 ? 0 : (targetLevel < 20 ? (targetLevel - 10) * 10 : targetLevel * 5);
4235 int32 const skillValue = player->GetPureSkillValue(skill);
4236
4237 // Double chances for elites
4238 player->UpdateGatherSkill(skill, skillValue, reqValue, creature->isElite() ? 2 : 1);
4239}
4240
4242{
4243 if (!unitTarget)
4244 return;
4245
4246 Unit* unitCaster = GetUnitCasterForEffectHandlers();
4247 if (!unitCaster)
4248 return;
4249
4251 {
4252 // charge changes fall time
4253 if (unitCaster->GetTypeId() == TYPEID_PLAYER)
4254 unitCaster->ToPlayer()->SetFallInformation(0, unitCaster->GetPositionZ());
4255
4256 float speed = G3D::fuzzyGt(m_spellInfo->Speed, 0.0f) ? m_spellInfo->Speed : SPEED_CHARGE;
4257 // Spell is not using explicit target - no generated path
4258 if (!m_preGeneratedPath)
4259 {
4260 //unitTarget->GetContactPoint(m_caster, pos.m_positionX, pos.m_positionY, pos.m_positionZ);
4262 unitCaster->GetMotionMaster()->MoveCharge(pos.m_positionX, pos.m_positionY, pos.m_positionZ, speed);
4263 }
4264 else
4265 unitCaster->GetMotionMaster()->MoveCharge(*m_preGeneratedPath, speed);
4266 }
4267
4269 {
4270 // not all charge effects used in negative spells
4272 unitCaster->Attack(unitTarget, true);
4273 }
4274}
4275
4277{
4279 return;
4280
4281 Unit* unitCaster = GetUnitCasterForEffectHandlers();
4282 if (!unitCaster)
4283 return;
4284
4285 if (m_targets.HasDst())
4286 {
4288
4289 if (!unitCaster->IsWithinLOS(pos.GetPositionX(), pos.GetPositionY(), pos.GetPositionZ()))
4290 {
4291 float angle = unitCaster->GetRelativeAngle(pos.GetPositionX(), pos.GetPositionY());
4292 float dist = unitCaster->GetDistance(pos);
4293 pos = unitCaster->GetFirstCollisionPosition(dist, angle);
4294 }
4295
4296 unitCaster->GetMotionMaster()->MoveCharge(pos.m_positionX, pos.m_positionY, pos.m_positionZ);
4297 }
4298}
4299
4301{
4303 return;
4304
4305 if (!unitTarget)
4306 return;
4307
4309 if (Creature* creatureTarget = unitTarget->ToCreature())
4310 if (creatureTarget->isWorldBoss() || creatureTarget->IsDungeonBoss())
4311 return;
4312
4313 // Spells with SPELL_EFFECT_KNOCK_BACK (like Thunderstorm) can't knockback target if target has ROOT
4315 return;
4316
4317 float ratio = 0.1f;
4318 float speedxy = float(effectInfo->MiscValue) * ratio;
4319 float speedz = float(damage) * ratio;
4320 if (speedxy < 0.01f && speedz < 0.01f)
4321 return;
4322
4323 float x, y;
4325 {
4326 if (m_targets.HasDst())
4327 destTarget->GetPosition(x, y);
4328 else
4329 return;
4330 }
4331 else //if (m_spellInfo->Effects[i].Effect == SPELL_EFFECT_KNOCK_BACK)
4332 m_caster->GetPosition(x, y);
4333
4334 unitTarget->KnockbackFrom(x, y, speedxy, speedz);
4335}
4336
4338{
4340 return;
4341
4342 if (!unitTarget)
4343 return;
4344
4345 float speedxy = effectInfo->MiscValue / 10.f;
4346 float speedz = damage/ 10.f;
4347 //1891: Disengage
4348 unitTarget->JumpTo(speedxy, speedz, m_spellInfo->SpellIconID != 1891);
4349
4350 // changes fall time
4353}
4354
4356{
4358 return;
4359
4361 return;
4362 Player* player = unitTarget->ToPlayer();
4363
4364 uint32 quest_id = effectInfo->MiscValue;
4365
4366 Quest const* quest = sObjectMgr->GetQuestTemplate(quest_id);
4367
4368 if (!quest)
4369 return;
4370
4371 // Player has never done this quest
4372 if (player->GetQuestStatus(quest_id) == QUEST_STATUS_NONE)
4373 return;
4374
4375 // remove all quest entries for 'entry' from quest log
4376 for (uint8 slot = 0; slot < MAX_QUEST_LOG_SIZE; ++slot)
4377 {
4378 uint32 logQuest = player->GetQuestSlotQuestId(slot);
4379 if (logQuest == quest_id)
4380 {
4381 player->SetQuestSlot(slot, 0);
4382
4383 // we ignore unequippable quest items in this case, it's still be equipped
4384 player->TakeQuestSourceItem(logQuest, false);
4385
4386 if (quest->HasFlag(QUEST_FLAGS_FLAGS_PVP))
4387 {
4388 player->pvpInfo.IsHostile = player->pvpInfo.IsInHostileArea || player->HasPvPForcingQuest();
4389 player->UpdatePvPState();
4390 }
4391 }
4392 }
4393
4394 player->RemoveActiveQuest(quest_id, false);
4395 player->RemoveRewardedQuest(quest_id);
4396
4397 sScriptMgr->OnQuestStatusChange(player, quest_id);
4398}
4399
4410
4412{
4414 return;
4415
4416 if (!unitTarget)
4417 return;
4418
4420
4421 // This is a blizzlike mistake: this should be 2D distance according to projectile motion formulas, but Blizzard erroneously used 3D distance.
4422 float distXY = unitTarget->GetExactDist(pos);
4423
4424 // Avoid division by 0
4425 if (distXY < 0.001)
4426 return;
4427
4428 float distZ = pos.GetPositionZ() - unitTarget->GetPositionZ();
4429 float speedXY = effectInfo->MiscValue ? effectInfo->MiscValue / 10.0f : 30.0f;
4430 float speedZ = (2 * speedXY * speedXY * distZ + Movement::gravity * distXY * distXY) / (2 * speedXY * distXY);
4431
4432 if (!std::isfinite(speedZ))
4433 {
4434 TC_LOG_ERROR("spells", "Spell {} with SPELL_EFFECT_PULL_TOWARDS called with invalid speedZ. {}", m_spellInfo->Id, GetDebugInfo());
4435 return;
4436 }
4437
4438 unitTarget->JumpTo(speedXY, speedZ, true, pos);
4439}
4440
4442{
4444 return;
4445
4446 if (!unitTarget)
4447 return;
4448
4449 if (!m_targets.HasDst())
4450 {
4451 TC_LOG_ERROR("spells", "Spell {} with SPELL_EFFECT_PULL_TOWARDS_DEST has no dest target", m_spellInfo->Id);
4452 return;
4453 }
4454
4455 Position const* pos = m_targets.GetDstPos();
4456 // This is a blizzlike mistake: this should be 2D distance according to projectile motion formulas, but Blizzard erroneously used 3D distance
4457 float distXY = unitTarget->GetExactDist(pos);
4458
4459 // Avoid division by 0
4460 if (distXY < 0.001)
4461 return;
4462
4463 float distZ = pos->GetPositionZ() - unitTarget->GetPositionZ();
4464
4465 float speedXY = effectInfo->MiscValue ? effectInfo->MiscValue / 10.0f : 30.0f;
4466 float speedZ = (2 * speedXY * speedXY * distZ + Movement::gravity * distXY * distXY) / (2 * speedXY * distXY);
4467
4468 if (!std::isfinite(speedZ))
4469 {
4470 TC_LOG_ERROR("spells", "Spell {} with SPELL_EFFECT_PULL_TOWARDS_DEST called with invalid speedZ. {}", m_spellInfo->Id, GetDebugInfo());
4471 return;
4472 }
4473
4474 unitTarget->JumpTo(speedXY, speedZ, true, *pos);
4475}
4476
4478{
4480 return;
4481
4482 if (!unitTarget)
4483 return;
4484
4485 uint32 mechanic = effectInfo->MiscValue;
4486 DispelList dispel_list;
4487 Unit::AuraMap const& auras = unitTarget->GetOwnedAuras();
4488 for (Unit::AuraMap::const_iterator itr = auras.begin(); itr != auras.end(); ++itr)
4489 {
4490 Aura* aura = itr->second;
4492 continue;
4494 if ((aura->GetSpellInfo()->GetAllEffectsMechanicMask() & (1 << mechanic)))
4495 dispel_list.emplace_back(aura->GetId(), aura->GetCasterGUID());
4496 }
4497
4498 for (auto itr = dispel_list.begin(); itr != dispel_list.end(); ++itr)
4499 unitTarget->RemoveAura(itr->first, itr->second, 0, AURA_REMOVE_BY_ENEMY_SPELL);
4500}
4501
4503{
4505 return;
4506
4507 if (damage < 0)
4508 return;
4509
4510 Player* player = m_caster->ToPlayer();
4511 if (!player)
4512 return;
4513
4514 // Maybe player dismissed dead pet or pet despawned?
4515 bool hadPet = true;
4516
4517 if (!player->GetPet())
4518 {
4519 // Position passed to SummonPet is irrelevant with current implementation,
4520 // pet will be relocated without using these coords in Pet::LoadPetFromDB
4521 player->SummonPet(0, 0.0f, 0.0f, 0.0f, 0.0f, SUMMON_PET, 0);
4522 hadPet = false;
4523 }
4524
4525 // TODO: Better to fail Hunter's "Revive Pet" at cast instead of here when casting ends
4526 Pet* pet = player->GetPet(); // Attempt to get current pet
4527 if (!pet || pet->IsAlive())
4528 return;
4529
4530 // If player did have a pet before reviving, teleport it
4531 if (hadPet)
4532 {
4533 // Reposition the pet's corpse before reviving so as not to grab aggro
4534 // We can use a different, more accurate version of GetClosePoint() since we have a pet
4535 float x, y, z; // Will be used later to reposition the pet if we have one
4536 player->GetClosePoint(x, y, z, pet->GetCombatReach(), PET_FOLLOW_DIST, pet->GetFollowAngle());
4537 pet->NearTeleportTo(x, y, z, player->GetOrientation());
4538 pet->Relocate(x, y, z, player->GetOrientation()); // This is needed so SaveStayPosition() will get the proper coords.
4539 }
4540
4543 pet->setDeathState(ALIVE);
4546
4547 // Reset things for when the AI to takes over
4548 CharmInfo *ci = pet->GetCharmInfo();
4549 if (ci)
4550 {
4551 // In case the pet was at stay, we don't want it running back
4552 ci->SaveStayPosition();
4554
4555 ci->SetIsFollowing(false);
4556 ci->SetIsCommandAttack(false);
4557 ci->SetIsCommandFollow(false);
4558 ci->SetIsReturning(false);
4559 }
4560
4562}
4563
4565{
4567 return;
4568
4569 Unit* unitCaster = GetUnitCasterForEffectHandlers();
4570 if (!unitCaster)
4571 return;
4572
4573 int32 mana = 0;
4574 for (uint8 slot = SUMMON_SLOT_TOTEM_FIRE; slot < MAX_TOTEM_SLOT; ++slot)
4575 {
4576 if (!unitCaster->m_SummonSlot[slot])
4577 continue;
4578
4579 Creature* totem = unitCaster->GetMap()->GetCreature(unitCaster->m_SummonSlot[slot]);
4580 if (totem && totem->IsTotem())
4581 {
4582 uint32 spell_id = totem->GetUInt32Value(UNIT_CREATED_BY_SPELL);
4583 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spell_id);
4584 if (spellInfo)
4585 {
4586 mana += spellInfo->ManaCost;
4587 mana += int32(CalculatePct(unitCaster->GetCreateMana(), spellInfo->ManaCostPercentage));
4588 }
4589 totem->ToTotem()->UnSummon();
4590 }
4591 }
4592 ApplyPct(mana, damage);
4593 if (mana)
4594 {
4597 unitCaster->CastSpell(unitCaster, 39104, args);
4598 }
4599}
4600
4602{
4604 return;
4605
4607 return;
4608
4609 int32 slot = effectInfo->MiscValue;
4610
4611 // -1 means all player equipped items and -2 all items
4612 if (slot < 0)
4613 {
4616 return;
4617 }
4618
4619 // invalid slot value
4620 if (slot >= INVENTORY_SLOT_BAG_END)
4621 return;
4622
4624 {
4627 }
4628}
4629
4631{
4633 return;
4634
4636 return;
4637
4638 int32 slot = effectInfo->MiscValue;
4639
4640 // FIXME: some spells effects have value -1/-2
4641 // Possibly its mean -1 all player equipped items and -2 all items
4642 if (slot < 0)
4643 {
4644 unitTarget->ToPlayer()->DurabilityLossAll(float(damage) / 100.0f, (slot < -1));
4645 return;
4646 }
4647
4648 // invalid slot value
4649 if (slot >= INVENTORY_SLOT_BAG_END)
4650 return;
4651
4652 if (damage <= 0)
4653 return;
4654
4656 unitTarget->ToPlayer()->DurabilityLoss(item, float(damage) / 100.0f);
4657}
4658
4660{
4662 return;
4663
4664 Unit* unitCaster = GetUnitCasterForEffectHandlers();
4665 if (!unitCaster || !unitTarget)
4666 return;
4667
4669}
4670
4672{
4674 return;
4675
4676 Unit* unitCaster = GetUnitCasterForEffectHandlers();
4677 if (!unitCaster)
4678 return;
4679
4680 uint32 name_id = effectInfo->MiscValue;
4681 GameObjectTemplate const* goinfo = sObjectMgr->GetGameObjectTemplate(name_id);
4682 if (!goinfo)
4683 {
4684 TC_LOG_ERROR("sql.sql", "Gameobject (Entry: {}) does not exist and is not created by spell (ID: {}) cast.", name_id, m_spellInfo->Id);
4685 return;
4686 }
4687
4688 float fx, fy, fz;
4689
4690 if (m_targets.HasDst())
4691 destTarget->GetPosition(fx, fy, fz);
4692 //FIXME: this can be better check for most objects but still hack
4693 else if (effectInfo->HasRadius() && m_spellInfo->Speed == 0)
4694 {
4695 float dis = effectInfo->CalcRadius(unitCaster);
4696 unitCaster->GetClosePoint(fx, fy, fz, DEFAULT_PLAYER_BOUNDING_RADIUS, dis);
4697 }
4698 else
4699 {
4700 //GO is always friendly to it's creator, get range for friends
4701 float min_dis = m_spellInfo->GetMinRange(true);
4702 float max_dis = m_spellInfo->GetMaxRange(true);
4703 float dis = (float)rand_norm() * (max_dis - min_dis) + min_dis;
4704
4705 unitCaster->GetClosePoint(fx, fy, fz, DEFAULT_PLAYER_BOUNDING_RADIUS, dis);
4706 }
4707
4708 Map* cMap = unitCaster->GetMap();
4709 // if gameobject is summoning object, it should be spawned right on caster's position
4710 if (goinfo->type == GAMEOBJECT_TYPE_RITUAL)
4711 unitCaster->GetPosition(fx, fy, fz);
4712
4713 GameObject* pGameObj = new GameObject;
4714
4715 Position pos = { fx, fy, fz, unitCaster->GetOrientation() };
4717 if (!pGameObj->Create(cMap->GenerateLowGuid<HighGuid::GameObject>(), name_id, cMap, unitCaster->GetPhaseMask(), pos, rot, 255, GO_STATE_READY))
4718 {
4719 delete pGameObj;
4720 return;
4721 }
4722
4723 int32 duration = m_spellInfo->GetDuration();
4724 switch (goinfo->type)
4725 {
4727 {
4728 unitCaster->SetChannelObjectGuid(pGameObj->GetGUID());
4729 unitCaster->AddGameObject(pGameObj); // will removed at spell cancel
4730
4731 // end time of range when possible catch fish (FISHING_BOBBER_READY_TIME..GetDuration(m_spellInfo))
4732 // start time == fish-FISHING_BOBBER_READY_TIME (0..GetDuration(m_spellInfo)-FISHING_BOBBER_READY_TIME)
4733 int32 lastSec = 0;
4734 switch (urand(0, 2))
4735 {
4736 case 0: lastSec = 3; break;
4737 case 1: lastSec = 7; break;
4738 case 2: lastSec = 13; break;
4739 }
4740
4741 // Duration of the fishing bobber can't be higher than the Fishing channeling duration
4742 duration = std::min(duration, duration - lastSec*IN_MILLISECONDS + FISHING_BOBBER_READY_TIME*IN_MILLISECONDS);
4743 break;
4744 }
4746 {
4747 if (unitCaster->GetTypeId() == TYPEID_PLAYER)
4748 {
4749 pGameObj->AddUniqueUse(unitCaster->ToPlayer());
4750 unitCaster->AddGameObject(pGameObj); // will be removed at spell cancel
4751 }
4752 break;
4753 }
4754 case GAMEOBJECT_TYPE_DUEL_ARBITER: // 52991
4755 unitCaster->AddGameObject(pGameObj);
4756 break;
4759 default:
4760 break;
4761 }
4762
4763 pGameObj->SetRespawnTime(duration > 0 ? duration/IN_MILLISECONDS : 0);
4764
4765 pGameObj->SetOwnerGUID(unitCaster->GetGUID());
4766
4767 //pGameObj->SetUInt32Value(GAMEOBJECT_LEVEL, unitCaster->GetLevel());
4768 pGameObj->SetSpellId(m_spellInfo->Id);
4769
4771
4772 TC_LOG_DEBUG("spells", "AddObject at SpellEfects.cpp EffectTransmitted");
4773 //unitCaster->AddGameObject(pGameObj);
4774 //m_ObjToDel.push_back(pGameObj);
4775
4776 cMap->AddToMap(pGameObj);
4777
4778 if (GameObject* linkedTrap = pGameObj->GetLinkedTrap())
4779 {
4780 linkedTrap->SetRespawnTime(duration > 0 ? duration/IN_MILLISECONDS : 0);
4781 //linkedTrap->SetUInt32Value(GAMEOBJECT_LEVEL, unitCaster->GetLevel());
4782 linkedTrap->SetSpellId(m_spellInfo->Id);
4783 linkedTrap->SetOwnerGUID(unitCaster->GetGUID());
4784
4786 }
4787}
4788
4790{
4792 return;
4793
4794 Player* player = m_caster->ToPlayer();
4795 if (!player)
4796 return;
4797
4799 return;
4800
4801 if (itemTarget->GetCount() < 5)
4802 return;
4803
4804 if (sWorld->getBoolConfig(CONFIG_SKILL_PROSPECTING))
4805 {
4806 uint32 SkillValue = player->GetPureSkillValue(SKILL_JEWELCRAFTING);
4807 uint32 reqSkillValue = itemTarget->GetTemplate()->GetRequiredSkillRank();
4808 player->UpdateGatherSkill(SKILL_JEWELCRAFTING, SkillValue, reqSkillValue);
4809 }
4810
4812}
4813
4815{
4817 return;
4818
4819 Player* player = m_caster->ToPlayer();
4820 if (!player)
4821 return;
4822
4824 return;
4825
4826 if (itemTarget->GetCount() < 5)
4827 return;
4828
4829 if (sWorld->getBoolConfig(CONFIG_SKILL_MILLING))
4830 {
4831 uint32 SkillValue = player->GetPureSkillValue(SKILL_INSCRIPTION);
4832 uint32 reqSkillValue = itemTarget->GetTemplate()->GetRequiredSkillRank();
4833 player->UpdateGatherSkill(SKILL_INSCRIPTION, SkillValue, reqSkillValue);
4834 }
4835
4837}
4838
4840{
4842 return;
4843
4844 TC_LOG_DEBUG("spells", "WORLD: SkillEFFECT");
4845}
4846
4847/* There is currently no need for this effect. We handle it in Battleground.cpp
4848 If we would handle the resurrection here, the spiritguide would instantly disappear as the
4849 player revives, and so we wouldn't see the spirit heal visual effect on the npc.
4850 This is why we use a half sec delay between the visual effect and the resurrection itself */
4852{
4854 return;
4855
4856 /*
4857 if (unitTarget->GetTypeId() != TYPEID_PLAYER)
4858 return;
4859 if (!unitTarget->IsInWorld())
4860 return;
4861
4862 //m_spellInfo->Effects[i].BasePoints; == 99 (percent?)
4863 //unitTarget->ToPlayer()->setResurrect(m_caster->GetGUID(), unitTarget->GetPositionX(), unitTarget->GetPositionY(), unitTarget->GetPositionZ(), unitTarget->GetMaxHealth(), unitTarget->GetMaxPower(POWER_MANA));
4864 unitTarget->ToPlayer()->ResurrectPlayer(1.0f);
4865 unitTarget->ToPlayer()->SpawnCorpseBones();
4866 */
4867}
4868
4869// remove insignia spell effect
4871{
4873 return;
4874
4875 TC_LOG_DEBUG("spells", "Effect: SkinPlayerCorpse");
4876
4877 Player* player = m_caster->ToPlayer();
4878
4879 Player* target = nullptr;
4880 if (unitTarget)
4881 target = unitTarget->ToPlayer();
4882 else if (m_corpseTarget)
4884
4885 if (!player || !target || target->IsAlive())
4886 return;
4887
4888 target->RemovedInsignia(player);
4889}
4890
4892{
4894 return;
4895
4896 TC_LOG_DEBUG("spells", "Effect: StealBeneficialBuff");
4897
4898 if (!unitTarget || unitTarget == m_caster) // can't steal from self
4899 return;
4900
4901 DispelChargesList stealList;
4902
4903 // Create dispel mask by dispel type
4905 Unit::AuraMap const& auras = unitTarget->GetOwnedAuras();
4906 for (Unit::AuraMap::const_iterator itr = auras.begin(); itr != auras.end(); ++itr)
4907 {
4908 Aura* aura = itr->second;
4909 AuraApplication const* aurApp = aura->GetApplicationOfTarget(unitTarget->GetGUID());
4910 if (!aurApp)
4911 continue;
4912
4913 if ((aura->GetSpellInfo()->GetDispelMask()) & dispelMask)
4914 {
4915 // Need check for passive? this
4916 if (!aurApp->IsPositive() || aura->IsPassive() || aura->GetSpellInfo()->HasAttribute(SPELL_ATTR4_NOT_STEALABLE))
4917 continue;
4918
4919 // 2.4.3 Patch Notes: "Dispel effects will no longer attempt to remove effects that have 100% dispel resistance."
4921 if (!chance)
4922 continue;
4923
4924 // The charges / stack amounts don't count towards the total number of auras that can be dispelled.
4925 // Ie: A dispel on a target with 5 stacks of Winters Chill and a Polymorph has 1 / (1 + 1) -> 50% chance to dispell
4926 // Polymorph instead of 1 / (5 + 1) -> 16%.
4927 bool dispelCharges = aura->GetSpellInfo()->HasAttribute(SPELL_ATTR7_DISPEL_CHARGES);
4928 uint8 charges = dispelCharges ? aura->GetCharges() : aura->GetStackAmount();
4929 if (charges > 0)
4930 stealList.emplace_back(aura, chance, charges);
4931 }
4932 }
4933
4934 if (stealList.empty())
4935 return;
4936
4937 size_t remaining = stealList.size();
4938
4939 // Ok if exist some buffs for dispel try dispel it
4940 uint32 failCount = 0;
4941 DispelList successList;
4942 successList.reserve(damage);
4943
4944 WorldPacket dataFail(SMSG_DISPEL_FAILED, 8 + 8 + 4 + 4 + damage * 4);
4945 // dispel N = damage buffs (or while exist buffs for dispel)
4946 for (int32 count = 0; count < damage && remaining > 0;)
4947 {
4948 // Random select buff for dispel
4949 DispelChargesList::iterator itr = stealList.begin();
4950 std::advance(itr, urand(0, remaining - 1));
4951
4952 if (itr->RollDispel())
4953 {
4954 successList.emplace_back(itr->GetAura()->GetId(), itr->GetAura()->GetCasterGUID());
4955 if (!itr->DecrementCharge())
4956 {
4957 --remaining;
4958 std::swap(*itr, stealList[remaining]);
4959 }
4960 }
4961 else
4962 {
4963 if (!failCount)
4964 {
4965 // Failed to dispell
4966 dataFail << m_caster->GetGUID(); // Caster GUID
4967 dataFail << unitTarget->GetGUID(); // Victim GUID
4968 dataFail << uint32(m_spellInfo->Id); // dispel spell id
4969 }
4970 ++failCount;
4971 dataFail << uint32(itr->GetAura()->GetId()); // Spell Id
4972 }
4973 ++count;
4974 }
4975
4976 if (failCount)
4977 m_caster->SendMessageToSet(&dataFail, true);
4978
4979 if (successList.empty())
4980 return;
4981
4982 WorldPacket dataSuccess(SMSG_SPELLSTEALLOG, 8 + 8 + 4 + 1 + 4 + damage * 5);
4983 dataSuccess << unitTarget->GetPackGUID(); // Victim GUID
4984 dataSuccess << m_caster->GetPackGUID(); // Caster GUID
4985 dataSuccess << uint32(m_spellInfo->Id); // dispel spell id
4986 dataSuccess << uint8(0); // not used
4987 dataSuccess << uint32(successList.size()); // count
4988 for (auto itr = successList.begin(); itr != successList.end(); ++itr)
4989 {
4990 dataSuccess << uint32(itr->first); // Spell Id
4991 dataSuccess << uint8(0); // 0 - steals !=0 transfers
4992 unitTarget->RemoveAurasDueToSpellBySteal(itr->first, itr->second, m_caster);
4993 }
4994 m_caster->SendMessageToSet(&dataSuccess, true);
4995}
4996
5007
5009{
5011 return;
5012
5014 return;
5015
5016 int32 creatureEntry = effectInfo->MiscValue;
5017 if (!creatureEntry)
5018 {
5019 if (m_spellInfo->Id == 42793) // Burn Body
5020 creatureEntry = 24008; // Fallen Combatant
5021 }
5022
5023 if (creatureEntry)
5025}
5026
5028{
5030 return;
5031
5033 return;
5034
5036}
5037
5039{
5041 return;
5042
5043 if (!unitTarget)
5044 return;
5045
5046 Player* player = unitTarget->ToPlayer();
5047 if (!player)
5048 return;
5049
5050 if (Quest const* quest = sObjectMgr->GetQuestTemplate(effectInfo->MiscValue))
5051 {
5052 if (!player->CanTakeQuest(quest, false))
5053 return;
5054
5055 if (quest->IsAutoAccept() && player->CanAddQuest(quest, false))
5056 player->AddQuestAndCheckCompletion(quest, player);
5057
5058 player->PlayerTalkClass->SendQuestGiverQuestDetails(quest, player->GetGUID(), true);
5059 }
5060}
5061
5063{
5065 return;
5066
5068 return;
5069
5070 Player* player = m_caster->ToPlayer();
5071
5072 if (player->GetClass() != CLASS_DEATH_KNIGHT)
5073 return;
5074
5075 // needed later
5077
5078 uint32 count = damage;
5079 if (count == 0)
5080 count = 1;
5081
5082 for (uint32 j = 0; j < MAX_RUNES && count > 0; ++j)
5083 {
5084 if (player->GetRuneCooldown(j) && player->GetCurrentRune(j) == RuneType(effectInfo->MiscValue))
5085 {
5086 player->SetRuneCooldown(j, 0);
5087 --count;
5088 }
5089 }
5090
5091 // Empower rune weapon
5092 if (m_spellInfo->Id == 47568)
5093 {
5094 // Need to do this just once
5096 return;
5097
5098 for (uint32 i = 0; i < MAX_RUNES; ++i)
5099 {
5100 if (player->GetRuneCooldown(i) && (player->GetBaseRune(i) == RUNE_FROST))
5101 player->SetRuneCooldown(i, 0);
5102 }
5103 }
5104}
5105
5107{
5109 return;
5110
5112 return;
5113
5114 uint32 creatureEntry = effectInfo->MiscValue;
5115 Pet* pet = unitTarget->CreateTamedPetFrom(creatureEntry, m_spellInfo->Id);
5116 if (!pet)
5117 return;
5118
5119 // relocate
5120 float px, py, pz;
5122 pet->Relocate(px, py, pz, unitTarget->GetOrientation());
5123
5124 // add to world
5125 pet->GetMap()->AddToMap(pet->ToCreature());
5126
5127 // unitTarget has pet now
5128 unitTarget->SetMinion(pet, true);
5129
5130 pet->InitTalentForLevel();
5131
5133 {
5136 }
5137}
5138
5140{
5142 return;
5143
5145 return;
5146 uint32 nodeid = effectInfo->MiscValue;
5147 if (sTaxiNodesStore.LookupEntry(nodeid))
5149}
5150
5159
5161{
5163 return;
5164
5165 Unit* unitCaster = GetUnitCasterForEffectHandlers();
5166 if (!unitCaster)
5167 return;
5168
5169 if (unitTarget)
5171}
5172
5174{
5176 return;
5177
5178 if (!gameObjTarget)
5179 return;
5180
5181 FactionTemplateEntry const* casterFaction = m_caster->GetFactionTemplateEntry();
5182 FactionTemplateEntry const* targetFaction = sFactionTemplateStore.LookupEntry(gameObjTarget->GetFaction());
5183 // Do not allow to damage GO's of friendly factions (ie: Wintergrasp Walls/Ulduar Storm Beacons)
5184 if (!targetFaction || (casterFaction && !casterFaction->IsFriendlyTo(*targetFaction)))
5186}
5187
5189{
5191 return;
5192
5193 if (!gameObjTarget)
5194 return;
5195
5197}
5198
5209
5210void Spell::SummonGuardian(SpellEffectInfo const& spellEffectInfo, uint32 entry, SummonPropertiesEntry const* properties, uint32 numGuardians)
5211{
5212 Unit* unitCaster = GetUnitCasterForEffectHandlers();
5213 if (!unitCaster)
5214 return;
5215
5216 if (unitCaster->IsTotem())
5217 unitCaster = unitCaster->ToTotem()->GetOwner();
5218
5219 // in another case summon new
5220 uint8 level = unitCaster->GetLevel();
5221
5222 // level of pet summoned using engineering item based at engineering skill level
5223 if (m_CastItem && unitCaster->GetTypeId() == TYPEID_PLAYER)
5224 if (ItemTemplate const* proto = m_CastItem->GetTemplate())
5225 if (proto->GetRequiredSkill() == SKILL_ENGINEERING)
5226 if (uint16 skill202 = unitCaster->ToPlayer()->GetSkillValue(SKILL_ENGINEERING))
5227 level = skill202 / 5;
5228
5229 float radius = 5.0f;
5230 int32 duration = m_spellInfo->GetDuration();
5231
5232 if (Player* modOwner = unitCaster->GetSpellModOwner())
5233 modOwner->ApplySpellMod(m_spellInfo->Id, SPELLMOD_DURATION, duration);
5234
5235 //TempSummonType summonType = (duration == 0) ? TEMPSUMMON_DEAD_DESPAWN : TEMPSUMMON_TIMED_DESPAWN;
5236 Map* map = unitCaster->GetMap();
5237 for (uint32 count = 0; count < numGuardians; ++count)
5238 {
5239 Position pos;
5240 if (count == 0)
5241 pos = *destTarget;
5242 else
5243 // randomize position for multiple summons
5244 pos = unitCaster->GetRandomPoint(*destTarget, radius);
5245
5246 TempSummon* summon = map->SummonCreature(entry, pos, properties, duration, unitCaster, m_spellInfo->Id);
5247 if (!summon)
5248 return;
5249
5251 ((Guardian*)summon)->InitStatsForLevel(level);
5252
5253 if (properties && properties->Control == SUMMON_CATEGORY_ALLY)
5254 summon->SetFaction(unitCaster->GetFaction());
5255
5257 ((Minion*)summon)->SetFollowAngle(unitCaster->GetAbsoluteAngle(summon));
5258
5259 if (summon->GetEntry() == 27893)
5260 {
5261 if (uint32 weapon = unitCaster->GetUInt32Value(PLAYER_VISIBLE_ITEM_16_ENTRYID))
5262 {
5263 summon->SetDisplayId(11686); // modelid2
5264 summon->SetVirtualItem(0, weapon);
5265 }
5266 else
5267 summon->SetDisplayId(1126); // modelid1
5268 }
5269
5270 ExecuteLogEffectSummonObject(spellEffectInfo.EffectIndex, summon);
5271 }
5272}
5273
5275{
5277 return;
5278
5280 !unitTarget->IsPet() || ((Pet*)unitTarget)->getPetType() != HUNTER_PET)
5281 return;
5282
5284}
5285
5287{
5289 return;
5290
5292 return;
5293
5294 uint32 soundid = effectInfo->MiscValue;
5295
5296 if (!sSoundEntriesStore.LookupEntry(soundid))
5297 {
5298 TC_LOG_ERROR("spells", "EffectPlayMusic: Sound (Id: {}) does not exist in spell {}.", soundid, m_spellInfo->Id);
5299 return;
5300 }
5301
5303}
5304
5306{
5308 return;
5309
5311 return;
5312
5314}
5315
5317{
5319 return;
5320
5322 return;
5323
5324 unitTarget->ToPlayer()->ActivateTalentGroup(damage-1); // damage is 1 or 2, spec is 0 or 1
5325}
5326
5328{
5330 return;
5331
5332 if (!unitTarget)
5333 return;
5334
5335 Player* player = unitTarget->ToPlayer();
5336 if (!player)
5337 return;
5338
5339 switch (m_spellInfo->Id)
5340 {
5341 case 58730: // Restricted Flight Area
5342 case 58600: // Restricted Flight Area
5344 break;
5345 default:
5346 break;
5347 }
5348
5349 uint32 soundId = effectInfo->MiscValue;
5350
5351 if (!sSoundEntriesStore.LookupEntry(soundId))
5352 {
5353 TC_LOG_ERROR("spells", "EffectPlaySound: Sound (Id: {}) does not exist in spell {}.", soundId, m_spellInfo->Id);
5354 return;
5355 }
5356
5357 player->PlayDirectSound(soundId, player);
5358}
5359
5361{
5363 return;
5364
5365 if (!unitTarget)
5366 return;
5367 // there may be need of specifying casterguid of removed auras
5369}
5370
5372{
5374 return;
5375
5376 Player* player = m_caster->ToPlayer();
5377 if (!player)
5378 return;
5379
5380 uint32 button_id = effectInfo->MiscValue + 132;
5381 uint32 n_buttons = effectInfo->MiscValueB;
5382
5383 for (; n_buttons; --n_buttons, ++button_id)
5384 {
5385 ActionButton const* ab = player->GetActionButton(button_id);
5386 if (!ab || ab->GetType() != ACTION_BUTTON_SPELL)
5387 continue;
5388
5391 uint32 spell_id = ab->GetAction();
5392 if (!spell_id)
5393 continue;
5394
5395 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spell_id);
5396 if (!spellInfo)
5397 continue;
5398
5399 if (!player->HasSpell(spell_id) || player->GetSpellHistory()->HasCooldown(spell_id))
5400 continue;
5401
5403 continue;
5404
5405 uint32 cost = spellInfo->CalcPowerCost(player, spellInfo->GetSchoolMask());
5406 if (player->GetPower(POWER_MANA) < cost)
5407 continue;
5408
5409 CastSpellExtraArgs args;
5411 m_caster->CastSpell(m_caster, spellInfo->Id, args);
5412 }
5413}
5414
5416{
5418 return;
5419
5421 return;
5422
5423 Player* player = m_caster->ToPlayer();
5424
5425 if (!player)
5426 return;
5427
5428 uint32 item_id = effectInfo->ItemType;
5429
5430 ItemTemplate const* pProto = sObjectMgr->GetItemTemplate(item_id);
5431 if (!pProto)
5432 {
5433 player->SendEquipError(EQUIP_ERR_ITEM_NOT_FOUND, nullptr, nullptr);
5434 return;
5435 }
5436
5437 if (Item* pItem = player->GetItemByEntry(item_id))
5438 {
5439 for (uint32 x = 0; x < pProto->Effects.size(); ++x)
5440 pItem->SetSpellCharges(x, pProto->Effects[x].Charges);
5441 pItem->SetState(ITEM_CHANGED, player);
5442 }
5443}
5444
5446{
5448 return;
5449
5451 return;
5452
5453 Player* player = unitTarget->ToPlayer();
5454
5455 WorldLocation homeLoc;
5456 uint32 areaId = player->GetAreaId();
5457
5458 if (effectInfo->MiscValue)
5459 areaId = effectInfo->MiscValue;
5460
5461 if (m_targets.HasDst())
5462 homeLoc.WorldRelocate(*destTarget);
5463 else
5464 homeLoc = player->GetWorldLocation();
5465
5466 player->SetHomebind(homeLoc, areaId);
5467 player->SendBindPointUpdate();
5468
5469 TC_LOG_DEBUG("spells", "EffectBind: New homebind X: {}, Y: {}, Z: {}, MapId: {}, AreaId: {}",
5470 homeLoc.GetPositionX(), homeLoc.GetPositionY(), homeLoc.GetPositionZ(), homeLoc.GetMapId(), areaId);
5471
5472 // zone update
5473 player->SendPlayerBound(m_caster->GetGUID(), areaId);
5474}
5475
@ SPELL_WS_MARK_WINNER
@ SPELL_AV_MARK_LOSER
@ SPELL_WS_MARK_LOSER
@ SPELL_AB_MARK_LOSER
@ SPELL_AB_MARK_WINNER
@ SPELL_AV_MARK_WINNER
@ IN_MILLISECONDS
Definition Common.h:35
@ MINUTE
Definition Common.h:29
#define M_PI
Definition Common.h:71
@ ITEM_ENCHANTMENT_TYPE_PRISMATIC_SOCKET
Definition DBCEnums.h:361
#define MAX_EFFECT_MASK
Definition DBCEnums.h:387
@ SUMMON_PROP_FLAG_PERSONAL_SPAWN
Definition DBCEnums.h:416
@ AREA_FLAG_ALLOW_DUELS
Definition DBCEnums.h:253
#define MAX_SPELL_EFFECTS
Definition DBCEnums.h:386
DBCStorage< SpellItemEnchantmentEntry > sSpellItemEnchantmentStore(SpellItemEnchantmentfmt)
DBCStorage< FactionEntry > sFactionStore(FactionEntryfmt)
SkillRaceClassInfoEntry const * GetSkillRaceClassInfo(uint32 skill, uint8 race, uint8 class_)
DBCStorage< GlyphSlotEntry > sGlyphSlotStore(GlyphSlotfmt)
DBCStorage< SummonPropertiesEntry > sSummonPropertiesStore(SummonPropertiesfmt)
DBCStorage< SkillTiersEntry > sSkillTiersStore(SkillTiersfmt)
DBCStorage< SoundEntriesEntry > sSoundEntriesStore(SoundEntriesfmt)
DBCStorage< FactionTemplateEntry > sFactionTemplateStore(FactionTemplateEntryfmt)
DBCStorage< TaxiNodesEntry > sTaxiNodesStore(TaxiNodesEntryfmt)
DBCStorage< GlyphPropertiesEntry > sGlyphPropertiesStore(GlyphPropertiesfmt)
DBCStorage< AreaTableEntry > sAreaTableStore(AreaTableEntryfmt)
#define MAX_VEHICLE_SEATS
#define MAX_ITEM_ENCHANTMENT_EFFECTS
uint8_t uint8
Definition Define.h:135
int64_t int64
Definition Define.h:128
int8_t int8
Definition Define.h:131
int32_t int32
Definition Define.h:129
uint16_t uint16
Definition Define.h:134
uint32_t uint32
Definition Define.h:133
std::chrono::milliseconds Milliseconds
Milliseconds shorthand typedef.
Definition Duration.h:24
@ DYNAMIC_OBJECT_FARSIGHT_FOCUS
@ DYNAMIC_OBJECT_AREA_SPELL
#define ASSERT
Definition Errors.h:68
GameObjectActions
@ GO_JUST_DEACTIVATED
Definition GameObject.h:79
#define FISHING_BOBBER_READY_TIME
Definition GameObject.h:83
EnchantmentSlot
@ PERM_ENCHANTMENT_SLOT
@ TEMP_ENCHANTMENT_SLOT
@ PRISMATIC_ENCHANTMENT_SLOT
InventoryResult
Definition ItemDefines.h:25
@ EQUIP_ERR_CLIENT_LOCKED_OUT
Definition ItemDefines.h:65
@ EQUIP_ERR_ITEM_NOT_FOUND
Definition ItemDefines.h:49
@ EQUIP_ERR_OK
Definition ItemDefines.h:26
@ EQUIP_ERR_INV_FULL
Definition ItemDefines.h:76
@ EQUIP_ERR_ITEM_MAX_COUNT
Definition ItemDefines.h:43
int32 GenerateItemRandomPropertyId(uint32 item_id)
@ ITEM_CLASS_ARMOR
@ ITEM_CLASS_WEAPON
@ ITEM_SUBCLASS_WEAPON_DAGGER
@ ITEM_FIELD_FLAG_UNLOCKED
@ ITEM_SPELLTRIGGER_LEARN_SPELL_ID
@ ITEM_FLAG_IS_MILLABLE
@ ITEM_FLAG_NO_REAGENT_COST
@ ITEM_FLAG_IS_PROSPECTABLE
#define MAX_ITEM_PROTO_DAMAGES
@ ITEM_CHANGED
Definition Item.h:54
@ LANG_ZONE_NOFLYZONE
Definition Language.h:771
#define TC_LOG_WARN(filterType__,...)
Definition Log.h:162
#define TC_LOG_DEBUG(filterType__,...)
Definition Log.h:156
#define TC_LOG_ERROR(filterType__,...)
Definition Log.h:165
#define sLog
Definition Log.h:130
LootStore LootTemplates_Spell("spell_loot_template", "spell id (random item creating)", false)
LootType
Definition Loot.h:89
@ LOOT_PICKPOCKETING
Definition Loot.h:93
@ LOOT_MILLING
Definition Loot.h:99
@ LOOT_DISENCHANTING
Definition Loot.h:95
@ LOOT_SKINNING
Definition Loot.h:97
@ LOOT_PROSPECTING
Definition Loot.h:98
#define SPEED_CHARGE
TempSummonType
@ TEMPSUMMON_DEAD_DESPAWN
@ TEMPSUMMON_TIMED_DESPAWN
#define DEFAULT_PLAYER_BOUNDING_RADIUS
@ TYPEID_UNIT
Definition ObjectGuid.h:38
@ TYPEID_PLAYER
Definition ObjectGuid.h:39
ScriptMapMap sEventScripts
Definition ObjectMgr.cpp:60
#define sObjectMgr
Definition ObjectMgr.h:1721
#define sOutdoorPvPMgr
@ PET_SAVE_NOT_IN_SLOT
Definition PetDefines.h:45
@ PET_SAVE_AS_CURRENT
Definition PetDefines.h:42
#define PET_FOLLOW_DIST
Definition PetDefines.h:85
@ SUMMON_PET
Definition PetDefines.h:31
@ HUNTER_PET
Definition PetDefines.h:32
@ EQUIPMENT_SLOT_MAINHAND
Definition Player.h:575
std::vector< ItemPosCount > ItemPosCountVec
Definition Player.h:632
@ DAMAGE_FIRE
Definition Player.h:684
@ INVENTORY_SLOT_BAG_END
Definition Player.h:585
@ TELE_TO_SPELL
Definition Player.h:671
@ PLAYER_FLAGS_GHOST
Definition Player.h:350
@ CHEAT_GOD
Definition Player.h:815
@ ACTION_BUTTON_SPELL
Definition Player.h:193
RuneType
Definition Player.h:289
@ RUNE_FROST
Definition Player.h:292
#define INVENTORY_SLOT_BAG_0
Definition Player.h:555
@ REPUTATION_SOURCE_SPELL
Definition Player.h:209
#define MAPID_INVALID
Definition Position.h:165
@ QUEST_FLAGS_TRACKING
Definition QuestDef.h:142
@ QUEST_FLAGS_FLAGS_PVP
Definition QuestDef.h:145
#define MAX_QUEST_LOG_SIZE
Definition QuestDef.h:36
@ QUEST_STATUS_NONE
Definition QuestDef.h:103
int32 irand(int32 min, int32 max)
Definition Random.cpp:35
uint32 urand(uint32 min, uint32 max)
Definition Random.cpp:42
double rand_norm()
Definition Random.cpp:75
bool roll_chance_f(float chance)
Definition Random.h:53
bool roll_chance_i(int chance)
Definition Random.h:59
#define sScriptMgr
Definition ScriptMgr.h:1168
@ GAMEOBJECT_TYPE_BUTTON
@ GAMEOBJECT_TYPE_SPELL_FOCUS
@ GAMEOBJECT_TYPE_DUEL_ARBITER
@ GAMEOBJECT_TYPE_TRAP
@ GAMEOBJECT_TYPE_CHEST
@ GAMEOBJECT_TYPE_FISHINGHOLE
@ GAMEOBJECT_TYPE_FLAGDROP
@ GAMEOBJECT_TYPE_QUESTGIVER
@ GAMEOBJECT_TYPE_FLAGSTAND
@ GAMEOBJECT_TYPE_GOOBER
@ GAMEOBJECT_TYPE_FISHINGNODE
@ GAMEOBJECT_TYPE_DOOR
@ GAMEOBJECT_TYPE_RITUAL
SpellEffIndex
@ EFFECT_1
@ EFFECT_0
@ EFFECT_2
@ SPELL_ATTR7_CAN_RESTORE_SECONDARY_POWER
@ SPELL_ATTR7_DISPEL_CHARGES
@ SPELL_ATTR7_SUMMON_PLAYER_TOTEM
@ SPELL_EFFECT_TRIGGER_MISSILE_SPELL_WITH_VALUE
@ SPELL_EFFECT_TRIGGER_SPELL_WITH_VALUE
@ SPELL_EFFECT_SUMMON_OBJECT_SLOT1
@ SPELL_EFFECT_WEAPON_DAMAGE
@ SPELL_EFFECT_NORMALIZED_WEAPON_DMG
@ SPELL_EFFECT_TRIGGER_SPELL
@ SPELL_EFFECT_WEAPON_PERCENT_DAMAGE
@ SPELL_EFFECT_KNOCK_BACK_DEST
@ SPELL_EFFECT_WEAPON_DAMAGE_NOSCHOOL
@ SPELL_EFFECT_PERSISTENT_AREA_AURA
@ TOTAL_SPELL_EFFECTS
@ SPELL_EFFECT_FORCE_CAST
@ SPELL_EFFECT_ENCHANT_ITEM_PRISMATIC
@ SPELL_EFFECT_FORCE_CAST_WITH_VALUE
#define MAX_RUNES
@ SPELL_PREVENTION_TYPE_SILENCE
@ SPELL_SCHOOL_MASK_NORMAL
@ EVENT_JUMP
@ UNIT_DYNFLAG_LOOTABLE
@ UNIT_DYNFLAG_NONE
@ SPELL_DAMAGE_CLASS_MAGIC
@ SPELL_DAMAGE_CLASS_MELEE
@ TEAM_ALLIANCE
@ TEAM_HORDE
#define MAX_GLYPH_SLOT_INDEX
@ SUMMON_TYPE_VEHICLE2
@ SUMMON_TYPE_LIGHTWELL
@ SUMMON_TYPE_MINION
@ SUMMON_TYPE_GUARDIAN
@ SUMMON_TYPE_PET
@ SUMMON_TYPE_TOTEM
@ SUMMON_TYPE_VEHICLE
@ SUMMON_TYPE_MINIPET
@ SUMMON_TYPE_GUARDIAN2
WeaponAttackType
@ OFF_ATTACK
@ BASE_ATTACK
@ RANGED_ATTACK
@ CLASS_HUNTER
@ CLASS_DEATH_KNIGHT
@ SPELLFAMILY_PRIEST
@ SPELLFAMILY_WARLOCK
@ SPELLFAMILY_GENERIC
@ SPELLFAMILY_WARRIOR
@ SPELLFAMILY_PALADIN
@ SPELLFAMILY_HUNTER
@ SPELLFAMILY_POTION
@ SPELLFAMILY_ROGUE
@ SPELLFAMILY_SHAMAN
@ SPELLFAMILY_DRUID
@ SPELLFAMILY_DEATHKNIGHT
GameObjectDestructibleState
@ ALLIANCE
Powers
@ MAX_POWERS
@ POWER_RAGE
@ POWER_RUNIC_POWER
@ POWER_HAPPINESS
@ POWER_ENERGY
@ POWER_MANA
uint32 const CREATURE_TYPEMASK_HUMANOID_OR_UNDEAD
#define MAX_TOTEM_SLOT
@ SUMMON_SLOT_TOTEM_FIRE
@ BATTLEGROUND_WS
@ BATTLEGROUND_EY
@ BATTLEGROUND_AV
@ BATTLEGROUND_AB
@ SPELL_MISS_REFLECT
@ AURA_STATE_DEADLY_POISON
@ AURA_STATE_BLEEDING
@ AURA_STATE_SWIFTMEND
@ AURA_STATE_CONFLAGRATE
DispelType
@ DISPEL_POISON
SpellCastResult
@ SPELL_FAILED_INTERRUPTED_COMBAT
@ SPELL_FAILED_GLYPH_SOCKET_LOCKED
@ SPELL_FAILED_DONT_REPORT
@ SPELL_FAILED_NO_DUELING
@ SPELL_CAST_OK
@ SPELL_FAILED_INVALID_GLYPH
@ GO_STATE_READY
@ SPELL_ATTR4_NOT_STEALABLE
@ SUMMON_CATEGORY_PET
@ SUMMON_CATEGORY_VEHICLE
@ SUMMON_CATEGORY_ALLY
@ SUMMON_CATEGORY_PUPPET
@ SUMMON_CATEGORY_WILD
@ SUMMON_CATEGORY_UNK
SkillType
@ SKILL_INSCRIPTION
@ SKILL_ENGINEERING
@ SKILL_NONE
@ SKILL_JEWELCRAFTING
@ SPELL_ATTR6_LIMIT_PCT_DAMAGE_MODS
bool CanCreateExtraItems(Player *player, uint32 spellId, float &additionalChance, uint8 &additionalMax)
bool CanCreatePerfectItem(Player *player, uint32 spellId, float &perfectCreateChance, uint32 &perfectItemType)
@ AURA_REMOVE_BY_ENEMY_SPELL
@ SPELL_AURA_PREVENT_RESURRECTION
@ SPELL_AURA_MOD_AURA_DURATION_BY_DISPEL_NOT_STACK
@ SPELL_AURA_PERIODIC_DAMAGE
@ SPELL_AURA_ADD_FLAT_MODIFIER
@ SPELL_AURA_CONTROL_VEHICLE
@ SPELL_AURA_MOD_STALKED
@ SPELL_AURA_PERIODIC_HEAL
@ SPELL_AURA_MOD_DECREASE_SPEED
@ SPELL_AURA_MOD_STUN
@ FORM_SHADOW
@ SPELL_INTERRUPT_FLAG_INTERRUPT
@ CHANNEL_INTERRUPT_FLAG_INTERRUPT
@ SPELLMOD_DAMAGE
@ SPELLMOD_DURATION
@ TARGET_FLAG_DEST_LOCATION
@ TARGET_FLAG_UNIT_MASK
@ TARGET_FLAG_GAMEOBJECT_MASK
@ TRIGGERED_FULL_MASK
Will return SPELL_FAILED_DONT_REPORT in CheckCast functions.
@ TRIGGERED_IGNORE_SPELL_AND_CATEGORY_CD
Will ignore GCD.
@ TRIGGERED_CAST_DIRECTLY
Will ignore combo point requirement.
@ TRIGGERED_IGNORE_CAST_IN_PROGRESS
Will ignore aura scaling.
@ TRIGGERED_IGNORE_GCD
Not triggered.
SpellValueMod
@ SPELLVALUE_BASE_POINT0
SpellEffectHandlerFn SpellEffectHandlers[TOTAL_SPELL_EFFECTS]
@ SPELL_ATTR0_CU_SHARE_DAMAGE
Definition SpellInfo.h:144
@ PROC_HIT_INTERRUPT
Definition SpellMgr.h:232
#define sSpellMgr
Definition SpellMgr.h:738
@ PROC_SPELL_TYPE_MASK_ALL
Definition SpellMgr.h:205
@ PROC_SPELL_PHASE_HIT
Definition SpellMgr.h:212
@ PROC_FLAG_DONE_SPELL_MELEE_DMG_CLASS
Definition SpellMgr.h:121
@ PROC_FLAG_TAKEN_SPELL_MAGIC_DMG_CLASS_NEG
Definition SpellMgr.h:140
@ PROC_FLAG_TAKEN_SPELL_MELEE_DMG_CLASS
Definition SpellMgr.h:122
@ PROC_FLAG_DONE_SPELL_MAGIC_DMG_CLASS_NEG
Definition SpellMgr.h:139
std::vector< std::pair< uint32, ObjectGuid > > DispelList
Definition Spell.h:147
void(Spell::*)() SpellEffectHandlerFn
Definition Spell.h:784
@ SPELL_EFFECT_HANDLE_LAUNCH_TARGET
Definition Spell.h:142
@ SPELL_EFFECT_HANDLE_LAUNCH
Definition Spell.h:141
@ SPELL_EFFECT_HANDLE_HIT
Definition Spell.h:143
@ SPELL_EFFECT_HANDLE_HIT_TARGET
Definition Spell.h:144
@ SPELL_STATE_PREPARING
Definition Spell.h:132
@ SPELL_STATE_CASTING
Definition Spell.h:133
@ UNIT_PET_FLAG_CAN_BE_RENAMED
@ REACT_DEFENSIVE
@ REACT_AGGRESSIVE
NPCFlags
Non Player Character flags.
@ COMMAND_STAY
@ MOVE_RUN
@ UNIT_FLAG_IMMUNE
@ UNIT_FLAG_SKINNABLE
float baseMoveSpeed[MAX_MOVE_TYPE]
Definition Unit.cpp:88
float playerBaseMoveSpeed[MAX_MOVE_TYPE]
Definition Unit.cpp:101
@ UNIT_MASK_GUARDIAN
Definition Unit.h:380
@ UNIT_MASK_MINION
Definition Unit.h:379
@ MINDAMAGE
Definition Unit.h:153
@ MAXDAMAGE
Definition Unit.h:154
UnitMods
Definition Unit.h:158
@ UNIT_MOD_DAMAGE_OFFHAND
Definition Unit.h:180
@ UNIT_MOD_DAMAGE_RANGED
Definition Unit.h:181
@ UNIT_MOD_DAMAGE_MAINHAND
Definition Unit.h:179
@ ALIVE
Definition Unit.h:225
#define CURRENT_FIRST_NON_MELEE_SPELL
Definition Unit.h:626
CurrentSpellTypes
Definition Unit.h:619
@ CURRENT_CHANNELED_SPELL
Definition Unit.h:622
@ CURRENT_GENERIC_SPELL
Definition Unit.h:621
@ CURRENT_AUTOREPEAT_SPELL
Definition Unit.h:623
@ UNIT_STATE_CONFUSED
Definition Unit.h:245
@ UNIT_STATE_ROOT
Definition Unit.h:244
@ UNIT_STATE_FLEEING
Definition Unit.h:241
@ UNIT_STATE_ALL_ERASABLE
Definition Unit.h:281
@ UNIT_STATE_STUNNED
Definition Unit.h:237
std::vector< DispelableAura > DispelChargesList
Definition Unit.h:133
@ NULL_BAG
Definition Unit.h:60
@ NULL_SLOT
Definition Unit.h:61
@ NODAMAGE
Definition Unit.h:371
@ DOT
Definition Unit.h:369
@ SPELL_DIRECT_DAMAGE
Definition Unit.h:368
@ HEAL
Definition Unit.h:370
@ TOTAL_PCT
Definition Unit.h:147
@ UNIT_FIELD_LEVEL
@ PLAYER_FLAGS
@ PLAYER_VISIBLE_ITEM_16_ENTRYID
@ PLAYER_DUEL_ARBITER
@ UNIT_CREATED_BY_SPELL
@ ITEM_FIELD_DURABILITY
@ ITEM_FIELD_MAXDURABILITY
T AddPct(T &base, U pct)
Definition Util.h:77
T ApplyPct(T &base, U pct)
Definition Util.h:83
T CalculatePct(T base, U pct)
Definition Util.h:71
@ VEHICLE_SPELL_RIDE_HARDCODED
bool IsPositive() const
Definition SpellAuras.h:81
void UpdateApplyEffectMask(uint8 newEffMask, bool canHandleNewEffects)
uint8 GetEffectsToApply() const
Definition SpellAuras.h:84
SpellInfo const * GetSpellInfo() const
uint32 GetId() const
Aura * GetBase() const
ObjectGuid GetCasterGUID() const
int32 GetAmount() const
static Aura * TryCreate(AuraCreateInfo &createInfo)
AuraApplication const * GetApplicationOfTarget(ObjectGuid guid) const
Definition SpellAuras.h:234
DynamicObject * GetDynobjOwner() const
Definition SpellAuras.h:148
void _RegisterForTargets()
Definition SpellAuras.h:160
ObjectGuid GetCasterGUID() const
Definition SpellAuras.h:144
uint32 GetId() const
Definition SpellAuras.h:141
int32 CalcDispelChance(Unit const *auraTarget, bool offensive) const
int32 GetDuration() const
Definition SpellAuras.h:173
DynObjAura * ToDynObjAura()
Definition SpellAuras.h:285
uint8 GetStackAmount() const
Definition SpellAuras.h:189
void _ApplyEffectForTargets(uint8 effIndex)
uint8 GetCharges() const
Definition SpellAuras.h:180
SpellInfo const * GetSpellInfo() const
Definition SpellAuras.h:140
bool IsPassive() const
ObjectGuid GetOwnerGUID() const override
Definition Corpse.h:81
void SetDisplayId(uint32 modelId) override
void SetReactState(ReactStates st)
Definition Creature.h:128
void DespawnOrUnsummon(Milliseconds timeToDespawn=0s, Seconds forceRespawnTime=0s)
CreatureTemplate const * GetCreatureTemplate() const
Definition Creature.h:195
void SetImmuneToAll(bool apply) override
Definition Creature.h:135
void SelectLevel()
bool isElite() const
uint32 GetResist() const
Definition Unit.h:480
uint32 GetDamage() const
Definition Unit.h:478
uint32 GetAbsorb() const
Definition Unit.h:479
void SetCasterViewpoint()
void SetDuration(int32 newDuration)
bool CreateDynamicObject(ObjectGuid::LowType guidlow, Unit *caster, SpellInfo const *spell, Position const &pos, float radius, DynamicObjectType type)
virtual bool OnGossipHello(Player *)
void UseDoorOrButton(uint32 time_to_restore=0, bool alternative=false, Unit *user=nullptr)
GameObjectTemplate const * GetGOInfo() const
Definition GameObject.h:102
uint32 GetFaction() const override
Definition GameObject.h:285
bool isSpawned() const
Definition GameObject.h:155
void SetOwnerGUID(ObjectGuid owner)
Definition GameObject.h:131
void SetDestructibleState(GameObjectDestructibleState state, WorldObject *attackerOrHealer=nullptr, bool setHealth=false)
void AddToSkillupList(ObjectGuid const &PlayerGuidLow)
Definition GameObject.h:206
void SetLootState(LootState s, Unit *unit=nullptr)
GameObjectAI * AI() const
Definition GameObject.h:275
GameObject * GetLinkedTrap()
void SetRespawnTime(int32 respawn)
bool IsInSkillupList(ObjectGuid const &playerGuid) const
Definition GameObject.h:207
void TriggeringLinkedGameObject(uint32 trapEntry, Unit *target)
GameobjectTypes GetGoType() const
Definition GameObject.h:176
ObjectGuid::LowType GetSpawnId() const
Definition GameObject.h:112
void ActivateObject(GameObjectActions action, WorldObject *spellCaster=nullptr, uint32 spellId=0, int32 effectIndex=-1)
void SetLevel(uint32 level)
Definition GameObject.h:175
void ModifyHealth(int32 change, WorldObject *attackerOrHealer=nullptr, uint32 spellId=0)
void Use(Unit *user)
void AddUniqueUse(Player *player)
bool Create(ObjectGuid::LowType guidlow, uint32 name_id, Map *map, uint32 phaseMask, Position const &pos, QuaternionData const &rotation, uint32 animprogress, GOState go_state, uint32 artKit=0, bool dynamic=false, ObjectGuid::LowType spawnid=0)
void SetSpellId(uint32 id)
Definition GameObject.h:143
void SetFaction(uint32 faction) override
Definition GameObject.h:286
Definition Item.h:62
std::string const & GetNameForLocaleIdx(LocaleConstant locale) const override
Definition Item.cpp:297
void SetState(ItemUpdateState state, Player *forplayer=nullptr)
Definition Item.cpp:644
uint8 GetSlot() const
Definition Item.h:143
void SetItemFlag(ItemFieldFlags flags)
Definition Item.h:92
uint32 GetEnchantmentId(EnchantmentSlot slot) const
Definition Item.h:165
static Item * CreateItem(uint32 itemEntry, uint32 count, Player const *player=nullptr)
Definition Item.cpp:1050
uint32 GetEnchantmentDuration(EnchantmentSlot slot) const
Definition Item.h:166
void SetCount(uint32 value)
Definition Item.cpp:1293
ItemTemplate const * GetTemplate() const
Definition Item.cpp:541
bool IsWeaponVellum() const
Definition Item.h:198
bool IsEquipped() const
Definition Item.cpp:722
bool IsArmorVellum() const
Definition Item.h:199
Player * GetOwner() const
Definition Item.cpp:546
ObjectGuid GetOwnerGUID() const
Definition Item.h:78
uint16 GetPos() const
Definition Item.h:147
void SetCreator(ObjectGuid guid)
Definition Item.h:83
uint32 GetEnchantmentCharges(EnchantmentSlot slot) const
Definition Item.h:167
void ClearSoulboundTradeable(Player *currentOwner)
Definition Item.cpp:1268
uint32 GetCount() const
Definition Item.h:136
uint8 GetBagSlot() const
Definition Item.cpp:717
void SetEnchantment(EnchantmentSlot slot, uint32 id, uint32 duration, uint32 charges, ObjectGuid caster=ObjectGuid::Empty)
Definition Item.cpp:889
Definition Map.h:302
bool IsDungeon() const
Definition Map.cpp:4231
void ScriptsStart(std::map< uint32, std::multimap< uint32, ScriptInfo > > const &scripts, uint32 id, Object *source, Object *target)
Put scripts in the execution queue.
bool AddToMap(T *)
Definition Map.cpp:630
ObjectGuid::LowType GenerateLowGuid()
Definition Map.h:607
GameObject * GetGameObject(ObjectGuid const &guid)
Definition Map.cpp:4425
TempSummon * SummonCreature(uint32 entry, Position const &pos, SummonPropertiesEntry const *properties=nullptr, uint32 duration=0, WorldObject *summoner=nullptr, uint32 spellId=0, uint32 vehId=0, ObjectGuid privateObjectOwner=ObjectGuid::Empty)
Definition Object.cpp:1853
Creature * GetCreature(ObjectGuid const &guid)
Definition Map.cpp:4392
Unit * GetOwner() const
float GetFollowAngle() const override
void MoveJump(Position const &pos, float speedXY, float speedZ, uint32 id=EVENT_JUMP, bool hasOrientation=false)
void MoveCharge(float x, float y, float z, float speed=SPEED_CHARGE, uint32 id=EVENT_CHARGE, bool generatePath=false)
void MoveDistract(uint32 time, float orientation)
bool IsEmpty() const
Definition ObjectGuid.h:172
std::string ToString() const
void Clear()
Definition ObjectGuid.h:150
static Creature * ToCreature(Object *o)
Definition Object.h:189
bool IsPlayer() const
Definition Object.h:182
PackedGuid const & GetPackGUID() const
Definition Object.h:80
static Unit * ToUnit(Object *o)
Definition Object.h:195
uint32 GetUInt32Value(uint16 index) const
Definition Object.cpp:241
static GameObject * ToGameObject(Object *o)
Definition Object.h:201
bool IsInWorld() const
Definition Object.h:73
TypeID GetTypeId() const
Definition Object.h:93
virtual void SetDynamicFlag(uint32 flag)
Definition Object.h:89
void SetGuidValue(uint16 index, ObjectGuid value)
Definition Object.cpp:691
uint32 GetEntry() const
Definition Object.h:81
bool HasFlag(uint16 index, uint32 flag) const
Definition Object.cpp:800
static ObjectGuid GetGUID(Object const *o)
Definition Object.h:78
void SetUInt32Value(uint16 index, uint32 value)
Definition Object.cpp:577
static Player * ToPlayer(Object *o)
Definition Object.h:183
std::size_t size() const
Definition ObjectGuid.h:278
Definition Pet.h:40
Player * GetOwner() const
Definition Pet.cpp:1997
void InitTalentForLevel()
Definition Pet.cpp:1785
void SavePetToDB(PetSaveMode mode)
Definition Pet.cpp:437
PetType getPetType() const
Definition Pet.h:51
bool isControlled() const
Definition Pet.h:53
void setDeathState(DeathState s) override
Definition Pet.cpp:582
void Remove(PetSaveMode mode, bool returnreagent=false)
Definition Pet.cpp:732
uint32 GetCurrentFoodBenefitLevel(uint32 itemlevel) const
Definition Pet.cpp:1150
bool learnSpell(uint32 spell_id)
Definition Pet.cpp:1497
void SendQuestGiverQuestDetails(Quest const *quest, ObjectGuid npcGUID, bool autoLaunched) const
void ClearMenus()
bool HasIgnore(ObjectGuid const &ignoreGuid)
void SetRuneCooldown(uint8 index, uint32 cooldown, bool casted=false)
Definition Player.cpp:24329
void SendEquipError(InventoryResult msg, Item const *item1=nullptr, Item const *item2=nullptr, uint32 itemId=0) const
Definition Player.cpp:13070
void KilledMonsterCredit(uint32 entry, ObjectGuid guid=ObjectGuid::Empty)
Definition Player.cpp:16153
void SendPlayerBound(ObjectGuid const &binderGuid, uint32 areaId) const
Definition Player.cpp:16875
uint32 GetArmorProficiency() const
Definition Player.h:1181
static bool IsEquipmentPos(uint16 pos)
Definition Player.h:1095
void LearnSpell(uint32 spell_id, bool dependent, uint32 fromSkill=0)
Definition Player.cpp:3381
void SendTalentsInfoData(bool pet)
Definition Player.cpp:25337
bool HasPvPForcingQuest() const
Definition Player.cpp:16700
uint32 GetNextResetTalentsCost() const
Definition Player.cpp:3688
InventoryResult CanEquipItem(uint8 slot, uint16 &dest, Item *pItem, bool swap, bool not_loading=true) const
Definition Player.cpp:10980
void SetCanTitanGrip(bool value, uint32 penaltySpellId=0, int32 allowedItemClass=0, int32 allowedItemSubClassMask=0)
Definition Player.cpp:13171
Item * StoreNewItem(ItemPosCountVec const &pos, uint32 itemId, bool update, int32 randomPropertyId=0, GuidSet const &allowedLooters=GuidSet())
Definition Player.cpp:11619
uint32 EnvironmentalDamage(EnviromentalDamage type, uint32 damage)
Definition Player.cpp:638
uint8 GetDrunkValue() const
Definition Player.h:1869
void SendDirectMessage(WorldPacket const *data) const
Definition Player.cpp:6163
uint16 GetSkillValue(uint32 skill) const
Definition Player.cpp:5906
Item * BankItem(ItemPosCountVec const &dest, Item *pItem, bool update)
Definition Player.cpp:11976
Item * GetItemByEntry(uint32 entry) const
Definition Player.cpp:12459
uint16 FindQuestSlot(uint32 quest_id) const
Definition Player.cpp:15948
void SetCanParry(bool value)
Definition Player.cpp:24058
InventoryResult CanStoreItem(uint8 bag, uint8 slot, ItemPosCountVec &dest, Item *pItem, bool swap=false) const
Definition Player.cpp:9992
void SendProficiency(ItemClass itemClass, uint32 itemSubclassMask) const
Definition Player.cpp:20942
void UpdatePvPState(bool onlyFFA=false)
Definition Player.cpp:21641
void DurabilityLossAll(double percent, bool inventory)
Definition Player.cpp:4573
bool UpdateCraftSkill(uint32 spellid)
Definition Player.cpp:5463
void SetResurrectRequestData(WorldObject const *caster, uint32 health, uint32 mana, uint32 appliedAura)
Definition Player.cpp:21726
void SpawnCorpseBones(bool triggerSave=true)
Definition Player.cpp:4555
void SetDrunkValue(uint8 newDrunkValue, uint32 itemId=0)
Definition Player.cpp:876
void SendPreparedGossip(WorldObject *source)
Definition Player.cpp:14053
void UpdateTalentGroupCount(uint8 count)
Definition Player.cpp:25615
void ActivateTalentGroup(uint8 group)
Definition Player.cpp:25662
uint32 GetGlyphSlot(uint8 slot) const
Definition Player.h:1506
void PetSpellInitialize()
Definition Player.cpp:20594
void SetFallInformation(uint32 time, float z)
Definition Player.cpp:24827
void ApplyEnchantment(Item *item, EnchantmentSlot slot, bool apply, bool apply_dur=true, bool ignore_condition=false)
Definition Player.cpp:13432
bool CanAddQuest(Quest const *quest, bool msg) const
Definition Player.cpp:14468
void SetSkill(uint32 id, uint16 step, uint16 newVal, uint16 maxVal)
Definition Player.cpp:5773
Pet * GetPet() const
Definition Player.cpp:20284
uint16 GetPureSkillValue(uint32 skill) const
Definition Player.cpp:5962
uint8 GetRunesState() const
Definition Player.h:2191
void RemoveTradeableItem(Item *item)
Definition Player.cpp:13270
void SetCanBlock(bool value)
Definition Player.cpp:24067
bool GetCommandStatus(uint32 command) const
Definition Player.h:1006
Item * StoreItem(ItemPosCountVec const &pos, Item *pItem, bool update)
Definition Player.cpp:11659
WorldSession * GetSession() const
Definition Player.h:1705
Item * GetItemByPos(uint16 pos) const
Definition Player.cpp:9550
void RepopAtGraveyard()
Definition Player.cpp:4792
void SendBindPointUpdate()
Definition Player.cpp:16866
uint32 GetQuestSlotQuestId(uint16 slot) const
Definition Player.cpp:15957
void DestroyItem(uint8 bag, uint8 slot, bool update)
Definition Player.cpp:12111
bool IsResurrectRequested() const
Definition Player.h:1549
static bool IsInventoryPos(uint16 pos)
Definition Player.h:1093
uint32 DestroyItemCount(uint32 item, uint32 count, bool update, bool unequip_check=false)
Definition Player.cpp:12207
void RemovePet(Pet *pet, PetSaveMode mode, bool returnreagent=false)
Definition Player.cpp:20308
int32 CalculateReputationGain(ReputationSource source, uint32 creatureOrQuestLevel, int32 rep, int32 faction, bool noQuestBonus=false)
Definition Player.cpp:6312
uint32 GetRuneCooldown(uint8 index) const
Definition Player.h:2194
void SendLoot(ObjectGuid guid, LootType loot_type)
Definition Player.cpp:8084
bool ActivateTaxiPathTo(std::vector< uint32 > const &nodes, Creature *npc=nullptr, uint32 spellid=0)
Definition Player.cpp:21005
ActionButton const * GetActionButton(uint8 button)
Definition Player.cpp:6096
void DurabilityLoss(Item *item, double percent)
Definition Player.cpp:4599
uint32 GetWeaponProficiency() const
Definition Player.h:1180
Battleground * GetBattleground() const
Definition Player.cpp:23024
void SetQuestSlot(uint16 slot, uint32 quest_id, uint32 timer=0)
Definition Player.cpp:15977
void RemoveSpell(uint32 spell_id, bool disabled=false, bool learn_low_rank=true)
Definition Player.cpp:3418
void SetRewardedQuest(uint32 quest_id)
Definition Player.cpp:15047
void SendNewItem(Item *item, uint32 count, bool received, bool created, bool broadcast=false, bool sendChatMessage=true)
Definition Player.cpp:13857
void AutoUnequipOffhandIfNeed(bool force=false)
Definition Player.cpp:23353
void AutoStoreLoot(uint8 bag, uint8 slot, uint32 loot_id, LootStore const &store, bool broadcast=false, bool createdByPlayer=false)
Definition Player.cpp:24504
RuneType GetCurrentRune(uint8 index) const
Definition Player.h:2193
bool IsGameMaster() const
Definition Player.h:976
Item * EquipItem(uint16 pos, Item *pItem, bool update)
Definition Player.cpp:11802
PvPInfo pvpInfo
Definition Player.h:1567
void SetGlyph(uint8 slot, uint32 glyph)
Definition Player.cpp:24256
void AddQuestAndCheckCompletion(Quest const *quest, Object *questGiver)
Definition Player.cpp:14625
bool TeleportTo(uint32 mapid, float x, float y, float z, float orientation, uint32 options=0)
Definition Player.cpp:1539
void DurabilityPointsLossAll(int32 points, bool inventory)
Definition Player.cpp:4617
Pet * SummonPet(uint32 entry, float x, float y, float z, float ang, PetType petType, uint32 despwtime)
Definition Player.cpp:26230
bool CanTakeQuest(Quest const *quest, bool msg) const
Definition Player.cpp:14456
uint8 GetActiveTalentGroup() const
Definition Player.h:1480
void SendSummonRequestFrom(Unit *summoner)
Definition Player.cpp:23282
void AreaExploredOrEventHappens(uint32 questId)
Definition Player.cpp:16021
bool TakeQuestSourceItem(uint32 questId, bool msg)
Definition Player.cpp:15605
void RemoveActiveQuest(uint32 questId, bool update=true)
Definition Player.cpp:15706
QuestStatus GetQuestStatus(uint32 quest_id) const
Definition Player.cpp:15655
uint32 GetGlyph(uint8 group, uint8 slot) const
Definition Player.h:1508
PlayerSocial * GetSocial()
Definition Player.h:960
void AddArmorProficiency(uint32 newflag)
Definition Player.h:1179
InventoryResult CanBankItem(uint8 bag, uint8 slot, ItemPosCountVec &dest, Item *pItem, bool swap, bool not_loading=true) const
Definition Player.cpp:11181
void SetHomebind(WorldLocation const &loc, uint32 areaId)
Definition Player.cpp:16849
void FailQuest(uint32 quest_id)
Definition Player.cpp:15053
void ItemAddedQuestCheck(uint32 entry, uint32 count)
Definition Player.cpp:16062
Item * GetWeaponForAttack(WeaponAttackType attackType, bool useable=false) const
Definition Player.cpp:9605
static bool IsBankPos(uint16 pos)
Definition Player.h:1098
bool RewardHonor(Unit *victim, uint32 groupsize, int32 honor=-1, bool pvptoken=false)
Definition Player.cpp:6525
void RemoveItem(uint8 bag, uint8 slot, bool update)
Definition Player.cpp:11981
bool HasSpell(uint32 spell) const override
Definition Player.cpp:3881
void SendRespecWipeConfirm(ObjectGuid const &guid, uint32 cost) const
Definition Player.cpp:9153
void BuildPlayerRepop()
Definition Player.cpp:4320
std::unique_ptr< DuelInfo > duel
Definition Player.h:1587
void RemoveRewardedQuest(uint32 questId, bool update=true)
Definition Player.cpp:15719
void DurabilityPointsLoss(Item *item, int32 points)
Definition Player.cpp:4643
void RemovedInsignia(Player *looterPlr)
Definition Player.cpp:8045
void AddWeaponProficiency(uint32 newflag)
Definition Player.h:1178
void PrepareGossipMenu(WorldObject *source, uint32 menuId=0, bool showQuests=false)
Definition Player.cpp:13887
InventoryResult CanStoreNewItem(uint8 bag, uint8 slot, ItemPosCountVec &dest, uint32 item, uint32 count, uint32 *no_space_count=nullptr) const
Definition Player.cpp:9987
RuneType GetBaseRune(uint8 index) const
Definition Player.h:2192
ReputationMgr & GetReputationMgr()
Definition Player.h:1834
PlayerMenu * PlayerTalkClass
Definition Player.h:1956
void AddPetAura(PetAura const *petSpell)
Definition Player.cpp:20398
void RewardPlayerAndGroupAtEvent(uint32 creature_id, WorldObject *pRewardSource)
Definition Player.cpp:23611
void ResurrectPlayer(float restore_percent, bool applySickness=false)
Definition Player.cpp:4374
bool UpdateGatherSkill(uint32 SkillId, uint32 SkillValue, uint32 RedLevel, uint32 Multiplicator=1)
Definition Player.cpp:5496
bool HasFlag(QuestFlags flag) const
Definition QuestDef.h:216
bool ModifyReputation(FactionEntry const *factionEntry, int32 standing, bool spillOverOnly=false)
void SetItemTarget(Item *item)
Definition Spell.cpp:350
void SetDst(float x, float y, float z, float orientation, uint32 mapId=MAPID_INVALID)
Definition Spell.cpp:428
void SetGOTarget(GameObject *target)
Definition Spell.cpp:307
ObjectGuid GetObjectTargetGUID() const
Definition Spell.cpp:338
void SetUnitTarget(Unit *target)
Definition Spell.cpp:281
bool HasDst() const
Definition Spell.cpp:480
Item * GetItemTarget() const
Unit * GetUnitTarget() const
Definition Spell.cpp:273
WorldLocation const * GetDstPos() const
Definition Spell.cpp:423
float CalcRadius(WorldObject *caster=nullptr, Spell *=nullptr) const
float CalcValueMultiplier(WorldObject *caster, Spell *spell=nullptr) const
uint32 TriggerSpell
Definition SpellInfo.h:228
SpellEffects Effect
Definition SpellInfo.h:210
bool HasRadius() const
bool IsEffect() const
int32 CalcValue(WorldObject const *caster=nullptr, int32 const *basePoints=nullptr) const
float ChainAmplitude
Definition SpellInfo.h:218
SpellEffIndex EffectIndex
Definition SpellInfo.h:209
uint32 GetProvidedTargetMask() const
void ResetAllCooldowns()
bool HasCooldown(SpellInfo const *spellInfo, uint32 itemId=0, bool ignoreCategoryCooldown=false) const
void LockSpellSchool(SpellSchoolMask schoolMask, uint32 lockoutTime)
uint32 ChannelInterruptFlags
Definition SpellInfo.h:323
uint32 TargetAuraState
Definition SpellInfo.h:309
uint32 GetMaxTicks() const
uint32 PreventionType
Definition SpellInfo.h:359
float GetMaxRange(bool positive=false, WorldObject *caster=nullptr, Spell *spell=nullptr) const
uint32 GetCategory() const
flag96 SpellFamilyFlags
Definition SpellInfo.h:357
uint32 StackAmount
Definition SpellInfo.h:340
uint32 Id
Definition SpellInfo.h:289
bool IsLootCrafting() const
uint32 GetDispelMask() const
bool NeedsToBeTriggeredByCaster(SpellInfo const *triggeringSpell) const
float Speed
Definition SpellInfo.h:339
float GetMinRange(bool positive=false) const
int32 EquippedItemClass
Definition SpellInfo.h:344
std::array< uint32, 2 > SpellVisual
Definition SpellInfo.h:348
SpellSchoolMask GetSchoolMask() const
bool HasAttribute(SpellAttr0 attribute) const
Definition SpellInfo.h:375
uint32 InterruptFlags
Definition SpellInfo.h:321
int32 CalcPowerCost(WorldObject const *caster, SpellSchoolMask schoolMask, Spell *spell=nullptr) const
int32 GetDuration() const
SpellEffectInfo const & GetEffect(SpellEffIndex index) const
Definition SpellInfo.h:483
uint32 ManaCostPercentage
Definition SpellInfo.h:336
int32 EquippedItemSubClassMask
Definition SpellInfo.h:345
uint32 GetExplicitTargetMask() const
uint32 GetAllEffectsMechanicMask() const
uint32 SpellIconID
Definition SpellInfo.h:349
bool IsPositive() const
uint32 DmgClass
Definition SpellInfo.h:358
bool HasAura(AuraType aura) const
std::array< SpellEffectInfo, MAX_SPELL_EFFECTS > const & GetEffects() const
Definition SpellInfo.h:482
uint32 SpellFamilyName
Definition SpellInfo.h:356
uint32 ManaCost
Definition SpellInfo.h:332
Definition Spell.h:152
void EffectSummonRaFFriend()
SpellInfo const * GetSpellInfo() const
Definition Spell.h:459
void EffectSendEvent()
void EffectTransmitted()
void EffectSpiritHeal()
void EffectBlock()
void EffectPlayMusic()
GameObject * gameObjTarget
Definition Spell.h:533
SpellMissInfo targetMissInfo
Definition Spell.h:537
void EffectCreateItem2()
void EffectEnchantHeldItem()
void EffectActivateRune()
Unit * m_originalCaster
Definition Spell.h:496
void EffectHealMaxHealth()
void EffectProspecting()
DynObjAura * _dynObjAura
Definition Spell.h:543
void EffectCharge()
void EffectSummonObject()
void EffectSendTaxi()
void EffectCreateItem()
void EffectTameCreature()
void EffectGameObjectDamage()
SpellCastTargets m_targets
Definition Spell.h:409
void EffectSummonChangeItem()
void EffectDummy()
std::unique_ptr< PathGenerator > m_preGeneratedPath
Definition Spell.h:717
void EffectHealthLeech()
void EffectStealBeneficialBuff()
void EffectStuck()
void EffectInterruptCast()
void EffectSummonPlayer()
void EffectWeaponDmg()
int32 damage
Definition Spell.h:536
void EffectEnchantItemPrismatic()
void EffectSummonType()
void EffectSkinPlayerCorpse()
void ExecuteLogEffectSummonObject(uint8 effIndex, WorldObject *obj)
Definition Spell.cpp:4612
SpellEffectHandleMode effectHandleMode
Definition Spell.h:538
void EffectHealMechanical()
void EffectGameObjectRepair()
void EffectSummonObjectWild()
void EffectActivateObject()
void EffectSkill()
void EffectLeap()
void EffectTradeSkill()
void EffectPersistentAA()
void EffectQuestClear()
void EffectModifyThreatPercent()
void EffectForceDeselect()
void EffectPull()
void EffectParry()
void EffectRenamePet()
void AddComboPointGain(Unit *target, int8 amount)
Definition Spell.h:411
void EffectResurrect()
void EffectDestroyAllTotems()
WeaponAttackType m_attackType
Definition Spell.h:500
void EffectResurrectPet()
void EffectTriggerSpell()
union Spell::@266 m_misc
void EffectPullTowards()
ObjectGuid m_originalCasterGUID
Definition Spell.h:494
WorldObject *const m_caster
Definition Spell.h:490
void EffectPowerBurn()
std::string GetDebugInfo() const
Definition Spell.cpp:8305
void EffectDurabilityDamage()
void EffectSanctuary()
void ExecuteLogEffectOpenLock(uint8 effIndex, Object *obj)
Definition Spell.cpp:4594
void EffectCastButtons()
Item * itemTarget
Definition Spell.h:532
int32 m_damage
Definition Spell.h:550
void ExecuteLogEffectTakeTargetPower(uint8 effIndex, Unit *target, uint32 powerType, uint32 powerTaken, float gainMultiplier)
Definition Spell.cpp:4563
void EffectKnockBack()
void EffectReputation()
void DoCreateItem(uint32 itemId)
void EffectDistract()
void EffectKillCredit()
void EffectSummonPet()
void EffectEnergizePct()
void EffectDispelMechanic()
void EffectSelfResurrect()
void EffectDispel()
void EffectBind()
void EffectFeedPet()
void EffectNULL()
void EffectRechargeManaGem()
void EffectApplyAura()
void EffectAddHonor()
void EffectTriggerRitualOfSummoning()
void EffectInstaKill()
void CalculateJumpSpeeds(SpellEffectInfo const &spellEffectInfo, float dist, float &speedXY, float &speedZ)
void EffectInebriate()
void EffectOpenLock()
void EffectEnvironmentalDMG()
void EffectRedirectThreat()
void EffectRemoveAura()
void EffectDualWield()
void EffectAddComboPoints()
int32 m_healing
Definition Spell.h:551
void EffectPickPocket()
void EffectProficiency()
SpellEffectInfo const * effectInfo
Definition Spell.h:539
void EffectDisEnchant()
Unit * GetUnitCasterForEffectHandlers() const
Definition Spell.cpp:7551
void EffectAddExtraAttacks()
void EffectTriggerMissileSpell()
UnitAura * _spellAura
Definition Spell.h:542
Unit * unitTarget
Definition Spell.h:531
void EffectEnchantItemTmp()
SpellSchoolMask m_spellSchoolMask
Definition Spell.h:499
void EffectCreateRandomItem()
void EffectTeleUnitsFaceCaster()
void ExecuteLogEffectUnsummonObject(uint8 effIndex, WorldObject *obj)
Definition Spell.cpp:4618
void EffectPullTowardsDest()
void EffectKillCreditPersonal()
void ExecuteLogEffectInterruptCast(uint8 effIndex, Unit *victim, uint32 spellId)
Definition Spell.cpp:4579
SpellCastResult prepare(SpellCastTargets const &targets, AuraEffect const *triggeredByAura=nullptr)
Definition Spell.cpp:3091
void ExecuteLogEffectResurrect(uint8 effIndex, Unit *target)
Definition Spell.cpp:4624
void EffectSchoolDMG()
void SendLoot(ObjectGuid guid, LootType loottype)
void EffectThreat()
Corpse * m_corpseTarget
Definition Spell.h:534
void SummonGuardian(SpellEffectInfo const &spellEffectInfo, uint32 entry, SummonPropertiesEntry const *properties, uint32 numSummons)
void EffectResurrectNew()
void EffectChargeDest()
void EffectUntrainTalents()
void EffectLearnSpell()
void EffectMilling()
void EffectHealPct()
void ExecuteLogEffectCreateItem(uint8 effIndex, uint32 entry)
Definition Spell.cpp:4600
void EffectJumpDest()
void EffectScriptEffect()
void EffectAddFarsight()
void EffectEnergize()
WorldLocation * destTarget
Definition Spell.h:535
void EffectGameObjectSetDestructionState()
void EffectApplyGlyph()
SpellCastResult CanOpenLock(SpellEffectInfo const &spellEffectInfo, uint32 lockid, SkillType &skillid, int32 &reqSkillValue, int32 &skillValue)
Definition Spell.cpp:7811
void EffectQuestComplete()
void ExecuteLogEffectDestroyItem(uint8 effIndex, uint32 entry)
Definition Spell.cpp:4606
void EffectDiscoverTaxi()
void EffectTeleportUnits()
void EffectPlaySound()
void EffectLearnPetSpell()
void EffectPowerDrain()
Item * m_CastItem
Definition Spell.h:397
void CallScriptSuccessfulDispel(SpellEffIndex effIndex)
Definition Spell.cpp:8059
uint32 m_castItemEntry
Definition Spell.h:399
void EffectTaunt()
void EffectLeapBack()
void EffectDurabilityDamagePCT()
SpellValue *const m_spellValue
Definition Spell.h:492
void EffectLearnSkill()
void SendResurrectRequest(Player *target)
Definition Spell.cpp:4698
void EffectActivateSpec()
void EffectForceCast()
void EffectDismissPet()
void EffectEnchantItemPerm()
void EffectQuestFail()
void EffectCreateTamedPet()
void EffectJump()
void ExecuteLogEffectDurabilityDamage(uint8 effIndex, Unit *victim, int32 itemId, int32 slot)
Definition Spell.cpp:4586
ObjectGuid m_castItemGUID
Definition Spell.h:398
int64 GetUnitTargetCountForEffect(SpellEffIndex effect) const
Definition Spell.cpp:2386
GameObject * focusObject
Definition Spell.h:547
void EffectTitanGrip()
void ExecuteLogEffectExtraAttacks(uint8 effIndex, Unit *victim, uint32 attCount)
Definition Spell.cpp:4572
void finish(bool ok=true)
Definition Spell.cpp:3943
void EffectSpecCount()
static void SendCastResult(Player *caster, SpellInfo const *spellInfo, uint8 castCount, SpellCastResult result, SpellCustomErrors customError=SPELL_CUSTOM_ERROR_NONE, uint32 *param1=nullptr, uint32 *param2=nullptr)
Definition Spell.cpp:4150
SpellInfo const *const m_spellInfo
Definition Spell.h:396
void EffectUnlearnSpecialization()
uint8 m_runesState
Definition Spell.h:506
void EffectQuestStart()
void EffectDuel()
void EffectUnused()
int32 CalculateDamage(SpellEffectInfo const &spellEffectInfo) const
Definition Spell.cpp:6398
void EffectSkinning()
void EffectHeal()
virtual void UnSummon(uint32 msTime=0)
void ModifyThreatByPercent(Unit *target, int32 percent)
Unit * GetCurrentVictim()
auto const & GetThreatenedByMeList() const
bool IsThreatListEmpty(bool includeOffline=false) const
void AddThreat(Unit *target, float amount, SpellInfo const *spell=nullptr, bool ignoreModifiers=false, bool ignoreRedirects=false)
== AFFECT MY THREAT LIST ==
void RegisterRedirectThreat(uint32 spellId, ObjectGuid const &victim, uint32 pct)
== REDIRECT SYSTEM ==
void MatchUnitThreatToHighestThreat(Unit *target)
void UnSummon(uint32 msTime=0) override
Definition Totem.cpp:103
Definition Unit.h:783
static uint32 DealDamage(Unit *attacker, Unit *victim, uint32 damage, CleanDamage const *cleanDamage=nullptr, DamageEffectType damagetype=DIRECT_DAMAGE, SpellSchoolMask damageSchoolMask=SPELL_SCHOOL_MASK_NORMAL, SpellInfo const *spellProto=nullptr, bool durabilityLoss=true)
Definition Unit.cpp:724
float GetPctModifierValue(UnitMods unitMod, UnitModifierPctType modifierType) const
Definition Unit.cpp:9040
void ClearUnitState(uint32 f)
Definition Unit.h:891
bool IsVehicle() const
Definition Unit.h:901
void ReplaceAllDynamicFlags(uint32 flag) override
Definition Unit.h:833
void SetMinion(Minion *minion, bool apply)
Definition Unit.cpp:5852
uint32 SpellHealingBonusTaken(Unit *caster, SpellInfo const *spellProto, uint32 healamount, DamageEffectType damagetype) const
Definition Unit.cpp:7498
int32 ModifyPower(Powers power, int32 val, bool withPowerUpdate=true)
Definition Unit.cpp:8379
void RemoveAurasByType(AuraType auraType, std::function< bool(AuraApplication const *)> const &check, AuraRemoveMode removeMode=AURA_REMOVE_BY_DEFAULT)
Definition Unit.cpp:3788
void JumpTo(float speedXY, float speedZ, bool forward=true, Optional< Position > dest={})
Definition Unit.cpp:12425
void RemoveGameObject(GameObject *gameObj, bool del)
Definition Unit.cpp:5161
AuraEffectList const & GetAuraEffectsByType(AuraType type) const
Definition Unit.h:1397
uint32 m_lastSanctuaryTime
Definition Unit.h:1585
void SetChannelObjectGuid(ObjectGuid guid)
Definition Unit.h:1474
Aura * GetAura(uint32 spellId, ObjectGuid casterGUID=ObjectGuid::Empty, ObjectGuid itemCasterGUID=ObjectGuid::Empty, uint8 reqEffMask=0) const
Definition Unit.cpp:4462
Pet * ToPet()
Definition Unit.h:1804
bool CanHaveThreatList() const
====================== THREAT & COMBAT ====================
Definition Unit.h:1136
float GetSpeed(UnitMoveType mtype) const
Definition Unit.cpp:8608
void RemoveAura(AuraApplicationMap::iterator &i, AuraRemoveMode mode=AURA_REMOVE_BY_DEFAULT)
Definition Unit.cpp:3661
ThreatManager & GetThreatManager()
Definition Unit.h:1169
virtual void SetCanDualWield(bool value)
Definition Unit.h:852
uint8 GetClass() const
Definition Unit.h:909
Totem * ToTotem()
Definition Unit.h:1807
uint32 MeleeDamageBonusTaken(Unit *attacker, uint32 pdamage, WeaponAttackType attType, SpellInfo const *spellProto=nullptr, SpellSchoolMask damageSchoolMask=SPELL_SCHOOL_MASK_NORMAL)
Definition Unit.cpp:7973
std::multimap< uint32, AuraApplication * > AuraApplicationMap
Definition Unit.h:794
ShapeshiftForm GetShapeshiftForm() const
Definition Unit.h:1503
void SetFaction(uint32 faction) override
Definition Unit.h:988
void RemoveAurasDueToSpellByDispel(uint32 spellId, uint32 dispellerSpellId, ObjectGuid casterGUID, WorldObject *dispeller, uint8 chargesRemoved=1)
Definition Unit.cpp:3840
uint32 SpellHealingBonusDone(Unit *victim, SpellInfo const *spellProto, uint32 healamount, DamageEffectType damagetype, SpellEffectInfo const &spellEffectInfo, Optional< float > const &donePctTotal, uint32 stack=1) const
Definition Unit.cpp:7274
Pet * CreateTamedPetFrom(Creature *creatureTarget, uint32 spell_id=0)
Definition Unit.cpp:10827
static void CalcAbsorbResist(DamageInfo &damageInfo, Spell *spell=nullptr)
Definition Unit.cpp:1780
Unit * GetVehicleBase() const
Definition Unit.cpp:11797
MotionMaster * GetMotionMaster()
Definition Unit.h:1683
bool IsPet() const
Definition Unit.h:898
Powers GetPowerType() const
Definition Unit.h:945
bool HasUnitFlag(UnitFlags flags) const
Definition Unit.h:967
void SetCreatedBySpell(int32 spellId)
Definition Unit.h:978
uint32 GetMaxHealth() const
Definition Unit.h:928
AuraEffect * GetAuraEffect(uint32 spellId, uint8 effIndex, ObjectGuid casterGUID=ObjectGuid::Empty) const
Definition Unit.cpp:4382
ObjectGuid m_ObjectSlot[MAX_GAMEOBJECT_SLOT]
Definition Unit.h:1501
uint32 GetSpellCritDamageReduction(uint32 damage) const
Definition Unit.h:1074
bool IsAlive() const
Definition Unit.h:1247
AuraEffect * IsScriptOverriden(SpellInfo const *spell, int32 script) const
Definition Unit.cpp:4662
float GetCombatReach() const override
Definition Unit.h:853
int32 HealBySpell(HealInfo &healInfo, bool critical=false)
Definition Unit.cpp:6360
void SetHealth(uint32 val)
Definition Unit.cpp:9338
void SendSpellNonMeleeDamageLog(SpellNonMeleeDamage const *log)
Definition Unit.cpp:5199
void SetPetFlag(UnitPetFlag flags)
Definition Unit.h:1008
TempSummon * ToTempSummon()
Definition Unit.h:1810
CharmInfo * GetCharmInfo()
Definition Unit.h:1300
bool HasAura(uint32 spellId, ObjectGuid casterGUID=ObjectGuid::Empty, ObjectGuid itemCasterGUID=ObjectGuid::Empty, uint8 reqEffMask=0) const
Definition Unit.cpp:4558
uint32 CalculateDamage(WeaponAttackType attType, bool normalized, bool addTotalPct, uint8 itemDamagesMask=0) const
Definition Unit.cpp:2293
void SetVirtualItem(uint32 slot, uint32 itemId)
Definition Unit.cpp:13839
uint32 SpellDamageBonusDone(Unit *victim, SpellInfo const *spellProto, uint32 pdamage, DamageEffectType damagetype, SpellEffectInfo const &spellEffectInfo, Optional< float > const &donePctTotal, uint32 stack=1) const
Definition Unit.cpp:6393
uint32 GetDiseasesByCaster(ObjectGuid casterGUID, bool remove=false)
Definition Unit.cpp:4674
void AddGameObject(GameObject *gameObj)
Definition Unit.cpp:5116
virtual bool IsImmunedToSpellEffect(SpellInfo const *spellInfo, SpellEffectInfo const &spellEffectInfo, WorldObject const *caster, bool requireImmunityPurgesEffectAttribute=false) const
Definition Unit.cpp:7751
int32 GetHealthGain(int32 dVal)
Definition Unit.cpp:8353
bool IsInFlight() const
Definition Unit.h:1133
bool Attack(Unit *victim, bool meleeAttack)
Definition Unit.cpp:5477
static void ProcSkillsAndAuras(Unit *actor, Unit *actionTarget, uint32 typeMaskActor, uint32 typeMaskActionTarget, uint32 spellTypeMask, uint32 spellPhaseMask, uint32 hitMask, Spell *spell, DamageInfo *damageInfo, HealInfo *healInfo)
Definition Unit.cpp:5218
AuraApplication * _CreateAuraApplication(Aura *aura, uint8 effMask)
Definition Unit.cpp:3337
uint32 GetMaxPower(Powers power) const
Definition Unit.h:950
void InterruptSpell(CurrentSpellTypes spellType, bool withDelayed=true, bool withInstant=true, SpellCastResult result=SPELL_FAILED_INTERRUPTED, Optional< SpellCastResult > resultOther={})
Definition Unit.cpp:3044
bool IsSummon() const
Definition Unit.h:896
uint32 GetHealth() const
Definition Unit.h:927
uint32 GetFaction() const override
Definition Unit.h:987
void SetPower(Powers power, uint32 val, bool withPowerUpdate=true, bool force=false)
Definition Unit.cpp:9398
bool HasAuraState(AuraStateType flag, SpellInfo const *spellProto=nullptr, Unit const *Caster=nullptr) const
Definition Unit.cpp:5757
void GetDispellableAuraList(WorldObject const *caster, uint32 dispelMask, DispelChargesList &dispelList, bool isReflect=false) const
Definition Unit.cpp:4486
AttackerSet const & getAttackers() const
Definition Unit.h:871
std::multimap< uint32, Aura * > AuraMap
Definition Unit.h:790
virtual uint32 GetShieldBlockValue() const =0
void RemoveAuraFromStack(uint32 spellId, ObjectGuid casterGUID=ObjectGuid::Empty, AuraRemoveMode removeMode=AURA_REMOVE_BY_DEFAULT)
Definition Unit.cpp:3823
bool HasAuraType(AuraType auraType) const
Definition Unit.cpp:4565
void NearTeleportTo(Position const &pos, bool casting=false)
Definition Unit.cpp:12803
uint32 GetAttackTime(WeaponAttackType att) const
Definition Unit.cpp:8411
void RemoveAurasDueToSpellBySteal(uint32 spellId, ObjectGuid casterGUID, WorldObject *stealer)
Definition Unit.cpp:3868
std::set< Unit * > AttackerSet
Definition Unit.h:786
void RemoveAurasDueToSpell(uint32 spellId, ObjectGuid casterGUID=ObjectGuid::Empty, uint8 reqEffMask=0, AuraRemoveMode removeMode=AURA_REMOVE_BY_DEFAULT)
Definition Unit.cpp:3807
void AddExtraAttacks(uint32 count)
Definition Unit.cpp:2150
void EnergizeBySpell(Unit *victim, uint32 spellId, int32 damage, Powers powerType)
Definition Unit.cpp:6380
void SetOwnerGUID(ObjectGuid owner)
Definition Unit.cpp:5782
bool HasUnitState(const uint32 f) const
Definition Unit.h:890
uint32 HasUnitTypeMask(uint32 mask) const
Definition Unit.h:894
uint8 GetComboPoints(Unit const *who=nullptr) const
--------—Combo point system----------------—
Definition Unit.h:1711
uint32 CountPctFromMaxHealth(int32 pct) const
Definition Unit.h:936
virtual void CalculateMinMaxDamage(WeaponAttackType attType, bool normalized, bool addTotalPct, float &minDamage, float &maxDamage, uint8 damageIndex) const =0
SpellHistory * GetSpellHistory()
Definition Unit.h:1497
bool IsControlledByPlayer() const
Definition Unit.h:1271
AuraEffect * GetDummyAuraEffect(SpellFamilyNames name, uint32 iconId, uint8 effIndex) const
Definition Unit.cpp:4438
void SetMaxHealth(uint32 val)
Definition Unit.cpp:9370
void SetCreatorGUID(ObjectGuid creator)
Definition Unit.h:1257
uint32 GetPower(Powers power) const
Definition Unit.h:948
void CombatStop(bool includingCast=false, bool mutualPvP=true)
Definition Unit.cpp:5633
uint32 GetCreatureTypeMask() const
Definition Unit.cpp:8898
AuraApplicationMap & GetAppliedAuras()
Definition Unit.h:1351
std::list< AuraEffect * > AuraEffectList
Definition Unit.h:801
void RemoveMovementImpairingAuras(bool withRoot)
Definition Unit.cpp:4092
uint32 GetCreateMana() const
Definition Unit.h:1465
bool IsTotem() const
Definition Unit.h:900
virtual bool IsEngaged() const
Definition Unit.h:1140
uint32 MeleeDamageBonusDone(Unit *pVictim, uint32 damage, WeaponAttackType attType, SpellInfo const *spellProto=nullptr, SpellSchoolMask damageSchoolMask=SPELL_SCHOOL_MASK_NORMAL)
Definition Unit.cpp:7811
void ReplaceAllNpcFlags(NPCFlags flags)
Definition Unit.h:1113
AuraMap & GetOwnedAuras()
Definition Unit.h:1341
int32 SpellBaseDamageBonusDone(SpellSchoolMask schoolMask) const
Definition Unit.cpp:6927
void KnockbackFrom(float x, float y, float speedXY, float speedZ)
Definition Unit.cpp:12175
ObjectGuid m_SummonSlot[MAX_SUMMON_SLOT]
Definition Unit.h:1500
ObjectGuid GetTarget() const
Definition Unit.h:1813
uint8 GetLevel() const
Definition Unit.h:903
uint8 GetRace() const
Definition Unit.h:906
float GetTotalAttackPowerValue(WeaponAttackType attType) const
Definition Unit.cpp:9289
void RemoveUnitFlag(UnitFlags flags)
Definition Unit.h:969
ObjectGuid GetPetGUID() const
Definition Unit.h:1260
uint32 SpellDamageBonusTaken(Unit *caster, SpellInfo const *spellProto, uint32 pdamage, DamageEffectType damagetype) const
Definition Unit.cpp:6850
bool isDead() const
Definition Unit.h:1249
Spell * GetCurrentSpell(CurrentSpellTypes spellType) const
Definition Unit.h:1489
void WorldRelocate(WorldLocation const &loc)
Definition Position.h:179
uint32 GetMapId() const
Definition Position.h:193
WorldLocation GetWorldLocation() const
Definition Position.h:188
uint32 m_mapId
Definition Position.h:195
uint32 GetPhaseMask() const
Definition Object.h:370
virtual void SendMessageToSet(WorldPacket const *data, bool self) const
Definition Object.cpp:1784
Map * GetMap() const
Definition Object.h:451
InstanceScript * GetInstanceScript() const
Definition Object.cpp:1088
bool IsWithinLOS(float x, float y, float z, LineOfSightChecks checks=LINEOFSIGHT_ALL_CHECKS, VMAP::ModelIgnoreFlags ignoreFlags=VMAP::ModelIgnoreFlags::Nothing) const
Definition Object.cpp:1207
ObjectGuid GetPrivateObjectOwner() const
Definition Object.h:597
void GetClosePoint(float &x, float &y, float &z, float size, float distance2d=0, float relAngle=0) const
Definition Object.cpp:3245
SpellCastResult CastSpell(CastSpellTargetArg const &targets, uint32 spellId, CastSpellExtraArgs const &args={ })
Definition Object.cpp:2833
void MovePositionToFirstCollision(Position &pos, float dist, float angle)
Definition Object.cpp:3324
TempSummon * SummonCreature(uint32 entry, Position const &pos, TempSummonType despawnType=TEMPSUMMON_MANUAL_DESPAWN, Milliseconds despawnTime=0s, uint32 vehId=0, uint32 spellId=0, ObjectGuid privateObjectOwner=ObjectGuid::Empty)
Definition Object.cpp:1993
Unit * GetOwner() const
Definition Object.cpp:2181
ZoneScript * GetZoneScript() const
Definition Object.h:457
bool IsPrivateObject() const
Definition Object.h:596
int32 ModSpellDuration(SpellInfo const *spellInfo, WorldObject const *target, int32 duration, bool positive, uint32 effectMask) const
Definition Object.cpp:2321
std::string const & GetName() const
Definition Object.h:384
float ApplyEffectModifiers(SpellInfo const *spellInfo, uint8 effIndex, float value) const
Definition Object.cpp:2282
Player * GetSpellModOwner() const
Definition Object.cpp:2224
Player * GetCharmerOrOwnerPlayerOrPlayerItself() const
Definition Object.cpp:2204
void SetName(std::string newname)
Definition Object.h:385
float GetVisibilityRange() const
Definition Object.cpp:1493
void PlayDirectSound(uint32 soundId, Player *target=nullptr)
Definition Object.cpp:3432
virtual uint32 GetFaction() const =0
float GetDistance(WorldObject const *obj) const
Definition Object.cpp:1124
uint32 GetAreaId() const
Definition Object.h:376
Position GetFirstCollisionPosition(float dist, float angle)
Definition Object.cpp:3258
bool IsFriendlyTo(WorldObject const *target) const
Definition Object.cpp:2802
virtual float GetCombatReach() const
Definition Object.h:360
Player * GetAffectingPlayer() const
Definition Object.cpp:2213
void GetRandomPoint(Position const &srcPos, float distance, float &rand_x, float &rand_y, float &rand_z) const
Definition Object.cpp:1377
FactionTemplateEntry const * GetFactionTemplateEntry() const
Definition Object.cpp:2635
int32 CalculateSpellDamage(SpellEffectInfo const &spellEffectInfo, int32 const *basePoints=nullptr) const
Definition Object.cpp:2249
void Initialize(uint16 opcode, size_t newres=200)
Definition WorldPacket.h:51
void SendNotification(char const *format,...) ATTR_PRINTF(2
bool HasPermission(uint32 permissionId)
uint32 GetAccountId() const
void SendDiscoverNewTaxiNode(uint32 nodeid)
@ SMSG_BREAK_TARGET
Definition Opcodes.h:367
@ SMSG_CLEAR_TARGET
Definition Opcodes.h:988
@ SMSG_DISPEL_FAILED
Definition Opcodes.h:639
@ SMSG_SPELLSTEALLOG
Definition Opcodes.h:848
@ SMSG_SPELLINSTAKILLLOG
Definition Opcodes.h:844
@ SMSG_SPELLDISPELLOG
Definition Opcodes.h:664
@ SMSG_DUEL_REQUESTED
Definition Opcodes.h:388
#define sWorld
Definition World.h:901
@ CONFIG_SKILL_MILLING
Definition World.h:110
@ CONFIG_SKILL_PROSPECTING
Definition World.h:109
@ CONFIG_CAST_UNSTUCK
Definition World.h:106
uint32 GetGameTimeMS()
Definition GameTime.cpp:47
TC_GAME_API float gravity
TC_GAME_API Player * FindPlayer(ObjectGuid const &)
uint32 hk_honor_at_level(uint8 level, float multiplier=1.0f)
Definition Formulas.h:41
@ RBAC_PERM_LOG_GM_TRADE
Definition RBAC.h:64
uint32 GetAction() const
Definition Player.h:225
ActionButtonType GetType() const
Definition Player.h:224
AuraCreateInfo & SetBaseAmount(int32 const *bp)
AuraCreateInfo & SetCaster(Unit *caster)
TriggerCastFlags TriggerFlags
CastSpellExtraArgs & AddSpellMod(SpellValueMod mod, int32 val)
static void VisitWorldObjects(WorldObject const *obj, T &visitor, float radius, bool dont_load=true)
Definition CellImpl.h:180
void SaveStayPosition()
Definition Unit.cpp:13169
void SetIsCommandFollow(bool val)
Definition Unit.cpp:13159
void SetIsAtStay(bool val)
Definition Unit.cpp:13190
void SetIsFollowing(bool val)
Definition Unit.cpp:13200
void SetIsReturning(bool val)
Definition Unit.cpp:13210
bool HasCommandState(CommandStates state) const
Definition Unit.h:697
void SetIsCommandAttack(bool val)
Definition Unit.cpp:13149
SkillType GetRequiredLootSkill() const
bool IsFriendlyTo(FactionTemplateEntry const &entry) const
bool CannotBeUsedUnderImmunity() const
struct GameObjectTemplate::@191::@200 spellFocus
struct GameObjectTemplate::@191::@202 goober
struct GameObjectTemplate::@191::@196 chest
struct GameObjectTemplate::@191::@195 questgiver
struct GameObjectTemplate::@191::@194 button
uint32 GetLockId() const
uint32 GetRequiredSkillRank() const
std::array< ItemEffect, MAX_ITEM_PROTO_SPELLS > Effects
uint32 GetBaseItemLevel() const
uint32 DisenchantID
uint32 GetMaxStackSize() const
bool HasSignature() const
bool HasFlag(ItemFlags flag) const
uint32 GetLockID() const
float m_positionZ
Definition Position.h:58
float GetExactDist2d(const float x, const float y) const
Definition Position.h:109
float GetRelativeAngle(float x, float y) const
Definition Position.h:139
float GetExactDist(float x, float y, float z) const
Definition Position.h:121
float m_positionX
Definition Position.h:56
float GetPositionZ() const
Definition Position.h:81
float m_positionY
Definition Position.h:57
float GetOrientation() const
Definition Position.h:82
float GetAbsoluteAngle(float x, float y) const
Definition Position.h:128
void SetOrientation(float orientation)
Definition Position.h:74
float GetPositionX() const
Definition Position.h:79
void GetPosition(float &x, float &y) const
Definition Position.h:84
float GetPositionY() const
Definition Position.h:80
void Relocate(float x, float y)
Definition Position.h:66
bool IsHostile
Definition Player.h:246
bool IsInHostileArea
Definition Player.h:247
static QuaternionData fromEulerAnglesZYX(float Z, float Y, float X)
uint32 Value[MAX_SKILL_STEP]
uint32 Effect[MAX_ITEM_ENCHANTMENT_EFFECTS]
int32 EffectBasePoints[MAX_SPELL_EFFECTS]
Definition Spell.h:122