diff --git a/sql/mangos_spell_check.sql b/sql/mangos_spell_check.sql index 1585270f7..e284285f0 100644 --- a/sql/mangos_spell_check.sql +++ b/sql/mangos_spell_check.sql @@ -38,6 +38,7 @@ CREATE TABLE `spell_check` ( INSERT INTO spell_check (spellid,SpellFamilyName,SpellFamilyMaskA,SpellFamilyMaskB,SpellIcon,SpellVisual,SpellCategory,EffectType,EffectAura,EffectIdx,Name,Code) VALUES /* sorted by spell ids */ /*id fm familyMaskA fmMaskB icon vis cat eff aur ef name code */ +(781, 9, -1, -1, -1, -1, -1, 3, -1,-1,'Disengage', 'Spell::EffectDummy'), (1454, 5,0x0000000000040000,0x00000000, -1, -1, -1, 3, -1,-1,'Life Tap', 'Spell::EffectDummy'), (1455, 5,0x0000000000040000,0x00000000, -1, -1, -1, 3, -1,-1,'Life Tap', 'Spell::EffectDummy'), (1456, 5,0x0000000000040000,0x00000000, -1, -1, -1, 3, -1,-1,'Life Tap', 'Spell::EffectDummy'), @@ -315,7 +316,10 @@ INSERT INTO spell_check (spellid,SpellFamilyName,SpellFamilyMaskA,SpellFamilyMas (55004, 0, -1, -1, -1, -1, -1, 3, -1,-1,'Nitro Boosts', 'Spell::EffectDummy'), (55441,11, -1, -1, -1, -1, -1, -1, 4,-1,'Glyph of Mana Tide', 'Spell::EffectDummy'), (56235,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Glyph of Conflagrate', 'Spell::EffectSchoolDMG'), +(56446,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Disengage', 'Spell::EffectDummy'), (57627,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Charge', 'Spell::EffectSchoolDMG'), +(57635, 9, -1, -1, -1, -1, -1, 3, -1,-1,'Disengage', 'Spell::EffectDummy'), +(57636,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Disengage', 'Spell::EffectDummy'), (57946, 5,0x0000000000040000,0x00000000, -1, -1, -1, 3, -1,-1,'Life Tap', 'Spell::EffectDummy'), (58367,-1, -1, -1, -1, -1, -1, -1, 4,-1,'Glyph of Execution', 'Spell::EffectDummy'), (58418, 0, -1, -1, -1, -1, -1, 3, -1,-1,'Portal to Orgrimmar', 'Spell::EffectDummy'), @@ -324,9 +328,13 @@ INSERT INTO spell_check (spellid,SpellFamilyName,SpellFamilyMaskA,SpellFamilyMas (59645,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Underbelly Elixir', 'Spell::EffectDummy'), (59831,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Underbelly Elixir', 'Spell::EffectDummy'), (59843,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Underbelly Elixir', 'Spell::EffectDummy'), +(60932, 0, -1, -1, -1, -1, -1, 3, -1,-1,'Disengage', 'Spell::EffectDummy'), +(60934,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Disengage', 'Spell::EffectDummy'), (61290, 5,0x0001000000000000,0x00000000, -1, -1, -1, 2, -1,-1,'Shadowflame', 'Spell::EffectSchoolDMG'), (61291,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Shadowflame', 'Spell::EffectSchoolDMG'), (61491, 0, -1, -1, -1, -1, -1, 2, -1,-1,'Intercept', 'Spell::EffectSchoolDMG'), +(61507, 9, -1, -1, -1, -1, -1, 3, -1,-1,'Disengage', 'Spell::EffectDummy'), +(61508,-1, -1, -1, -1, -1, -1, -1, -1,-1,'Disengage', 'Spell::EffectDummy'), (63375,-1, -1, -1, -1, -1, -1, 30, -1,-1,'Improved Stormstrike', 'Spell::EffectEnergize'), /* sorted by spell names */ @@ -344,6 +352,7 @@ INSERT INTO spell_check (spellid,SpellFamilyName,SpellFamilyMaskA,SpellFamilyMas ( 0,15,0x0000000000002000,0x00000000, -1, -1, -1, 3, -1,-1,'Death Coil', 'Spell::EffectDummy'), ( 0,15,0x0000000000000010,0x00000000, -1, -1, -1, 3, -1,-1,'Death Strike', 'Spell::EffectDummy'), ( 0, 5, -1, -1, -1, -1, 12, 38, -1,-1,'Devour Magic', 'Spell::EffectDispel'), +( 0, 9,0x0000400000000000,0x00000000, -1, -1, -1, 3, -1,-1,'Disengage', 'Spell::EffectDummy'), ( 0, 8,0x0000000800000000,0x00000000, -1, -1, -1, 2, -1,-1,'Envenom', 'Spell::EffectSchoolDMG'), ( 0, 8,0x0000000000020000,0x00000000, -1, -1, -1, 2, -1,-1,'Eviscerate', 'Spell::EffectSchoolDMG'), (0, 4,0x0000000020000000,0x00000000, -1, -1, -1, 3, -1,-1,'Execute', 'Spell::EffectDummy'), diff --git a/src/game/MovementHandler.cpp b/src/game/MovementHandler.cpp index b43eb2a8c..7696e1e48 100644 --- a/src/game/MovementHandler.cpp +++ b/src/game/MovementHandler.cpp @@ -498,43 +498,41 @@ void WorldSession::HandleMountSpecialAnimOpcode(WorldPacket& /*recvdata*/) GetPlayer()->SendMessageToSet(&data, false); } -void WorldSession::HandleMoveKnockBackAck( WorldPacket & /*recv_data*/ ) +void WorldSession::HandleMoveKnockBackAck( WorldPacket & recv_data ) { sLog.outDebug("CMSG_MOVE_KNOCK_BACK_ACK"); - // Currently not used but maybe use later for recheck final player position - // (must be at call same as into "recv_data >> x >> y >> z >> orientation;" - /* - uint32 flags, time; - float x, y, z, orientation; - uint64 guid; - uint32 sequence; - uint32 ukn1; - float xdirection,ydirection,hspeed,vspeed; + recv_data.read_skip(); // guid + recv_data.read_skip(); // unk - recv_data >> guid; - recv_data >> sequence; - recv_data >> flags >> time; - recv_data >> x >> y >> z >> orientation; - recv_data >> ukn1; //unknown - recv_data >> vspeed >> xdirection >> ydirection >> hspeed; - - // skip not personal message; - if(GetPlayer()->GetGUID()!=guid) - return; - - // check code - */ + MovementInfo movementInfo; + ReadMovementInfo(recv_data, &movementInfo); } -void WorldSession::HandleMoveHoverAck( WorldPacket& /*recv_data*/ ) +void WorldSession::HandleMoveHoverAck( WorldPacket& recv_data ) { sLog.outDebug("CMSG_MOVE_HOVER_ACK"); + + recv_data.read_skip(); // guid + recv_data.read_skip(); // unk + + MovementInfo movementInfo; + ReadMovementInfo(recv_data, &movementInfo); + + recv_data.read_skip(); // unk2 } -void WorldSession::HandleMoveWaterWalkAck(WorldPacket& /*recv_data*/) +void WorldSession::HandleMoveWaterWalkAck(WorldPacket& recv_data) { sLog.outDebug("CMSG_MOVE_WATER_WALK_ACK"); + + recv_data.read_skip(); // guid + recv_data.read_skip(); // unk + + MovementInfo movementInfo; + ReadMovementInfo(recv_data, &movementInfo); + + recv_data.read_skip(); // unk2 } void WorldSession::HandleSummonResponseOpcode(WorldPacket& recv_data) diff --git a/src/game/SharedDefines.h b/src/game/SharedDefines.h index 3b5bad699..5b0f0b911 100644 --- a/src/game/SharedDefines.h +++ b/src/game/SharedDefines.h @@ -670,7 +670,7 @@ enum SpellEffects SPELL_EFFECT_CALL_PET = 135, SPELL_EFFECT_HEAL_PCT = 136, SPELL_EFFECT_ENERGIZE_PCT = 137, - SPELL_EFFECT_138 = 138, + SPELL_EFFECT_LEAP_BACK = 138, SPELL_EFFECT_CLEAR_QUEST = 139, SPELL_EFFECT_FORCE_CAST = 140, SPELL_EFFECT_141 = 141, diff --git a/src/game/Spell.h b/src/game/Spell.h index 8e8dcf412..d3092c895 100644 --- a/src/game/Spell.h +++ b/src/game/Spell.h @@ -280,7 +280,8 @@ class Spell void EffectResurrect(uint32 i); void EffectParry(uint32 i); void EffectBlock(uint32 i); - void EffectMomentMove(uint32 i); + void EffectLeapForward(uint32 i); + void EffectLeapBack(uint32 i); void EffectTransmitted(uint32 i); void EffectDisEnchant(uint32 i); void EffectInebriate(uint32 i); diff --git a/src/game/SpellEffects.cpp b/src/game/SpellEffects.cpp index 93fd6dc03..a52d57323 100644 --- a/src/game/SpellEffects.cpp +++ b/src/game/SpellEffects.cpp @@ -86,7 +86,7 @@ pEffect SpellEffects[TOTAL_SPELL_EFFECTS]= &Spell::EffectUnused, // 26 SPELL_EFFECT_DEFENSE one spell: Defense &Spell::EffectPersistentAA, // 27 SPELL_EFFECT_PERSISTENT_AREA_AURA &Spell::EffectSummonType, // 28 SPELL_EFFECT_SUMMON - &Spell::EffectMomentMove, // 29 SPELL_EFFECT_LEAP + &Spell::EffectLeapForward, // 29 SPELL_EFFECT_LEAP &Spell::EffectEnergize, // 30 SPELL_EFFECT_ENERGIZE &Spell::EffectWeaponDmg, // 31 SPELL_EFFECT_WEAPON_PERCENT_DAMAGE &Spell::EffectTriggerMissileSpell, // 32 SPELL_EFFECT_TRIGGER_MISSILE @@ -195,7 +195,7 @@ pEffect SpellEffects[TOTAL_SPELL_EFFECTS]= &Spell::EffectNULL, //135 SPELL_EFFECT_CALL_PET &Spell::EffectHealPct, //136 SPELL_EFFECT_HEAL_PCT &Spell::EffectEnergisePct, //137 SPELL_EFFECT_ENERGIZE_PCT - &Spell::EffectNULL, //138 SPELL_EFFECT_138 Leap + &Spell::EffectLeapBack, //138 SPELL_EFFECT_LEAP_BACK Leap back &Spell::EffectUnused, //139 SPELL_EFFECT_CLEAR_QUEST (misc - is quest ID) &Spell::EffectForceCast, //140 SPELL_EFFECT_FORCE_CAST &Spell::EffectNULL, //141 SPELL_EFFECT_141 damage and reduce speed? @@ -1238,6 +1238,11 @@ void Spell::EffectDummy(uint32 i) m_caster->CastSpell(m_caster,spell_id,true,NULL); return; } + case 60932: // Disengage (one from creature versions) + if (!unitTarget) + return; + m_caster->CastSpell(unitTarget,60934,true,NULL); + return; } //All IconID Check in there @@ -1572,6 +1577,28 @@ void Spell::EffectDummy(uint32 i) return; } + // Disengage + if (m_spellInfo->SpellFamilyFlags & UI64LIT(0x0000400000000000)) + { + Unit* target = unitTarget; + uint32 spellid; + switch(m_spellInfo->Id) + { + case 781: // player case + target = m_caster; + spellid = 56446; + break; + case 57635: spellid = 57636; break; // one from creature cases + case 61507: spellid = 61508; break; // one from creature cases + default: + sLog.outError("Spell %u not handled propertly in EffectDummy(Disengage)",m_spellInfo->Id); + return; + } + if (!target || !target->isAlive()) + return; + m_caster->CastSpell(target,spellid,true,NULL); + } + switch(m_spellInfo->Id) { case 23989: // Readiness talent @@ -5992,7 +6019,7 @@ void Spell::EffectBlock(uint32 /*i*/) ((Player*)unitTarget)->SetCanBlock(true); } -void Spell::EffectMomentMove(uint32 i) +void Spell::EffectLeapForward(uint32 i) { if(unitTarget->isInFlight()) return; @@ -6020,6 +6047,14 @@ void Spell::EffectMomentMove(uint32 i) } } +void Spell::EffectLeapBack(uint32 i) +{ + if(unitTarget->isInFlight()) + return; + + m_caster->KnockBackFrom(unitTarget,float(m_spellInfo->EffectMiscValue[i])/10,float(damage)/10); +} + void Spell::EffectReputation(uint32 i) { if(!unitTarget || unitTarget->GetTypeId() != TYPEID_PLAYER) @@ -6249,25 +6284,10 @@ void Spell::EffectSummonCritter(uint32 i) void Spell::EffectKnockBack(uint32 i) { - if(!unitTarget || !m_caster) + if(!unitTarget) return; - // Effect only works on players - if(unitTarget->GetTypeId()!=TYPEID_PLAYER) - return; - - float vsin = sin(m_caster->GetAngle(unitTarget)); - float vcos = cos(m_caster->GetAngle(unitTarget)); - - WorldPacket data(SMSG_MOVE_KNOCK_BACK, 8+4+4+4+4+4); - data.append(unitTarget->GetPackGUID()); - data << uint32(0); // Sequence - data << float(vcos); // x direction - data << float(vsin); // y direction - data << float(m_spellInfo->EffectMiscValue[i])/10; // Horizontal speed - data << float(damage/-10); // Z Movement speed (vertical) - - ((Player*)unitTarget)->GetSession()->SendPacket(&data); + unitTarget->KnockBackFrom(m_caster,float(m_spellInfo->EffectMiscValue[i])/10,float(damage)/10); } void Spell::EffectSendTaxi(uint32 i) @@ -6280,26 +6300,10 @@ void Spell::EffectSendTaxi(uint32 i) void Spell::EffectPlayerPull(uint32 i) { - if(!unitTarget || !m_caster) + if(!unitTarget) return; - // Effect only works on players - if(unitTarget->GetTypeId()!=TYPEID_PLAYER) - return; - - float vsin = sin(unitTarget->GetAngle(m_caster)); - float vcos = cos(unitTarget->GetAngle(m_caster)); - - WorldPacket data(SMSG_MOVE_KNOCK_BACK, 8+4+4+4+4+4); - data.append(unitTarget->GetPackGUID()); - data << uint32(0); // Sequence - data << float(vcos); // x direction - data << float(vsin); // y direction - // Horizontal speed - data << float(damage ? damage : unitTarget->GetDistance2d(m_caster)); - data << float(m_spellInfo->EffectMiscValue[i])/-10; // Z Movement speed - - ((Player*)unitTarget)->GetSession()->SendPacket(&data); + unitTarget->KnockBackFrom(m_caster,float(damage ? damage : unitTarget->GetDistance2d(m_caster)),float(m_spellInfo->EffectMiscValue[i])/10); } void Spell::EffectDispelMechanic(uint32 i) diff --git a/src/game/Unit.cpp b/src/game/Unit.cpp index 802c949f1..56002a5f3 100644 --- a/src/game/Unit.cpp +++ b/src/game/Unit.cpp @@ -44,6 +44,7 @@ #include "CellImpl.h" #include "Path.h" #include "Traveller.h" +#include "VMapFactory.h" #include @@ -12051,3 +12052,47 @@ void Unit::SetPvP( bool state ) if(Creature *totem = GetMap()->GetCreature(m_TotemSlot[i])) totem->SetPvP(state); } + +void Unit::KnockBackFrom(Unit* target, float horizintalSpeed, float verticalSpeed) +{ + float angle = this == target ? GetOrientation() + M_PI : target->GetAngle(this); + float vsin = sin(angle); + float vcos = cos(angle); + + // Effect propertly implemented only for players + if(GetTypeId()==TYPEID_PLAYER) + { + WorldPacket data(SMSG_MOVE_KNOCK_BACK, 8+4+4+4+4+4); + data.append(GetPackGUID()); + data << uint32(0); // Sequence + data << float(vcos); // x direction + data << float(vsin); // y direction + data << float(horizintalSpeed); // Horizontal speed + data << float(-verticalSpeed); // Z Movement speed (vertical) + ((Player*)this)->GetSession()->SendPacket(&data); + } + else + { + float dis = horizintalSpeed; + + float ox, oy, oz; + GetPosition(ox, oy, oz); + + float fx = ox + dis * vcos; + float fy = oy + dis * vsin; + float fz = oz; + + float fx2, fy2, fz2; // getObjectHitPos overwrite last args in any result case + if(VMAP::VMapFactory::createOrGetVMapManager()->getObjectHitPos(GetMapId(), ox,oy,oz+0.5, fx,fy,oz+0.5,fx2,fy2,fz2, -0.5)) + { + fx = fx2; + fy = fy2; + fz = fz2; + UpdateGroundPositionZ(fx, fy, fz); + } + + //FIXME: this mostly hack, must exist some packet for proper creature move at client side + // with CreatureRelocation at server side + NearTeleportTo(fx, fy, fz, GetOrientation(), this == target); + } +} diff --git a/src/game/Unit.h b/src/game/Unit.h index 30875044d..385224077 100644 --- a/src/game/Unit.h +++ b/src/game/Unit.h @@ -1450,6 +1450,8 @@ class MANGOS_DLL_SPEC Unit : public WorldObject void SetHover(bool on); bool isHover() const { return HasAuraType(SPELL_AURA_HOVER); } + void KnockBackFrom(Unit* target, float horizintalSpeed, float verticalSpeed); + void _RemoveAllAuraMods(); void _ApplyAllAuraMods(); diff --git a/src/shared/revision_nr.h b/src/shared/revision_nr.h index 7359cbf66..1e4ce9b58 100644 --- a/src/shared/revision_nr.h +++ b/src/shared/revision_nr.h @@ -1,4 +1,4 @@ #ifndef __REVISION_NR_H__ #define __REVISION_NR_H__ - #define REVISION_NR "8424" + #define REVISION_NR "8425" #endif // __REVISION_NR_H__