mirror of
https://github.com/mangosfour/server.git
synced 2025-12-13 22:37:03 +00:00
Mobs fleeing and getting assistance feature implementaion.
Signed-off-by: VladimirMangos <vladimir@getmangos.com> Also rename ACTION_T_FLEE to ACTION_T_FLEE_FOR_ASSIST for clear use
This commit is contained in:
parent
f332c000d1
commit
fa03b3663a
21 changed files with 238 additions and 19 deletions
|
|
@ -114,7 +114,7 @@ Params are always read from Param1, then Param2, then Param3.
|
||||||
22 ACTION_T_SET_PHASE Phase Sets the current phase to (param1)
|
22 ACTION_T_SET_PHASE Phase Sets the current phase to (param1)
|
||||||
23 ACTION_T_INC_PHASE Value Increments the phase by (param1). May be negative to decrement phase but should not be 0.
|
23 ACTION_T_INC_PHASE Value Increments the phase by (param1). May be negative to decrement phase but should not be 0.
|
||||||
24 ACTION_T_EVADE No Params Forces the creature to evade. Wiping all threat and dropping combat.
|
24 ACTION_T_EVADE No Params Forces the creature to evade. Wiping all threat and dropping combat.
|
||||||
25 ACTION_T_FLEE No Params Causes the .creature to flee. Please use this action instead of directly casting this spell so we may change this when a more correct approach is found.
|
25 ACTION_T_FLEE_FOR_ASSIST No Params Causes the creature to flee for assistence (at low helth mostly).
|
||||||
26 ACTION_T_QUEST_EVENT_ALL QuestId Calls GroupEventHappens with (param1). Only used if it's _expected_ event should complete for all players in current party
|
26 ACTION_T_QUEST_EVENT_ALL QuestId Calls GroupEventHappens with (param1). Only used if it's _expected_ event should complete for all players in current party
|
||||||
27 ACTION_T_CASTCREATUREGO_ALL QuestId, SpellId Calls CastedCreatureOrGo for all players on the threat list with QuestID(Param1) and SpellId(Param2)
|
27 ACTION_T_CASTCREATUREGO_ALL QuestId, SpellId Calls CastedCreatureOrGo for all players on the threat list with QuestID(Param1) and SpellId(Param2)
|
||||||
28 ACTION_T_REMOVEAURASFROMSPELL Target, Spellid Removes all auras on Target caused by Spellid
|
28 ACTION_T_REMOVEAURASFROMSPELL Target, Spellid Removes all auras on Target caused by Spellid
|
||||||
|
|
|
||||||
|
|
@ -111,7 +111,7 @@ m_deathTimer(0), m_respawnTime(0), m_respawnDelay(25), m_corpseDelay(60), m_resp
|
||||||
m_gossipOptionLoaded(false), m_isPet(false), m_isVehicle(false), m_isTotem(false),
|
m_gossipOptionLoaded(false), m_isPet(false), m_isVehicle(false), m_isTotem(false),
|
||||||
m_defaultMovementType(IDLE_MOTION_TYPE), m_DBTableGuid(0), m_equipmentId(0), m_AlreadyCallAssistance(false),
|
m_defaultMovementType(IDLE_MOTION_TYPE), m_DBTableGuid(0), m_equipmentId(0), m_AlreadyCallAssistance(false),
|
||||||
m_regenHealth(true), m_AI_locked(false), m_isDeadByDefault(false), m_meleeDamageSchoolMask(SPELL_SCHOOL_MASK_NORMAL),
|
m_regenHealth(true), m_AI_locked(false), m_isDeadByDefault(false), m_meleeDamageSchoolMask(SPELL_SCHOOL_MASK_NORMAL),
|
||||||
m_creatureInfo(NULL), m_isActiveObject(false)
|
m_creatureInfo(NULL), m_isActiveObject(false), m_AlreadySearchedAssistance(false)
|
||||||
{
|
{
|
||||||
m_regenTimer = 200;
|
m_regenTimer = 200;
|
||||||
m_valuesCount = UNIT_END;
|
m_valuesCount = UNIT_END;
|
||||||
|
|
@ -506,6 +506,36 @@ void Creature::RegenerateHealth()
|
||||||
ModifyHealth(addvalue);
|
ModifyHealth(addvalue);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Creature::DoFleeToGetAssistance()
|
||||||
|
{
|
||||||
|
if (!getVictim())
|
||||||
|
return;
|
||||||
|
|
||||||
|
float radius = sWorld.getConfig(CONFIG_CREATURE_FAMILY_FLEE_ASSISTANCE_RADIUS);
|
||||||
|
if (radius >0)
|
||||||
|
{
|
||||||
|
Creature* pCreature = NULL;
|
||||||
|
|
||||||
|
CellPair p(MaNGOS::ComputeCellPair(GetPositionX(), GetPositionY()));
|
||||||
|
Cell cell(p);
|
||||||
|
cell.data.Part.reserved = ALL_DISTRICT;
|
||||||
|
cell.SetNoCreate();
|
||||||
|
MaNGOS::NearestAssistCreatureInCreatureRangeCheck u_check(this, getVictim(), radius);
|
||||||
|
MaNGOS::CreatureLastSearcher<MaNGOS::NearestAssistCreatureInCreatureRangeCheck> searcher(this, pCreature, u_check);
|
||||||
|
|
||||||
|
TypeContainerVisitor<MaNGOS::CreatureLastSearcher<MaNGOS::NearestAssistCreatureInCreatureRangeCheck>, GridTypeMapContainer > grid_creature_searcher(searcher);
|
||||||
|
|
||||||
|
CellLock<GridReadGuard> cell_lock(cell, p);
|
||||||
|
cell_lock->Visit(cell_lock, grid_creature_searcher, *GetMap());
|
||||||
|
|
||||||
|
SetNoSearchAssistance(true);
|
||||||
|
if(!pCreature)
|
||||||
|
SetFeared(true, getVictim()->GetGUID(), 0 ,sWorld.getConfig(CONFIG_CREATURE_FAMILY_FLEE_DELAY));
|
||||||
|
else
|
||||||
|
GetMotionMaster()->MoveSeekAssistance(pCreature->GetPositionX(), pCreature->GetPositionY(), pCreature->GetPositionZ());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool Creature::AIM_Initialize()
|
bool Creature::AIM_Initialize()
|
||||||
{
|
{
|
||||||
// make sure nothing can change the AI during AI update
|
// make sure nothing can change the AI during AI update
|
||||||
|
|
@ -1473,6 +1503,7 @@ void Creature::setDeathState(DeathState s)
|
||||||
if (canFly() && FallGround())
|
if (canFly() && FallGround())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
SetNoSearchAssistance(false);
|
||||||
Unit::setDeathState(CORPSE);
|
Unit::setDeathState(CORPSE);
|
||||||
}
|
}
|
||||||
if(s == JUST_ALIVED)
|
if(s == JUST_ALIVED)
|
||||||
|
|
|
||||||
|
|
@ -601,8 +601,11 @@ class MANGOS_DLL_SPEC Creature : public Unit
|
||||||
|
|
||||||
float GetAttackDistance(Unit const* pl) const;
|
float GetAttackDistance(Unit const* pl) const;
|
||||||
|
|
||||||
|
void DoFleeToGetAssistance();
|
||||||
void CallAssistance();
|
void CallAssistance();
|
||||||
void SetNoCallAssistance(bool val) { m_AlreadyCallAssistance = val; }
|
void SetNoCallAssistance(bool val) { m_AlreadyCallAssistance = val; }
|
||||||
|
void SetNoSearchAssistance(bool val) { m_AlreadySearchedAssistance = val; }
|
||||||
|
bool HasSearchedAssistance() { return m_AlreadySearchedAssistance; }
|
||||||
bool CanAssistTo(const Unit* u, const Unit* enemy, bool checkfaction = true) const;
|
bool CanAssistTo(const Unit* u, const Unit* enemy, bool checkfaction = true) const;
|
||||||
|
|
||||||
MovementGeneratorType GetDefaultMovementType() const { return m_defaultMovementType; }
|
MovementGeneratorType GetDefaultMovementType() const { return m_defaultMovementType; }
|
||||||
|
|
@ -694,6 +697,7 @@ class MANGOS_DLL_SPEC Creature : public Unit
|
||||||
uint32 m_equipmentId;
|
uint32 m_equipmentId;
|
||||||
|
|
||||||
bool m_AlreadyCallAssistance;
|
bool m_AlreadyCallAssistance;
|
||||||
|
bool m_AlreadySearchedAssistance;
|
||||||
bool m_regenHealth;
|
bool m_regenHealth;
|
||||||
bool m_AI_locked;
|
bool m_AI_locked;
|
||||||
bool m_isDeadByDefault;
|
bool m_isDeadByDefault;
|
||||||
|
|
|
||||||
|
|
@ -623,9 +623,8 @@ void CreatureEventAI::ProcessAction(CreatureEventAI_Action const& action, uint32
|
||||||
case ACTION_T_EVADE:
|
case ACTION_T_EVADE:
|
||||||
EnterEvadeMode();
|
EnterEvadeMode();
|
||||||
break;
|
break;
|
||||||
case ACTION_T_FLEE:
|
case ACTION_T_FLEE_FOR_ASSIST:
|
||||||
//TODO: Replace with Flee movement generator
|
m_creature->DoFleeToGetAssistance();
|
||||||
m_creature->CastSpell(m_creature, SPELL_RUN_AWAY, true);
|
|
||||||
break;
|
break;
|
||||||
case ACTION_T_QUEST_EVENT_ALL:
|
case ACTION_T_QUEST_EVENT_ALL:
|
||||||
if (pActionInvoker && pActionInvoker->GetTypeId() == TYPEID_PLAYER)
|
if (pActionInvoker && pActionInvoker->GetTypeId() == TYPEID_PLAYER)
|
||||||
|
|
|
||||||
|
|
@ -28,7 +28,6 @@ class Player;
|
||||||
class WorldObject;
|
class WorldObject;
|
||||||
|
|
||||||
#define EVENT_UPDATE_TIME 500
|
#define EVENT_UPDATE_TIME 500
|
||||||
#define SPELL_RUN_AWAY 8225
|
|
||||||
#define MAX_ACTIONS 3
|
#define MAX_ACTIONS 3
|
||||||
#define MAX_PHASE 32
|
#define MAX_PHASE 32
|
||||||
|
|
||||||
|
|
@ -88,7 +87,7 @@ enum EventAI_ActionType
|
||||||
ACTION_T_SET_PHASE = 22, // Phase
|
ACTION_T_SET_PHASE = 22, // Phase
|
||||||
ACTION_T_INC_PHASE = 23, // Value (may be negative to decrement phase, should not be 0)
|
ACTION_T_INC_PHASE = 23, // Value (may be negative to decrement phase, should not be 0)
|
||||||
ACTION_T_EVADE = 24, // No Params
|
ACTION_T_EVADE = 24, // No Params
|
||||||
ACTION_T_FLEE = 25, // No Params
|
ACTION_T_FLEE_FOR_ASSIST = 25, // No Params
|
||||||
ACTION_T_QUEST_EVENT_ALL = 26, // QuestID
|
ACTION_T_QUEST_EVENT_ALL = 26, // QuestID
|
||||||
ACTION_T_CAST_EVENT_ALL = 27, // CreatureId, SpellId
|
ACTION_T_CAST_EVENT_ALL = 27, // CreatureId, SpellId
|
||||||
ACTION_T_REMOVEAURASFROMSPELL = 28, // Target, Spellid
|
ACTION_T_REMOVEAURASFROMSPELL = 28, // Target, Spellid
|
||||||
|
|
|
||||||
|
|
@ -626,7 +626,7 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, action.update_template.creatureId);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, action.update_template.creatureId);
|
||||||
break;
|
break;
|
||||||
case ACTION_T_EVADE: //No Params
|
case ACTION_T_EVADE: //No Params
|
||||||
case ACTION_T_FLEE: //No Params
|
case ACTION_T_FLEE_FOR_ASSIST: //No Params
|
||||||
case ACTION_T_DIE: //No Params
|
case ACTION_T_DIE: //No Params
|
||||||
case ACTION_T_ZONE_COMBAT_PULSE: //No Params
|
case ACTION_T_ZONE_COMBAT_PULSE: //No Params
|
||||||
case ACTION_T_AUTO_ATTACK: //AllowAttackState (0 = stop attack, anything else means continue attacking)
|
case ACTION_T_AUTO_ATTACK: //AllowAttackState (0 = stop attack, anything else means continue attacking)
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "Creature.h"
|
#include "Creature.h"
|
||||||
|
#include "CreatureAI.h"
|
||||||
#include "MapManager.h"
|
#include "MapManager.h"
|
||||||
#include "FleeingMovementGenerator.h"
|
#include "FleeingMovementGenerator.h"
|
||||||
#include "DestinationHolderImp.h"
|
#include "DestinationHolderImp.h"
|
||||||
|
|
@ -384,3 +385,33 @@ template void FleeingMovementGenerator<Player>::Reset(Player &);
|
||||||
template void FleeingMovementGenerator<Creature>::Reset(Creature &);
|
template void FleeingMovementGenerator<Creature>::Reset(Creature &);
|
||||||
template bool FleeingMovementGenerator<Player>::Update(Player &, const uint32 &);
|
template bool FleeingMovementGenerator<Player>::Update(Player &, const uint32 &);
|
||||||
template bool FleeingMovementGenerator<Creature>::Update(Creature &, const uint32 &);
|
template bool FleeingMovementGenerator<Creature>::Update(Creature &, const uint32 &);
|
||||||
|
|
||||||
|
void TimedFleeingMovementGenerator::Finalize(Unit &owner)
|
||||||
|
{
|
||||||
|
owner.clearUnitState(UNIT_STAT_FLEEING);
|
||||||
|
if (Unit* victim = owner.getVictim())
|
||||||
|
{
|
||||||
|
if (owner.isAlive())
|
||||||
|
{
|
||||||
|
owner.AttackStop(true);
|
||||||
|
((Creature*)&owner)->AI()->AttackStart(victim);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool TimedFleeingMovementGenerator::Update(Unit & owner, const uint32 & time_diff)
|
||||||
|
{
|
||||||
|
if( !owner.isAlive() )
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if( owner.hasUnitState(UNIT_STAT_ROOT | UNIT_STAT_STUNNED) )
|
||||||
|
return true;
|
||||||
|
|
||||||
|
i_totalFleeTime.Update(time_diff);
|
||||||
|
if (i_totalFleeTime.Passed())
|
||||||
|
return false;
|
||||||
|
|
||||||
|
// This calls grant-parent Update method hiden by FleeingMovementGenerator::Update(Creature &, const uint32 &) version
|
||||||
|
// This is done instead of casting Unit& to Creature& and call parent method, then we can use Unit directly
|
||||||
|
return MovementGeneratorMedium< Creature, FleeingMovementGenerator<Creature> >::Update(owner, time_diff);
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -58,4 +58,21 @@ class MANGOS_DLL_SPEC FleeingMovementGenerator
|
||||||
|
|
||||||
DestinationHolder< Traveller<T> > i_destinationHolder;
|
DestinationHolder< Traveller<T> > i_destinationHolder;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class MANGOS_DLL_SPEC TimedFleeingMovementGenerator
|
||||||
|
: public FleeingMovementGenerator<Creature>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
TimedFleeingMovementGenerator(uint64 fright, uint32 time) :
|
||||||
|
FleeingMovementGenerator<Creature>(fright),
|
||||||
|
i_totalFleeTime(time) {}
|
||||||
|
|
||||||
|
MovementGeneratorType GetMovementGeneratorType() { return TIMED_FLEEING_MOTION_TYPE; }
|
||||||
|
bool Update(Unit &, const uint32 &);
|
||||||
|
void Finalize(Unit &);
|
||||||
|
|
||||||
|
private:
|
||||||
|
TimeTracker i_totalFleeTime;
|
||||||
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
||||||
|
|
@ -914,6 +914,38 @@ namespace MaNGOS
|
||||||
float i_range;
|
float i_range;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class NearestAssistCreatureInCreatureRangeCheck
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
NearestAssistCreatureInCreatureRangeCheck(Creature* obj, Unit* enemy, float range)
|
||||||
|
: i_obj(obj), i_enemy(enemy), i_range(range) {}
|
||||||
|
|
||||||
|
bool operator()(Creature* u)
|
||||||
|
{
|
||||||
|
if(u == i_obj)
|
||||||
|
return false;
|
||||||
|
if(!u->CanAssistTo(i_obj,i_enemy))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if(!i_obj->IsWithinDistInMap(u, i_range))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if(!i_obj->IsWithinLOSInMap(u))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
i_range = i_obj->GetDistance(u); // use found unit range as new range limit for next check
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
float GetLastRange() const { return i_range; }
|
||||||
|
private:
|
||||||
|
Creature* const i_obj;
|
||||||
|
Unit* const i_enemy;
|
||||||
|
float i_range;
|
||||||
|
|
||||||
|
// prevent clone this object
|
||||||
|
NearestAssistCreatureInCreatureRangeCheck(NearestAssistCreatureInCreatureRangeCheck const&);
|
||||||
|
};
|
||||||
|
|
||||||
// Success at unit in range, range update for next check (this can be use with CreatureLastSearcher to find nearest creature)
|
// Success at unit in range, range update for next check (this can be use with CreatureLastSearcher to find nearest creature)
|
||||||
class NearestCreatureEntryWithLiveStateInObjectRangeCheck
|
class NearestCreatureEntryWithLiveStateInObjectRangeCheck
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -17,7 +17,8 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "IdleMovementGenerator.h"
|
#include "IdleMovementGenerator.h"
|
||||||
#include "Unit.h"
|
#include "CreatureAI.h"
|
||||||
|
#include "Creature.h"
|
||||||
|
|
||||||
IdleMovementGenerator si_idleMovement;
|
IdleMovementGenerator si_idleMovement;
|
||||||
|
|
||||||
|
|
@ -47,3 +48,17 @@ DistractMovementGenerator::Update(Unit& /*owner*/, const uint32& time_diff)
|
||||||
m_timer -= time_diff;
|
m_timer -= time_diff;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
AssistanceDistractMovementGenerator::Finalize(Unit &unit)
|
||||||
|
{
|
||||||
|
unit.clearUnitState(UNIT_STAT_DISTRACTED);
|
||||||
|
if (Unit* victim = unit.getVictim())
|
||||||
|
{
|
||||||
|
if (unit.isAlive())
|
||||||
|
{
|
||||||
|
unit.AttackStop(true);
|
||||||
|
((Creature*)&unit)->AI()->AttackStart(victim);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -49,4 +49,14 @@ class MANGOS_DLL_SPEC DistractMovementGenerator : public MovementGenerator
|
||||||
uint32 m_timer;
|
uint32 m_timer;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class MANGOS_DLL_SPEC AssistanceDistractMovementGenerator : public DistractMovementGenerator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
AssistanceDistractMovementGenerator(uint32 timer) :
|
||||||
|
DistractMovementGenerator(timer) {}
|
||||||
|
|
||||||
|
MovementGeneratorType GetMovementGeneratorType() { return ASSISTANCE_DISTRACT_MOTION_TYPE; }
|
||||||
|
void Finalize(Unit& unit);
|
||||||
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
||||||
|
|
@ -331,7 +331,37 @@ MotionMaster::MovePoint(uint32 id, float x, float y, float z)
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
MotionMaster::MoveFleeing(Unit* enemy)
|
MotionMaster::MoveSeekAssistance(float x, float y, float z)
|
||||||
|
{
|
||||||
|
if(i_owner->GetTypeId()==TYPEID_PLAYER)
|
||||||
|
{
|
||||||
|
sLog.outError("Player (GUID: %u) attempt to seek assistance",i_owner->GetGUIDLow());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
DEBUG_LOG("Creature (Entry: %u GUID: %u) seek assistance (X: %f Y: %f Z: %f)",
|
||||||
|
i_owner->GetEntry(), i_owner->GetGUIDLow(), x, y, z );
|
||||||
|
Mutate(new AssistanceMovementGenerator(x,y,z));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
MotionMaster::MoveSeekAssistanceDistract(uint32 time)
|
||||||
|
{
|
||||||
|
if(i_owner->GetTypeId()==TYPEID_PLAYER)
|
||||||
|
{
|
||||||
|
sLog.outError("Player (GUID: %u) attempt to call distract after assistance",i_owner->GetGUIDLow());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
DEBUG_LOG("Creature (Entry: %u GUID: %u) is distracted after assistance call (Time: %u)",
|
||||||
|
i_owner->GetEntry(), i_owner->GetGUIDLow(), time );
|
||||||
|
Mutate(new AssistanceDistractMovementGenerator(time));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
MotionMaster::MoveFleeing(Unit* enemy, uint32 time)
|
||||||
{
|
{
|
||||||
if(!enemy)
|
if(!enemy)
|
||||||
return;
|
return;
|
||||||
|
|
@ -345,11 +375,15 @@ MotionMaster::MoveFleeing(Unit* enemy)
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
DEBUG_LOG("Creature (Entry: %u GUID: %u) flee from %s (GUID: %u)",
|
DEBUG_LOG("Creature (Entry: %u GUID: %u) flee from %s (GUID: %u)%s",
|
||||||
i_owner->GetEntry(), i_owner->GetGUIDLow(),
|
i_owner->GetEntry(), i_owner->GetGUIDLow(),
|
||||||
enemy->GetTypeId()==TYPEID_PLAYER ? "player" : "creature",
|
enemy->GetTypeId()==TYPEID_PLAYER ? "player" : "creature",
|
||||||
enemy->GetTypeId()==TYPEID_PLAYER ? enemy->GetGUIDLow() : ((Creature*)enemy)->GetDBTableGUIDLow() );
|
enemy->GetTypeId()==TYPEID_PLAYER ? enemy->GetGUIDLow() : ((Creature*)enemy)->GetDBTableGUIDLow(),
|
||||||
Mutate(new FleeingMovementGenerator<Creature>(enemy->GetGUID()));
|
time ? " for a limited time" : "");
|
||||||
|
if (time)
|
||||||
|
Mutate(new TimedFleeingMovementGenerator(enemy->GetGUID(), time));
|
||||||
|
else
|
||||||
|
Mutate(new FleeingMovementGenerator<Creature>(enemy->GetGUID()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -44,6 +44,9 @@ enum MovementGeneratorType
|
||||||
POINT_MOTION_TYPE = 8, // PointMovementGenerator.h
|
POINT_MOTION_TYPE = 8, // PointMovementGenerator.h
|
||||||
FLEEING_MOTION_TYPE = 9, // FleeingMovementGenerator.h
|
FLEEING_MOTION_TYPE = 9, // FleeingMovementGenerator.h
|
||||||
DISTRACT_MOTION_TYPE = 10, // IdleMovementGenerator.h
|
DISTRACT_MOTION_TYPE = 10, // IdleMovementGenerator.h
|
||||||
|
ASSISTANCE_MOTION_TYPE= 11, // PointMovementGenerator.h (first part of flee for assistance)
|
||||||
|
ASSISTANCE_DISTRACT_MOTION_TYPE = 12, // IdleMovementGenerator.h (second part of flee for assistance)
|
||||||
|
TIMED_FLEEING_MOTION_TYPE = 13, // FleeingMovementGenerator.h (alt.second part of flee for assistance)
|
||||||
};
|
};
|
||||||
|
|
||||||
enum MMCleanFlag
|
enum MMCleanFlag
|
||||||
|
|
@ -107,8 +110,10 @@ class MANGOS_DLL_SPEC MotionMaster : private std::stack<MovementGenerator *>
|
||||||
void MoveFollow(Unit* target, float dist, float angle);
|
void MoveFollow(Unit* target, float dist, float angle);
|
||||||
void MoveChase(Unit* target, float dist = 0.0f, float angle = 0.0f);
|
void MoveChase(Unit* target, float dist = 0.0f, float angle = 0.0f);
|
||||||
void MoveConfused();
|
void MoveConfused();
|
||||||
void MoveFleeing(Unit* enemy);
|
void MoveFleeing(Unit* enemy, uint32 time = 0);
|
||||||
void MovePoint(uint32 id, float x,float y,float z);
|
void MovePoint(uint32 id, float x,float y,float z);
|
||||||
|
void MoveSeekAssistance(float x,float y,float z);
|
||||||
|
void MoveSeekAssistanceDistract(uint32 timer);
|
||||||
void MoveTaxiFlight(uint32 path, uint32 pathnode);
|
void MoveTaxiFlight(uint32 path, uint32 pathnode);
|
||||||
void MoveDistract(uint32 time);
|
void MoveDistract(uint32 time);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -21,6 +21,7 @@
|
||||||
#include "Creature.h"
|
#include "Creature.h"
|
||||||
#include "CreatureAI.h"
|
#include "CreatureAI.h"
|
||||||
#include "DestinationHolderImp.h"
|
#include "DestinationHolderImp.h"
|
||||||
|
#include "World.h"
|
||||||
|
|
||||||
//----- Point Movement Generator
|
//----- Point Movement Generator
|
||||||
template<class T>
|
template<class T>
|
||||||
|
|
@ -73,3 +74,11 @@ template void PointMovementGenerator<Player>::MovementInform(Player&);
|
||||||
|
|
||||||
template void PointMovementGenerator<Creature>::Initialize(Creature&);
|
template void PointMovementGenerator<Creature>::Initialize(Creature&);
|
||||||
template bool PointMovementGenerator<Creature>::Update(Creature&, const uint32 &diff);
|
template bool PointMovementGenerator<Creature>::Update(Creature&, const uint32 &diff);
|
||||||
|
|
||||||
|
void AssistanceMovementGenerator::Finalize(Unit &unit)
|
||||||
|
{
|
||||||
|
((Creature*)&unit)->SetNoCallAssistance(false);
|
||||||
|
((Creature*)&unit)->CallAssistance();
|
||||||
|
if (unit.isAlive())
|
||||||
|
unit.GetMotionMaster()->MoveSeekAssistanceDistract(sWorld.getConfig(CONFIG_CREATURE_FAMILY_ASSISTANCE_DELAY));
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -48,4 +48,16 @@ class MANGOS_DLL_SPEC PointMovementGenerator
|
||||||
TimeTracker i_nextMoveTime;
|
TimeTracker i_nextMoveTime;
|
||||||
DestinationHolder< Traveller<T> > i_destinationHolder;
|
DestinationHolder< Traveller<T> > i_destinationHolder;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class MANGOS_DLL_SPEC AssistanceMovementGenerator
|
||||||
|
: public PointMovementGenerator<Creature>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
AssistanceMovementGenerator(float _x, float _y, float _z) :
|
||||||
|
PointMovementGenerator<Creature>(0, _x, _y, _z) {}
|
||||||
|
|
||||||
|
MovementGeneratorType GetMovementGeneratorType() { return ASSISTANCE_MOTION_TYPE; }
|
||||||
|
void Finalize(Unit &);
|
||||||
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
||||||
|
|
@ -92,7 +92,10 @@ template<class T>
|
||||||
void
|
void
|
||||||
TargetedMovementGenerator<T>::Initialize(T &owner)
|
TargetedMovementGenerator<T>::Initialize(T &owner)
|
||||||
{
|
{
|
||||||
owner.RemoveUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
|
if (owner.GetTypeId() == TYPEID_UNIT && ((Creature*)&owner)->HasSearchedAssistance())
|
||||||
|
owner.AddUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
|
||||||
|
else
|
||||||
|
owner.RemoveUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
|
||||||
|
|
||||||
if (owner.GetTypeId() == TYPEID_UNIT && ((Creature*)&owner)->canFly())
|
if (owner.GetTypeId() == TYPEID_UNIT && ((Creature*)&owner)->canFly())
|
||||||
owner.AddUnitMovementFlag(MOVEMENTFLAG_FLYING2);
|
owner.AddUnitMovementFlag(MOVEMENTFLAG_FLYING2);
|
||||||
|
|
|
||||||
|
|
@ -7299,7 +7299,10 @@ bool Unit::AttackStop(bool targetSwitch /*=false*/)
|
||||||
|
|
||||||
// reset only at real combat stop
|
// reset only at real combat stop
|
||||||
if(!targetSwitch && GetTypeId()==TYPEID_UNIT )
|
if(!targetSwitch && GetTypeId()==TYPEID_UNIT )
|
||||||
|
{
|
||||||
((Creature*)this)->SetNoCallAssistance(false);
|
((Creature*)this)->SetNoCallAssistance(false);
|
||||||
|
((Creature*)this)->SetNoSearchAssistance(false);
|
||||||
|
}
|
||||||
|
|
||||||
SendAttackStop(victim);
|
SendAttackStop(victim);
|
||||||
|
|
||||||
|
|
@ -10918,7 +10921,7 @@ void Unit::StopMoving()
|
||||||
SendMessageToSet(&data,false);
|
SendMessageToSet(&data,false);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Unit::SetFeared(bool apply, uint64 casterGUID, uint32 spellID)
|
void Unit::SetFeared(bool apply, uint64 casterGUID, uint32 spellID, uint32 time)
|
||||||
{
|
{
|
||||||
if( apply )
|
if( apply )
|
||||||
{
|
{
|
||||||
|
|
@ -10932,7 +10935,7 @@ void Unit::SetFeared(bool apply, uint64 casterGUID, uint32 spellID)
|
||||||
|
|
||||||
Unit* caster = ObjectAccessor::GetUnit(*this,casterGUID);
|
Unit* caster = ObjectAccessor::GetUnit(*this,casterGUID);
|
||||||
|
|
||||||
GetMotionMaster()->MoveFleeing(caster); // caster==NULL processed in MoveFleeing
|
GetMotionMaster()->MoveFleeing(caster, time); // caster==NULL processed in MoveFleeing
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -1407,7 +1407,7 @@ class MANGOS_DLL_SPEC Unit : public WorldObject
|
||||||
uint32 GetUnitMovementFlags() const { return m_unit_movement_flags; }
|
uint32 GetUnitMovementFlags() const { return m_unit_movement_flags; }
|
||||||
void SetUnitMovementFlags(uint32 f) { m_unit_movement_flags = f; }
|
void SetUnitMovementFlags(uint32 f) { m_unit_movement_flags = f; }
|
||||||
|
|
||||||
void SetFeared(bool apply, uint64 casterGUID = 0, uint32 spellID = 0);
|
void SetFeared(bool apply, uint64 casterGUID = 0, uint32 spellID = 0, uint32 time = 0);
|
||||||
void SetConfused(bool apply, uint64 casterGUID = 0, uint32 spellID = 0);
|
void SetConfused(bool apply, uint64 casterGUID = 0, uint32 spellID = 0);
|
||||||
|
|
||||||
void AddComboPointHolder(uint32 lowguid) { m_ComboPointHolders.insert(lowguid); }
|
void AddComboPointHolder(uint32 lowguid) { m_ComboPointHolders.insert(lowguid); }
|
||||||
|
|
|
||||||
|
|
@ -877,8 +877,10 @@ void World::LoadConfigSettings(bool reload)
|
||||||
|
|
||||||
m_configs[CONFIG_EVENT_ANNOUNCE] = sConfig.GetIntDefault("Event.Announce",0);
|
m_configs[CONFIG_EVENT_ANNOUNCE] = sConfig.GetIntDefault("Event.Announce",0);
|
||||||
|
|
||||||
|
m_configs[CONFIG_CREATURE_FAMILY_FLEE_ASSISTANCE_RADIUS] = sConfig.GetIntDefault("CreatureFamilyFleeAssistanceRadius",30);
|
||||||
m_configs[CONFIG_CREATURE_FAMILY_ASSISTANCE_RADIUS] = sConfig.GetIntDefault("CreatureFamilyAssistanceRadius",10);
|
m_configs[CONFIG_CREATURE_FAMILY_ASSISTANCE_RADIUS] = sConfig.GetIntDefault("CreatureFamilyAssistanceRadius",10);
|
||||||
m_configs[CONFIG_CREATURE_FAMILY_ASSISTANCE_DELAY] = sConfig.GetIntDefault("CreatureFamilyAssistanceDelay",1500);
|
m_configs[CONFIG_CREATURE_FAMILY_ASSISTANCE_DELAY] = sConfig.GetIntDefault("CreatureFamilyAssistanceDelay",1500);
|
||||||
|
m_configs[CONFIG_CREATURE_FAMILY_FLEE_DELAY] = sConfig.GetIntDefault("CreatureFamilyFleeDelay",7000);
|
||||||
|
|
||||||
m_configs[CONFIG_WORLD_BOSS_LEVEL_DIFF] = sConfig.GetIntDefault("WorldBossLevelDiff",3);
|
m_configs[CONFIG_WORLD_BOSS_LEVEL_DIFF] = sConfig.GetIntDefault("WorldBossLevelDiff",3);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -162,8 +162,10 @@ enum WorldConfigs
|
||||||
CONFIG_CHATFLOOD_MESSAGE_DELAY,
|
CONFIG_CHATFLOOD_MESSAGE_DELAY,
|
||||||
CONFIG_CHATFLOOD_MUTE_TIME,
|
CONFIG_CHATFLOOD_MUTE_TIME,
|
||||||
CONFIG_EVENT_ANNOUNCE,
|
CONFIG_EVENT_ANNOUNCE,
|
||||||
|
CONFIG_CREATURE_FAMILY_FLEE_ASSISTANCE_RADIUS,
|
||||||
CONFIG_CREATURE_FAMILY_ASSISTANCE_RADIUS,
|
CONFIG_CREATURE_FAMILY_ASSISTANCE_RADIUS,
|
||||||
CONFIG_CREATURE_FAMILY_ASSISTANCE_DELAY,
|
CONFIG_CREATURE_FAMILY_ASSISTANCE_DELAY,
|
||||||
|
CONFIG_CREATURE_FAMILY_FLEE_DELAY,
|
||||||
CONFIG_WORLD_BOSS_LEVEL_DIFF,
|
CONFIG_WORLD_BOSS_LEVEL_DIFF,
|
||||||
CONFIG_QUEST_LOW_LEVEL_HIDE_DIFF,
|
CONFIG_QUEST_LOW_LEVEL_HIDE_DIFF,
|
||||||
CONFIG_QUEST_HIGH_LEVEL_HIDE_DIFF,
|
CONFIG_QUEST_HIGH_LEVEL_HIDE_DIFF,
|
||||||
|
|
|
||||||
|
|
@ -678,8 +678,13 @@ TalentsInspecting = 1
|
||||||
# 1.5 - 150%
|
# 1.5 - 150%
|
||||||
# 0 - off (0%)
|
# 0 - off (0%)
|
||||||
#
|
#
|
||||||
|
# CreatureFamilyFleeAssistanceRadius
|
||||||
|
# Radius which creature will use to seek for a near creature for assistance. Creature will flee to this creature.
|
||||||
|
# Default: 30
|
||||||
|
# 0 - off
|
||||||
|
#
|
||||||
# CreatureFamilyAssistanceRadius
|
# CreatureFamilyAssistanceRadius
|
||||||
# Creature family assistance radius
|
# Radius which creature will use to call assistance without moving
|
||||||
# Default: 10
|
# Default: 10
|
||||||
# 0 - off
|
# 0 - off
|
||||||
#
|
#
|
||||||
|
|
@ -687,6 +692,10 @@ TalentsInspecting = 1
|
||||||
# Reaction time for creature assistance call
|
# Reaction time for creature assistance call
|
||||||
# Default: 1500 (1.5s)
|
# Default: 1500 (1.5s)
|
||||||
#
|
#
|
||||||
|
# CreatureFamilyFleeDelay
|
||||||
|
# Time during which creature can flee when no assistant found
|
||||||
|
# Default: 7000 (7s)
|
||||||
|
#
|
||||||
# WorldBossLevelDiff
|
# WorldBossLevelDiff
|
||||||
# Difference for boss dynamic level with target
|
# Difference for boss dynamic level with target
|
||||||
# Default: 3
|
# Default: 3
|
||||||
|
|
@ -743,8 +752,10 @@ TalentsInspecting = 1
|
||||||
|
|
||||||
ThreatRadius = 100
|
ThreatRadius = 100
|
||||||
Rate.Creature.Aggro = 1
|
Rate.Creature.Aggro = 1
|
||||||
|
CreatureFamilyFleeAssistanceRadius = 30
|
||||||
CreatureFamilyAssistanceRadius = 10
|
CreatureFamilyAssistanceRadius = 10
|
||||||
CreatureFamilyAssistanceDelay = 1500
|
CreatureFamilyAssistanceDelay = 1500
|
||||||
|
CreatureFamilyFleeDelay = 7000
|
||||||
WorldBossLevelDiff = 3
|
WorldBossLevelDiff = 3
|
||||||
Corpse.Decay.NORMAL = 60
|
Corpse.Decay.NORMAL = 60
|
||||||
Corpse.Decay.RARE = 300
|
Corpse.Decay.RARE = 300
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue