aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authormegamage <none@none>2009-08-29 23:20:16 -0500
committermegamage <none@none>2009-08-29 23:20:16 -0500
commitd802cd3811c77a1b0bef95a65fdfc4872ff557a8 (patch)
tree68be363ef1f3ce843a32254a9b8fd122b7803434
parent6954eae60ac320639451bd83782f294da367b733 (diff)
*More update about positions.
*Ulduar: do not allow demolisher to regenerate pyrite. Player must shoot down and grab the containers to refill pyrite. --HG-- branch : trunk
-rw-r--r--sql/FULL/world_spell_full.sql3
-rw-r--r--sql/updates/5475_world_scripts_ulduar.sql3
-rw-r--r--src/bindings/scripts/scripts/eastern_kingdoms/hinterlands.cpp16
-rw-r--r--src/bindings/scripts/scripts/eastern_kingdoms/karazhan/boss_prince_malchezaar.cpp13
-rw-r--r--src/bindings/scripts/scripts/eastern_kingdoms/karazhan/bosses_opera.cpp8
-rw-r--r--src/bindings/scripts/scripts/eastern_kingdoms/stratholme/stratholme.cpp5
-rw-r--r--src/bindings/scripts/scripts/eastern_kingdoms/undercity.cpp19
-rw-r--r--src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/dark_portal.cpp13
-rw-r--r--src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp18
-rw-r--r--src/bindings/scripts/scripts/kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp6
-rw-r--r--src/bindings/scripts/scripts/northrend/naxxramas/boss_sapphiron.cpp4
-rw-r--r--src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_flame_leviathan.cpp7
-rw-r--r--src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_kologarn.cpp22
-rw-r--r--src/bindings/scripts/scripts/outland/shadowmoon_valley.cpp19
-rw-r--r--src/game/Creature.cpp11
-rw-r--r--src/game/CreatureAIImpl.h15
-rw-r--r--src/game/DBCStructure.h2
-rw-r--r--src/game/DBCfmt.h4
-rw-r--r--src/game/DynamicObject.cpp12
-rw-r--r--src/game/DynamicObject.h2
-rw-r--r--src/game/MotionMaster.cpp14
-rw-r--r--src/game/MotionMaster.h5
-rw-r--r--src/game/Object.cpp31
-rw-r--r--src/game/Object.h44
-rw-r--r--src/game/PetHandler.cpp10
-rw-r--r--src/game/PointMovementGenerator.cpp3
-rw-r--r--src/game/SharedDefines.h1
-rw-r--r--src/game/Spell.cpp215
-rw-r--r--src/game/Spell.h61
-rw-r--r--src/game/SpellEffects.cpp102
-rw-r--r--src/game/Unit.cpp6
-rw-r--r--src/game/Vehicle.cpp43
-rw-r--r--src/game/Vehicle.h6
33 files changed, 352 insertions, 391 deletions
diff --git a/sql/FULL/world_spell_full.sql b/sql/FULL/world_spell_full.sql
index aa5bb7610a6..7e54af3df84 100644
--- a/sql/FULL/world_spell_full.sql
+++ b/sql/FULL/world_spell_full.sql
@@ -2193,12 +2193,13 @@ spell5 = VALUES(spell5),
spell6 = VALUES(spell6),
vehicleid = VALUES(vehicleid);
-DELETE FROM `spell_script_target` WHERE `entry` IN (62427,62374,62399,62056,63985);
+DELETE FROM `spell_script_target` WHERE `entry` IN (62427,62496,62374,62399,62056,63985);
INSERT INTO `spell_script_target` (`entry`, `type`, `targetEntry`) VALUES
(62427, 1, 33109), # Load into Catapult
(62374, 1, 33060), # Pursued
(62374, 1, 33109),
(62399, 1, 33139), # Overload Circuit
+(62496, 1, 33167), # Liquid Pyrite - Salvaged Demolisher Mechanic Seat
(63985, 1, 32934), # Stone Grip
(62056, 1, 32934);
diff --git a/sql/updates/5475_world_scripts_ulduar.sql b/sql/updates/5475_world_scripts_ulduar.sql
new file mode 100644
index 00000000000..8939ee109a7
--- /dev/null
+++ b/sql/updates/5475_world_scripts_ulduar.sql
@@ -0,0 +1,3 @@
+DELETE FROM `spell_script_target` WHERE `entry` IN (62496);
+INSERT INTO `spell_script_target` (`entry`, `type`, `targetEntry`) VALUES
+(62496, 1, 33167); # Liquid Pyrite - Salvaged Demolisher Mechanic Seat
diff --git a/src/bindings/scripts/scripts/eastern_kingdoms/hinterlands.cpp b/src/bindings/scripts/scripts/eastern_kingdoms/hinterlands.cpp
index fbcbd2f6045..5542c06e2e4 100644
--- a/src/bindings/scripts/scripts/eastern_kingdoms/hinterlands.cpp
+++ b/src/bindings/scripts/scripts/eastern_kingdoms/hinterlands.cpp
@@ -81,19 +81,19 @@ struct MANGOS_DLL_DECL npc_00x09hlAI : public npc_escortAI
case 27:
for(uint8 i = 0; i < 3; ++i)
{
- float fX, fY, fZ;
- m_creature->GetRandomPoint(147.927444f, -3851.513428f, 130.893f, 7.0f, fX, fY, fZ);
-
- m_creature->SummonCreature(NPC_MARAUDING_OWL, fX, fY, fZ, 0.0f, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 25000);
+ const Position src = {147.927444f, -3851.513428f, 130.893f, 0};
+ Position pos;
+ me->GetRandomNearPosition(pos, 7.0f);
+ DoSummon(NPC_MARAUDING_OWL, pos, 25000, TEMPSUMMON_CORPSE_TIMED_DESPAWN);
}
break;
case 44:
for(uint8 i = 0; i < 3; ++i)
{
- float fX, fY, fZ;
- m_creature->GetRandomPoint(-141.151581f, -4291.213867f, 120.130f, 7.0f, fX, fY, fZ);
-
- m_creature->SummonCreature(NPC_VILE_AMBUSHER, fX, fY, fZ, 0.0f, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 25000);
+ const Position src = {-141.151581f, -4291.213867f, 120.130f, 0};
+ Position dst;
+ m_creature->GetRandomPoint(src, 7.0f, dst);
+ m_creature->SummonCreature(NPC_VILE_AMBUSHER, dst, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 25000);
}
break;
}
diff --git a/src/bindings/scripts/scripts/eastern_kingdoms/karazhan/boss_prince_malchezaar.cpp b/src/bindings/scripts/scripts/eastern_kingdoms/karazhan/boss_prince_malchezaar.cpp
index 7bcf8fa44ba..d960cfb2222 100644
--- a/src/bindings/scripts/scripts/eastern_kingdoms/karazhan/boss_prince_malchezaar.cpp
+++ b/src/bindings/scripts/scripts/eastern_kingdoms/karazhan/boss_prince_malchezaar.cpp
@@ -339,23 +339,18 @@ struct TRINITY_DLL_DECL boss_malchezaarAI : public ScriptedAI
void SummonInfernal(const uint32 diff)
{
InfernalPoint *point = NULL;
- float posX,posY,posZ;
+ Position pos;
if ((m_creature->GetMapId() != 532) || positions.empty())
- {
- m_creature->GetRandomPoint(m_creature->GetPositionX(), m_creature->GetPositionY(), m_creature->GetPositionZ(), 60, posX, posY, posZ);
- }
+ me->GetRandomNearPosition(pos, 60);
else
{
std::vector<InfernalPoint*>::iterator itr = positions.begin()+rand()%positions.size();
point = *itr;
positions.erase(itr);
-
- posX = point->x;
- posY = point->y;
- posZ = INFERNAL_Z;
+ pos.Relocate(point->x, point->y, INFERNAL_Z);
}
- Creature *Infernal = m_creature->SummonCreature(NETHERSPITE_INFERNAL, posX, posY, posZ, 0, TEMPSUMMON_TIMED_DESPAWN, 180000);
+ Creature *Infernal = m_creature->SummonCreature(NETHERSPITE_INFERNAL, pos, TEMPSUMMON_TIMED_DESPAWN, 180000);
if (Infernal)
{
diff --git a/src/bindings/scripts/scripts/eastern_kingdoms/karazhan/bosses_opera.cpp b/src/bindings/scripts/scripts/eastern_kingdoms/karazhan/bosses_opera.cpp
index 01a12847bd9..2952d47b540 100644
--- a/src/bindings/scripts/scripts/eastern_kingdoms/karazhan/bosses_opera.cpp
+++ b/src/bindings/scripts/scripts/eastern_kingdoms/karazhan/bosses_opera.cpp
@@ -654,11 +654,9 @@ struct TRINITY_DLL_DECL mob_cycloneAI : public ScriptedAI
if (MoveTimer < diff)
{
- float x,y,z;
- m_creature->GetPosition(x,y,z);
- float PosX, PosY, PosZ;
- m_creature->GetRandomPoint(x,y,z,10, PosX, PosY, PosZ);
- m_creature->GetMotionMaster()->MovePoint(0, PosX, PosY, PosZ);
+ Position pos;
+ m_creature->GetRandomNearPosition(pos, 10);
+ m_creature->GetMotionMaster()->MovePoint(0, pos);
MoveTimer = 5000 + rand()%3000;
}else MoveTimer -= diff;
}
diff --git a/src/bindings/scripts/scripts/eastern_kingdoms/stratholme/stratholme.cpp b/src/bindings/scripts/scripts/eastern_kingdoms/stratholme/stratholme.cpp
index ea8fe41fef0..02c10b348f8 100644
--- a/src/bindings/scripts/scripts/eastern_kingdoms/stratholme/stratholme.cpp
+++ b/src/bindings/scripts/scripts/eastern_kingdoms/stratholme/stratholme.cpp
@@ -205,13 +205,10 @@ struct TRINITY_DLL_DECL mobs_spectral_ghostly_citizenAI : public ScriptedAI
{
for(uint32 i = 1; i <= 4; ++i)
{
- float x,y,z;
- m_creature->GetRandomPoint(m_creature->GetPositionX(),m_creature->GetPositionY(),m_creature->GetPositionZ(),20.0f,x,y,z);
-
//100%, 50%, 33%, 25% chance to spawn
uint32 j = urand(1,i);
if (j==1)
- m_creature->SummonCreature(ENTRY_RESTLESS,x,y,z,0,TEMPSUMMON_CORPSE_DESPAWN,600000);
+ DoSummon(ENTRY_RESTLESS, me, 20.0f, 600000);
}
}
}
diff --git a/src/bindings/scripts/scripts/eastern_kingdoms/undercity.cpp b/src/bindings/scripts/scripts/eastern_kingdoms/undercity.cpp
index 8b27dc1beeb..d3bcb63a139 100644
--- a/src/bindings/scripts/scripts/eastern_kingdoms/undercity.cpp
+++ b/src/bindings/scripts/scripts/eastern_kingdoms/undercity.cpp
@@ -63,16 +63,8 @@ struct TRINITY_DLL_DECL npc_lady_sylvanas_windrunnerAI : public ScriptedAI
bool LamentEvent;
uint64 targetGUID;
- float myX;
- float myY;
- float myZ;
-
void Reset()
{
- myX = m_creature->GetPositionX();
- myY = m_creature->GetPositionY();
- myZ = m_creature->GetPositionZ();
-
LamentEvent_Timer = 5000;
LamentEvent = false;
targetGUID = 0;
@@ -86,8 +78,8 @@ struct TRINITY_DLL_DECL npc_lady_sylvanas_windrunnerAI : public ScriptedAI
{
if (Unit* target = Unit::GetUnit(*summoned,targetGUID))
{
- target->SendMonsterMove(target->GetPositionX(), target->GetPositionY(), myZ+15.0,0);
- target->GetMap()->CreatureRelocation(m_creature, target->GetPositionX(), target->GetPositionY(), myZ+15.0, 0.0f);
+ target->SendMonsterMove(target->GetPositionX(), target->GetPositionY(), me->GetPositionZ()+15.0,0);
+ target->GetMap()->CreatureRelocation(m_creature, target->GetPositionX(), target->GetPositionY(), me->GetPositionZ()+15.0, 0.0f);
summoned->CastSpell(target, SPELL_RIBBON_OF_SOULS, false);
}
@@ -102,12 +94,7 @@ struct TRINITY_DLL_DECL npc_lady_sylvanas_windrunnerAI : public ScriptedAI
{
if (LamentEvent_Timer < diff)
{
- float raX = myX;
- float raY = myY;
- float raZ = myZ;
-
- m_creature->GetRandomPoint(myX, myY, myZ, 20.0, raX, raY, raZ);
- m_creature->SummonCreature(ENTRY_HIGHBORNE_BUNNY, raX, raY, myZ, 0, TEMPSUMMON_TIMED_DESPAWN, 3000);
+ DoSummon(ENTRY_HIGHBORNE_BUNNY, me, 10.0f, 3000, TEMPSUMMON_TIMED_DESPAWN);
LamentEvent_Timer = 2000;
if (!m_creature->HasAura(SPELL_SYLVANAS_CAST))
diff --git a/src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/dark_portal.cpp b/src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/dark_portal.cpp
index 8c82722ed5d..6984f287950 100644
--- a/src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/dark_portal.cpp
+++ b/src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/dark_portal.cpp
@@ -286,20 +286,15 @@ struct TRINITY_DLL_DECL npc_time_riftAI : public ScriptedAI
return;
}
- float x,y,z;
- m_creature->GetRandomPoint(m_creature->GetPositionX(),m_creature->GetPositionY(),m_creature->GetPositionZ(),10.0f,x,y,z);
+ Position pos;
+ m_creature->GetRandomNearPosition(pos, 10.0f);
//normalize Z-level if we can, if rift is not at ground level.
- z = std::max(m_creature->GetMap()->GetHeight(x, y, MAX_HEIGHT), m_creature->GetMap()->GetWaterLevel(x, y));
+ pos.m_positionZ = std::max(m_creature->GetMap()->GetHeight(pos.m_positionX, pos.m_positionY, MAX_HEIGHT), m_creature->GetMap()->GetWaterLevel(pos.m_positionX, pos.m_positionY));
- Unit *Summon = m_creature->SummonCreature(creature_entry,x,y,z,m_creature->GetOrientation(),
- TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,30000);
-
- if (Summon)
- {
+ if(Unit *Summon = DoSummon(creature_entry, pos, 30000, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT))
if (Unit *temp = Unit::GetUnit(*m_creature, pInstance ? pInstance->GetData64(DATA_MEDIVH) : 0))
Summon->AddThreat(temp,0.0f);
- }
}
void DoSelectSummon()
diff --git a/src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp b/src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp
index f406bca7113..b6d08ee82d8 100644
--- a/src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp
+++ b/src/bindings/scripts/scripts/kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp
@@ -245,25 +245,23 @@ struct TRINITY_DLL_DECL instance_dark_portal : public ScriptedInstance
return 0;
}
- Creature* SummonedPortalBoss(Creature* pSource)
+ Creature* SummonedPortalBoss(Creature* m_creature)
{
uint32 entry = RiftWaves[GetRiftWaveId()].PortalBoss;
if (entry == RIFT_BOSS)
entry = RandRiftBoss();
- float x,y,z;
- pSource->GetRandomPoint(pSource->GetPositionX(),pSource->GetPositionY(),pSource->GetPositionZ(),10.0f,x,y,z);
- //normalize Z-level if we can, if rift is not at ground level.
- z = std::max(instance->GetHeight(x, y, MAX_HEIGHT), instance->GetWaterLevel(x, y));
-
debug_log("TSCR: Instance Dark Portal: Summoning rift boss entry %u.",entry);
- Creature* pSummoned = pSource->SummonCreature(entry,x,y,z,pSource->GetOrientation(),
- TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,600000);
+ Position pos;
+ m_creature->GetRandomNearPosition(pos, 10.0f);
+
+ //normalize Z-level if we can, if rift is not at ground level.
+ pos.m_positionZ = std::max(m_creature->GetMap()->GetHeight(pos.m_positionX, pos.m_positionY, MAX_HEIGHT), m_creature->GetMap()->GetWaterLevel(pos.m_positionX, pos.m_positionY));
- if (pSummoned)
- return pSummoned;
+ if(Creature *summon = m_creature->SummonCreature(entry, pos, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 600000))
+ return summon;
debug_log("TSCR: Instance Dark Portal: what just happened there? No boss, no loot, no fun...");
return NULL;
diff --git a/src/bindings/scripts/scripts/kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp b/src/bindings/scripts/scripts/kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp
index 4819a74fc0c..f017c274eba 100644
--- a/src/bindings/scripts/scripts/kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp
+++ b/src/bindings/scripts/scripts/kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp
@@ -165,9 +165,9 @@ struct TRINITY_DLL_DECL mob_doomfire_targettingAI : public ScriptedAI
}
else
{
- float x,y,z = 0.0;
- m_creature->GetRandomPoint(m_creature->GetPositionX(), m_creature->GetPositionY(), m_creature->GetPositionZ(), 40, x, y, z);
- m_creature->GetMotionMaster()->MovePoint(0, x, y, z);
+ Position pos;
+ m_creature->GetRandomNearPosition(pos, 40);
+ m_creature->GetMotionMaster()->MovePoint(0, pos.m_positionX, pos.m_positionY, pos.m_positionZ);
}
ChangeTargetTimer = 5000;
diff --git a/src/bindings/scripts/scripts/northrend/naxxramas/boss_sapphiron.cpp b/src/bindings/scripts/scripts/northrend/naxxramas/boss_sapphiron.cpp
index 9813fddcd6a..62b90bbb742 100644
--- a/src/bindings/scripts/scripts/northrend/naxxramas/boss_sapphiron.cpp
+++ b/src/bindings/scripts/scripts/northrend/naxxramas/boss_sapphiron.cpp
@@ -255,9 +255,7 @@ struct TRINITY_DLL_DECL boss_sapphironAI : public BossAI
case EVENT_BLIZZARD:
{
//DoCastAOE(SPELL_SUMMON_BLIZZARD);
- float x, y, z;
- me->GetGroundPointAroundUnit(x, y, z, rand_norm()*20, rand_norm()*2*M_PI);
- if (Creature *summon = me->SummonCreature(MOB_BLIZZARD, x, y, z, 0, TEMPSUMMON_TIMED_DESPAWN, 25000+rand()%5000))
+ if(Creature *summon = DoSummon(MOB_BLIZZARD, me, 25000+rand()%5000, TEMPSUMMON_TIMED_DESPAWN))
summon->GetMotionMaster()->MoveRandom(40);
events.ScheduleEvent(EVENT_BLIZZARD, HEROIC(20000,7000), 0, PHASE_GROUND);
break;
diff --git a/src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_flame_leviathan.cpp b/src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_flame_leviathan.cpp
index 98238022d36..9e46a377701 100644
--- a/src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_flame_leviathan.cpp
+++ b/src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_flame_leviathan.cpp
@@ -295,12 +295,7 @@ struct TRINITY_DLL_DECL boss_flame_leviathan_safety_containerAI : public Passive
void UpdateAI(const uint32 diff)
{
if(!me->GetVehicle() && me->isSummon() && me->GetMotionMaster()->GetCurrentMovementGeneratorType() != POINT_MOTION_TYPE)
- {
- //me->AddUnitMovementFlag(MOVEMENTFLAG_FALLING);
- me->RemoveUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
- me->SendMovementFlagUpdate();
- me->GetMotionMaster()->MovePoint(me->GetEntry(), me->GetPositionX(), me->GetPositionY(), 409.8f);
- }
+ me->GetMotionMaster()->MoveFall(409.8f, me->GetEntry());
}
};
diff --git a/src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_kologarn.cpp b/src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_kologarn.cpp
index b17682a9104..9242f5184e5 100644
--- a/src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_kologarn.cpp
+++ b/src/bindings/scripts/scripts/northrend/ulduar/ulduar/boss_kologarn.cpp
@@ -44,7 +44,20 @@ struct TRINITY_DLL_DECL boss_kologarnAI : public BossAI
void AttackStart(Unit *who)
{
- me->Attack(who, false);
+ me->Attack(who, true);
+ if(leftArm)
+ leftArm->Attack(who, true);
+ if(rightArm)
+ rightArm->Attack(who, true);
+ }
+
+ void MeleeSwing(WeaponAttackType type)
+ {
+ me->AttackerStateUpdate(me->getVictim(), type);
+ if(leftArm)
+ leftArm->AttackerStateUpdate(me->getVictim(), type);
+ if(rightArm)
+ rightArm->AttackerStateUpdate(me->getVictim(), type);
}
void PassengerBoarded(Unit *who, int8 seatId, bool apply)
@@ -66,10 +79,9 @@ struct TRINITY_DLL_DECL boss_kologarnAI : public BossAI
//If we are within range melee the target
if (me->IsWithinMeleeRange(me->getVictim()))
{
- Unit *attacker = me;
- if(leftArm) attacker = leftArm;
- if(rightArm && rand()%2) attacker = rightArm;
- attacker->AttackerStateUpdate(me->getVictim());
+ WeaponAttackType type = BASE_ATTACK;
+ if(leftArm && (!rightArm || rand()%2)) type = OFF_ATTACK;
+ MeleeSwing(type);
me->resetAttackTimer();
}
}
diff --git a/src/bindings/scripts/scripts/outland/shadowmoon_valley.cpp b/src/bindings/scripts/scripts/outland/shadowmoon_valley.cpp
index e7ee5a45569..9580752caca 100644
--- a/src/bindings/scripts/scripts/outland/shadowmoon_valley.cpp
+++ b/src/bindings/scripts/scripts/outland/shadowmoon_valley.cpp
@@ -274,19 +274,17 @@ struct TRINITY_DLL_DECL mob_enslaved_netherwing_drakeAI : public ScriptedAI
m_creature->GetRandomPoint(x, y, z, 20, dx, dy, dz);
dz += 20; // so it's in the air, not ground*/
- float dx, dy, dz;
-
- Unit* EscapeDummy = me->FindNearestCreature(CREATURE_ESCAPE_DUMMY, 30);
- if (EscapeDummy)
- EscapeDummy->GetPosition(dx, dy, dz);
+ Position pos;
+ if(Unit* EscapeDummy = me->FindNearestCreature(CREATURE_ESCAPE_DUMMY, 30))
+ EscapeDummy->GetPosition(&pos);
else
{
- m_creature->GetRandomPoint(m_creature->GetPositionX(), m_creature->GetPositionY(), m_creature->GetPositionZ(), 20, dx, dy, dz);
- dz += 25;
+ m_creature->GetRandomNearPosition(pos, 20);
+ pos.m_positionZ += 25;
}
m_creature->AddUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
- m_creature->GetMotionMaster()->MovePoint(1, dx, dy, dz);
+ m_creature->GetMotionMaster()->MovePoint(1, pos);
}
}
}else FlyTimer -= diff;
@@ -962,10 +960,7 @@ struct TRINITY_DLL_DECL npc_earthmender_wildaAI : public npc_escortAI
void DoSpawnAssassin()
{
//unknown where they actually appear
- float fX, fY, fZ;
- m_creature->GetRandomPoint(m_creature->GetPositionX(), m_creature->GetPositionY(), m_creature->GetPositionZ(), 15.0f, fX, fY, fZ);
-
- m_creature->SummonCreature(NPC_COILSKAR_ASSASSIN, fX, fY, fZ, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 5000);
+ DoSummon(NPC_COILSKAR_ASSASSIN, me, 15.0f, 5000, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT);
}
void Aggro(Unit* pWho)
diff --git a/src/game/Creature.cpp b/src/game/Creature.cpp
index 40507387226..47515638490 100644
--- a/src/game/Creature.cpp
+++ b/src/game/Creature.cpp
@@ -556,7 +556,10 @@ void Creature::Update(uint32 diff)
RegenerateHealth();
if(getPowerType() == POWER_ENERGY)
- Regenerate(POWER_ENERGY);
+ {
+ if(!IsVehicle() || GetVehicleKit()->GetVehicleInfo()->m_powerType != POWER_PYRITE)
+ Regenerate(POWER_ENERGY);
+ }
else
RegenerateMana();
@@ -1834,11 +1837,7 @@ bool Creature::FallGround()
if (fabs(ground_Z - z) < 0.1f)
return false;
- SetFlying(false);
- RemoveUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
- SendMovementFlagUpdate();
- //AddUnitMovementFlag(MOVEMENTFLAG_FALLING);
- GetMotionMaster()->MovePoint(EVENT_FALL_GROUND, x, y, ground_Z);
+ GetMotionMaster()->MoveFall(ground_Z, EVENT_FALL_GROUND);
Unit::setDeathState(DEAD_FALLING);
return true;
}
diff --git a/src/game/CreatureAIImpl.h b/src/game/CreatureAIImpl.h
index d143daa288c..569c0fad9da 100644
--- a/src/game/CreatureAIImpl.h
+++ b/src/game/CreatureAIImpl.h
@@ -332,18 +332,19 @@ inline Creature *CreatureAI::DoSummon(uint32 uiEntry, const Position &pos, uint3
return me->SummonCreature(uiEntry, pos, uiType, uiDespawntime);
}
-inline Creature *CreatureAI::DoSummon(uint32 uiEntry, WorldObject* pGo, float fRadius, uint32 uiDespawntime, TempSummonType uiType)
+inline Creature *CreatureAI::DoSummon(uint32 uiEntry, WorldObject* obj, float fRadius, uint32 uiDespawntime, TempSummonType uiType)
{
- float fX, fY, fZ;
- pGo->GetGroundPointAroundUnit(fX, fY, fZ, fRadius * rand_norm(), rand_norm()*2*M_PI);
- return me->SummonCreature(uiEntry, fX, fY, fZ, me->GetOrientation(), uiType, uiDespawntime);
+ Position pos;
+ obj->GetRandomNearPosition(pos, fRadius);
+ return me->SummonCreature(uiEntry, pos, uiType, uiDespawntime);
}
inline Creature *CreatureAI::DoSummonFlyer(uint32 uiEntry, WorldObject *obj, float _fZ, float fRadius, uint32 uiDespawntime, TempSummonType uiType)
{
- float fX, fY, fZ;
- obj->GetGroundPointAroundUnit(fX, fY, fZ, fRadius * rand_norm(), rand_norm()*2*M_PI);
- return me->SummonCreature(uiEntry, fX, fY, fZ + _fZ, me->GetOrientation(), uiType, uiDespawntime);
+ Position pos;
+ obj->GetRandomNearPosition(pos, fRadius);
+ pos.m_positionZ += _fZ;
+ return me->SummonCreature(uiEntry, pos, uiType, uiDespawntime);
}
#endif
diff --git a/src/game/DBCStructure.h b/src/game/DBCStructure.h
index c0af3a9be00..7e459c61e8b 100644
--- a/src/game/DBCStructure.h
+++ b/src/game/DBCStructure.h
@@ -1678,7 +1678,7 @@ struct VehicleEntry
uint32 m_uiLocomotionType; // 34
float m_msslTrgtImpactTexRadius; // 35
uint32 m_uiSeatIndicatorType; // 36
- // 37, new in 3.1
+ uint32 m_powerType; // 37, new in 3.1
// 38, new in 3.1
// 39, new in 3.1
};
diff --git a/src/game/DBCfmt.h b/src/game/DBCfmt.h
index 290514872f9..7487ac116a2 100644
--- a/src/game/DBCfmt.h
+++ b/src/game/DBCfmt.h
@@ -86,7 +86,7 @@ const char SkillLineAbilityfmt[]="niiiixxiiiiixx";
const char SoundEntriesfmt[]="nxxxxxxxxxxxxxxxxxxxxxxxxxxxxx";
const char SpellCastTimefmt[]="nixx";
const char SpellDurationfmt[]="niii";
-const char SpellEntryfmt[]="niiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiifxiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiffffffiiiiiiiiiiiiiiiiiiiiifffiiiiiiiiiiiiiiifffiiiiiiiiiiiiixssssssssssssssssxssssssssssssssssxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxiiiiiiiiiiixfffxxxiiiiixx";
+const char SpellEntryfmt[]="niiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiifxiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiffffffiiiiiiiiiiiiiiiiiiiiifffiiiiiiiiiiiiiiifffiiiiiiiiiiiiixssssssssssssssssxssssssssssssssssxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxiiiiiiiiiiixfffxxxiiiiixx";
const std::string CustomSpellEntryfmt="pappppppppaaapaaaaaaaaaaapaaapapppppppaaaaapaapaaaaaaaaaaaaaaaaaappppppppppppppppppppppppppppppppppppppppppaaaaaapppppppppaaapppppppppaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaappppppppapppaaaaappaaa";
const std::string CustomSpellEntryIndex = "Id";
const char SpellFocusObjectfmt[]="nxxxxxxxxxxxxxxxxx";
@@ -104,7 +104,7 @@ const char TaxiNodesEntryfmt[]="nifffssssssssssssssssxii";
const char TaxiPathEntryfmt[]="niii";
const char TaxiPathNodeEntryfmt[]="diiifffiixx";
const char TotemCategoryEntryfmt[]="nxxxxxxxxxxxxxxxxxii";
-const char VehicleEntryfmt[]="niffffiiiiiiiifffffffffffffffssssfifixxx";
+const char VehicleEntryfmt[]="niffffiiiiiiiifffffffffffffffssssfifiixx";
const char VehicleSeatEntryfmt[]="niiffffffffffiiiiiifffffffiiifffiiiiiiiffiiiiixxxxxxxxxxxx";
const char WorldMapAreaEntryfmt[]="xinxffffix";
const char WorldMapOverlayEntryfmt[]="nxiiiixxxxxxxxxxx";
diff --git a/src/game/DynamicObject.cpp b/src/game/DynamicObject.cpp
index 34b009bc7d4..5dd4059e21c 100644
--- a/src/game/DynamicObject.cpp
+++ b/src/game/DynamicObject.cpp
@@ -70,12 +70,10 @@ void DynamicObject::RemoveFromWorld()
}
}
-bool DynamicObject::Create(uint32 guidlow, Unit *caster, uint32 spellId, uint32 effMask, float x, float y, float z, int32 duration, float radius, bool active)
+bool DynamicObject::Create(uint32 guidlow, Unit *caster, uint32 spellId, uint32 effMask, const Position &pos, int32 duration, float radius, bool active)
{
SetMap(caster->GetMap());
-
- Relocate(x, y, z, 0);
-
+ Relocate(pos);
if(!IsPositionValid())
{
sLog.outError("DynamicObject (spell %u eff %u) not created. Suggested coordinates isn't valid (X: %f Y: %f)",spellId,effMask,GetPositionX(),GetPositionY());
@@ -90,9 +88,9 @@ bool DynamicObject::Create(uint32 guidlow, Unit *caster, uint32 spellId, uint32
SetUInt32Value( DYNAMICOBJECT_BYTES, 0x00000001 );
SetUInt32Value( DYNAMICOBJECT_SPELLID, spellId );
SetFloatValue( DYNAMICOBJECT_RADIUS, radius);
- SetFloatValue( DYNAMICOBJECT_POS_X, x );
- SetFloatValue( DYNAMICOBJECT_POS_Y, y );
- SetFloatValue( DYNAMICOBJECT_POS_Z, z );
+ SetFloatValue( DYNAMICOBJECT_POS_X, pos.m_positionX );
+ SetFloatValue( DYNAMICOBJECT_POS_Y, pos.m_positionY );
+ SetFloatValue( DYNAMICOBJECT_POS_Z, pos.m_positionZ );
SetUInt32Value( DYNAMICOBJECT_CASTTIME, getMSTime() ); // new 2.4.0
m_aliveDuration = duration;
diff --git a/src/game/DynamicObject.h b/src/game/DynamicObject.h
index 94985f247d7..13747891964 100644
--- a/src/game/DynamicObject.h
+++ b/src/game/DynamicObject.h
@@ -35,7 +35,7 @@ class DynamicObject : public WorldObject
void AddToWorld();
void RemoveFromWorld();
- bool Create(uint32 guidlow, Unit *caster, uint32 spellId, uint32 effMask, float x, float y, float z, int32 duration, float radius, bool active);
+ bool Create(uint32 guidlow, Unit *caster, uint32 spellId, uint32 effMask, const Position &pos, int32 duration, float radius, bool active);
void Update(uint32 p_time);
void Delete();
uint32 GetSpellId() const { return m_spellId; }
diff --git a/src/game/MotionMaster.cpp b/src/game/MotionMaster.cpp
index b1168cac78d..81d72f8db6f 100644
--- a/src/game/MotionMaster.cpp
+++ b/src/game/MotionMaster.cpp
@@ -344,7 +344,7 @@ void MotionMaster::MoveJump(float x, float y, float z, float speedXY, float spee
}
void
-MotionMaster::MoveCharge(float x, float y, float z, float speed)
+MotionMaster::MoveCharge(float x, float y, float z, float speed, uint32 id)
{
if(Impl[MOTION_SLOT_CONTROLLED] && Impl[MOTION_SLOT_CONTROLLED]->GetMovementGeneratorType() != DISTRACT_MOTION_TYPE)
return;
@@ -354,16 +354,24 @@ MotionMaster::MoveCharge(float x, float y, float z, float speed)
if(i_owner->GetTypeId()==TYPEID_PLAYER)
{
DEBUG_LOG("Player (GUID: %u) charge point (X: %f Y: %f Z: %f)", i_owner->GetGUIDLow(), x, y, z );
- Mutate(new PointMovementGenerator<Player>(0,x,y,z), MOTION_SLOT_CONTROLLED);
+ Mutate(new PointMovementGenerator<Player>(id,x,y,z), MOTION_SLOT_CONTROLLED);
}
else
{
DEBUG_LOG("Creature (Entry: %u GUID: %u) charge point (X: %f Y: %f Z: %f)",
i_owner->GetEntry(), i_owner->GetGUIDLow(), x, y, z );
- Mutate(new PointMovementGenerator<Creature>(0,x,y,z), MOTION_SLOT_CONTROLLED);
+ Mutate(new PointMovementGenerator<Creature>(id,x,y,z), MOTION_SLOT_CONTROLLED);
}
}
+void MotionMaster::MoveFall(float z, uint32 id)
+{
+ i_owner->SetFlying(false);
+ i_owner->SendMovementFlagUpdate();
+ //AddUnitMovementFlag(MOVEMENTFLAG_FALLING);
+ MoveCharge(i_owner->GetPositionX(), i_owner->GetPositionY(), z, SPEED_CHARGE, id);
+}
+
void
MotionMaster::MoveSeekAssistance(float x, float y, float z)
{
diff --git a/src/game/MotionMaster.h b/src/game/MotionMaster.h
index 197f0d07499..9494627f166 100644
--- a/src/game/MotionMaster.h
+++ b/src/game/MotionMaster.h
@@ -149,8 +149,11 @@ class TRINITY_DLL_SPEC MotionMaster //: private std::stack<MovementGenerator *>
void MoveChase(Unit* target, float dist = 0.0f, float angle = 0.0f);
void MoveConfused();
void MoveFleeing(Unit* enemy, uint32 time = 0);
+ void MovePoint(uint32 id, const Position &pos)
+ { MovePoint(id, pos.m_positionX, pos.m_positionY, pos.m_positionZ); }
void MovePoint(uint32 id, float x,float y,float z);
- void MoveCharge(float x, float y, float z, float speed = SPEED_CHARGE);
+ void MoveCharge(float x, float y, float z, float speed = SPEED_CHARGE, uint32 id = EVENT_CHARGE);
+ void MoveFall(float z, uint32 id = 0);
void MoveKnockbackFrom(float srcX, float srcY, float speedXY, float speedZ);
void MoveJumpTo(float angle, float speedXY, float speedZ);
void MoveJump(float x, float y, float z, float speedXY, float speedZ);
diff --git a/src/game/Object.cpp b/src/game/Object.cpp
index 7d365b35710..5206a5a4219 100644
--- a/src/game/Object.cpp
+++ b/src/game/Object.cpp
@@ -1079,7 +1079,7 @@ bool Object::PrintIndexError(uint32 index, bool set) const
return false;
}
-bool Position::IsInLine(const Unit * const target, float distance, float width) const
+bool Position::HasInLine(const Unit * const target, float distance, float width) const
{
if(!HasInArc(M_PI, target) || !target->IsWithinDist3d(m_positionX, m_positionY, m_positionZ, distance)) return false;
width += target->GetObjectSize();
@@ -1382,13 +1382,11 @@ bool WorldObject::IsInBetween(const WorldObject *obj1, const WorldObject *obj2,
return abs(sin(angle)) * GetExactDist2d(obj1->GetPositionX(), obj1->GetPositionY()) < size;
}
-void WorldObject::GetRandomPoint( float x, float y, float z, float distance, float &rand_x, float &rand_y, float &rand_z) const
+void WorldObject::GetRandomPoint(const Position &pos, float distance, float &rand_x, float &rand_y, float &rand_z) const
{
- if(distance == 0)
+ if(!distance)
{
- rand_x = x;
- rand_y = y;
- rand_z = z;
+ pos.GetPosition(rand_x, rand_y, rand_z);
return;
}
@@ -1396,9 +1394,9 @@ void WorldObject::GetRandomPoint( float x, float y, float z, float distance, flo
float angle = rand_norm()*2*M_PI;
float new_dist = rand_norm()*distance;
- rand_x = x + new_dist * cos(angle);
- rand_y = y + new_dist * sin(angle);
- rand_z = z;
+ rand_x = pos.m_positionX + new_dist * cos(angle);
+ rand_y = pos.m_positionY + new_dist * sin(angle);
+ rand_z = pos.m_positionZ;
Trinity::NormalizeMapCoord(rand_x);
Trinity::NormalizeMapCoord(rand_y);
@@ -2175,14 +2173,15 @@ void WorldObject::GetNearPoint(WorldObject const* searcher, float &x, float &y,
*/
}
-void WorldObject::GetGroundPoint(float &x, float &y, float &z, float dist, float angle)
+void WorldObject::MovePosition(Position &pos, float dist, float angle)
{
- angle += GetOrientation();
- x += dist * cos(angle);
- y += dist * sin(angle);
- Trinity::NormalizeMapCoord(x);
- Trinity::NormalizeMapCoord(y);
- UpdateGroundPositionZ(x, y, z);
+ angle += m_orientation;
+ pos.m_positionX += dist * cos(angle);
+ pos.m_positionY += dist * sin(angle);
+ Trinity::NormalizeMapCoord(pos.m_positionX);
+ Trinity::NormalizeMapCoord(pos.m_positionY);
+ UpdateGroundPositionZ(pos.m_positionX, pos.m_positionY, pos.m_positionZ);
+ pos.m_orientation = m_orientation;
}
void WorldObject::SetPhaseMask(uint32 newPhaseMask, bool update)
diff --git a/src/game/Object.h b/src/game/Object.h
index af4b6eb5301..761495b7f48 100644
--- a/src/game/Object.h
+++ b/src/game/Object.h
@@ -417,22 +417,22 @@ struct TRINITY_DLL_SPEC Position
bool IsInDist(const Position *pos, float dist) const
{ return GetExactDistSq(pos) < dist * dist; }
bool HasInArc(float arcangle, const Position *pos) const;
- bool IsInLine(const Unit *target, float distance, float width) const;
+ bool HasInLine(const Unit *target, float distance, float width) const;
};
+#define MAPID_INVALID 0xFFFFFFFF
+
class WorldLocation : public Position
{
public:
- explicit WorldLocation(uint32 _mapid = 0, float _x = 0, float _y = 0, float _z = 0, float _o = 0)
+ explicit WorldLocation(uint32 _mapid = MAPID_INVALID, float _x = 0, float _y = 0, float _z = 0, float _o = 0)
: m_mapId(_mapid) { Relocate(_x, _y, _z, _o); }
- WorldLocation(const WorldLocation &loc)
- : m_mapId(loc.GetMapId()) { Relocate(&loc); }
+ WorldLocation(const WorldLocation &loc) { WorldRelocate(loc); }
- //void GetPosition(const WorldLocation &loc) const
- // { loc.mapid = GetMapId(); Position::GetPosition(loc.coord_x, loc.coord_y, loc.coord_z); loc.orientation = GetOrientation(); }
+ void WorldRelocate(const WorldLocation &loc)
+ { m_mapId = loc.GetMapId(); Relocate(loc); }
uint32 GetMapId() const { return m_mapId; }
- protected:
uint32 m_mapId;
};
@@ -452,12 +452,18 @@ class TRINITY_DLL_SPEC WorldObject : public Object, public WorldLocation
// angle calculated from current orientation
GetNearPoint(NULL,x,y,z,size,distance2d,GetOrientation() + angle);
}
- void GetGroundPoint(float &x, float &y, float &z, float dist, float angle);
- void GetGroundPointAroundUnit(float &x, float &y, float &z, float dist, float angle)
+ void MovePosition(Position &pos, float dist, float angle);
+ void GetNearPosition(Position &pos, float dist, float angle)
+ {
+ GetPosition(&pos);
+ MovePosition(pos, dist, angle);
+ }
+ void GetRandomNearPosition(Position &pos, float radius)
{
- GetPosition(x, y, z);
- GetGroundPoint(x, y, z, dist, angle);
+ GetPosition(&pos);
+ MovePosition(pos, radius * rand_norm(), rand_norm() * 2 * M_PI);
}
+
void GetContactPoint( const WorldObject* obj, float &x, float &y, float &z, float distance2d = CONTACT_DISTANCE) const
{
// angle to face `obj` to `this` using distance includes size of `obj`
@@ -470,7 +476,13 @@ class TRINITY_DLL_SPEC WorldObject : public Object, public WorldLocation
}
void UpdateGroundPositionZ(float x, float y, float &z) const;
- void GetRandomPoint( float x, float y, float z, float distance, float &rand_x, float &rand_y, float &rand_z ) const;
+ void GetRandomPoint(const Position &srcPos, float distance, float &rand_x, float &rand_y, float &rand_z) const;
+ void GetRandomPoint(const Position &srcPos, float distance, Position &pos) const
+ {
+ float x, y, z;
+ GetRandomPoint(srcPos, distance, x, y, z);
+ pos.Relocate(x, y, z, GetOrientation());
+ }
uint32 GetInstanceId() const { return m_InstanceId; }
@@ -490,8 +502,10 @@ class TRINITY_DLL_SPEC WorldObject : public Object, public WorldLocation
virtual const char* GetNameForLocaleIdx(int32 /*locale_idx*/) const { return GetName(); }
- float GetDistance( const WorldObject* obj ) const
+ float GetDistance(const WorldObject *obj) const
{ return GetExactDist(obj) + GetObjectSize() + obj->GetObjectSize(); }
+ float GetDistance(const Position &pos) const
+ { return GetExactDist(&pos) + GetObjectSize(); }
float GetDistance(float x, float y, float z) const
{ return GetExactDist(x, y, z) + GetObjectSize(); }
float GetDistance2d(const WorldObject* obj) const
@@ -506,8 +520,12 @@ class TRINITY_DLL_SPEC WorldObject : public Object, public WorldLocation
}
bool IsWithinDist3d(float x, float y, float z, float dist) const
{ return IsInDist(x, y, z, dist + GetObjectSize()); }
+ bool IsWithinDist3d(const Position *pos, float dist) const
+ { return IsInDist(pos, dist + GetObjectSize()); }
bool IsWithinDist2d(float x, float y, float dist) const
{ return IsInDist2d(x, y, dist + GetObjectSize()); }
+ bool IsWithinDist2d(const Position *pos, float dist) const
+ { return IsInDist2d(pos, dist + GetObjectSize()); }
bool _IsWithinDist(WorldObject const* obj, float dist2compare, bool is3D) const;
bool IsWithinDist(WorldObject const* obj, float dist2compare, bool is3D = true) const
// use only if you will sure about placing both object at same map
diff --git a/src/game/PetHandler.cpp b/src/game/PetHandler.cpp
index 9da36fc9215..53c9873be72 100644
--- a/src/game/PetHandler.cpp
+++ b/src/game/PetHandler.cpp
@@ -167,7 +167,7 @@ void WorldSession::HandlePetActionHelper(Unit *pet, uint64 guid1, uint16 spellid
else if(pet->GetOwnerGUID() == GetPlayer()->GetGUID())
{
assert(pet->GetTypeId() == TYPEID_UNIT);
- if(((Creature*)pet)->isPet())
+ if(pet->isPet())
{
if(((Pet*)pet)->getPetType() == HUNTER_PET)
GetPlayer()->RemovePet((Pet*)pet, PET_SAVE_AS_DELETED);
@@ -175,7 +175,7 @@ void WorldSession::HandlePetActionHelper(Unit *pet, uint64 guid1, uint16 spellid
//dismissing a summoned pet is like killing them (this prevents returning a soulshard...)
pet->setDeathState(CORPSE);
}
- else if(((Creature*)pet)->HasUnitTypeMask(UNIT_MASK_MINION))
+ else if(pet->HasUnitTypeMask(UNIT_MASK_MINION))
{
((Minion*)pet)->UnSummon();
}
@@ -232,7 +232,7 @@ void WorldSession::HandlePetActionHelper(Unit *pet, uint64 guid1, uint16 spellid
SpellCastResult result = spell->CheckPetCast(unit_target);
//auto turn to target unless possessed
- if(result == SPELL_FAILED_UNIT_NOT_INFRONT && !pet->isPossessed())
+ if(result == SPELL_FAILED_UNIT_NOT_INFRONT && !pet->isPossessed() && !pet->IsVehicle())
{
if(unit_target)
{
@@ -267,7 +267,7 @@ void WorldSession::HandlePetActionHelper(Unit *pet, uint64 guid1, uint16 spellid
pet->SendPetAIReaction(guid1);
}
- if( unit_target && !GetPlayer()->IsFriendlyTo(unit_target) && !pet->isPossessed())
+ if( unit_target && !GetPlayer()->IsFriendlyTo(unit_target) && !pet->isPossessed() && !pet->IsVehicle())
{
// This is true if pet has no target or has target but targets differs.
if (pet->getVictim() != unit_target)
@@ -284,7 +284,7 @@ void WorldSession::HandlePetActionHelper(Unit *pet, uint64 guid1, uint16 spellid
}
else
{
- if(pet->isPossessed())
+ if(pet->isPossessed() || pet->IsVehicle())
Spell::SendCastResult(GetPlayer(),spellInfo,0,result);
else
pet->SendPetCastFail(spellid, result);
diff --git a/src/game/PointMovementGenerator.cpp b/src/game/PointMovementGenerator.cpp
index a24178ccb99..035c046b26a 100644
--- a/src/game/PointMovementGenerator.cpp
+++ b/src/game/PointMovementGenerator.cpp
@@ -68,8 +68,7 @@ void PointMovementGenerator<T>:: Finalize(T &unit)
{
if(unit.hasUnitState(UNIT_STAT_CHARGING))
unit.clearUnitState(UNIT_STAT_CHARGING | UNIT_STAT_JUMPING);
- else if(arrived)
- MovementInform(unit);
+ MovementInform(unit);
}
template<class T>
diff --git a/src/game/SharedDefines.h b/src/game/SharedDefines.h
index 1037b65b624..8731fe1a399 100644
--- a/src/game/SharedDefines.h
+++ b/src/game/SharedDefines.h
@@ -2525,6 +2525,7 @@ enum EventId
{
EVENT_SPELLCLICK = 1001,
EVENT_FALL_GROUND = 1002,
+ EVENT_CHARGE = 1003,
};
enum ResponseCodes
diff --git a/src/game/Spell.cpp b/src/game/Spell.cpp
index 848f7e6e02c..3eada04fe42 100644
--- a/src/game/Spell.cpp
+++ b/src/game/Spell.cpp
@@ -124,7 +124,7 @@ SpellCastTargets::SpellCastTargets() : m_elevation(0), m_speed(0)
m_itemTargetGUID = 0;
m_itemTargetEntry = 0;
- m_srcX = m_srcY = m_srcZ = m_destX = m_destY = m_destZ = 0;
+ m_srcPos.Relocate(0,0,0,0);
m_strTarget = "";
m_targetMask = 0;
}
@@ -145,48 +145,36 @@ void SpellCastTargets::setUnitTarget(Unit *target)
void SpellCastTargets::setSrc(float x, float y, float z)
{
- m_srcX = x;
- m_srcY = y;
- m_srcZ = z;
+ m_srcPos.Relocate(x, y, z);
m_targetMask |= TARGET_FLAG_SOURCE_LOCATION;
}
-void SpellCastTargets::setSrc(WorldObject *target)
+void SpellCastTargets::setSrc(Position *pos)
{
- if(!target)
- return;
-
- target->GetPosition(m_srcX, m_srcY, m_srcZ);
- m_targetMask |= TARGET_FLAG_SOURCE_LOCATION;
+ if(pos)
+ {
+ m_srcPos.Relocate(pos);
+ m_targetMask |= TARGET_FLAG_SOURCE_LOCATION;
+ }
}
-void SpellCastTargets::setDestination(float x, float y, float z, int32 mapId)
+void SpellCastTargets::setDst(float x, float y, float z, uint32 mapId)
{
- m_destX = x;
- m_destY = y;
- m_destZ = z;
+ m_dstPos.Relocate(x, y, z);
m_targetMask |= TARGET_FLAG_DEST_LOCATION;
- if(mapId >= 0)
- m_mapId = mapId;
+ if(mapId != MAPID_INVALID)
+ m_dstPos.m_mapId = mapId;
}
-void SpellCastTargets::setDestination(WorldObject *target)
+void SpellCastTargets::setDst(Position *pos)
{
- if(!target)
- return;
-
- target->GetPosition(m_destX, m_destY, m_destZ);
- m_targetMask |= TARGET_FLAG_DEST_LOCATION;
+ if(pos)
+ {
+ m_dstPos.Relocate(pos);
+ m_targetMask |= TARGET_FLAG_DEST_LOCATION;
+ }
}
-/*void SpellCastTargets::setSource(float x, float y, float z)
-{
- m_srcX = x;
- m_srcY = y;
- m_srcZ = z;
- m_targetMask |= TARGET_FLAG_SOURCE_LOCATION;
-}*/
-
void SpellCastTargets::setGOTarget(GameObject *target)
{
m_GOTarget = target;
@@ -269,10 +257,12 @@ bool SpellCastTargets::read ( WorldPacket * data, Unit *caster )
if(data->rpos() + 4 + 4 + 4 > data->size())
return false;
- *data >> m_srcX >> m_srcY >> m_srcZ;
- if(!Trinity::IsValidMapCoord(m_srcX, m_srcY, m_srcZ))
+ *data >> m_srcPos.m_positionX >> m_srcPos.m_positionY >> m_srcPos.m_positionZ;
+ if(!m_srcPos.IsPositionValid())
return false;
}
+ else
+ m_srcPos.Relocate(caster);
if( m_targetMask & TARGET_FLAG_DEST_LOCATION )
{
@@ -282,8 +272,8 @@ bool SpellCastTargets::read ( WorldPacket * data, Unit *caster )
if(!data->readPackGUID(m_unitTargetGUID))
return false;
- *data >> m_destX >> m_destY >> m_destZ;
- if(!Trinity::IsValidMapCoord(m_destX, m_destY, m_destZ))
+ *data >> m_dstPos.m_positionX >> m_dstPos.m_positionY >> m_dstPos.m_positionZ;
+ if(!m_dstPos.IsPositionValid())
return false;
if( m_targetMask & TARGET_FLAG_SOURCE_LOCATION )
@@ -291,11 +281,15 @@ bool SpellCastTargets::read ( WorldPacket * data, Unit *caster )
if(data->rpos() + 4 + 4 <= data->size())
{
*data >> m_elevation >> m_speed;
+ // TODO: should also read
+ m_srcPos.m_orientation = caster->GetOrientation();
//*data >> uint16 >> uint8 >> uint32 >> uint32;
//*data >> float >> float >> float >> float...
}
}
}
+ else
+ m_dstPos.Relocate(caster);
if( m_targetMask & TARGET_FLAG_STRING )
{
@@ -346,7 +340,7 @@ void SpellCastTargets::write ( WorldPacket * data )
}
if( m_targetMask & TARGET_FLAG_SOURCE_LOCATION )
- *data << m_srcX << m_srcY << m_srcZ;
+ *data << m_srcPos.m_positionX << m_srcPos.m_positionY << m_srcPos.m_positionZ;
if( m_targetMask & TARGET_FLAG_DEST_LOCATION )
{
@@ -355,7 +349,7 @@ void SpellCastTargets::write ( WorldPacket * data )
else
*data << uint8(0);
- *data << m_destX << m_destY << m_destZ;
+ *data << m_dstPos.m_positionX << m_dstPos.m_positionY << m_dstPos.m_positionZ;
}
if( m_targetMask & TARGET_FLAG_STRING )
@@ -760,7 +754,7 @@ void Spell::SelectSpellTargets()
}
else if(m_spellInfo->speed > 0.0f)
{
- float dist = m_caster->GetDistance(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ);
+ float dist = m_caster->GetDistance(m_targets.m_dstPos);
m_delayMoment = (uint64) floor(dist / m_spellInfo->speed * 1000.0f);
}
}
@@ -1683,20 +1677,16 @@ void Spell::SearchChainTarget(std::list<Unit*> &TagUnitMap, float max_range, uin
void Spell::SearchAreaTarget(std::list<Unit*> &TagUnitMap, float radius, SpellNotifyPushType type, SpellTargets TargetType, uint32 entry)
{
- float x, y, z;
+ Position *pos;
switch(type)
{
case PUSH_DST_CENTER:
CheckDst();
- x = m_targets.m_destX;
- y = m_targets.m_destY;
- z = m_targets.m_destZ;
+ pos = &m_targets.m_dstPos;
break;
case PUSH_SRC_CENTER:
CheckSrc();
- x = m_targets.m_srcX;
- y = m_targets.m_srcY;
- z = m_targets.m_srcZ;
+ pos = &m_targets.m_srcPos;
break;
case PUSH_CHAIN:
{
@@ -1706,24 +1696,20 @@ void Spell::SearchAreaTarget(std::list<Unit*> &TagUnitMap, float radius, SpellNo
sLog.outError( "SPELL: cannot find unit target for spell ID %u\n", m_spellInfo->Id );
return;
}
- x = target->GetPositionX();
- y = target->GetPositionY();
- z = target->GetPositionZ();
+ pos = target;
break;
}
default:
- x = m_caster->GetPositionX();
- y = m_caster->GetPositionY();
- z = m_caster->GetPositionZ();
+ pos = m_caster;
break;
}
- Trinity::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius, type, TargetType, entry, x, y, z);
+ Trinity::SpellNotifierCreatureAndPlayer notifier(m_caster, TagUnitMap, radius, type, TargetType, pos, entry);
if((m_spellInfo->AttributesEx3 & SPELL_ATTR_EX3_PLAYERS_ONLY)
|| TargetType == SPELL_TARGETS_ENTRY && !entry)
- m_caster->GetMap()->VisitWorld(x, y, radius, notifier);
+ m_caster->GetMap()->VisitWorld(pos->m_positionX, pos->m_positionY, radius, notifier);
else
- m_caster->GetMap()->VisitAll(x, y, radius, notifier);
+ m_caster->GetMap()->VisitAll(pos->m_positionX, pos->m_positionY, radius, notifier);
if(m_customAttr & SPELL_ATTR_CU_EXCLUDE_SELF)
TagUnitMap.remove(m_caster);
@@ -1847,7 +1833,7 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
float dis = rand_norm() * (max_dis - min_dis) + min_dis;
float x, y, z;
m_caster->GetClosePoint(x, y, z, DEFAULT_WORLD_OBJECT_SIZE, dis);
- m_targets.setDestination(x, y, z);
+ m_targets.setDst(x, y, z);
break;
}
case TARGET_UNIT_MASTER:
@@ -1983,11 +1969,11 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
}
else if(cur == TARGET_DST_CASTER)
{
- m_targets.setDestination(m_caster);
+ m_targets.setDst(m_caster);
break;
}
- float x, y, z, angle, dist;
+ float angle, dist;
float objSize = m_caster->GetObjectSize();
dist = GetSpellRadiusForFriend(sSpellRadiusStore.LookupEntry(m_spellInfo->EffectRadiusIndex[i]));
@@ -2011,8 +1997,9 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
default: angle = rand_norm()*2*M_PI; break;
}
- m_caster->GetGroundPointAroundUnit(x, y, z, dist, angle);
- m_targets.setDestination(x, y, z);
+ Position pos;
+ m_caster->GetNearPosition(pos, dist, angle);
+ m_targets.setDst(&pos); // also flag
break;
}
@@ -2027,11 +2014,11 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
if(cur == TARGET_DST_TARGET_ENEMY || cur == TARGET_DEST_TARGET_ANY)
{
- m_targets.setDestination(target);
+ m_targets.setDst(target);
break;
}
- float x, y, z, angle, dist;
+ float angle, dist;
float objSize = target->GetObjectSize();
dist = target->GetSpellRadiusForTarget(target, sSpellRadiusStore.LookupEntry(m_spellInfo->EffectRadiusIndex[i]));
@@ -2053,8 +2040,9 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
default: angle = rand_norm()*2*M_PI; break;
}
- target->GetGroundPointAroundUnit(x, y, z, dist, angle);
- m_targets.setDestination(x, y, z);
+ Position pos;
+ target->GetNearPosition(pos, dist, angle);
+ m_targets.setDst(&pos);
break;
}
@@ -2088,16 +2076,13 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
default: angle = rand_norm()*2*M_PI; break;
}
- float dist, x, y, z;
+ float dist;
dist = GetSpellRadiusForFriend(sSpellRadiusStore.LookupEntry(m_spellInfo->EffectRadiusIndex[i]));
if (cur == TARGET_DEST_DEST_RANDOM)
dist *= rand_norm();
- x = m_targets.m_destX;
- y = m_targets.m_destY;
- z = m_targets.m_destZ;
- m_caster->GetGroundPoint(x, y, z, dist, angle);
- m_targets.setDestination(x, y, z);
+ // must has dst, no need to set flag
+ m_caster->MovePosition(m_targets.m_dstPos, dist, angle);
break;
}
@@ -2112,9 +2097,9 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
if(m_spellInfo->Effect[0] == SPELL_EFFECT_TELEPORT_UNITS
|| m_spellInfo->Effect[1] == SPELL_EFFECT_TELEPORT_UNITS
|| m_spellInfo->Effect[2] == SPELL_EFFECT_TELEPORT_UNITS)
- m_targets.setDestination(st->target_X, st->target_Y, st->target_Z, (int32)st->target_mapId);
+ m_targets.setDst(st->target_X, st->target_Y, st->target_Z, (int32)st->target_mapId);
else if(st->target_mapId == m_caster->GetMapId())
- m_targets.setDestination(st->target_X, st->target_Y, st->target_Z);
+ m_targets.setDst(st->target_X, st->target_Y, st->target_Z);
}
else
{
@@ -2122,12 +2107,12 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
Unit *target = NULL;
if(uint64 guid = m_caster->GetUInt64Value(UNIT_FIELD_TARGET))
target = ObjectAccessor::GetUnit(*m_caster, guid);
- m_targets.setDestination(target ? target : m_caster);
+ m_targets.setDst(target ? target : m_caster);
}
break;
case TARGET_DST_HOME:
if(m_caster->GetTypeId() == TYPEID_PLAYER)
- m_targets.setDestination(((Player*)m_caster)->m_homebindX,((Player*)m_caster)->m_homebindY,((Player*)m_caster)->m_homebindZ, ((Player*)m_caster)->m_homebindMapId);
+ m_targets.setDst(((Player*)m_caster)->m_homebindX,((Player*)m_caster)->m_homebindY,((Player*)m_caster)->m_homebindZ, ((Player*)m_caster)->m_homebindMapId);
break;
case TARGET_DST_NEARBY_ENTRY:
{
@@ -2135,7 +2120,7 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
if(modOwner) modOwner->ApplySpellMod(m_spellInfo->Id, SPELLMOD_RANGE, range, this);
if(WorldObject *target = SearchNearbyTarget(range, SPELL_TARGETS_ENTRY))
- m_targets.setDestination(target);
+ m_targets.setDst(target);
break;
}
}
@@ -2162,7 +2147,7 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
if(m_originalCaster->GetCurrentSpell(CURRENT_CHANNELED_SPELL)->m_targets.HasDst())
m_targets = m_originalCaster->GetCurrentSpell(CURRENT_CHANNELED_SPELL)->m_targets;
else if(Unit* target = m_originalCaster->GetCurrentSpell(CURRENT_CHANNELED_SPELL)->m_targets.getUnitTarget())
- m_targets.setDestination(target);
+ m_targets.setDst(target);
else
sLog.outError( "SPELL: cannot find channel spell destination for spell ID %u", m_spellInfo->Id );
break;
@@ -2300,7 +2285,7 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
switch(result->GetTypeId())
{
case TYPEID_UNIT:
- m_targets.setDestination(result);
+ m_targets.setDst(result);
}
}
break;
@@ -2389,22 +2374,17 @@ void Spell::SelectEffectTargets(uint32 i, uint32 cur)
if(cur == TARGET_OBJECT_AREA_SRC)
{
if(m_targets.HasSrc())
- {
- x = m_targets.m_srcX;
- y = m_targets.m_srcY;
- z = m_targets.m_srcZ;
- }
+ m_targets.m_srcPos.GetPosition(x, y, z);
else
break;
}
- else if(m_targets.HasDst())
+ else
{
- x = m_targets.m_destX;
- y = m_targets.m_destY;
- z = m_targets.m_destZ;
+ if(m_targets.HasDst())
+ m_targets.m_dstPos.GetPosition(x, y, z);
+ else
+ break;
}
- else
- break;
Trinity::GameObjectInRangeCheck check(x, y, z, radius + 50);
std::list<GameObject*> goList;
@@ -3127,7 +3107,7 @@ void Spell::_handle_immediate_phase()
if(EffectTargetType[m_spellInfo->Effect[j]] == SPELL_REQUIRE_DEST)
{
if(!m_targets.HasDst()) // FIXME: this will ignore dest set in effect
- m_targets.setDestination(m_caster);
+ m_targets.setDst(m_caster);
HandleEffects(m_originalCaster, NULL, NULL, j);
m_effectMask |= (1<<j);
}
@@ -4419,6 +4399,7 @@ SpellCastResult Spell::CheckCast(bool strict)
if(m_spellInfo->CasterAuraStateNot && m_caster->HasAuraState(AuraState(m_spellInfo->CasterAuraStateNot), m_spellInfo, m_caster))
return SPELL_FAILED_CASTER_AURASTATE;
+ // Note: spell 62473 requres casterAuraSpell = triggering spell
if(m_spellInfo->casterAuraSpell && !m_caster->HasAura(m_spellInfo->casterAuraSpell))
return SPELL_FAILED_CASTER_AURASTATE;
if(m_spellInfo->excludeCasterAuraSpell && m_caster->HasAura(m_spellInfo->excludeCasterAuraSpell))
@@ -4705,7 +4686,7 @@ SpellCastResult Spell::CheckCast(bool strict)
if (m_spellInfo->EffectImplicitTargetA[j] == TARGET_DST_NEARBY_ENTRY ||
m_spellInfo->EffectImplicitTargetB[j] == TARGET_DST_NEARBY_ENTRY )
{
- m_targets.setDestination(creatureScriptTarget->GetPositionX(),creatureScriptTarget->GetPositionY(),creatureScriptTarget->GetPositionZ());
+ m_targets.setDst(creatureScriptTarget->GetPositionX(),creatureScriptTarget->GetPositionY(),creatureScriptTarget->GetPositionZ());
if(m_spellInfo->EffectImplicitTargetA[j] == TARGET_DST_NEARBY_ENTRY && m_spellInfo->EffectImplicitTargetB[j] == 0 && m_spellInfo->Effect[j]!=SPELL_EFFECT_PERSISTENT_AREA_AURA)
AddUnitTarget(creatureScriptTarget, j);
@@ -4720,7 +4701,7 @@ SpellCastResult Spell::CheckCast(bool strict)
if (m_spellInfo->EffectImplicitTargetA[j] == TARGET_DST_NEARBY_ENTRY ||
m_spellInfo->EffectImplicitTargetB[j] == TARGET_DST_NEARBY_ENTRY )
{
- m_targets.setDestination(goScriptTarget->GetPositionX(),goScriptTarget->GetPositionY(),goScriptTarget->GetPositionZ());
+ m_targets.setDst(goScriptTarget->GetPositionX(),goScriptTarget->GetPositionY(),goScriptTarget->GetPositionZ());
if(m_spellInfo->EffectImplicitTargetA[j] == TARGET_DST_NEARBY_ENTRY && m_spellInfo->EffectImplicitTargetB[j] == 0 && m_spellInfo->Effect[j]!=SPELL_EFFECT_PERSISTENT_AREA_AURA)
AddGOTarget(goScriptTarget, j);
@@ -5465,11 +5446,11 @@ SpellCastResult Spell::CheckRange(bool strict)
return SPELL_FAILED_UNIT_NOT_INFRONT;
}
- if(m_targets.m_targetMask == TARGET_FLAG_DEST_LOCATION && m_targets.m_destX != 0 && m_targets.m_destY != 0 && m_targets.m_destZ != 0)
+ if(m_targets.HasDst() && !m_targets.HasTraj())
{
- if(!m_caster->IsWithinDist3d(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ, max_range))
+ if(!m_caster->IsWithinDist3d(&m_targets.m_dstPos, max_range))
return SPELL_FAILED_OUT_OF_RANGE;
- if(min_range && m_caster->IsWithinDist3d(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ, min_range))
+ if(min_range && m_caster->IsWithinDist3d(&m_targets.m_dstPos, min_range))
return SPELL_FAILED_TOO_CLOSE;
}
@@ -6613,7 +6594,7 @@ void Spell::SelectTrajTargets()
if(!dist2d)
return;
- float dz = m_targets.m_destZ - m_targets.m_srcZ;
+ float dz = m_targets.m_dstPos.m_positionZ - m_targets.m_srcPos.m_positionZ;
UnitList unitList;
SearchAreaTarget(unitList, dist2d, PUSH_IN_THIN_LINE, SPELL_TARGETS_ANY);
@@ -6627,7 +6608,8 @@ void Spell::SelectTrajTargets()
if(a > -0.0001f) a = 0;
DEBUG_TRAJ(sLog.outError("Spell::SelectTrajTargets: a %f b %f", a, b);)
- float bestDist;
+ float bestDist = GetSpellMaxRange(m_spellInfo, false);
+
UnitList::const_iterator itr = unitList.begin();
for(; itr != unitList.end(); ++itr)
{
@@ -6636,15 +6618,15 @@ void Spell::SelectTrajTargets()
const float size = std::max((*itr)->GetObjectSize() * 0.7f, 1.0f); // 1/sqrt(3)
// TODO: all calculation should be based on src instead of m_caster
- const float objDist2d = (*itr)->GetExactDist2d(m_targets.m_srcX, m_targets.m_srcY) * cos(m_caster->GetRelativeAngle(*itr));
- const float dz = (*itr)->GetPositionZ() - m_targets.m_srcZ;
+ const float objDist2d = m_targets.m_srcPos.GetExactDist2d(*itr) * cos(m_targets.m_srcPos.GetRelativeAngle(*itr));
+ const float dz = (*itr)->GetPositionZ() - m_targets.m_srcPos.m_positionZ;
DEBUG_TRAJ(sLog.outError("Spell::SelectTrajTargets: check %u, dist between %f %f, height between %f %f.", (*itr)->GetEntry(), objDist2d - size, objDist2d + size, dz - size, dz + size);)
float dist = objDist2d - size;
float height = dist * (a * dist + b);
DEBUG_TRAJ(sLog.outError("Spell::SelectTrajTargets: dist %f, height %f.", dist, height);)
- if(height < dz + size && height > dz - size)
+ if(dist < bestDist && height < dz + size && height > dz - size)
{
bestDist = dist > 0 ? dist : 0;
break;
@@ -6652,8 +6634,8 @@ void Spell::SelectTrajTargets()
#define CHECK_DIST {\
DEBUG_TRAJ(sLog.outError("Spell::SelectTrajTargets: dist %f, height %f.", dist, height);)\
- if(dist < objDist2d + size && dist > objDist2d - size)\
- { bestDist = dist; break; }\
+ if(dist > bestDist) continue;\
+ if(dist < objDist2d + size && dist > objDist2d - size) { bestDist = dist; break; }\
}
if(!a)
@@ -6697,28 +6679,31 @@ void Spell::SelectTrajTargets()
}
}
- if(itr != unitList.end())
+ if(m_targets.m_srcPos.GetExactDist2d(&m_targets.m_dstPos) > bestDist)
{
- float x = m_targets.m_srcX + cos(m_caster->GetOrientation()) * bestDist;
- float y = m_targets.m_srcY + sin(m_caster->GetOrientation()) * bestDist;
- float z = m_targets.m_srcZ + bestDist * (a * bestDist + b);
+ float x = m_targets.m_srcPos.m_positionX + cos(m_caster->GetOrientation()) * bestDist;
+ float y = m_targets.m_srcPos.m_positionY + sin(m_caster->GetOrientation()) * bestDist;
+ float z = m_targets.m_srcPos.m_positionZ + bestDist * (a * bestDist + b);
- float distSq = (*itr)->GetExactDistSq(x, y, z);
- float sizeSq = (*itr)->GetObjectSize();
- sizeSq *= sizeSq;
- DEBUG_TRAJ(sLog.outError("Initial %f %f %f %f %f", x, y, z, distSq, sizeSq);)
- if(distSq > sizeSq)
+ if(itr != unitList.end())
{
- float factor = 1 - sqrt(sizeSq / distSq);
- x += factor * ((*itr)->GetPositionX() - x);
- y += factor * ((*itr)->GetPositionY() - y);
- z += factor * ((*itr)->GetPositionZ() - z);
-
- distSq = (*itr)->GetExactDistSq(x, y, z);
+ float distSq = (*itr)->GetExactDistSq(x, y, z);
+ float sizeSq = (*itr)->GetObjectSize();
+ sizeSq *= sizeSq;
DEBUG_TRAJ(sLog.outError("Initial %f %f %f %f %f", x, y, z, distSq, sizeSq);)
+ if(distSq > sizeSq)
+ {
+ float factor = 1 - sqrt(sizeSq / distSq);
+ x += factor * ((*itr)->GetPositionX() - x);
+ y += factor * ((*itr)->GetPositionY() - y);
+ z += factor * ((*itr)->GetPositionZ() - z);
+
+ distSq = (*itr)->GetExactDistSq(x, y, z);
+ DEBUG_TRAJ(sLog.outError("Initial %f %f %f %f %f", x, y, z, distSq, sizeSq);)
+ }
}
- m_targets.setDestination(x, y, z);
+ m_targets.setDst(x, y, z);
}
}
diff --git a/src/game/Spell.h b/src/game/Spell.h
index b6aab83bea8..997800d9989 100644
--- a/src/game/Spell.h
+++ b/src/game/Spell.h
@@ -131,13 +131,8 @@ class SpellCastTargets
m_itemTargetEntry = target.m_itemTargetEntry;
- m_srcX = target.m_srcX;
- m_srcY = target.m_srcY;
- m_srcZ = target.m_srcZ;
-
- m_destX = target.m_destX;
- m_destY = target.m_destY;
- m_destZ = target.m_destZ;
+ m_srcPos = target.m_srcPos;
+ m_dstPos.Relocate(target.m_dstPos);
m_elevation = target.m_elevation;
m_speed = target.m_speed;
@@ -146,8 +141,6 @@ class SpellCastTargets
m_targetMask = target.m_targetMask;
- m_mapId = -1;
-
return *this;
}
@@ -155,9 +148,9 @@ class SpellCastTargets
Unit *getUnitTarget() const { return m_unitTarget; }
void setUnitTarget(Unit *target);
void setSrc(float x, float y, float z);
- void setSrc(WorldObject *target);
- void setDestination(float x, float y, float z, int32 mapId = -1);
- void setDestination(WorldObject *target);
+ void setSrc(Position *pos);
+ void setDst(float x, float y, float z, uint32 mapId = MAPID_INVALID);
+ void setDst(Position *pos);
uint64 getGOTargetGUID() const { return m_GOTargetGUID; }
GameObject *getGOTarget() const { return m_GOTarget; }
@@ -183,22 +176,15 @@ class SpellCastTargets
bool HasDst() const { return m_targetMask & TARGET_FLAG_DEST_LOCATION; }
bool HasTraj() const { return m_speed != 0; }
- float GetDist2d() const
- {
- float dx = m_destX - m_srcX;
- float dy = m_destY - m_srcY;
- return sqrt(dx*dx + dy*dy);
- }
-
+ float GetDist2d() const { return m_srcPos.GetExactDist2d(&m_dstPos); }
float GetSpeedXY() const { return m_speed * cos(m_elevation); }
float GetSpeedZ() const { return m_speed * sin(m_elevation); }
void Update(Unit* caster);
- float m_srcX, m_srcY, m_srcZ;
- float m_destX, m_destY, m_destZ;
+ Position m_srcPos;
+ WorldLocation m_dstPos;
float m_elevation, m_speed;
- int32 m_mapId;
std::string m_strTarget;
uint32 m_targetMask;
@@ -434,7 +420,7 @@ class Spell
bool CheckTarget( Unit* target, uint32 eff );
bool CanAutoCast(Unit* target);
void CheckSrc() { if(!m_targets.HasSrc()) m_targets.setSrc(m_caster); }
- void CheckDst() { if(!m_targets.HasDst()) m_targets.setDestination(m_caster); }
+ void CheckDst() { if(!m_targets.HasDst()) m_targets.setDst(m_caster); }
static void MANGOS_DLL_SPEC SendCastResult(Player* caster, SpellEntry const* spellInfo, uint8 cast_count, SpellCastResult result);
void SendCastResult(SpellCastResult result);
@@ -678,20 +664,18 @@ namespace Trinity
struct TRINITY_DLL_DECL SpellNotifierCreatureAndPlayer
{
std::list<Unit*> *i_data;
- Spell &i_spell;
SpellNotifyPushType i_push_type;
float i_radius;
SpellTargets i_TargetType;
- Unit* i_source;
+ const Unit * const i_source;
uint32 i_entry;
- float i_x, i_y, i_z;
+ const Position * const i_pos;
- SpellNotifierCreatureAndPlayer(Spell &spell, std::list<Unit*> &data, float radius, SpellNotifyPushType type,
- SpellTargets TargetType = SPELL_TARGETS_ENEMY, uint32 entry = 0, float x = 0, float y = 0, float z = 0)
- : i_data(&data), i_spell(spell), i_push_type(type), i_radius(radius)
- , i_TargetType(TargetType), i_entry(entry), i_x(x), i_y(y), i_z(z)
+ SpellNotifierCreatureAndPlayer(Unit *source, std::list<Unit*> &data, float radius, SpellNotifyPushType type,
+ SpellTargets TargetType = SPELL_TARGETS_ENEMY, const Position *pos = NULL, uint32 entry = 0)
+ : i_source(source), i_data(&data), i_radius(radius), i_push_type(type)
+ , i_TargetType(TargetType), i_pos(pos), i_entry(entry)
{
- i_source = spell.GetCaster();
assert(i_source);
}
@@ -701,14 +685,13 @@ namespace Trinity
{
Unit *target = (Unit*)itr->getSource();
- // mostly phase check
- if(!itr->getSource()->IsInMap(i_source))
+ if(!target->InSamePhase(i_source))
continue;
switch (i_TargetType)
{
case SPELL_TARGETS_ENEMY:
- if(target->GetTypeId() == TYPEID_UNIT && ((Creature*)target)->isTotem())
+ if(target->isTotem())
continue;
if(!target->isAttackableByAOE())
continue;
@@ -724,7 +707,7 @@ namespace Trinity
}
break;
case SPELL_TARGETS_ALLY:
- if(target->GetTypeId() == TYPEID_UNIT && ((Creature*)target)->isTotem())
+ if(target->isTotem())
continue;
if(!target->isAttackableByAOE() || !i_source->IsFriendlyTo(target))
continue;
@@ -744,7 +727,7 @@ namespace Trinity
case PUSH_DST_CENTER:
case PUSH_CHAIN:
default:
- if(target->IsWithinDist3d(i_x, i_y, i_z, i_radius))
+ if(target->IsWithinDist3d(i_pos, i_radius))
i_data->push_back(target);
break;
case PUSH_IN_FRONT:
@@ -756,11 +739,11 @@ namespace Trinity
i_data->push_back(target);
break;
case PUSH_IN_LINE:
- if(i_source->IsInLine(target, i_radius, i_source->GetObjectSize()))
+ if(i_source->HasInLine(target, i_radius, i_source->GetObjectSize()))
i_data->push_back(target);
break;
- case PUSH_IN_THIN_LINE:
- if(i_source->IsInLine(target, i_radius, 0))
+ case PUSH_IN_THIN_LINE: // only traj
+ if(i_pos->HasInLine(target, i_radius, 0))
i_data->push_back(target);
break;
}
diff --git a/src/game/SpellEffects.cpp b/src/game/SpellEffects.cpp
index 5fa12a92eca..8629c544b28 100644
--- a/src/game/SpellEffects.cpp
+++ b/src/game/SpellEffects.cpp
@@ -1247,7 +1247,7 @@ void Spell::EffectDummy(uint32 i)
if(Unit *device = seat->GetPassenger(2))
if(!device->GetCurrentSpell(CURRENT_CHANNELED_SPELL))
{
- float dist = (*itr)->GetExactDistSq(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ);
+ float dist = (*itr)->GetExactDistSq(&m_targets.m_dstPos);
if(dist < minDist)
{
minDist = dist;
@@ -1255,12 +1255,14 @@ void Spell::EffectDummy(uint32 i)
}
}
}
- if(target && target->GetBase()->IsWithinDist2d(m_targets.m_destX, m_targets.m_destY, GetSpellRadius(m_spellInfo, i, false) * 2)) // now we use *2 because the location of the seat is not correct
+ if(target && target->GetBase()->IsWithinDist2d(&m_targets.m_dstPos, GetSpellRadius(m_spellInfo, i, false) * 2)) // now we use *2 because the location of the seat is not correct
passenger->EnterVehicle(target, 0);
else
{
passenger->ExitVehicle();
- passenger->GetMotionMaster()->MoveJump(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ, m_targets.GetSpeedXY(), m_targets.GetSpeedZ());
+ float x, y, z;
+ m_targets.m_dstPos.GetPosition(x, y, z);
+ passenger->GetMotionMaster()->MoveJump(x, y, z, m_targets.GetSpeedXY(), m_targets.GetSpeedZ());
}
}
}
@@ -1922,11 +1924,11 @@ void Spell::EffectDummy(uint32 i)
if (m_targets.HasDst())
{
- targets.setDestination(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ);
+ targets.setDst(&m_targets.m_dstPos);
}
else
{
- targets.setDestination(m_caster);
+ targets.setDst(m_caster);
// Corpse not found - take reagents ( only not triggered cast can take them)
triggered = false;
}
@@ -1938,7 +1940,7 @@ void Spell::EffectDummy(uint32 i)
else if (m_spellInfo->Id ==48289)
{
if (m_targets.HasDst())
- targets.setDestination(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ);
+ targets.setDst(&m_targets.m_dstPos);
spell_id = m_currentBasePoints[0];
}
@@ -2268,7 +2270,9 @@ void Spell::EffectTriggerMissileSpell(uint32 effect_idx)
&& m_spellInfo->Category == spellInfo->Category)
((Player*)m_caster)->RemoveSpellCooldown(spellInfo->Id);
- m_caster->CastSpell(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ, spellInfo->Id, true, m_CastItem, 0, m_originalCasterGUID);
+ float x, y, z;
+ m_targets.m_dstPos.GetPosition(x, y, z);
+ m_caster->CastSpell(x, y, z, spellInfo->Id, true, m_CastItem, 0, m_originalCasterGUID);
}
void Spell::EffectJump(uint32 i)
@@ -2280,9 +2284,7 @@ void Spell::EffectJump(uint32 i)
float x,y,z,o;
if(m_targets.HasDst())
{
- x = m_targets.m_destX;
- y = m_targets.m_destY;
- z = m_targets.m_destZ;
+ m_targets.m_dstPos.GetPosition(x, y, z);
if(m_spellInfo->EffectImplicitTargetA[i] == TARGET_DEST_TARGET_BACK)
{
@@ -2342,11 +2344,10 @@ void Spell::EffectTeleportUnits(uint32 i)
}
// Init dest coordinates
- int32 mapid = m_targets.m_mapId;
- if(mapid < 0) mapid = (int32)unitTarget->GetMapId();
- float x = m_targets.m_destX;
- float y = m_targets.m_destY;
- float z = m_targets.m_destZ;
+ uint32 mapid = m_targets.m_dstPos.GetMapId();
+ if(mapid == MAPID_INVALID) mapid = unitTarget->GetMapId();
+ float x, y, z;
+ m_targets.m_dstPos.GetPosition(x, y, z);
float orientation = m_targets.getUnitTarget() ? m_targets.getUnitTarget()->GetOrientation() : unitTarget->GetOrientation();
sLog.outDebug("Spell::EffectTeleportUnits - teleport unit to %u %f %f %f\n", mapid, x, y, z);
@@ -2948,7 +2949,7 @@ void Spell::EffectPersistentAA(uint32 i)
Unit *caster = m_caster->GetEntry() == WORLD_TRIGGER ? m_originalCaster : m_caster;
int32 duration = GetSpellDuration(m_spellInfo);
DynamicObject* dynObj = new DynamicObject;
- if(!dynObj->Create(objmgr.GenerateLowGuid(HIGHGUID_DYNAMICOBJECT), caster, m_spellInfo->Id, 1<<i, m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ, duration, radius, false))
+ if(!dynObj->Create(objmgr.GenerateLowGuid(HIGHGUID_DYNAMICOBJECT), caster, m_spellInfo->Id, 1<<i, m_targets.m_dstPos, duration, radius, false))
{
delete dynObj;
return;
@@ -3679,7 +3680,7 @@ void Spell::EffectDistract(uint32 /*i*/)
if( unitTarget->hasUnitState(UNIT_STAT_CONFUSED | UNIT_STAT_STUNNED | UNIT_STAT_FLEEING ) )
return;
- float angle = unitTarget->GetAngle(m_targets.m_destX, m_targets.m_destY);
+ float angle = unitTarget->GetAngle(&m_targets.m_dstPos);
if ( unitTarget->GetTypeId() == TYPEID_PLAYER )
{
@@ -3733,7 +3734,7 @@ void Spell::EffectAddFarsight(uint32 i)
float radius = GetSpellRadiusForFriend(sSpellRadiusStore.LookupEntry(m_spellInfo->EffectRadiusIndex[i]));
int32 duration = GetSpellDuration(m_spellInfo);
DynamicObject* dynObj = new DynamicObject;
- if(!dynObj->Create(objmgr.GenerateLowGuid(HIGHGUID_DYNAMICOBJECT), m_caster, m_spellInfo->Id, 0, m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ, duration, radius, true))
+ if(!dynObj->Create(objmgr.GenerateLowGuid(HIGHGUID_DYNAMICOBJECT), m_caster, m_spellInfo->Id, 0, m_targets.m_dstPos, duration, radius, true))
{
delete dynObj;
return;
@@ -4635,11 +4636,7 @@ void Spell::EffectSummonObjectWild(uint32 i)
float x, y, z;
if(m_targets.m_targetMask & TARGET_FLAG_DEST_LOCATION)
- {
- x = m_targets.m_destX;
- y = m_targets.m_destY;
- z = m_targets.m_destZ;
- }
+ m_targets.m_dstPos.GetPosition(x, y, z);
else
m_caster->GetClosePoint(x, y, z, DEFAULT_WORLD_OBJECT_SIZE);
@@ -5163,7 +5160,7 @@ void Spell::EffectScriptEffect(uint32 effIndex)
float radius = GetSpellRadius(m_spellInfo, effIndex, true);
for(uint32 i = 0; i < 15; ++i)
{
- m_caster->GetRandomPoint(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ, radius, x, y, z);
+ m_caster->GetRandomPoint(m_targets.m_dstPos, radius, x, y, z);
m_caster->CastSpell(x, y, z, 54522, true);
}
break;
@@ -5306,7 +5303,8 @@ void Spell::EffectScriptEffect(uint32 effIndex)
{
if(Creature *oldContainer = dynamic_cast<Creature*>(seat->GetPassenger(1)))
oldContainer->DisappearAndDie();
- unitTarget->CastSpell(seat->GetBase(), 62473, true);
+ // TODO: a hack, range = 11, should after some time cast, otherwise too far
+ unitTarget->CastSpell(seat->GetBase(), 62496, true);
unitTarget->EnterVehicle(seat, 1);
}
}
@@ -6093,12 +6091,8 @@ void Spell::EffectSummonObject(uint32 i)
float x, y, z;
// If dest location if present
- if (m_targets.m_targetMask & TARGET_FLAG_DEST_LOCATION)
- {
- x = m_targets.m_destX;
- y = m_targets.m_destY;
- z = m_targets.m_destZ;
- }
+ if (m_targets.HasDst())
+ m_targets.m_dstPos.GetPosition(x, y, z);
// Summon in random point all other units if location present
else
m_caster->GetClosePoint(x, y, z, DEFAULT_WORLD_OBJECT_SIZE);
@@ -6373,11 +6367,7 @@ void Spell::EffectCharge2(uint32 /*i*/)
{
float x, y, z;
if(m_targets.HasDst())
- {
- x = m_targets.m_destX;
- y = m_targets.m_destY;
- z = m_targets.m_destZ;
- }
+ m_targets.m_dstPos.GetPosition(x, y, z);
else if(Unit *target = m_targets.getUnitTarget())
{
target->GetContactPoint(m_caster, x, y, z);
@@ -6423,16 +6413,10 @@ void Spell::EffectKnockBack(uint32 i)
return;
float x, y;
- if(m_targets.m_targetMask & TARGET_FLAG_DEST_LOCATION)
- {
- x = m_targets.m_destX;
- y = m_targets.m_destY;
- }
+ if(m_targets.HasDst())
+ m_targets.m_dstPos.GetPosition(x, y);
else
- {
- x = m_caster->GetPositionX();
- y = m_caster->GetPositionY();
- }
+ m_caster->GetPosition(x, y);
unitTarget->KnockbackFrom(x, y, speedxy, speedz);
}
@@ -6615,12 +6599,8 @@ void Spell::EffectTransmitted(uint32 effIndex)
float fx, fy, fz;
- if(m_targets.m_targetMask & TARGET_FLAG_DEST_LOCATION)
- {
- fx = m_targets.m_destX;
- fy = m_targets.m_destY;
- fz = m_targets.m_destZ;
- }
+ if(m_targets.HasDst())
+ m_targets.m_dstPos.GetPosition(fx, fy, fz);
//FIXME: this can be better check for most objects but still hack
else if(m_spellInfo->EffectRadiusIndex[effIndex] && m_spellInfo->speed==0)
{
@@ -7014,11 +6994,13 @@ void Spell::SummonGuardian(uint32 i, uint32 entry, SummonPropertiesEntry const *
void Spell::GetSummonPosition(uint32 i, Position &pos, float radius, uint32 count)
{
+ pos.SetOrientation(m_caster->GetOrientation());
+
if (m_targets.m_targetMask & TARGET_FLAG_DEST_LOCATION)
{
// Summon 1 unit in dest location
if (count == 0)
- pos.Relocate(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ, m_caster->GetOrientation());
+ pos.Relocate(m_targets.m_dstPos);
// Summon in random point all other units if location present
else
{
@@ -7027,22 +7009,14 @@ void Spell::GetSummonPosition(uint32 i, Position &pos, float radius, uint32 coun
{
case TARGET_MINION:
case TARGET_DEST_CASTER_RANDOM:
- {
- float x, y, z;
- m_caster->GetGroundPointAroundUnit(x, y, z, radius * rand_norm(), rand_norm()*2*M_PI);
- pos.Relocate(x, y, z, m_caster->GetOrientation());
+ m_caster->GetNearPosition(pos, radius * rand_norm(), rand_norm()*2*M_PI);
break;
- }
case TARGET_DEST_DEST_RANDOM:
case TARGET_DEST_TARGET_RANDOM:
- {
- float x, y, z;
- m_caster->GetRandomPoint(m_targets.m_destX,m_targets.m_destY,m_targets.m_destZ,radius,x,y,z);
- pos.Relocate(x, y, z, m_caster->GetOrientation());
+ m_caster->GetRandomPoint(m_targets.m_dstPos, radius, pos);
break;
- }
default:
- pos.Relocate(m_targets.m_destX, m_targets.m_destY, m_targets.m_destZ, m_caster->GetOrientation());
+ pos.Relocate(m_targets.m_dstPos);
break;
}
}
@@ -7052,7 +7026,7 @@ void Spell::GetSummonPosition(uint32 i, Position &pos, float radius, uint32 coun
{
float x, y, z;
m_caster->GetClosePoint(x,y,z,3.0f);
- pos.Relocate(x, y, z, m_caster->GetOrientation());
+ pos.Relocate(x, y, z);
}
}
diff --git a/src/game/Unit.cpp b/src/game/Unit.cpp
index 34661a91c4f..6600879d0eb 100644
--- a/src/game/Unit.cpp
+++ b/src/game/Unit.cpp
@@ -936,7 +936,7 @@ void Unit::CastSpell(Unit* Victim,SpellEntry const *spellInfo, bool triggered, I
sLog.outError("CastSpell: spell id %i by caster: %s %u) does not have destination", spellInfo->Id,(GetTypeId()==TYPEID_PLAYER ? "player (GUID:" : "creature (Entry:"),(GetTypeId()==TYPEID_PLAYER ? GetGUIDLow() : GetEntry()));
return;
}
- targets.setDestination(Victim);
+ targets.setDst(Victim);
}
if (castItem)
@@ -1003,7 +1003,7 @@ void Unit::CastCustomSpell(uint32 spellId, CustomSpellValues const &value, Unit*
sLog.outError("CastSpell: spell id %i by caster: %s %u) does not have destination", spellInfo->Id,(GetTypeId()==TYPEID_PLAYER ? "player (GUID:" : "creature (Entry:"),(GetTypeId()==TYPEID_PLAYER ? GetGUIDLow() : GetEntry()));
return;
}
- targets.setDestination(Victim);
+ targets.setDst(Victim);
}
if(!originalCaster && triggeredByAura)
@@ -1043,7 +1043,7 @@ void Unit::CastSpell(float x, float y, float z, uint32 spellId, bool triggered,
Spell *spell = new Spell(this, spellInfo, triggered, originalCaster );
SpellCastTargets targets;
- targets.setDestination(x, y, z);
+ targets.setDst(x, y, z);
if(OriginalVictim)
targets.setUnitTarget(OriginalVictim);
spell->m_CastItem = castItem;
diff --git a/src/game/Vehicle.cpp b/src/game/Vehicle.cpp
index 510214c5a23..853440169eb 100644
--- a/src/game/Vehicle.cpp
+++ b/src/game/Vehicle.cpp
@@ -52,23 +52,36 @@ void Vehicle::Install()
{
if(Creature *cre = dynamic_cast<Creature*>(me))
{
- for(uint32 i = 0; i < MAX_SPELL_VEHICLE; ++i)
+ if(m_vehicleInfo->m_powerType == POWER_STEAM)
{
- if(!cre->m_spells[i])
- continue;
-
- SpellEntry const *spellInfo = sSpellStore.LookupEntry(cre->m_spells[i]);
- if(!spellInfo)
- continue;
-
- if(spellInfo->powerType == POWER_MANA)
- break;
-
- if(spellInfo->powerType == POWER_ENERGY)
+ me->setPowerType(POWER_ENERGY);
+ me->SetMaxPower(POWER_ENERGY, 100);
+ }
+ else if(m_vehicleInfo->m_powerType == POWER_PYRITE)
+ {
+ me->setPowerType(POWER_ENERGY);
+ me->SetMaxPower(POWER_ENERGY, 50);
+ }
+ else
+ {
+ for(uint32 i = 0; i < MAX_SPELL_VEHICLE; ++i)
{
- me->setPowerType(POWER_ENERGY);
- me->SetMaxPower(POWER_ENERGY, 100);
- break;
+ if(!cre->m_spells[i])
+ continue;
+
+ SpellEntry const *spellInfo = sSpellStore.LookupEntry(cre->m_spells[i]);
+ if(!spellInfo)
+ continue;
+
+ if(spellInfo->powerType == POWER_MANA)
+ break;
+
+ if(spellInfo->powerType == POWER_ENERGY)
+ {
+ me->setPowerType(POWER_ENERGY);
+ me->SetMaxPower(POWER_ENERGY, 100);
+ break;
+ }
}
}
}
diff --git a/src/game/Vehicle.h b/src/game/Vehicle.h
index 3c1bd3508f5..620f194a15b 100644
--- a/src/game/Vehicle.h
+++ b/src/game/Vehicle.h
@@ -25,6 +25,12 @@ struct VehicleEntry;
struct VehicleSeatEntry;
class Unit;
+enum PowerType
+{
+ POWER_STEAM = 61,
+ POWER_PYRITE = 41,
+};
+
struct VehicleSeat
{
explicit VehicleSeat(VehicleSeatEntry const *_seatInfo) : seatInfo(_seatInfo), passenger(NULL) {}