AzerothCore 3.3.5a
OpenSource WoW Emulator
Loading...
Searching...
No Matches
SmartScript Class Reference

#include "SmartScript.h"

Classes

struct  SmartScriptFrame
 

Public Types

typedef std::unordered_map< uint32, uint32 > CounterMap
 

Public Member Functions

 SmartScript ()
 
 ~SmartScript ()
 
void OnInitialize (WorldObject *obj, AreaTrigger const *at=nullptr)
 
void GetScript ()
 
void FillScript (SmartAIEventList e, WorldObject *obj, AreaTrigger const *at)
 
void ProcessEventsFor (SMART_EVENT e, Unit *unit=nullptr, uint32 var0=0, uint32 var1=0, bool bvar=false, SpellInfo const *spell=nullptr, GameObject *gob=nullptr)
 
void ProcessEvent (SmartScriptHolder &e, Unit *unit=nullptr, uint32 var0=0, uint32 var1=0, bool bvar=false, SpellInfo const *spell=nullptr, GameObject *gob=nullptr)
 
bool CheckTimer (SmartScriptHolder const &e) const
 
void UpdateTimer (SmartScriptHolder &e, uint32 const diff)
 
void ProcessAction (SmartScriptHolder &e, Unit *unit=nullptr, uint32 var0=0, uint32 var1=0, bool bvar=false, SpellInfo const *spell=nullptr, GameObject *gob=nullptr)
 
void ProcessTimedAction (SmartScriptHolder &e, uint32 const &min, uint32 const &max, Unit *unit=nullptr, uint32 var0=0, uint32 var1=0, bool bvar=false, SpellInfo const *spell=nullptr, GameObject *gob=nullptr)
 
void GetTargets (ObjectVector &targets, SmartScriptHolder const &e, WorldObject *invoker=nullptr) const
 
void GetWorldObjectsInDist (ObjectVector &objects, float dist) const
 
void InstallTemplate (SmartScriptHolder const &e)
 
void AddEvent (SMART_EVENT e, uint32 event_flags, uint32 event_param1, uint32 event_param2, uint32 event_param3, uint32 event_param4, uint32 event_param5, uint32 event_param6, SMART_ACTION action, uint32 action_param1, uint32 action_param2, uint32 action_param3, uint32 action_param4, uint32 action_param5, uint32 action_param6, SMARTAI_TARGETS t, uint32 target_param1, uint32 target_param2, uint32 target_param3, uint32 target_param4, uint32 phaseMask)
 
void SetPathId (uint32 id)
 
uint32 GetPathId () const
 
WorldObject * GetBaseObject () const
 
void OnUpdate (const uint32 diff)
 
void OnMoveInLineOfSight (Unit *who)
 
Unit * DoSelectLowestHpFriendly (float range, uint32 MinHPDiff) const
 
Unit * DoSelectLowestHpPercentFriendly (float range, uint32 minHpPct, uint32 maxHpPct) const
 
void DoFindFriendlyCC (std::vector< Creature * > &creatures, float range) const
 
void DoFindFriendlyMissingBuff (std::vector< Creature * > &creatures, float range, uint32 spellid) const
 
Unit * DoFindClosestFriendlyInRange (float range, bool playerOnly) const
 
bool IsSmart (Creature *c, bool silent=false) const
 
bool IsSmart (GameObject *g, bool silent=false) const
 
bool IsSmart (bool silent=false) const
 
void StoreTargetList (ObjectVector const &targets, uint32 id)
 
ObjectVector const * GetStoredTargetVector (uint32 id, WorldObject const &ref) const
 
void StoreCounter (uint32 id, uint32 value, uint32 reset, uint32 subtract)
 
uint32 GetCounterValue (uint32 id)
 
GameObject * FindGameObjectNear (WorldObject *searchObject, ObjectGuid::LowType guid) const
 
Creature * FindCreatureNear (WorldObject *searchObject, ObjectGuid::LowType guid) const
 
void OnReset ()
 
void ResetBaseObject ()
 
void SetScript9 (SmartScriptHolder &e, uint32 entry)
 
WorldObject * GetLastInvoker (WorldObject *invoker=nullptr) const
 
bool AllowPhaseReset () const
 
void SetPhaseReset (bool allow)
 
void AddCreatureSummon (ObjectGuid const &guid)
 
void RemoveCreatureSummon (ObjectGuid const &guid)
 
SmartAIEventList const & GetEvents () const
 

Static Public Member Functions

static void RecalcTimer (SmartScriptHolder &e, uint32 min, uint32 max)
 
static void InitTimer (SmartScriptHolder &e)
 
static SmartScriptHolder CreateSmartEvent (SMART_EVENT e, uint32 event_flags, uint32 event_param1, uint32 event_param2, uint32 event_param3, uint32 event_param4, uint32 event_param5, uint32 event_param6, SMART_ACTION action, uint32 action_param1, uint32 action_param2, uint32 action_param3, uint32 action_param4, uint32 action_param5, uint32 action_param6, SMARTAI_TARGETS t, uint32 target_param1, uint32 target_param2, uint32 target_param3, uint32 target_param4, uint32 phaseMask)
 
static bool IsUnit (WorldObject *obj)
 
static bool IsPlayer (WorldObject *obj)
 
static bool IsCreature (WorldObject *obj)
 
static bool IsCharmedCreature (WorldObject *obj)
 
static bool IsGameObject (WorldObject *obj)
 

Public Attributes

ObjectGuid mLastInvoker
 
CounterMap mCounterList
 

Private Member Functions

void IncPhase (uint32 p)
 
void DecPhase (uint32 p)
 
void SetPhase (uint32 p)
 
bool IsInPhase (uint32 p) const
 
void SortEvents (SmartAIEventList &events)
 
void RaisePriority (SmartScriptHolder &e)
 
void RetryLater (SmartScriptHolder &e, bool ignoreChanceRoll=false)
 
void InstallEvents ()
 
void RemoveStoredEvent (uint32 id)
 
std::optional< std::reference_wrapper< SmartScriptHolder > > FindLinkedEvent (uint32 link)
 

Private Attributes

SmartAIEventList mEvents
 
SmartAIEventList mInstallEvents
 
SmartAIEventList mTimedActionList
 
bool isProcessingTimedActionList
 
Creature * me
 
ObjectGuid meOrigGUID
 
GameObject * go
 
ObjectGuid goOrigGUID
 
AreaTrigger const * trigger
 
SmartScriptType mScriptType
 
uint32 mEventPhase
 
std::unordered_map< int32, int32 > mStoredDecimals
 
uint32 mPathId
 
SmartAIEventStoredList mStoredEvents
 
std::list< uint32 > mRemIDs
 
uint32 mTextTimer
 
uint32 mLastTextID
 
uint32 mTalkerEntry
 
bool mUseTextTimer
 
uint32 mCurrentPriority
 
bool mEventSortingRequired
 
bool _allowPhaseReset
 
ObjectVectorMap _storedTargets
 
SMARTAI_TEMPLATE mTemplate
 
GuidUnorderedSet _summonList
 
std::deque< SmartScriptFrame > executionStack
 

Detailed Description

Member Typedef Documentation

◆ CounterMap

typedef std::unordered_map<uint32, uint32> SmartScript::CounterMap

Constructor & Destructor Documentation

◆ SmartScript()

SmartScript::SmartScript ( )
69{
70 go = nullptr;
71 me = nullptr;
72 trigger = nullptr;
73 mEventPhase = 0;
74 mPathId = 0;
75 mTextTimer = 0;
76 mLastTextID = 0;
77 mUseTextTimer = false;
78 mTalkerEntry = 0;
84 _allowPhaseReset = true;
85}
@ SMART_SCRIPT_TYPE_CREATURE
Definition SmartScriptMgr.h:1803
@ SMARTAI_TEMPLATE_BASIC
Definition SmartScriptMgr.h:1539
uint32 mEventPhase
Definition SmartScript.h:232
SMARTAI_TEMPLATE mTemplate
Definition SmartScript.h:251
Creature * me
Definition SmartScript.h:226
uint32 mPathId
Definition SmartScript.h:235
SmartScriptType mScriptType
Definition SmartScript.h:231
bool _allowPhaseReset
Definition SmartScript.h:247
bool mUseTextTimer
Definition SmartScript.h:242
uint32 mLastTextID
Definition SmartScript.h:240
uint32 mTextTimer
Definition SmartScript.h:239
GameObject * go
Definition SmartScript.h:228
AreaTrigger const * trigger
Definition SmartScript.h:230
uint32 mCurrentPriority
Definition SmartScript.h:243
uint32 mTalkerEntry
Definition SmartScript.h:241
bool isProcessingTimedActionList
Definition SmartScript.h:225
bool mEventSortingRequired
Definition SmartScript.h:244

References _allowPhaseReset, go, isProcessingTimedActionList, mCurrentPriority, me, mEventPhase, mEventSortingRequired, mLastTextID, mPathId, mScriptType, mTalkerEntry, mTemplate, mTextTimer, mUseTextTimer, SMART_SCRIPT_TYPE_CREATURE, SMARTAI_TEMPLATE_BASIC, and trigger.

◆ ~SmartScript()

SmartScript::~SmartScript ( )
88{
89}

Member Function Documentation

◆ AddCreatureSummon()

void SmartScript::AddCreatureSummon ( ObjectGuid const &  guid)
5713{
5714 _summonList.insert(guid);
5715}
GuidUnorderedSet _summonList
Definition SmartScript.h:284

References _summonList.

Referenced by SmartAI::JustSummoned().

◆ AddEvent()

void SmartScript::AddEvent ( SMART_EVENT  e,
uint32  event_flags,
uint32  event_param1,
uint32  event_param2,
uint32  event_param3,
uint32  event_param4,
uint32  event_param5,
uint32  event_param6,
SMART_ACTION  action,
uint32  action_param1,
uint32  action_param2,
uint32  action_param3,
uint32  action_param4,
uint32  action_param5,
uint32  action_param6,
SMARTAI_TARGETS  t,
uint32  target_param1,
uint32  target_param2,
uint32  target_param3,
uint32  target_param4,
uint32  phaseMask 
)
3590{
3591 mInstallEvents.push_back(CreateSmartEvent(e, event_flags, event_param1, event_param2, event_param3, event_param4, event_param5, event_param6, action, action_param1, action_param2, action_param3, action_param4, action_param5, action_param6, t, target_param1, target_param2, target_param3, target_param4, phaseMask));
3592}
SmartAIEventList mInstallEvents
Definition SmartScript.h:223
static SmartScriptHolder CreateSmartEvent(SMART_EVENT e, uint32 event_flags, uint32 event_param1, uint32 event_param2, uint32 event_param3, uint32 event_param4, uint32 event_param5, uint32 event_param6, SMART_ACTION action, uint32 action_param1, uint32 action_param2, uint32 action_param3, uint32 action_param4, uint32 action_param5, uint32 action_param6, SMARTAI_TARGETS t, uint32 target_param1, uint32 target_param2, uint32 target_param3, uint32 target_param4, uint32 phaseMask)
Definition SmartScript.cpp:3594

References CreateSmartEvent(), and mInstallEvents.

Referenced by InstallTemplate().

◆ AllowPhaseReset()

bool SmartScript::AllowPhaseReset ( ) const
inline
204{ return _allowPhaseReset; }

References _allowPhaseReset.

Referenced by OnReset().

◆ CheckTimer()

bool SmartScript::CheckTimer ( SmartScriptHolder const &  e) const
5253{
5254 return e.active;
5255}

References SmartScriptHolder::active.

◆ CreateSmartEvent()

SmartScriptHolder SmartScript::CreateSmartEvent ( SMART_EVENT  e,
uint32  event_flags,
uint32  event_param1,
uint32  event_param2,
uint32  event_param3,
uint32  event_param4,
uint32  event_param5,
uint32  event_param6,
SMART_ACTION  action,
uint32  action_param1,
uint32  action_param2,
uint32  action_param3,
uint32  action_param4,
uint32  action_param5,
uint32  action_param6,
SMARTAI_TARGETS  t,
uint32  target_param1,
uint32  target_param2,
uint32  target_param3,
uint32  target_param4,
uint32  phaseMask 
)
static
3595{
3596 SmartScriptHolder script;
3597 script.event.type = e;
3598 script.event.raw.param1 = event_param1;
3599 script.event.raw.param2 = event_param2;
3600 script.event.raw.param3 = event_param3;
3601 script.event.raw.param4 = event_param4;
3602 script.event.raw.param5 = event_param5;
3603 script.event.raw.param6 = event_param6;
3604 script.event.event_phase_mask = phaseMask;
3605 script.event.event_flags = event_flags;
3606 script.event.event_chance = 100;
3607
3608 script.action.type = action;
3609 script.action.raw.param1 = action_param1;
3610 script.action.raw.param2 = action_param2;
3611 script.action.raw.param3 = action_param3;
3612 script.action.raw.param4 = action_param4;
3613 script.action.raw.param5 = action_param5;
3614 script.action.raw.param6 = action_param6;
3615
3616 script.target.type = t;
3617 script.target.raw.param1 = target_param1;
3618 script.target.raw.param2 = target_param2;
3619 script.target.raw.param3 = target_param3;
3620 script.target.raw.param4 = target_param4;
3621
3623 InitTimer(script);
3624 return script;
3625}
static void InitTimer(SmartScriptHolder &e)
Definition SmartScript.cpp:5103
uint32 param3
Definition SmartScriptMgr.h:1063
uint32 param5
Definition SmartScriptMgr.h:1065
uint32 param1
Definition SmartScriptMgr.h:1061
SMART_ACTION type
Definition SmartScriptMgr.h:747
struct SmartAction::@75::@195 raw
uint32 param4
Definition SmartScriptMgr.h:1064
uint32 param6
Definition SmartScriptMgr.h:1504
uint32 param2
Definition SmartScriptMgr.h:1062
uint32 param1
Definition SmartScriptMgr.h:514
uint32 event_flags
Definition SmartScriptMgr.h:209
struct SmartEvent::@30::@74 raw
uint32 event_phase_mask
Definition SmartScriptMgr.h:207
uint32 param2
Definition SmartScriptMgr.h:515
uint32 param4
Definition SmartScriptMgr.h:517
uint32 param3
Definition SmartScriptMgr.h:516
uint32 param6
Definition SmartScriptMgr.h:519
uint32 event_chance
Definition SmartScriptMgr.h:208
uint32 param5
Definition SmartScriptMgr.h:518
SMART_EVENT type
Definition SmartScriptMgr.h:206
Definition SmartScriptMgr.h:2008
SmartAction action
Definition SmartScriptMgr.h:2019
SmartScriptType source_type
Definition SmartScriptMgr.h:2014
SmartEvent event
Definition SmartScriptMgr.h:2018
SmartTarget target
Definition SmartScriptMgr.h:2020
uint32 param4
Definition SmartScriptMgr.h:1763
uint32 param1
Definition SmartScriptMgr.h:1760
uint32 param3
Definition SmartScriptMgr.h:1762
struct SmartTarget::@201::@225 raw
SMARTAI_TARGETS type
Definition SmartScriptMgr.h:1612
uint32 param2
Definition SmartScriptMgr.h:1761

References SmartScriptHolder::action, SmartScriptHolder::event, SmartEvent::event_chance, SmartEvent::event_flags, SmartEvent::event_phase_mask, InitTimer(), SmartEvent::param1, SmartAction::param1, SmartTarget::param1, SmartEvent::param2, SmartAction::param2, SmartTarget::param2, SmartEvent::param3, SmartAction::param3, SmartTarget::param3, SmartEvent::param4, SmartAction::param4, SmartTarget::param4, SmartEvent::param5, SmartAction::param5, SmartEvent::param6, SmartAction::param6, SmartEvent::raw, SmartAction::raw, SmartTarget::raw, SMART_SCRIPT_TYPE_CREATURE, SmartScriptHolder::source_type, SmartScriptHolder::target, SmartEvent::type, SmartAction::type, and SmartTarget::type.

Referenced by AddEvent(), and ProcessAction().

◆ DecPhase()

void SmartScript::DecPhase ( uint32  p)
private
5679{
5680 if (p >= mEventPhase)
5681 {
5682 SetPhase(0);
5683 }
5684 else
5685 {
5686 SetPhase(mEventPhase - p);
5687 }
5688}
void SetPhase(uint32 p)
Definition SmartScript.cpp:5690

References mEventPhase, and SetPhase().

Referenced by ProcessAction().

◆ DoFindClosestFriendlyInRange()

Unit * SmartScript::DoFindClosestFriendlyInRange ( float  range,
bool  playerOnly 
) const
5584{
5585 if (!me)
5586 return nullptr;
5587
5588 Unit* unit = nullptr;
5589 Acore::AnyFriendlyNotSelfUnitInObjectRangeCheck u_check(me, me, range, playerOnly);
5591 Cell::VisitObjects(me, searcher, range);
5592 return unit;
5593}
Definition Unit.h:665
Definition GridNotifiers.h:429
static void VisitObjects(WorldObject const *obj, T &visitor, float radius)
Definition CellImpl.h:165

References me, and Cell::VisitObjects().

Referenced by GetTargets().

◆ DoFindFriendlyCC()

void SmartScript::DoFindFriendlyCC ( std::vector< Creature * > &  creatures,
float  range 
) const
5564{
5565 if (!me)
5566 return;
5567
5568 Acore::FriendlyCCedInRange u_check(me, range);
5570 Cell::VisitObjects(me, searcher, range);
5571}
creatures
Definition boss_prince_malchezaar.cpp:51
Definition GridNotifiers.h:841
Definition GridNotifiers.h:496

References me, and Cell::VisitObjects().

Referenced by ProcessEvent().

◆ DoFindFriendlyMissingBuff()

void SmartScript::DoFindFriendlyMissingBuff ( std::vector< Creature * > &  creatures,
float  range,
uint32  spellid 
) const
5574{
5575 if (!me)
5576 return;
5577
5578 Acore::FriendlyMissingBuffInRange u_check(me, range, spellid);
5580 Cell::VisitObjects(me, searcher, range);
5581}
Definition GridNotifiers.h:859

References me, and Cell::VisitObjects().

Referenced by ProcessEvent().

◆ DoSelectLowestHpFriendly()

Unit * SmartScript::DoSelectLowestHpFriendly ( float  range,
uint32  MinHPDiff 
) const
5537{
5538 if (!me)
5539 return nullptr;
5540
5541 Unit* unit = nullptr;
5542
5543 Acore::MostHPMissingInRange u_check(me, range, MinHPDiff);
5545 Cell::VisitObjects(me, searcher, range);
5546 return unit;
5547}
Definition GridNotifiers.h:798

References me, and Cell::VisitObjects().

Referenced by ProcessEvent().

◆ DoSelectLowestHpPercentFriendly()

Unit * SmartScript::DoSelectLowestHpPercentFriendly ( float  range,
uint32  minHpPct,
uint32  maxHpPct 
) const
5550{
5551 if (!me)
5552 {
5553 return nullptr;
5554 }
5555
5556 Unit* unit = nullptr;
5557 Acore::MostHPPercentMissingInRange u_check(me, range, minHpPct, maxHpPct);
5559 Cell::VisitObjects(me, searcher, range);
5560 return unit;
5561}
Definition GridNotifiers.h:817

References me, and Cell::VisitObjects().

Referenced by ProcessEvent().

◆ FillScript()

void SmartScript::FillScript ( SmartAIEventList  e,
WorldObject *  obj,
AreaTrigger const *  at 
)
5364{
5365 (void)at; // ensure that the variable is referenced even if extra logs are disabled in order to pass compiler checks
5366
5367 if (e.empty())
5368 {
5369 if (obj)
5370 LOG_DEBUG("sql.sql", "SmartScript: EventMap for Entry {} is empty but is using SmartScript.", obj->GetEntry());
5371
5372 if (at)
5373 LOG_DEBUG("sql.sql", "SmartScript: EventMap for AreaTrigger {} is empty but is using SmartScript.", at->entry);
5374 return;
5375 }
5376 for (SmartAIEventList::iterator i = e.begin(); i != e.end(); ++i)
5377 {
5378#ifndef ACORE_DEBUG
5379 if ((*i).event.event_flags & SMART_EVENT_FLAG_DEBUG_ONLY)
5380 continue;
5381#endif
5382
5383 if ((*i).event.event_flags & SMART_EVENT_FLAG_DIFFICULTY_ALL)//if has instance flag add only if in it
5384 {
5385 if (obj && obj->GetMap()->IsDungeon())
5386 {
5387 if ((1 << (obj->GetMap()->GetSpawnMode() + 1)) & (*i).event.event_flags)
5388 {
5389 mEvents.push_back((*i));
5390 }
5391 }
5392 continue;
5393 }
5394 mEvents.push_back((*i));//NOTE: 'world(0)' events still get processed in ANY instance mode
5395 }
5396}
#define LOG_DEBUG(filterType__,...)
Definition Log.h:157
@ SMART_EVENT_FLAG_DIFFICULTY_ALL
Definition SmartScriptMgr.h:1972
@ SMART_EVENT_FLAG_DEBUG_ONLY
Definition SmartScriptMgr.h:1968
bool IsDungeon() const
Definition Map.h:299
uint8 GetSpawnMode() const
Definition Map.h:271
uint32 GetEntry() const
Definition Object.h:123
SmartAIEventList mEvents
Definition SmartScript.h:222
Map * GetMap() const
Definition Object.h:637

References AreaTrigger::entry, Object::GetEntry(), WorldObject::GetMap(), Map::GetSpawnMode(), Map::IsDungeon(), LOG_DEBUG, mEvents, SMART_EVENT_FLAG_DEBUG_ONLY, and SMART_EVENT_FLAG_DIFFICULTY_ALL.

Referenced by GetScript().

◆ FindCreatureNear()

Creature * SmartScript::FindCreatureNear ( WorldObject *  searchObject,
ObjectGuid::LowType  guid 
) const
inline
152 {
153 auto bounds = searchObject->GetMap()->GetCreatureBySpawnIdStore().equal_range(guid);
154 if (bounds.first == bounds.second)
155 return nullptr;
156
157 auto creatureItr = std::find_if(bounds.first, bounds.second, [](Map::CreatureBySpawnIdContainer::value_type const& pair)
158 {
159 return pair.second->IsAlive();
160 });
161
162 return creatureItr != bounds.second ? creatureItr->second : bounds.first->second;
163 }
CreatureBySpawnIdContainer & GetCreatureBySpawnIdStore()
Definition Map.h:361

References Map::GetCreatureBySpawnIdStore(), and WorldObject::GetMap().

Referenced by GetTargets(), and ProcessEvent().

◆ FindGameObjectNear()

GameObject * SmartScript::FindGameObjectNear ( WorldObject *  searchObject,
ObjectGuid::LowType  guid 
) const
inline
143 {
144 auto bounds = searchObject->GetMap()->GetGameObjectBySpawnIdStore().equal_range(guid);
145 if (bounds.first == bounds.second)
146 return nullptr;
147
148 return bounds.first->second;
149 }
GameObjectBySpawnIdContainer & GetGameObjectBySpawnIdStore()
Definition Map.h:364

References Map::GetGameObjectBySpawnIdStore(), and WorldObject::GetMap().

Referenced by GetTargets(), and ProcessEvent().

◆ FindLinkedEvent()

std::optional< std::reference_wrapper< SmartScriptHolder > > SmartScript::FindLinkedEvent ( uint32  link)
inlineprivate
270 {
271 if (!mEvents.empty())
272 {
273 for (SmartAIEventList::iterator i = mEvents.begin(); i != mEvents.end(); ++i)
274 {
275 if (i->event_id == link)
276 {
277 return std::ref(*i);
278 }
279 }
280 }
281 return std::nullopt;
282 }

References mEvents.

Referenced by ProcessAction().

◆ GetBaseObject()

WorldObject * SmartScript::GetBaseObject ( ) const
inline
65 {
66 WorldObject* obj = nullptr;
67 if (me)
68 obj = me;
69 else if (go)
70 obj = go;
71 return obj;
72 }
Definition Object.h:482

References go, and me.

Referenced by GetLastInvoker(), GetTargets(), GetWorldObjectsInDist(), InstallTemplate(), OnUpdate(), ProcessAction(), ProcessEvent(), ProcessEventsFor(), and ProcessTimedAction().

◆ GetCounterValue()

uint32 SmartScript::GetCounterValue ( uint32  id)
inline
135 {
136 CounterMap::iterator itr = mCounterList.find(id);
137 if (itr != mCounterList.end())
138 return itr->second;
139 return 0;
140 }
CounterMap mCounterList
Definition SmartScript.h:202

References mCounterList.

Referenced by ProcessEvent().

◆ GetEvents()

SmartAIEventList const & SmartScript::GetEvents ( ) const
inline
210{ return mEvents; }

References mEvents.

Referenced by SmartAI::InitializeAI().

◆ GetLastInvoker()

WorldObject * SmartScript::GetLastInvoker ( WorldObject *  invoker = nullptr) const
5631{
5632 // Xinef: Look for invoker only on map of base object... Prevents multithreaded crashes
5633 if (GetBaseObject())
5635 // xinef: used for area triggers invoker cast
5636 else if (invoker)
5638 return nullptr;
5639}
ObjectGuid mLastInvoker
Definition SmartScript.h:200
WorldObject * GetBaseObject() const
Definition SmartScript.h:64
WorldObject * GetWorldObject(WorldObject const &, ObjectGuid const &guid)
Definition ObjectAccessor.cpp:139

References GetBaseObject(), ObjectAccessor::GetWorldObject(), and mLastInvoker.

Referenced by GetTargets(), and ProcessAction().

◆ GetPathId()

uint32 SmartScript::GetPathId ( ) const
inline
63{ return mPathId; }

References mPathId.

Referenced by ProcessEvent().

◆ GetScript()

void SmartScript::GetScript ( )
5399{
5401 if (me)
5402 {
5403 bool usingEntryScript = false;
5404
5405 e = sSmartScriptMgr->GetScript(-((int32)me->GetSpawnId()), mScriptType);
5406 if (e.empty())
5407 {
5408 e = sSmartScriptMgr->GetScript((int32)me->GetEntry(), mScriptType);
5409 usingEntryScript = true;
5410 }
5411
5412 FillScript(e, me, nullptr);
5413
5414 if (!usingEntryScript)
5415 {
5416 if (CreatureTemplate const* cInfo = me->GetCreatureTemplate())
5417 {
5418 if (cInfo->HasFlagsExtra(CREATURE_FLAG_EXTRA_DONT_OVERRIDE_ENTRY_SAI))
5419 {
5420 e = sSmartScriptMgr->GetScript((int32)me->GetEntry(), mScriptType);
5421 FillScript(e, me, nullptr);
5422 }
5423 }
5424 }
5425 }
5426 else if (go)
5427 {
5428 e = sSmartScriptMgr->GetScript(-((int32)go->GetSpawnId()), mScriptType);
5429 if (e.empty())
5430 e = sSmartScriptMgr->GetScript((int32)go->GetEntry(), mScriptType);
5431 FillScript(e, go, nullptr);
5432 }
5433 else if (trigger)
5434 {
5435 e = sSmartScriptMgr->GetScript((int32)trigger->entry, mScriptType);
5436 FillScript(e, nullptr, trigger);
5437 }
5438}
@ CREATURE_FLAG_EXTRA_DONT_OVERRIDE_ENTRY_SAI
Definition CreatureData.h:73
std::int32_t int32
Definition Define.h:103
std::vector< SmartScriptHolder > SmartAIEventList
Definition SmartScriptMgr.h:2105
#define sSmartScriptMgr
Definition SmartScriptMgr.h:2281
ObjectGuid::LowType GetSpawnId() const
Definition Creature.h:69
CreatureTemplate const * GetCreatureTemplate() const
Definition Creature.h:207
ObjectGuid::LowType GetSpawnId() const
Definition GameObject.h:144
void FillScript(SmartAIEventList e, WorldObject *obj, AreaTrigger const *at)
Definition SmartScript.cpp:5363
uint32 entry
Definition ObjectMgr.h:424
Definition CreatureData.h:187

References CREATURE_FLAG_EXTRA_DONT_OVERRIDE_ENTRY_SAI, AreaTrigger::entry, FillScript(), Creature::GetCreatureTemplate(), Object::GetEntry(), Creature::GetSpawnId(), GameObject::GetSpawnId(), go, me, mScriptType, sSmartScriptMgr, and trigger.

Referenced by OnInitialize().

◆ GetStoredTargetVector()

ObjectVector const * SmartScript::GetStoredTargetVector ( uint32  id,
WorldObject const &  ref 
) const
inline
101 {
102 auto itr = _storedTargets.find(id);
103 if (itr != _storedTargets.end())
104 return itr->second.GetObjectVector(ref);
105 return nullptr;
106 }
ObjectVectorMap _storedTargets
Definition SmartScript.h:249

References _storedTargets.

Referenced by SmartAI::EndPath(), GetTargets(), and ProcessAction().

◆ GetTargets()

void SmartScript::GetTargets ( ObjectVector &  targets,
SmartScriptHolder const &  e,
WorldObject *  invoker = nullptr 
) const
3628{
3629 WorldObject* scriptTrigger = nullptr;
3630 if (invoker)
3631 scriptTrigger = invoker;
3632 else if (WorldObject* tempLastInvoker = GetLastInvoker())
3633 scriptTrigger = tempLastInvoker;
3634
3635 WorldObject* baseObject = GetBaseObject();
3636
3637 switch (e.GetTargetType())
3638 {
3639 case SMART_TARGET_SELF:
3640 if (baseObject)
3641 targets.push_back(baseObject);
3642 break;
3644 if (me)
3645 if (Unit* victim = me->GetVictim())
3646 targets.push_back(victim);
3647 break;
3649 if (me)
3650 {
3651 if (e.target.hostileRandom.powerType)
3652 {
3653 if (Unit* u = me->AI()->SelectTarget(SelectTargetMethod::MaxThreat, 0, PowerUsersSelector(me, Powers(e.target.hostileRandom.powerType - 1), (float)e.target.hostileRandom.maxDist, e.target.hostileRandom.playerOnly, false)))
3654 targets.push_back(u);
3655 }
3656 else if (Unit* u = me->AI()->SelectTarget(SelectTargetMethod::MaxThreat, 0, (float)e.target.hostileRandom.maxDist, e.target.hostileRandom.playerOnly, false, -e.target.hostileRandom.aura))
3657 targets.push_back(u);
3658 }
3659 break;
3661 if (me)
3662 {
3663 if (e.target.hostileRandom.powerType)
3664 {
3665 if (Unit* u = me->AI()->SelectTarget(SelectTargetMethod::MinThreat, 0, PowerUsersSelector(me, Powers(e.target.hostileRandom.powerType - 1), (float)e.target.hostileRandom.maxDist, e.target.hostileRandom.playerOnly)))
3666 targets.push_back(u);
3667 }
3668 else if (Unit* u = me->AI()->SelectTarget(SelectTargetMethod::MinThreat, 0, (float)e.target.hostileRandom.maxDist, e.target.hostileRandom.playerOnly, true, -e.target.hostileRandom.aura))
3669 targets.push_back(u);
3670 }
3671 break;
3673 if (me)
3674 {
3675 if (e.target.hostileRandom.powerType)
3676 {
3677 if (Unit* u = me->AI()->SelectTarget(SelectTargetMethod::Random, 0, PowerUsersSelector(me, Powers(e.target.hostileRandom.powerType - 1), (float)e.target.hostileRandom.maxDist, e.target.hostileRandom.playerOnly)))
3678 targets.push_back(u);
3679 }
3680 else if (Unit* u = me->AI()->SelectTarget(SelectTargetMethod::Random, 0, (float)e.target.hostileRandom.maxDist, e.target.hostileRandom.playerOnly, true, -e.target.hostileRandom.aura))
3681 targets.push_back(u);
3682 }
3683 break;
3685 if (me)
3686 {
3687 if (e.target.hostileRandom.powerType)
3688 {
3689 if (Unit* u = me->AI()->SelectTarget(SelectTargetMethod::Random, 0, PowerUsersSelector(me, Powers(e.target.hostileRandom.powerType - 1), (float)e.target.hostileRandom.maxDist, e.target.hostileRandom.playerOnly, false)))
3690 targets.push_back(u);
3691 }
3692 else if (Unit* u = me->AI()->SelectTarget(SelectTargetMethod::Random, 0, (float)e.target.hostileRandom.maxDist, e.target.hostileRandom.playerOnly, false, -e.target.hostileRandom.aura))
3693 targets.push_back(u);
3694 }
3695 break;
3697 if (me)
3698 {
3699 if (Unit* u = me->AI()->SelectTarget(SelectTargetMethod::MinDistance, 0, RangeSelector(me, e.target.farthest.maxDist, e.target.farthest.playerOnly, e.target.farthest.isInLos, e.target.farthest.minDist)))
3700 targets.push_back(u);
3701 }
3702 break;
3704 if (scriptTrigger)
3705 targets.push_back(scriptTrigger);
3706 break;
3708 if (scriptTrigger && IsUnit(scriptTrigger))
3709 if (scriptTrigger->ToUnit()->GetVehicle() && scriptTrigger->ToUnit()->GetVehicle()->GetBase())
3710 targets.push_back(scriptTrigger->ToUnit()->GetVehicle()->GetBase());
3711 break;
3713 if (scriptTrigger)
3714 {
3715 if (Player* player = scriptTrigger->ToPlayer())
3716 {
3717 if (Group* group = player->GetGroup())
3718 {
3719 for (GroupReference* groupRef = group->GetFirstMember(); groupRef != nullptr; groupRef = groupRef->next())
3720 if (Player* member = groupRef->GetSource())
3721 {
3722 if (member->IsInMap(player))
3723 targets.push_back(member);
3724
3725 if (e.target.invokerParty.includePets)
3726 if (Creature* pet = ObjectAccessor::GetCreatureOrPetOrVehicle(*member, member->GetPetGUID()))
3727 if (pet->IsPet() && pet->IsInMap(player))
3728 targets.push_back(pet);
3729 }
3730 }
3731 // We still add the player to the list if there is no group. If we do
3732 // this even if there is a group (thus the else-check), it will add the
3733 // same player to the list twice. We don't want that to happen.
3734 else
3735 targets.push_back(scriptTrigger);
3736 }
3737 }
3738 break;
3740 {
3741 WorldObject* ref = baseObject;
3742 if (!ref)
3743 ref = scriptTrigger;
3744
3745 if (!ref)
3746 {
3747 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_CREATURE_RANGE: Entry {} SourceType {} Event {} Action {} Target {} is missing base object or invoker",
3748 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
3749 break;
3750 }
3751
3752 ObjectVector units;
3753 GetWorldObjectsInDist(units, static_cast<float>(e.target.unitRange.maxDist));
3754
3755 for (WorldObject* unit : units)
3756 {
3757 if (!IsCreature(unit))
3758 continue;
3759
3760 if (me && me->GetGUID() == unit->GetGUID())
3761 continue;
3762
3763 // check alive state - 1 alive, 2 dead, 0 both
3764 if (uint32 state = e.target.unitRange.livingState)
3765 {
3766 if (unit->ToCreature()->IsAlive() && state == 2)
3767 continue;
3768 if (!unit->ToCreature()->IsAlive() && state == 1)
3769 continue;
3770 }
3771
3772 if (((e.target.unitRange.creature && unit->ToCreature()->GetEntry() == e.target.unitRange.creature) || !e.target.unitRange.creature) && ref->IsInRange(unit, (float)e.target.unitRange.minDist, (float)e.target.unitRange.maxDist))
3773 targets.push_back(unit);
3774 }
3775
3776 break;
3777 }
3779 {
3780 ObjectVector units;
3781 GetWorldObjectsInDist(units, static_cast<float>(e.target.unitDistance.dist));
3782
3783 for (WorldObject* unit : units)
3784 {
3785 if (!IsCreature(unit))
3786 continue;
3787
3788 if (me && me->GetGUID() == unit->GetGUID())
3789 continue;
3790
3791 // check alive state - 1 alive, 2 dead, 0 both
3792 if (uint32 state = e.target.unitDistance.livingState)
3793 {
3794 if (unit->ToCreature()->IsAlive() && state == 2)
3795 continue;
3796 if (!unit->ToCreature()->IsAlive() && state == 1)
3797 continue;
3798 }
3799
3800 if ((e.target.unitDistance.creature && unit->ToCreature()->GetEntry() == e.target.unitDistance.creature) || !e.target.unitDistance.creature)
3801 targets.push_back(unit);
3802 }
3803
3804 break;
3805 }
3807 {
3808 ObjectVector units;
3809 GetWorldObjectsInDist(units, static_cast<float>(e.target.goDistance.dist));
3810
3811 for (WorldObject* unit : units)
3812 {
3813 if (!IsGameObject(unit))
3814 continue;
3815
3816 if (go && go->GetGUID() == unit->GetGUID())
3817 continue;
3818
3819 if ((e.target.goDistance.entry && unit->ToGameObject()->GetEntry() == e.target.goDistance.entry) || !e.target.goDistance.entry)
3820 targets.push_back(unit);
3821 }
3822
3823 break;
3824 }
3826 {
3827
3828 WorldObject* ref = baseObject;
3829 if (!ref)
3830 ref = scriptTrigger;
3831
3832 if (!ref)
3833 {
3834 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_GAMEOBJECT_RANGE: Entry: {} SourceType {} Event {} Action {} Target {} is missing base object or invoker.",
3835 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
3836 break;
3837 }
3838
3839 ObjectVector units;
3840 GetWorldObjectsInDist(units, static_cast<float>(e.target.goRange.maxDist));
3841
3842 for (WorldObject* unit : units)
3843 {
3844 if (!IsGameObject(unit))
3845 continue;
3846
3847 if (go && go->GetGUID() == unit->GetGUID())
3848 continue;
3849
3850 if (((e.target.goRange.entry && IsGameObject(unit) && unit->ToGameObject()->GetEntry() == e.target.goRange.entry) || !e.target.goRange.entry) && ref->IsInRange((unit), (float)e.target.goRange.minDist, (float)e.target.goRange.maxDist))
3851 targets.push_back(unit);
3852 }
3853
3854 break;
3855 }
3857 {
3858 if (!scriptTrigger && !baseObject)
3859 {
3860 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_CREATURE_GUID: Entry {} SourceType {} Event {} Action {} Target {} is missing base object or invoker.",
3861 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
3862 break;
3863 }
3864
3865 Creature* target = FindCreatureNear(scriptTrigger ? scriptTrigger : GetBaseObject(), e.target.unitGUID.dbGuid);
3866 if (target && (!e.target.unitGUID.entry || target->GetEntry() == e.target.unitGUID.entry))
3867 targets.push_back(target);
3868 break;
3869 }
3871 {
3872 if (!scriptTrigger && !GetBaseObject())
3873 {
3874 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_GAMEOBJECT_GUID: Entry {} SourceType {} Event {} Action {} Target {} is missing base object or invoker.",
3875 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
3876 break;
3877 }
3878
3879 GameObject* target = FindGameObjectNear(scriptTrigger ? scriptTrigger : GetBaseObject(), e.target.goGUID.dbGuid);
3880 if (target && (!e.target.goGUID.entry || target->GetEntry() == e.target.goGUID.entry))
3881 targets.push_back(target);
3882 break;
3883 }
3885 {
3886 ObjectVector units;
3887 GetWorldObjectsInDist(units, static_cast<float>(e.target.playerRange.maxDist));
3888
3889 if (!units.empty() && baseObject)
3890 for (WorldObject* unit : units)
3891 if (IsPlayer(unit) && !unit->ToPlayer()->IsGameMaster() && baseObject->IsInRange(unit, float(e.target.playerRange.minDist), float(e.target.playerRange.maxDist)))
3892 targets.push_back(unit);
3893
3894 if (e.target.playerRange.maxCount)
3895 Acore::Containers::RandomResize(targets, e.target.playerRange.maxCount);
3896
3897 break;
3898 }
3900 {
3901 ObjectVector units;
3902 GetWorldObjectsInDist(units, static_cast<float>(e.target.playerDistance.dist));
3903
3904 for (WorldObject* unit : units)
3905 if (IsPlayer(unit))
3906 targets.push_back(unit);
3907 break;
3908 }
3910 {
3911 WorldObject* ref = baseObject;
3912 if (!ref)
3913 ref = scriptTrigger;
3914
3915 if (!ref)
3916 {
3917 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_STORED: Entry {} SourceType {} Event {} Action {} Target {} is missing base object or invoker.",
3918 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
3919 break;
3920 }
3921
3922 if (ObjectVector const* stored = GetStoredTargetVector(e.target.stored.id, *ref))
3923 targets.assign(stored->begin(), stored->end());
3924 break;
3925 }
3927 {
3928 WorldObject* ref = baseObject;
3929
3930 if (!ref)
3931 ref = scriptTrigger;
3932
3933 if (!ref)
3934 {
3935 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_CLOSEST_CREATURE: Entry {} SourceType {} Event {} Action {} Target {} is missing base object or invoker.",
3936 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
3937 break;
3938 }
3939
3940 Creature* target = GetClosestCreatureWithEntry(ref, e.target.unitClosest.entry, (float)(e.target.unitClosest.dist ? e.target.unitClosest.dist : 100), !e.target.unitClosest.dead);
3941 if (target)
3942 targets.push_back(target);
3943 break;
3944 }
3946 {
3947 WorldObject* ref = baseObject;
3948
3949 if (!ref)
3950 ref = scriptTrigger;
3951
3952 if (!ref)
3953 {
3954 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_CLOSEST_GAMEOBJECT: Entry {} SourceType {} Event {} Action {} Target {} is missing base object or invoker.",
3955 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
3956 break;
3957 }
3958
3959 GameObject* target = GetClosestGameObjectWithEntry(ref, e.target.goClosest.entry, (float)(e.target.goClosest.dist ? e.target.goClosest.dist : 100), e.target.goClosest.onlySpawned);
3960 if (target)
3961 targets.push_back(target);
3962 break;
3963 }
3965 {
3966 WorldObject* ref = baseObject;
3967
3968 if (!ref)
3969 ref = scriptTrigger;
3970
3971 if (!ref)
3972 {
3973 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_CLOSEST_PLAYER: Entry {} SourceType {} Event {} Action {} Target {} is missing base object or invoker.",
3974 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
3975 break;
3976 }
3977
3978 if (Player* target = ref->SelectNearestPlayer((float)e.target.playerDistance.dist))
3979 targets.push_back(target);
3980 break;
3981 }
3983 /*
3984 * Owners/Summoners should be WorldObjects. This allows to have other objects
3985 * such as gameobjects to execute SmartScripts using this type of target.
3986 * Otherwise, only Units like creatures can summon other creatures.
3987 */
3988 {
3989 if (me)
3990 {
3992 {
3993 targets.push_back(owner);
3994 }
3995 else if (me->IsSummon() && me->ToTempSummon()->GetSummonerUnit())
3996 {
3997 targets.push_back(me->ToTempSummon()->GetSummonerUnit());
3998 }
3999 }
4000 else if (go)
4001 {
4003 {
4004 targets.push_back(owner);
4005 }
4006 }
4007
4008 // xinef: Get owner of owner
4009 if (e.target.owner.useCharmerOrOwner && !targets.empty())
4010 {
4011 if (WorldObject* owner = targets.front())
4012 {
4013 targets.clear();
4014
4015 if (IsCreature(owner))
4016 {
4017 if (Unit* base = ObjectAccessor::GetUnit(*owner, owner->ToCreature()->GetCharmerOrOwnerGUID()))
4018 targets.push_back(base);
4019 }
4020 else if (IsGameObject(owner))
4021 {
4022 if (Unit* base = ObjectAccessor::GetUnit(*owner, owner->ToGameObject()->GetOwnerGUID()))
4023 targets.push_back(base);
4024 }
4025 else if (IsPlayer(owner))
4026 {
4027 if (Unit* base = owner->ToPlayer()->GetCharmerOrOwner())
4028 targets.push_back(base);
4029 }
4030 }
4031 }
4032 break;
4033 }
4035 {
4036 if (me)
4037 {
4038 for (ThreatReference const* ref : me->GetThreatMgr().GetUnsortedThreatList())
4039 if (Unit* temp = ref->GetVictim())
4040 // Xinef: added distance check
4041 if (e.target.threatList.maxDist == 0 || me->IsWithinCombatRange(temp, (float)e.target.threatList.maxDist))
4042 targets.push_back(temp);
4043 }
4044 break;
4045 }
4047 {
4048 if (me)
4049 if (Unit* target = me->SelectNearestTarget(e.target.closestAttackable.maxDist, e.target.closestAttackable.playerOnly))
4050 targets.push_back(target);
4051
4052 break;
4053 }
4055 {
4056 if (me)
4057 if (Unit* target = DoFindClosestFriendlyInRange(e.target.closestFriendly.maxDist, e.target.closestFriendly.playerOnly))
4058 targets.push_back(target);
4059
4060 break;
4061 }
4063 {
4064 ObjectVector units;
4065 GetWorldObjectsInDist(units, static_cast<float>(e.target.playerDistance.dist));
4066
4067 for (WorldObject* unit : units)
4068 if (IsPlayer(unit) && unit->ToPlayer()->IsAlive() && !unit->ToPlayer()->IsGameMaster())
4069 if (GetBaseObject()->IsInRange(unit, (float)e.target.playerWithAura.distMin, (float)e.target.playerWithAura.distMax))
4070 if (bool(e.target.playerWithAura.negation) != unit->ToPlayer()->HasAura(e.target.playerWithAura.spellId))
4071 targets.push_back(unit);
4072
4073 if (e.target.o > 0)
4074 Acore::Containers::RandomResize(targets, e.target.o);
4075
4076 break;
4077 }
4079 {
4080 ObjectVector units;
4081 GetWorldObjectsInDist(units, static_cast<float>(e.target.playerDistance.dist));
4082 // 1 = Tanks, 2 = Healer, 4 = Damage
4083 uint32 roleMask = e.target.roleSelection.roleMask;
4084 for (WorldObject* unit : units)
4085 if (Player* targetPlayer = unit->ToPlayer())
4086 if (targetPlayer->IsAlive() && !targetPlayer->IsGameMaster())
4087 {
4088 if (roleMask & SMART_TARGET_ROLE_FLAG_TANKS)
4089 {
4090 if (targetPlayer->HasTankSpec())
4091 {
4092 targets.push_back(unit);
4093 continue;
4094 }
4095 }
4096 if (roleMask & SMART_TARGET_ROLE_FLAG_HEALERS)
4097 {
4098 if (targetPlayer->HasHealSpec())
4099 {
4100 targets.push_back(unit);
4101 continue;
4102 }
4103 }
4104 if (roleMask & SMART_TARGET_ROLE_FLAG_DAMAGERS)
4105 {
4106 if (targetPlayer->HasCasterSpec() || targetPlayer->HasMeleeSpec())
4107 {
4108 targets.push_back(unit);
4109 continue;
4110 }
4111 }
4112 }
4113
4114 if (e.target.roleSelection.resize > 0)
4115 Acore::Containers::RandomResize(targets, e.target.roleSelection.resize);
4116
4117 break;
4118 }
4120 {
4121 if (me && me->IsVehicle())
4122 {
4123 if (Unit* target = me->GetVehicleKit()->GetPassenger(e.target.vehicle.seatMask))
4124 {
4125 targets.push_back(target);
4126 }
4127 }
4128 break;
4129 }
4131 {
4132 if (me)
4133 {
4134 if (Group* lootGroup = me->GetLootRecipientGroup())
4135 {
4136 for (GroupReference* it = lootGroup->GetFirstMember(); it != nullptr; it = it->next())
4137 {
4138 if (Player* recipient = it->GetSource())
4139 {
4140 targets.push_back(recipient);
4141 }
4142 }
4143 }
4144 else
4145 {
4146 if (Player* recipient = me->GetLootRecipient())
4147 {
4148 targets.push_back(recipient);
4149 }
4150 }
4151 }
4152 break;
4153 }
4155 {
4156 if (me)
4157 {
4158 for (ObjectGuid const& guid : _summonList)
4159 {
4160 if (!e.target.summonedCreatures.entry || guid.GetEntry() == e.target.summonedCreatures.entry)
4161 {
4162 if (Creature* creature = me->GetMap()->GetCreature(guid))
4163 {
4164 targets.push_back(creature);
4165 }
4166 }
4167 }
4168 }
4169 break;
4170 }
4172 {
4173 InstanceScript* instance = nullptr;
4174
4175 if (e.IsAreatriggerScript() && scriptTrigger)
4176 instance = scriptTrigger->GetInstanceScript();
4177 else
4178 instance = GetBaseObject()->GetInstanceScript();
4179
4180 if (!instance)
4181 {
4182 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_INSTANCE_STORAGE: Entry {} SourceType {} Event {} Action {} Target {} called outside an instance map.",
4183 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
4184 return;
4185 }
4186
4187 if (e.target.instanceStorage.type == 1)
4188 {
4189 if (Creature* creature = instance->GetCreature(e.target.instanceStorage.index))
4190 targets.push_back(creature);
4191 }
4192 else if (e.target.instanceStorage.type == 2)
4193 {
4194 if (GameObject* go = instance->GetGameObject(e.target.instanceStorage.index))
4195 targets.push_back(go);
4196 }
4197
4198 break;
4199 }
4201 {
4202 if (me)
4203 {
4204 if (CreatureGroup* group = me->GetFormation())
4205 {
4206 uint32 formationType = e.target.formation.type;
4207 uint32 entry = e.target.formation.entry;
4208 bool excludeSelf = e.target.formation.excludeSelf;
4209
4210 if (formationType == 1) // Leader only
4211 {
4212 if (Creature* leader = group->GetLeader())
4213 {
4214 if ((!excludeSelf || leader != me) && (!entry || leader->GetEntry() == entry))
4215 targets.push_back(leader);
4216 }
4217 }
4218 else // 0 = Members only, 2 = All
4219 {
4220 for (auto const& itr : group->GetMembers())
4221 {
4222 Creature* member = itr.first;
4223
4224 if (!member)
4225 continue;
4226
4227 if (excludeSelf && member == me)
4228 continue;
4229
4230 if (entry && member->GetEntry() != entry)
4231 continue;
4232
4233 if (formationType == 0 && member == group->GetLeader())
4234 continue;
4235
4236 targets.push_back(member);
4237 }
4238 }
4239 }
4240 }
4241 break;
4242 }
4244 {
4245 WorldObject* ref = GetBaseObject();
4246
4247 if (!ref)
4248 {
4249 LOG_ERROR("scripts.ai.sai", "SMART_TARGET_SHARED_OWNER_ENTITIES: Entry {} SourceType {} Event {} Action {} Target {} is missing base object.",
4250 e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
4251 break;
4252 }
4253
4254 ObjectGuid ownerGUID = GetSummonerOrOwnerGUID(ref);
4255 if (!ownerGUID)
4256 break;
4257
4258 bool const wantGameObject = e.target.sharedOwnerEntities.type == 2;
4259 uint32 const entry = e.target.sharedOwnerEntities.entry;
4260
4261 float const dist = e.target.sharedOwnerEntities.maxDist ? (float)e.target.sharedOwnerEntities.maxDist : ref->GetVisibilityRange();
4262
4263 ObjectVector units;
4264 GetWorldObjectsInDist(units, dist);
4265
4266 for (WorldObject* unit : units)
4267 {
4268 // an object is never a sibling of itself
4269 if (unit->GetGUID() == ref->GetGUID())
4270 continue;
4271
4272 if (wantGameObject ? !IsGameObject(unit) : !IsCreature(unit))
4273 continue;
4274
4275 if (entry && unit->GetEntry() != entry)
4276 continue;
4277
4278 if (GetSummonerOrOwnerGUID(unit) != ownerGUID)
4279 continue;
4280
4281 targets.push_back(unit);
4282 }
4283
4284 break;
4285 }
4286 case SMART_TARGET_NONE:
4288 default:
4289 break;
4290 }
4291}
std::uint32_t uint32
Definition Define.h:107
#define LOG_ERROR(filterType__,...)
Definition Log.h:145
Creature * GetClosestCreatureWithEntry(WorldObject *source, uint32 entry, float maxSearchRange, bool alive)
Definition ScriptedCreature.cpp:933
GameObject * GetClosestGameObjectWithEntry(WorldObject *source, uint32 entry, float maxSearchRange, bool onlySpawned)
Definition ScriptedCreature.cpp:938
Powers
Definition SharedDefines.h:256
@ SMART_TARGET_ROLE_FLAG_HEALERS
Definition SmartScriptMgr.h:1797
@ SMART_TARGET_ROLE_FLAG_TANKS
Definition SmartScriptMgr.h:1796
@ SMART_TARGET_ROLE_FLAG_DAMAGERS
Definition SmartScriptMgr.h:1798
@ SMART_TARGET_LOOT_RECIPIENTS
Definition SmartScriptMgr.h:1577
@ SMART_TARGET_CLOSEST_CREATURE
Definition SmartScriptMgr.h:1569
@ SMART_TARGET_CREATURE_DISTANCE
Definition SmartScriptMgr.h:1561
@ SMART_TARGET_HOSTILE_RANDOM_NOT_TOP
Definition SmartScriptMgr.h:1556
@ SMART_TARGET_INVOKER_PARTY
Definition SmartScriptMgr.h:1566
@ SMART_TARGET_FORMATION
Definition SmartScriptMgr.h:1592
@ SMART_TARGET_CLOSEST_FRIENDLY
Definition SmartScriptMgr.h:1576
@ SMART_TARGET_CLOSEST_GAMEOBJECT
Definition SmartScriptMgr.h:1570
@ SMART_TARGET_VEHICLE_PASSENGER
Definition SmartScriptMgr.h:1579
@ SMART_TARGET_GAMEOBJECT_RANGE
Definition SmartScriptMgr.h:1563
@ SMART_TARGET_CREATURE_GUID
Definition SmartScriptMgr.h:1560
@ SMART_TARGET_PLAYER_RANGE
Definition SmartScriptMgr.h:1567
@ SMART_TARGET_SUMMONED_CREATURES
Definition SmartScriptMgr.h:1590
@ SMART_TARGET_VICTIM
Definition SmartScriptMgr.h:1552
@ SMART_TARGET_GAMEOBJECT_DISTANCE
Definition SmartScriptMgr.h:1565
@ SMART_TARGET_CREATURE_RANGE
Definition SmartScriptMgr.h:1559
@ SMART_TARGET_CLOSEST_PLAYER
Definition SmartScriptMgr.h:1571
@ SMART_TARGET_HOSTILE_RANDOM
Definition SmartScriptMgr.h:1555
@ SMART_TARGET_GAMEOBJECT_GUID
Definition SmartScriptMgr.h:1564
@ SMART_TARGET_HOSTILE_SECOND_AGGRO
Definition SmartScriptMgr.h:1553
@ SMART_TARGET_OWNER_OR_SUMMONER
Definition SmartScriptMgr.h:1573
@ SMART_TARGET_SELF
Definition SmartScriptMgr.h:1551
@ SMART_TARGET_PLAYER_WITH_AURA
Definition SmartScriptMgr.h:1587
@ SMART_TARGET_ROLE_SELECTION
Definition SmartScriptMgr.h:1589
@ SMART_TARGET_ACTION_INVOKER
Definition SmartScriptMgr.h:1557
@ SMART_TARGET_POSITION
Definition SmartScriptMgr.h:1558
@ SMART_TARGET_HOSTILE_LAST_AGGRO
Definition SmartScriptMgr.h:1554
@ SMART_TARGET_SHARED_OWNER_ENTITIES
Definition SmartScriptMgr.h:1593
@ SMART_TARGET_ACTION_INVOKER_VEHICLE
Definition SmartScriptMgr.h:1572
@ SMART_TARGET_INSTANCE_STORAGE
Definition SmartScriptMgr.h:1591
@ SMART_TARGET_FARTHEST
Definition SmartScriptMgr.h:1578
@ SMART_TARGET_THREAT_LIST
Definition SmartScriptMgr.h:1574
@ SMART_TARGET_CLOSEST_ENEMY
Definition SmartScriptMgr.h:1575
@ SMART_TARGET_NONE
Definition SmartScriptMgr.h:1550
@ SMART_TARGET_PLAYER_DISTANCE
Definition SmartScriptMgr.h:1568
@ SMART_TARGET_STORED
Definition SmartScriptMgr.h:1562
std::vector< WorldObject * > ObjectVector
Definition SmartScriptMgr.h:2045
Definition CreatureGroups.h:95
Definition Creature.h:47
CreatureGroup const * GetFormation() const
Definition Creature.h:372
Player * GetLootRecipient() const
Definition Creature.cpp:1310
Group * GetLootRecipientGroup() const
Definition Creature.cpp:1317
Unit * SelectNearestTarget(float dist=0, bool playerOnly=false) const
Select nearest hostile unit within the given distance (regardless of threat list).
Definition Creature.cpp:2446
CreatureAI * AI() const
Definition Creature.h:144
Definition GameObject.h:120
ObjectGuid GetOwnerGUID() const override
Definition GameObject.h:174
Definition GroupReference.h:27
Definition Group.h:177
Definition InstanceScript.h:143
Creature * GetCreature(uint32 type)
Definition InstanceScript.cpp:120
GameObject * GetGameObject(uint32 type)
Definition InstanceScript.cpp:125
Creature * GetCreature(ObjectGuid const &guid)
Definition Map.cpp:2442
Definition ObjectGuid.h:121
Player * ToPlayer()
Definition Object.h:208
static ObjectGuid GetGUID(Object const *o)
Definition Object.h:120
Unit * ToUnit()
Definition Object.h:216
Definition Player.h:1086
static bool IsUnit(WorldObject *obj)
Definition SmartScript.cpp:5641
static bool IsPlayer(WorldObject *obj)
Definition SmartScript.cpp:5646
static bool IsCreature(WorldObject *obj)
Definition SmartScript.cpp:5651
WorldObject * GetLastInvoker(WorldObject *invoker=nullptr) const
Definition SmartScript.cpp:5630
void GetWorldObjectsInDist(ObjectVector &objects, float dist) const
Definition SmartScript.cpp:4293
Creature * FindCreatureNear(WorldObject *searchObject, ObjectGuid::LowType guid) const
Definition SmartScript.h:151
static bool IsGameObject(WorldObject *obj)
Definition SmartScript.cpp:5667
ObjectVector const * GetStoredTargetVector(uint32 id, WorldObject const &ref) const
Definition SmartScript.h:100
Unit * DoFindClosestFriendlyInRange(float range, bool playerOnly) const
Definition SmartScript.cpp:5583
GameObject * FindGameObjectNear(WorldObject *searchObject, ObjectGuid::LowType guid) const
Definition SmartScript.h:142
Unit * GetSummonerUnit() const
Definition TemporarySummon.cpp:44
Definition ThreatManager.h:267
Unit * SelectTarget(SelectTargetMethod targetType, uint32 position=0, float dist=0.0f, bool playerOnly=false, bool withTank=true, int32 aura=0)
Definition UnitAI.cpp:112
bool IsVehicle() const
Definition Unit.h:801
Vehicle * GetVehicle() const
Definition Unit.h:1932
TempSummon * ToTempSummon()
Definition Unit.h:732
ObjectGuid GetCharmerOrOwnerGUID() const override
Definition Unit.h:1300
Unit * GetCharmerOrOwner() const
Definition Unit.h:1291
bool IsSummon() const
Definition Unit.h:795
Unit * GetVictim() const
Definition Unit.h:904
Vehicle * GetVehicleKit() const
Definition Unit.h:1931
Unit * GetBase() const
May be called from scripts.
Definition Vehicle.h:37
Unit * GetPassenger(int8 seatId) const
Definition Vehicle.cpp:253
InstanceScript * GetInstanceScript() const
Definition Object.cpp:1247
Player * SelectNearestPlayer(float distance=0) const
Definition Object.cpp:2585
bool IsInRange(WorldObject const *obj, float minRange, float maxRange, bool is3D=true) const
Definition Object.cpp:1469
void RandomResize(C &container, std::size_t requestedSize)
Definition Containers.h:79
Unit * GetUnit(WorldObject const &, ObjectGuid const &guid)
Definition ObjectAccessor.cpp:223
Creature * GetCreatureOrPetOrVehicle(WorldObject const &, ObjectGuid const &)
Definition ObjectAccessor.cpp:258
Definition UnitAI.h:135
Definition UnitAI.h:170

References _summonList, Creature::AI(), SmartTarget::aura, SmartTarget::closestAttackable, SmartTarget::closestFriendly, SmartTarget::creature, SmartTarget::dbGuid, SmartTarget::dead, SmartTarget::dist, SmartTarget::distMax, SmartTarget::distMin, DoFindClosestFriendlyInRange(), SmartTarget::entry, SmartScriptHolder::entryOrGuid, SmartScriptHolder::event_id, SmartTarget::excludeSelf, SmartTarget::farthest, FindCreatureNear(), FindGameObjectNear(), SmartTarget::formation, SmartScriptHolder::GetActionType(), Vehicle::GetBase(), GetBaseObject(), Unit::GetCharmerOrOwner(), Unit::GetCharmerOrOwnerGUID(), GetClosestCreatureWithEntry(), GetClosestGameObjectWithEntry(), Map::GetCreature(), InstanceScript::GetCreature(), ObjectAccessor::GetCreatureOrPetOrVehicle(), Object::GetEntry(), Creature::GetFormation(), InstanceScript::GetGameObject(), Object::GetGUID(), WorldObject::GetInstanceScript(), GetLastInvoker(), Creature::GetLootRecipient(), Creature::GetLootRecipientGroup(), WorldObject::GetMap(), GameObject::GetOwnerGUID(), Vehicle::GetPassenger(), SmartScriptHolder::GetScriptType(), GetStoredTargetVector(), TempSummon::GetSummonerUnit(), SmartScriptHolder::GetTargetType(), Unit::GetThreatMgr(), ObjectAccessor::GetUnit(), ThreatManager::GetUnsortedThreatList(), Unit::GetVehicle(), Unit::GetVehicleKit(), Unit::GetVictim(), WorldObject::GetVisibilityRange(), ObjectAccessor::GetWorldObject(), GetWorldObjectsInDist(), go, SmartTarget::goClosest, SmartTarget::goDistance, SmartTarget::goGUID, SmartTarget::goRange, SmartTarget::hostileRandom, SmartTarget::id, SmartTarget::includePets, SmartTarget::index, SmartTarget::instanceStorage, SmartTarget::invokerParty, SmartScriptHolder::IsAreatriggerScript(), IsCreature(), IsGameObject(), SmartTarget::isInLos, WorldObject::IsInRange(), IsPlayer(), Unit::IsSummon(), IsUnit(), Unit::IsVehicle(), Unit::IsWithinCombatRange(), SmartTarget::livingState, LOG_ERROR, SmartTarget::maxCount, SmartTarget::maxDist, MaxThreat, me, SmartTarget::minDist, MinDistance, MinThreat, SmartTarget::negation, SmartTarget::o, SmartTarget::onlySpawned, SmartTarget::owner, SmartTarget::playerDistance, SmartTarget::playerOnly, SmartTarget::playerRange, SmartTarget::playerWithAura, SmartTarget::powerType, Random, Acore::Containers::RandomResize(), SmartTarget::resize, SmartTarget::roleMask, SmartTarget::roleSelection, SmartTarget::seatMask, WorldObject::SelectNearestPlayer(), Creature::SelectNearestTarget(), UnitAI::SelectTarget(), SmartTarget::sharedOwnerEntities, SMART_TARGET_ACTION_INVOKER, SMART_TARGET_ACTION_INVOKER_VEHICLE, SMART_TARGET_CLOSEST_CREATURE, SMART_TARGET_CLOSEST_ENEMY, SMART_TARGET_CLOSEST_FRIENDLY, SMART_TARGET_CLOSEST_GAMEOBJECT, SMART_TARGET_CLOSEST_PLAYER, SMART_TARGET_CREATURE_DISTANCE, SMART_TARGET_CREATURE_GUID, SMART_TARGET_CREATURE_RANGE, SMART_TARGET_FARTHEST, SMART_TARGET_FORMATION, SMART_TARGET_GAMEOBJECT_DISTANCE, SMART_TARGET_GAMEOBJECT_GUID, SMART_TARGET_GAMEOBJECT_RANGE, SMART_TARGET_HOSTILE_LAST_AGGRO, SMART_TARGET_HOSTILE_RANDOM, SMART_TARGET_HOSTILE_RANDOM_NOT_TOP, SMART_TARGET_HOSTILE_SECOND_AGGRO, SMART_TARGET_INSTANCE_STORAGE, SMART_TARGET_INVOKER_PARTY, SMART_TARGET_LOOT_RECIPIENTS, SMART_TARGET_NONE, SMART_TARGET_OWNER_OR_SUMMONER, SMART_TARGET_PLAYER_DISTANCE, SMART_TARGET_PLAYER_RANGE, SMART_TARGET_PLAYER_WITH_AURA, SMART_TARGET_POSITION, SMART_TARGET_ROLE_FLAG_DAMAGERS, SMART_TARGET_ROLE_FLAG_HEALERS, SMART_TARGET_ROLE_FLAG_TANKS, SMART_TARGET_ROLE_SELECTION, SMART_TARGET_SELF, SMART_TARGET_SHARED_OWNER_ENTITIES, SMART_TARGET_STORED, SMART_TARGET_SUMMONED_CREATURES, SMART_TARGET_THREAT_LIST, SMART_TARGET_VEHICLE_PASSENGER, SMART_TARGET_VICTIM, SmartTarget::spellId, SmartTarget::stored, SmartTarget::summonedCreatures, SmartScriptHolder::target, SmartTarget::threatList, Object::ToPlayer(), Unit::ToTempSummon(), Object::ToUnit(), SmartTarget::type, SmartTarget::unitClosest, SmartTarget::unitDistance, SmartTarget::unitGUID, SmartTarget::unitRange, SmartTarget::useCharmerOrOwner, and SmartTarget::vehicle.

Referenced by ProcessAction(), and ProcessEvent().

◆ GetWorldObjectsInDist()

void SmartScript::GetWorldObjectsInDist ( ObjectVector &  objects,
float  dist 
) const
4294{
4295 WorldObject* obj = GetBaseObject();
4296 if (!obj)
4297 return;
4298
4299 Acore::AllWorldObjectsInRange u_check(obj, dist);
4301 Cell::VisitObjects(obj, searcher, dist);
4302}
Definition GridNotifiers.h:1648
Definition GridNotifiers.h:262

References GetBaseObject(), and Cell::VisitObjects().

Referenced by GetTargets(), ProcessAction(), and ProcessEvent().

◆ IncPhase()

void SmartScript::IncPhase ( uint32  p)
private
5673{
5674 // protect phase from overflowing
5675 SetPhase(std::min<uint32>(SMART_EVENT_PHASE_12, mEventPhase + p));
5676}
@ SMART_EVENT_PHASE_12
Definition SmartScriptMgr.h:57

References mEventPhase, SetPhase(), and SMART_EVENT_PHASE_12.

Referenced by ProcessAction().

◆ InitTimer()

void SmartScript::InitTimer ( SmartScriptHolder &  e)
static
5104{
5105 switch (e.GetEventType())
5106 {
5107 //set only events which have initial timers
5111 break;
5112 case SMART_EVENT_UPDATE:
5115 case SMART_EVENT_RANGE:
5122 break;
5126 break;
5130 break;
5131 default:
5132 e.active = true;
5133 break;
5134 }
5135}
@ SMART_EVENT_FRIENDLY_HEALTH_PCT
Definition SmartScriptMgr.h:173
@ SMART_EVENT_NEAR_PLAYERS_NEGATION
Definition SmartScriptMgr.h:191
@ SMART_EVENT_AREA_CASTING
Definition SmartScriptMgr.h:194
@ SMART_EVENT_DISTANCE_GAMEOBJECT
Definition SmartScriptMgr.h:175
@ SMART_EVENT_RANGE
Definition SmartScriptMgr.h:108
@ SMART_EVENT_NEAR_UNIT_NEGATION
Definition SmartScriptMgr.h:193
@ SMART_EVENT_UPDATE_IC
Definition SmartScriptMgr.h:99
@ SMART_EVENT_IS_IN_MELEE_RANGE
Definition SmartScriptMgr.h:199
@ SMART_EVENT_AREA_RANGE
Definition SmartScriptMgr.h:195
@ SMART_EVENT_UPDATE
Definition SmartScriptMgr.h:159
@ SMART_EVENT_IS_BEHIND_TARGET
Definition SmartScriptMgr.h:166
@ SMART_EVENT_UPDATE_OOC
Definition SmartScriptMgr.h:100
@ SMART_EVENT_NEAR_UNIT
Definition SmartScriptMgr.h:192
@ SMART_EVENT_DISTANCE_CREATURE
Definition SmartScriptMgr.h:174
@ SMART_EVENT_NEAR_PLAYERS
Definition SmartScriptMgr.h:190
static void RecalcTimer(SmartScriptHolder &e, uint32 min, uint32 max)
Definition SmartScript.cpp:5136
struct SmartEvent::@30::@68 nearPlayer
struct SmartEvent::@30::@32 minMaxRepeat
struct SmartEvent::@30::@70 nearUnit
uint32 repeat
Definition SmartScriptMgr.h:449
uint32 min
Definition SmartScriptMgr.h:214
uint32 firstTimer
Definition SmartScriptMgr.h:464
uint32 max
Definition SmartScriptMgr.h:215
uint32 timer
Definition SmartScriptMgr.h:484
struct SmartEvent::@30::@66 distance
bool active
Definition SmartScriptMgr.h:2032
uint32 GetEventType() const
Definition SmartScriptMgr.h:2024

References SmartScriptHolder::active, SmartEvent::distance, SmartScriptHolder::event, SmartEvent::firstTimer, SmartScriptHolder::GetEventType(), SmartEvent::max, SmartEvent::min, SmartEvent::minMaxRepeat, SmartEvent::nearPlayer, SmartEvent::nearUnit, RecalcTimer(), SmartEvent::repeat, SMART_EVENT_AREA_CASTING, SMART_EVENT_AREA_RANGE, SMART_EVENT_DISTANCE_CREATURE, SMART_EVENT_DISTANCE_GAMEOBJECT, SMART_EVENT_FRIENDLY_HEALTH_PCT, SMART_EVENT_IS_BEHIND_TARGET, SMART_EVENT_IS_IN_MELEE_RANGE, SMART_EVENT_NEAR_PLAYERS, SMART_EVENT_NEAR_PLAYERS_NEGATION, SMART_EVENT_NEAR_UNIT, SMART_EVENT_NEAR_UNIT_NEGATION, SMART_EVENT_RANGE, SMART_EVENT_UPDATE, SMART_EVENT_UPDATE_IC, SMART_EVENT_UPDATE_OOC, and SmartEvent::timer.

Referenced by CreateSmartEvent(), OnInitialize(), OnReset(), ProcessAction(), and SetScript9().

◆ InstallEvents()

void SmartScript::InstallEvents ( )
private
5258{
5259 if (!mInstallEvents.empty())
5260 {
5261 for (SmartAIEventList::iterator i = mInstallEvents.begin(); i != mInstallEvents.end(); ++i)
5262 mEvents.push_back(*i);//must be before UpdateTimers
5263
5264 mInstallEvents.clear();
5265 }
5266}

References mEvents, and mInstallEvents.

Referenced by OnInitialize(), and OnUpdate().

◆ InstallTemplate()

void SmartScript::InstallTemplate ( SmartScriptHolder const &  e)
3516{
3517 if (!GetBaseObject())
3518 return;
3520 {
3521 LOG_ERROR("sql.sql", "SmartScript::InstallTemplate: Entry {} SourceType {} AI Template can not be set more then once, skipped.", e.entryOrGuid, e.GetScriptType());
3522 return;
3523 }
3524 mTemplate = (SMARTAI_TEMPLATE)e.action.installTtemplate.id;
3525 switch ((SMARTAI_TEMPLATE)e.action.installTtemplate.id)
3526 {
3528 {
3529 AddEvent(SMART_EVENT_UPDATE_IC, 0, 0, 0, e.action.installTtemplate.param2, e.action.installTtemplate.param3, 0, 0, SMART_ACTION_CAST, e.action.installTtemplate.param1, e.target.raw.param1, 0, 0, 0, 0, SMART_TARGET_VICTIM, 0, 0, 0, 0, 1);
3530 AddEvent(SMART_EVENT_RANGE, 0, e.action.installTtemplate.param4, 300, 0, 0, 0, 0, SMART_ACTION_ALLOW_COMBAT_MOVEMENT, 1, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 1);
3531 AddEvent(SMART_EVENT_RANGE, 0, 0, e.action.installTtemplate.param4 > 10 ? e.action.installTtemplate.param4 - 10 : 0, 0, 0, 0, 0, SMART_ACTION_ALLOW_COMBAT_MOVEMENT, 0, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 1);
3532 AddEvent(SMART_EVENT_MANA_PCT, 0, e.action.installTtemplate.param5 - 15 > 100 ? 100 : e.action.installTtemplate.param5 + 15, 100, 1000, 1000, 0, 0, SMART_ACTION_SET_EVENT_PHASE, 1, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 0);
3533 AddEvent(SMART_EVENT_MANA_PCT, 0, 0, e.action.installTtemplate.param5, 1000, 1000, 0, 0, SMART_ACTION_SET_EVENT_PHASE, 0, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 0);
3534 AddEvent(SMART_EVENT_MANA_PCT, 0, 0, e.action.installTtemplate.param5, 1000, 1000, 0, 0, SMART_ACTION_ALLOW_COMBAT_MOVEMENT, 1, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 0);
3535 break;
3536 }
3538 {
3539 AddEvent(SMART_EVENT_UPDATE_IC, 0, 0, 0, e.action.installTtemplate.param2, e.action.installTtemplate.param3, 0, 0, SMART_ACTION_CAST, e.action.installTtemplate.param1, e.target.raw.param1, 0, 0, 0, 0, SMART_TARGET_VICTIM, 0, 0, 0, 0, 0);
3540 AddEvent(SMART_EVENT_JUST_CREATED, 0, 0, 0, 0, 0, 0, 0, SMART_ACTION_ALLOW_COMBAT_MOVEMENT, 0, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 0);
3541 break;
3542 }
3544 {
3545 if (!me)
3546 return;
3547 //store cage as id1
3548 AddEvent(SMART_EVENT_DATA_SET, 0, 0, 0, 0, 0, 0, 0, SMART_ACTION_STORE_TARGET_LIST, 1, 0, 0, 0, 0, 0, SMART_TARGET_CLOSEST_GAMEOBJECT, e.action.installTtemplate.param1, 10, 0, 0, 0);
3549
3550 //reset(close) cage on hostage(me) respawn
3551 AddEvent(SMART_EVENT_UPDATE, SMART_EVENT_FLAG_NOT_REPEATABLE, 0, 0, 0, 0, 0, 0, SMART_ACTION_RESET_GOBJECT, 0, 0, 0, 0, 0, 0, SMART_TARGET_GAMEOBJECT_DISTANCE, e.action.installTtemplate.param1, 5, 0, 0, 0);
3552
3553 AddEvent(SMART_EVENT_DATA_SET, 0, 0, 0, 0, 0, 0, 0, SMART_ACTION_SET_RUN, e.action.installTtemplate.param3, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 0);
3554 AddEvent(SMART_EVENT_DATA_SET, 0, 0, 0, 0, 0, 0, 0, SMART_ACTION_SET_EVENT_PHASE, 1, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 0);
3555
3556 AddEvent(SMART_EVENT_UPDATE, SMART_EVENT_FLAG_NOT_REPEATABLE, 1000, 1000, 0, 0, 0, 0, SMART_ACTION_MOVE_FORWARD, e.action.installTtemplate.param4, 0, 0, 0, 0, 0, SMART_TARGET_SELF, 0, 0, 0, 0, 1);
3557 //phase 1: give quest credit on movepoint reached
3559 //phase 1: despawn after time on movepoint reached
3560 AddEvent(SMART_EVENT_MOVEMENTINFORM, 0, POINT_MOTION_TYPE, SMART_RANDOM_POINT, 0, 0, 0, 0, SMART_ACTION_FORCE_DESPAWN, e.action.installTtemplate.param2, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 1);
3561
3562 if (sCreatureTextMgr->TextExist(me->GetEntry(), (uint8)e.action.installTtemplate.param5))
3563 AddEvent(SMART_EVENT_MOVEMENTINFORM, 0, POINT_MOTION_TYPE, SMART_RANDOM_POINT, 0, 0, 0, 0, SMART_ACTION_TALK, e.action.installTtemplate.param5, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 1);
3564 break;
3565 }
3567 {
3568 if (!go)
3569 return;
3570 //store hostage as id1
3571 AddEvent(SMART_EVENT_GO_STATE_CHANGED, 0, 2, 0, 0, 0, 0, 0, SMART_ACTION_STORE_TARGET_LIST, 1, 0, 0, 0, 0, 0, SMART_TARGET_CLOSEST_CREATURE, e.action.installTtemplate.param1, 10, 0, 0, 0);
3572 //store invoker as id2
3573 AddEvent(SMART_EVENT_GO_STATE_CHANGED, 0, 2, 0, 0, 0, 0, 0, SMART_ACTION_STORE_TARGET_LIST, 2, 0, 0, 0, 0, 0, SMART_TARGET_NONE, 0, 0, 0, 0, 0);
3574 //signal hostage
3575 AddEvent(SMART_EVENT_GO_STATE_CHANGED, 0, 2, 0, 0, 0, 0, 0, SMART_ACTION_SET_DATA, 0, 0, 0, 0, 0, 0, SMART_TARGET_STORED, 1, 0, 0, 0, 0);
3576 //when hostage raeched end point, give credit to invoker
3577 if (e.action.installTtemplate.param2)
3578 AddEvent(SMART_EVENT_DATA_SET, 0, 0, 0, 0, 0, 0, 0, SMART_ACTION_CALL_KILLEDMONSTER, e.action.installTtemplate.param1, 0, 0, 0, 0, 0, SMART_TARGET_STORED, 2, 0, 0, 0, 0);
3579 else
3580 AddEvent(SMART_EVENT_GO_STATE_CHANGED, 0, 2, 0, 0, 0, 0, 0, SMART_ACTION_CALL_KILLEDMONSTER, e.action.installTtemplate.param1, 0, 0, 0, 0, 0, SMART_TARGET_STORED, 2, 0, 0, 0, 0);
3581 break;
3582 }
3584 default:
3585 return;
3586 }
3587}
#define sCreatureTextMgr
Definition CreatureTextMgr.h:123
std::uint8_t uint8
Definition Define.h:109
@ POINT_MOTION_TYPE
Definition MotionMaster.h:48
SMARTAI_TEMPLATE
Definition SmartScriptMgr.h:1538
@ SMARTAI_TEMPLATE_CAGED_GO_PART
Definition SmartScriptMgr.h:1543
@ SMARTAI_TEMPLATE_CAGED_NPC_PART
Definition SmartScriptMgr.h:1544
@ SMARTAI_TEMPLATE_CASTER
Definition SmartScriptMgr.h:1540
@ SMARTAI_TEMPLATE_TURRET
Definition SmartScriptMgr.h:1541
@ SMART_EVENT_FLAG_NOT_REPEATABLE
Definition SmartScriptMgr.h:1961
@ SMART_ACTION_STORE_TARGET_LIST
Definition SmartScriptMgr.h:606
@ SMART_ACTION_FORCE_DESPAWN
Definition SmartScriptMgr.h:583
@ SMART_ACTION_CAST
Definition SmartScriptMgr.h:553
@ SMART_ACTION_ALLOW_COMBAT_MOVEMENT
Definition SmartScriptMgr.h:563
@ SMART_ACTION_MOVE_FORWARD
Definition SmartScriptMgr.h:588
@ SMART_ACTION_CALL_KILLEDMONSTER
Definition SmartScriptMgr.h:575
@ SMART_ACTION_TALK
Definition SmartScriptMgr.h:543
@ SMART_ACTION_SET_DATA
Definition SmartScriptMgr.h:587
@ SMART_ACTION_SET_RUN
Definition SmartScriptMgr.h:601
@ SMART_ACTION_SET_EVENT_PHASE
Definition SmartScriptMgr.h:564
@ SMART_ACTION_RESET_GOBJECT
Definition SmartScriptMgr.h:574
@ SMART_EVENT_DATA_SET
Definition SmartScriptMgr.h:137
@ SMART_EVENT_JUST_CREATED
Definition SmartScriptMgr.h:162
@ SMART_EVENT_MOVEMENTINFORM
Definition SmartScriptMgr.h:133
@ SMART_EVENT_MANA_PCT
Definition SmartScriptMgr.h:102
@ SMART_EVENT_GO_STATE_CHANGED
Definition SmartScriptMgr.h:169
@ SMART_RANDOM_POINT
Definition SmartScriptMgr.h:39
void AddEvent(SMART_EVENT e, uint32 event_flags, uint32 event_param1, uint32 event_param2, uint32 event_param3, uint32 event_param4, uint32 event_param5, uint32 event_param6, SMART_ACTION action, uint32 action_param1, uint32 action_param2, uint32 action_param3, uint32 action_param4, uint32 action_param5, uint32 action_param6, SMARTAI_TARGETS t, uint32 target_param1, uint32 target_param2, uint32 target_param3, uint32 target_param4, uint32 phaseMask)
Definition SmartScript.cpp:3589

References SmartScriptHolder::action, AddEvent(), SmartScriptHolder::entryOrGuid, GetBaseObject(), Object::GetEntry(), SmartScriptHolder::GetScriptType(), go, SmartAction::id, SmartAction::installTtemplate, LOG_ERROR, me, mTemplate, SmartAction::param1, SmartTarget::param1, SmartAction::param2, SmartAction::param3, SmartAction::param4, SmartAction::param5, POINT_MOTION_TYPE, SmartTarget::raw, sCreatureTextMgr, SMART_ACTION_ALLOW_COMBAT_MOVEMENT, SMART_ACTION_CALL_KILLEDMONSTER, SMART_ACTION_CAST, SMART_ACTION_FORCE_DESPAWN, SMART_ACTION_MOVE_FORWARD, SMART_ACTION_RESET_GOBJECT, SMART_ACTION_SET_DATA, SMART_ACTION_SET_EVENT_PHASE, SMART_ACTION_SET_RUN, SMART_ACTION_STORE_TARGET_LIST, SMART_ACTION_TALK, SMART_EVENT_DATA_SET, SMART_EVENT_FLAG_NOT_REPEATABLE, SMART_EVENT_GO_STATE_CHANGED, SMART_EVENT_JUST_CREATED, SMART_EVENT_MANA_PCT, SMART_EVENT_MOVEMENTINFORM, SMART_EVENT_RANGE, SMART_EVENT_UPDATE, SMART_EVENT_UPDATE_IC, SMART_RANDOM_POINT, SMART_TARGET_CLOSEST_CREATURE, SMART_TARGET_CLOSEST_GAMEOBJECT, SMART_TARGET_GAMEOBJECT_DISTANCE, SMART_TARGET_NONE, SMART_TARGET_SELF, SMART_TARGET_STORED, SMART_TARGET_VICTIM, SMARTAI_TEMPLATE_BASIC, SMARTAI_TEMPLATE_CAGED_GO_PART, SMARTAI_TEMPLATE_CAGED_NPC_PART, SMARTAI_TEMPLATE_CASTER, SMARTAI_TEMPLATE_TURRET, and SmartScriptHolder::target.

Referenced by ProcessAction().

◆ IsCharmedCreature()

bool SmartScript::IsCharmedCreature ( WorldObject *  obj)
static
5657{
5658 if (!obj)
5659 return false;
5660
5661 if (Creature* creatureObj = obj->ToCreature())
5662 return creatureObj->IsCharmed();
5663
5664 return false;
5665}
Creature * ToCreature()
Definition Object.h:212

References Object::ToCreature().

Referenced by ProcessEvent().

◆ IsCreature()

bool SmartScript::IsCreature ( WorldObject *  obj)
static
5652{
5653 return obj && obj->IsCreature();
5654}
bool IsCreature() const
Definition Object.h:211

References Object::IsCreature().

Referenced by GetTargets(), ProcessAction(), and ProcessEvent().

◆ IsGameObject()

bool SmartScript::IsGameObject ( WorldObject *  obj)
static
5668{
5669 return obj && obj->IsGameObject();
5670}
bool IsGameObject() const
Definition Object.h:219

References Object::IsGameObject().

Referenced by GetTargets(), ProcessAction(), and ProcessEvent().

◆ IsInPhase()

bool SmartScript::IsInPhase ( uint32  p) const
private
5703{
5704 if (mEventPhase == 0)
5705 {
5706 return false;
5707 }
5708
5709 return ((1 << (mEventPhase - 1)) & p) != 0;
5710}

References mEventPhase.

Referenced by ProcessEvent(), and UpdateTimer().

◆ IsPlayer()

bool SmartScript::IsPlayer ( WorldObject *  obj)
static
5647{
5648 return obj && obj->IsPlayer();
5649}
bool IsPlayer() const
Definition Object.h:207

References Object::IsPlayer().

Referenced by SmartAI::EndPath(), GetTargets(), SmartAI::IsEscortInvokerInRange(), ProcessAction(), and ProcessEvent().

◆ IsSmart() [1/3]

bool SmartScript::IsSmart ( bool  silent = false) const
122{
123 if (me)
124 return IsSmart(me, silent);
125 if (go)
126 return IsSmart(go, silent);
127
128 return false;
129}
bool IsSmart(Creature *c, bool silent=false) const
Definition SmartScript.cpp:91

References go, IsSmart(), and me.

◆ IsSmart() [2/3]

bool SmartScript::IsSmart ( Creature *  c,
bool  silent = false 
) const
92{
93 if (!c)
94 return false;
95
96 bool smart = true;
97 if (!dynamic_cast<SmartAI*>(c->AI()))
98 smart = false;
99
100 if (!smart && !silent)
101 LOG_ERROR("sql.sql", "SmartScript: Action target Creature(entry: {}) is not using SmartAI, action skipped to prevent crash.", c ? c->GetEntry() : (me ? me->GetEntry() : 0));
102
103 return smart;
104}
Definition SmartAI.h:46

References Creature::AI(), Object::GetEntry(), LOG_ERROR, and me.

Referenced by IsSmart(), and ProcessAction().

◆ IsSmart() [3/3]

bool SmartScript::IsSmart ( GameObject *  g,
bool  silent = false 
) const
107{
108 if (!g)
109 return false;
110
111 bool smart = true;
112 if (!dynamic_cast<SmartGameObjectAI*>(g->AI()))
113 smart = false;
114
115 if (!smart && !silent)
116 LOG_ERROR("sql.sql", "SmartScript: Action target GameObject(entry: {}) is not using SmartGameObjectAI, action skipped to prevent crash.", g ? g->GetEntry() : (go ? go->GetEntry() : 0));
117
118 return smart;
119}
GameObjectAI * AI() const
Definition GameObject.h:308
Definition SmartAI.h:289

References GameObject::AI(), Object::GetEntry(), go, and LOG_ERROR.

◆ IsUnit()

bool SmartScript::IsUnit ( WorldObject *  obj)
static
5642{
5643 return obj && (obj->IsCreature() || obj->IsPlayer());
5644}

References Object::IsCreature(), and Object::IsPlayer().

Referenced by GetTargets(), ProcessAction(), and ProcessEvent().

◆ OnInitialize()

void SmartScript::OnInitialize ( WorldObject *  obj,
AreaTrigger const *  at = nullptr 
)
5441{
5442 if (obj)//handle object based scripts
5443 {
5444 switch (obj->GetTypeId())
5445 {
5446 case TYPEID_UNIT:
5448 me = obj->ToCreature();
5449 LOG_DEBUG("sql.sql", "SmartScript::OnInitialize: source is Creature {}", me->GetEntry());
5450 break;
5451 case TYPEID_GAMEOBJECT:
5453 go = obj->ToGameObject();
5454 LOG_DEBUG("sql.sql", "SmartScript::OnInitialize: source is GameObject {}", go->GetEntry());
5455 break;
5456 default:
5457 LOG_ERROR("scripts.ai.sai", "SmartScript::OnInitialize: Unhandled TypeID !WARNING!");
5458 return;
5459 }
5460 }
5461 else if (at)
5462 {
5464 trigger = at;
5465 LOG_DEBUG("sql.sql", "SmartScript::OnInitialize: source is AreaTrigger {}", trigger->entry);
5466 }
5467 else
5468 {
5469 LOG_ERROR("scripts.ai.sai", "SmartScript::OnInitialize: !WARNING! Initialized objects are nullptr.");
5470 return;
5471 }
5472
5473 GetScript();//load copy of script
5474
5475 for (SmartScriptHolder& event : mEvents)
5476 InitTimer(event);//calculate timers for first time use
5477
5479 InstallEvents();
5481}
@ TYPEID_GAMEOBJECT
Definition ObjectGuid.h:40
@ TYPEID_UNIT
Definition ObjectGuid.h:38
@ SMART_SCRIPT_TYPE_GAMEOBJECT
Definition SmartScriptMgr.h:1804
@ SMART_SCRIPT_TYPE_AREATRIGGER
Definition SmartScriptMgr.h:1805
@ SMART_EVENT_AI_INIT
Definition SmartScriptMgr.h:136
TypeID GetTypeId() const
Definition Object.h:135
GameObject * ToGameObject()
Definition Object.h:220
void ProcessEventsFor(SMART_EVENT e, Unit *unit=nullptr, uint32 var0=0, uint32 var1=0, bool bvar=false, SpellInfo const *spell=nullptr, GameObject *gob=nullptr)
Definition SmartScript.cpp:157
void InstallEvents()
Definition SmartScript.cpp:5257
void GetScript()
Definition SmartScript.cpp:5398

References AreaTrigger::entry, Object::GetEntry(), GetScript(), Object::GetTypeId(), go, InitTimer(), InstallEvents(), LOG_DEBUG, LOG_ERROR, me, mEvents, mScriptType, ProcessEventsFor(), SMART_EVENT_AI_INIT, SMART_EVENT_JUST_CREATED, SMART_SCRIPT_TYPE_AREATRIGGER, SMART_SCRIPT_TYPE_CREATURE, SMART_SCRIPT_TYPE_GAMEOBJECT, Object::ToCreature(), Object::ToGameObject(), trigger, TYPEID_GAMEOBJECT, and TYPEID_UNIT.

Referenced by SmartAI::InitializeAI(), SmartGameObjectAI::InitializeAI(), and SmartTrigger::OnTrigger().

◆ OnMoveInLineOfSight()

void SmartScript::OnMoveInLineOfSight ( Unit *  who)
5484{
5485 if (!me)
5486 return;
5487
5489}
@ SMART_EVENT_IC_LOS
Definition SmartScriptMgr.h:125
@ SMART_EVENT_OOC_LOS
Definition SmartScriptMgr.h:109
bool IsEngaged() const override
Definition Creature.cpp:2958

References Creature::IsEngaged(), me, ProcessEventsFor(), SMART_EVENT_IC_LOS, and SMART_EVENT_OOC_LOS.

Referenced by SmartAI::MoveInLineOfSight().

◆ OnReset()

void SmartScript::OnReset ( )
132{
133 // xinef: check if we allow phase reset
134 if (AllowPhaseReset())
135 SetPhase(0);
136
138 for (SmartAIEventList::iterator i = mEvents.begin(); i != mEvents.end(); ++i)
139 {
140 if (!((*i).event.event_flags & SMART_EVENT_FLAG_DONT_RESET))
141 {
142 InitTimer((*i));
143 (*i).runOnce = false;
144 }
145
146 if ((*i).priority != SmartScriptHolder::DEFAULT_PRIORITY)
147 {
150 }
151 }
154 mCounterList.clear();
155}
@ SMART_EVENT_FLAG_DONT_RESET
Definition SmartScriptMgr.h:1969
@ SMART_EVENT_RESET
Definition SmartScriptMgr.h:124
void Clear()
Definition ObjectGuid.h:141
bool AllowPhaseReset() const
Definition SmartScript.h:204
void ResetBaseObject()
Definition SmartScript.h:166
static constexpr uint32 DEFAULT_PRIORITY
Definition SmartScriptMgr.h:2042

References AllowPhaseReset(), ObjectGuid::Clear(), SmartScriptHolder::DEFAULT_PRIORITY, InitTimer(), mCounterList, mEvents, mEventSortingRequired, mLastInvoker, ProcessEventsFor(), ResetBaseObject(), SetPhase(), SMART_EVENT_FLAG_DONT_RESET, and SMART_EVENT_RESET.

Referenced by SmartAI::EnterEvadeMode(), SmartAI::JustReachedHome(), ProcessAction(), and SmartGameObjectAI::Reset().

◆ OnUpdate()

void SmartScript::OnUpdate ( const uint32  diff)
5269{
5271 return;
5272
5273 InstallEvents();//before UpdateTimers
5274
5276 {
5278 mEventSortingRequired = false;
5279 }
5280
5281 for (SmartAIEventList::iterator i = mEvents.begin(); i != mEvents.end(); ++i)
5282 UpdateTimer(*i, diff);
5283
5284 if (!mStoredEvents.empty())
5285 {
5286 SmartAIEventStoredList::iterator i, icurr;
5287 for (i = mStoredEvents.begin(); i != mStoredEvents.end();)
5288 {
5289 icurr = i++;
5290 UpdateTimer(*icurr, diff);
5291 }
5292 }
5293
5294 bool needCleanup = true;
5295 if (!mTimedActionList.empty())
5296 {
5298 for (SmartAIEventList::iterator i = mTimedActionList.begin(); i != mTimedActionList.end(); ++i)
5299 {
5300 if ((*i).enableTimed)
5301 {
5302 UpdateTimer(*i, diff);
5303 needCleanup = false;
5304 }
5305 }
5306
5308 }
5309 if (needCleanup)
5310 mTimedActionList.clear();
5311
5312 if (!mRemIDs.empty())
5313 {
5314 for (std::list<uint32>::const_iterator i = mRemIDs.begin(); i != mRemIDs.end(); ++i)
5316
5317 // xinef: clear list after cleaning...
5318 mRemIDs.clear();
5319 }
5320 if (mUseTextTimer && me)
5321 {
5322 if (mTextTimer < diff)
5323 {
5324 uint32 textID = mLastTextID;
5325 mLastTextID = 0;
5326 uint32 entry = mTalkerEntry;
5327 mTalkerEntry = 0;
5328 mTextTimer = 0;
5329 mUseTextTimer = false;
5330 ProcessEventsFor(SMART_EVENT_TEXT_OVER, nullptr, textID, entry);
5331 }
5332 else mTextTimer -= diff;
5333 }
5334}
@ SMART_EVENT_TEXT_OVER
Definition SmartScriptMgr.h:151
void UpdateTimer(SmartScriptHolder &e, uint32 const diff)
Definition SmartScript.cpp:5143
void SortEvents(SmartAIEventList &events)
Definition SmartScript.cpp:5336
SmartAIEventStoredList mStoredEvents
Definition SmartScript.h:236
std::list< uint32 > mRemIDs
Definition SmartScript.h:237
SmartAIEventList mTimedActionList
Definition SmartScript.h:224
void RemoveStoredEvent(uint32 id)
Definition SmartScript.h:254

References GetBaseObject(), InstallEvents(), isProcessingTimedActionList, me, mEvents, mEventSortingRequired, mLastTextID, mRemIDs, mScriptType, mStoredEvents, mTalkerEntry, mTextTimer, mTimedActionList, mUseTextTimer, ProcessEventsFor(), RemoveStoredEvent(), SMART_EVENT_TEXT_OVER, SMART_SCRIPT_TYPE_CREATURE, SMART_SCRIPT_TYPE_GAMEOBJECT, SortEvents(), and UpdateTimer().

Referenced by SmartAI::UpdateAI(), and SmartGameObjectAI::UpdateAI().

◆ ProcessAction()

void SmartScript::ProcessAction ( SmartScriptHolder &  e,
Unit *  unit = nullptr,
uint32  var0 = 0,
uint32  var1 = 0,
bool  bvar = false,
SpellInfo const *  spell = nullptr,
GameObject *  gob = nullptr 
)
186{
187 e.runOnce = true;//used for repeat check
188
189 //calc random
191 {
192 uint32 rnd = urand(1, 100);
193 if (e.event.event_chance <= rnd)
194 return;
195 }
196
197 // Remove SMART_EVENT_FLAG_TEMP_IGNORE_CHANCE_ROLL flag after processing roll chances as it's not needed anymore
198 e.event.event_flags &= ~SMART_EVENT_FLAG_TEMP_IGNORE_CHANCE_ROLL;
199
200 if (unit)
201 mLastInvoker = unit->GetGUID();
202 else if (gob)
203 mLastInvoker = gob->GetGUID();
204
205 if (WorldObject* tempInvoker = GetLastInvoker())
206 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: Invoker: {} ({})", tempInvoker->GetName(), tempInvoker->GetGUID().ToString());
207
208 bool isControlled = e.action.moveToPos.controlled > 0;
209
210 ObjectVector targets;
211 WorldObject* invoker = nullptr;
212 if (unit)
213 invoker = unit;
214 else if (gob)
215 invoker = gob;
216
217 GetTargets(targets, e, invoker);
218
219 switch (e.GetActionType())
220 {
222 {
223 Creature* talker = e.target.type == 0 ? me : nullptr;
224 WorldObject* talkTarget = nullptr;
225
226 for (WorldObject* target : targets)
227 {
228 if (IsCreature((target)) && !target->ToCreature()->IsPet()) // Prevented sending text to pets.
229 {
231 {
232 talker = me;
233 talkTarget = target->ToCreature();
234 }
235 else
236 talker = target->ToCreature();
237 break;
238 }
239 else if (IsPlayer((target)))
240 {
241 talker = me; // xinef: added
242 talkTarget = target->ToPlayer();
243 break;
244 }
245 }
246
247 if (!talkTarget)
248 talkTarget = GetLastInvoker();
249
250 if (!talker)
251 break;
252
253 if (!sCreatureTextMgr->TextExist(talker->GetEntry(), uint8(e.action.talk.textGroupID)))
254 {
255 LOG_ERROR("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_TALK: EntryOrGuid {} SourceType {} EventType {} TargetType {} using non-existent Text id {} for talker {}, ignored.", e.entryOrGuid, e.GetScriptType(), e.GetEventType(), e.GetTargetType(), e.action.talk.textGroupID, talker->GetEntry());
256 break;
257 }
258
259 mTalkerEntry = talker->GetEntry();
262 mUseTextTimer = true;
263
264 talker->AI()->Talk(e.action.talk.textGroupID, talkTarget, Milliseconds(e.action.talk.delay));
265 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_TALK: talker: {} ({}), textId: {}", talker->GetName(), talker->GetGUID().ToString(), mLastTextID);
266 break;
267 }
269 {
270 for (WorldObject* target : targets)
271 {
272 if (IsCreature(target))
273 sCreatureTextMgr->SendChat(target->ToCreature(), uint8(e.action.simpleTalk.textGroupID), IsPlayer(GetLastInvoker()) ? GetLastInvoker() : 0);
274 else if (IsPlayer(target) && me)
275 {
276 WorldObject* templastInvoker = GetLastInvoker();
277 sCreatureTextMgr->SendChat(me, uint8(e.action.simpleTalk.textGroupID), IsPlayer(templastInvoker) ? templastInvoker : 0, CHAT_MSG_ADDON, LANG_ADDON, TEXT_RANGE_NORMAL, 0, TEAM_NEUTRAL, false, target->ToPlayer());
278 }
279
280 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_SIMPLE_TALK: talker: {} ({}), textGroupId: {}",
281 target->GetName(), target->GetGUID().ToString(), uint8(e.action.simpleTalk.textGroupID));
282 }
283 break;
284 }
286 {
287 for (WorldObject* target : targets)
288 {
289 if (IsUnit(target))
290 {
291 target->ToUnit()->HandleEmoteCommand(e.action.emote.emote);
292 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_PLAY_EMOTE: target: {} ({}), emote: {}",
293 target->GetName(), target->GetGUID().ToString(), e.action.emote.emote);
294 }
295 }
296 break;
297 }
299 {
300 for (WorldObject* target : targets)
301 {
302 if (IsUnit(target))
303 {
304 if (e.action.sound.distance == 1)
305 target->PlayDistanceSound(e.action.sound.sound, e.action.sound.onlySelf ? target->ToPlayer() : nullptr);
306 else
307 target->PlayDirectSound(e.action.sound.sound, e.action.sound.onlySelf ? target->ToPlayer() : nullptr);
308 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_SOUND: target: {} ({}), sound: {}, onlyself: {}",
309 target->GetName(), target->GetGUID().ToString(), e.action.sound.sound, e.action.sound.onlySelf);
310 }
311 }
312 break;
313 }
315 {
316 uint32 sounds[4];
317 sounds[0] = e.action.randomSound.sound1;
318 sounds[1] = e.action.randomSound.sound2;
319 sounds[2] = e.action.randomSound.sound3;
320 sounds[3] = e.action.randomSound.sound4;
321 uint32 temp[4];
322 uint32 count = 0;
323 for (unsigned int sound : sounds)
324 {
325 if (sound)
326 {
327 temp[count] = sound;
328 ++count;
329 }
330 }
331
332 if (count == 0)
333 {
334 break;
335 }
336
337 for (WorldObject* target : targets)
338 {
339 if (IsUnit(target))
340 {
341 uint32 sound = temp[urand(0, count - 1)];
342 target->PlayDirectSound(sound, e.action.randomSound.onlySelf ? target->ToPlayer() : nullptr);
343 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_RANDOM_SOUND: target: {} ({}), sound: {}, onlyself: {}",
344 target->GetName(), target->GetGUID().ToString(), sound, e.action.randomSound.onlySelf);
345 }
346 }
347
348 break;
349 }
351 {
352 ObjectVector targets;
353
354 if (e.action.music.type > 0)
355 {
356 if (me && me->FindMap())
357 {
358 Map::PlayerList const& players = me->GetMap()->GetPlayers();
359
360 if (!players.IsEmpty())
361 {
362 for (Map::PlayerList::const_iterator i = players.begin(); i != players.end(); ++i)
363 if (Player* player = i->GetSource())
364 {
365 if (player->GetZoneId() == me->GetZoneId())
366 {
367 if (e.action.music.type > 1)
368 {
369 if (player->GetAreaId() == me->GetAreaId())
370 targets.push_back(player);
371 }
372 else
373 targets.push_back(player);
374 }
375 }
376 }
377 }
378 }
379 else
380 GetTargets(targets, e);
381
382 if (!targets.empty())
383 {
384 for (WorldObject* target : targets)
385 {
386 if (IsUnit(target))
387 {
388 target->SendPlayMusic(e.action.music.sound, e.action.music.onlySelf > 0);
389 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_MUSIC: target: {} ({}), sound: {}, onlySelf: {}, type: {}",
390 target->GetName(), target->GetGUID().ToString(), e.action.music.sound, e.action.music.onlySelf, e.action.music.type);
391 }
392 }
393 }
394 break;
395 }
397 {
398 ObjectVector targets;
399
400 if (e.action.randomMusic.type > 0)
401 {
402 if (me && me->FindMap())
403 {
404 Map::PlayerList const& players = me->GetMap()->GetPlayers();
405
406 if (!players.IsEmpty())
407 {
408 for (Map::PlayerList::const_iterator i = players.begin(); i != players.end(); ++i)
409 if (Player* player = i->GetSource())
410 {
411 if (player->GetZoneId() == me->GetZoneId())
412 {
413 if (e.action.randomMusic.type > 1)
414 {
415 if (player->GetAreaId() == me->GetAreaId())
416 targets.push_back(player);
417 }
418 else
419 targets.push_back(player);
420 }
421 }
422 }
423 }
424 }
425 else
426 GetTargets(targets, e);
427
428 if (targets.empty())
429 break;
430
431 uint32 sounds[4];
432 sounds[0] = e.action.randomMusic.sound1;
433 sounds[1] = e.action.randomMusic.sound2;
434 sounds[2] = e.action.randomMusic.sound3;
435 sounds[3] = e.action.randomMusic.sound4;
436 uint32 temp[4];
437 uint32 count = 0;
438 for (unsigned int sound : sounds)
439 {
440 if (sound)
441 {
442 temp[count] = sound;
443 ++count;
444 }
445 }
446
447 if (count == 0)
448 {
449 break;
450 }
451
452 for (WorldObject* target : targets)
453 {
454 if (IsUnit(target))
455 {
456 uint32 sound = temp[urand(0, count - 1)];
457 target->SendPlayMusic(sound, e.action.randomMusic.onlySelf > 0);
458 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_RANDOM_MUSIC: target: {} ({}), sound: {}, onlyself: {}, type: {}",
459 target->GetName(), target->GetGUID().ToString(), sound, e.action.randomMusic.onlySelf, e.action.randomMusic.type);
460 }
461 }
462
463 break;
464 }
466 {
467 for (WorldObject* target : targets)
468 {
469 if (IsCreature(target))
470 {
472 {
473 target->ToCreature()->SetFaction(e.action.faction.factionID);
474 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_SET_FACTION: Creature entry {}, GuidLow {} set faction to {}",
475 target->GetEntry(), target->GetGUID().ToString(), e.action.faction.factionID);
476 }
477 else
478 {
479 if (CreatureTemplate const* ci = sObjectMgr->GetCreatureTemplate(target->ToCreature()->GetEntry()))
480 {
481 if (target->ToCreature()->GetFaction() != ci->faction)
482 {
483 target->ToCreature()->SetFaction(ci->faction);
484 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_SET_FACTION: Creature entry {}, GuidLow {} set faction to {}",
485 target->GetEntry(), target->GetGUID().ToString(), ci->faction);
486 }
487 }
488 }
489 }
490 }
491 break;
492 }
494 {
495 for (WorldObject* target : targets)
496 {
497 if (!IsCreature(target))
498 continue;
499
501 {
502 //set model based on entry from creature_template
504 {
505 if (CreatureTemplate const* ci = sObjectMgr->GetCreatureTemplate(e.action.morphOrMount.creature))
506 {
507 CreatureModel const* model = ObjectMgr::ChooseDisplayId(ci);
508 target->ToCreature()->SetDisplayId(model->CreatureDisplayID, model->DisplayScale);
509 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_MORPH_TO_ENTRY_OR_MODEL: Creature entry {}, GuidLow {} set displayid to {}",
510 target->GetEntry(), target->GetGUID().ToString(), model->CreatureDisplayID);
511 }
512 }
513 //if no param1, then use value from param2 (modelId)
514 else
515 {
516 target->ToCreature()->SetDisplayId(e.action.morphOrMount.model);
517 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_MORPH_TO_ENTRY_OR_MODEL: Creature entry {}, GuidLow {} set displayid to {}",
518 target->GetEntry(), target->GetGUID().ToString(), e.action.morphOrMount.model);
519 }
520 }
521 else
522 {
523 target->ToCreature()->DeMorph();
524 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_MORPH_TO_ENTRY_OR_MODEL: Creature entry {}, GuidLow {} demorphs.",
525 target->GetEntry(), target->GetGUID().ToString());
526 }
527 }
528 break;
529 }
531 {
532 for (WorldObject* target : targets)
533 {
534 if (IsPlayer(target))
535 {
536 target->ToPlayer()->FailQuest(e.action.quest.quest);
537 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_FAIL_QUEST: Player guidLow {} fails quest {}",
538 target->GetGUID().ToString(), e.action.quest.quest);
539 }
540 }
541 break;
542 }
544 {
545 for (WorldObject* target : targets)
546 {
547 if (Player* player = target->ToPlayer())
548 {
549 if (Quest const* q = sObjectMgr->GetQuestTemplate(e.action.questOffer.questID))
550 {
551 if (me && e.action.questOffer.directAdd == 0)
552 {
553 if (player->CanTakeQuest(q, true))
554 {
555 if (WorldSession* session = player->GetSession())
556 {
557 PlayerMenu menu(session);
558 menu.SendQuestGiverQuestDetails(q, me->GetGUID(), true);
559 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_OFFER_QUEST: Player guidLow {} - offering quest {}",
560 player->GetGUID().ToString(), e.action.questOffer.questID);
561 }
562 }
563 }
564 else
565 {
566 player->AddQuestAndCheckCompletion(q, nullptr);
567 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_OFFER_QUEST: Player guidLow {} - quest {} added",
568 player->GetGUID().ToString(), e.action.questOffer.questID);
569 }
570 }
571 }
572 }
573 break;
574 }
576 {
577 for (WorldObject* target : targets)
578 {
579 if (!IsCreature(target))
580 continue;
581
582 target->ToCreature()->SetReactState(ReactStates(e.action.react.state));
583 }
584 break;
585 }
587 {
588 std::vector<uint32> emotes;
589 std::copy_if(e.action.randomEmote.emotes.begin(), e.action.randomEmote.emotes.end(),
590 std::back_inserter(emotes), [](uint32 emote) { return emote != 0; });
591
592 for (WorldObject* target : targets)
593 {
594 if (IsUnit(target))
595 {
597 target->ToUnit()->HandleEmoteCommand(emote);
598 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_RANDOM_EMOTE: Creature guidLow {} handle random emote {}",
599 target->GetGUID().ToString(), emote);
600 }
601 }
602 break;
603 }
605 {
606 if (!me)
607 break;
608
609 for (ThreatReference* ref : me->GetThreatMgr().GetModifiableThreatList())
610 {
611 ref->ModifyThreatByPercent(std::max<int32>(-100, int32(e.action.threatPCT.threatINC) - int32(e.action.threatPCT.threatDEC)));
612 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_THREAT_ALL_PCT: Creature {} modify threat for unit {}, value {}",
613 me->GetGUID().ToString(), ref->GetVictim()->GetGUID().ToString(), int32(e.action.threatPCT.threatINC) - int32(e.action.threatPCT.threatDEC));
614 }
615 break;
616 }
618 {
619 if (!me)
620 break;
621
622 for (WorldObject* target : targets)
623 {
624 if (IsUnit(target))
625 {
626 me->GetThreatMgr().ModifyThreatByPercent(target->ToUnit(), std::max<int32>(-100, int32(e.action.threatPCT.threatINC) - int32(e.action.threatPCT.threatDEC)));
627 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_THREAT_SINGLE_PCT: Creature {} modify threat for unit {}, value {}",
628 me->GetGUID().ToString(), target->GetGUID().ToString(), int32(e.action.threatPCT.threatINC) - int32(e.action.threatPCT.threatDEC));
629 }
630 }
631 break;
632 }
634 {
635 for (WorldObject* target : targets)
636 {
637 // Special handling for vehicles
638 if (IsUnit(target))
639 if (Vehicle* vehicle = target->ToUnit()->GetVehicleKit())
640 for (auto & Seat : vehicle->Seats)
641 if (Player* player = ObjectAccessor::GetPlayer(*target, Seat.second.Passenger.Guid))
642 player->AreaExploredOrEventHappens(e.action.quest.quest);
643
644 if (IsPlayer(target))
645 {
646 target->ToPlayer()->AreaExploredOrEventHappens(e.action.quest.quest);
647
648 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_CALL_AREAEXPLOREDOREVENTHAPPENS: Player guidLow {} credited quest {}",
649 target->GetGUID().ToString(), e.action.quest.quest);
650 }
651 }
652 break;
653 }
655 {
656 if (targets.empty())
657 break;
658
659 Unit* caster = me;
660 // Areatrigger Cast!
661 if (e.IsAreatriggerScript())
662 caster = unit->SummonTrigger(unit->GetPositionX(), unit->GetPositionY(), unit->GetPositionZ(), unit->GetOrientation(), 5000);
663
666
667 bool failedSpellCast = false, successfulSpellCast = false;
668
669 for (WorldObject* target : targets)
670 {
671 // may be nullptr
672 if (go)
673 go->CastSpell(target->ToUnit(), e.action.cast.spell);
674
675 if (!IsUnit(target))
676 continue;
677
678 if (caster && caster != me) // Areatrigger cast
679 {
680 caster->CastSpell(target->ToUnit(), e.action.cast.spell, (e.action.cast.castFlags & SMARTCAST_TRIGGERED));
681 }
682 else if (me)
683 {
684 // If target has the aura, skip
685 if ((e.action.cast.castFlags & SMARTCAST_AURA_NOT_PRESENT) && target->ToUnit()->HasAura(e.action.cast.spell))
686 continue;
687
688 // If the threatlist is a singleton, cancel
690 if (me->GetThreatMgr().GetThreatListSize() <= 1)
691 break;
692
693 // If target does not use mana, skip
694 if ((e.action.cast.castFlags & SMARTCAST_TARGET_POWER_MANA) && !target->ToUnit()->GetPower(POWER_MANA))
695 continue;
696
697 // Interrupts current spellcast
700
701 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(e.action.cast.spell);
702 float distanceToTarget = me->GetDistance(target->ToUnit());
703 float spellMaxRange = me->GetSpellMaxRangeForTarget(target->ToUnit(), spellInfo);
704 float spellMinRange = me->GetSpellMinRangeForTarget(target->ToUnit(), spellInfo);
705 float meleeRange = me->GetMeleeRange(target->ToUnit());
706
707 bool isWithinLOSInMap = me->IsWithinLOSInMap(target->ToUnit(), VMAP::ModelIgnoreFlags::M2);
708 bool isWithinMeleeRange = distanceToTarget <= meleeRange;
709 bool isRangedAttack = spellMaxRange > NOMINAL_MELEE_RANGE;
710 bool isTargetRooted = target->ToUnit()->HasUnitState(UNIT_STATE_ROOT);
711 // To prevent running back and forth when OOM, we must have more than 10% mana.
712 bool canCastSpell = me->GetPowerPct(POWER_MANA) > 10.0f && spellInfo->CalcPowerCost(me, spellInfo->GetSchoolMask()) < (int32)me->GetPower(POWER_MANA) && !me->HasFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_SILENCED);
713 bool isSpellIgnoreLOS = spellInfo->HasAttribute(SPELL_ATTR2_IGNORE_LINE_OF_SIGHT);
714
715 // If target is rooted we move out of melee range before casting, but not further than spell max range.
716 if (isWithinLOSInMap && isWithinMeleeRange && isRangedAttack && isTargetRooted && canCastSpell && !me->IsVehicle())
717 {
718 failedSpellCast = true; // Mark spellcast as failed so we can retry it later
719
720 if (me->IsRooted()) // Rooted inhabit type, never move/reposition
721 continue;
722
723 float minDistance = std::max(meleeRange, spellMinRange) - distanceToTarget + NOMINAL_MELEE_RANGE;
724 CAST_AI(SmartAI, me->AI())->DistanceYourself(std::min(minDistance, spellMaxRange));
725 continue;
726 }
727
728 if (distanceToTarget > spellMaxRange && isWithinLOSInMap)
729 {
730 failedSpellCast = true;
731
732 if (me->IsRooted()) // Rooted inhabit type, never move/reposition
733 continue;
734
736 {
737 CAST_AI(SmartAI, me->AI())->SetCombatMovement(true, false);
738 CAST_AI(SmartAI, me->AI())->SetCurrentRangeMode(
739 true, std::max(spellMaxRange - NOMINAL_MELEE_RANGE, 0.0f));
740 }
741
742 continue;
743 }
744 else if (distanceToTarget < spellMinRange || !(isWithinLOSInMap || isSpellIgnoreLOS))
745 {
746 failedSpellCast = true;
747
748 if (me->IsRooted()) // Rooted inhabit type, never move/reposition
749 continue;
750
751 CAST_AI(SmartAI, me->AI())->SetCurrentRangeMode(true, 0.f);
753 CAST_AI(SmartAI, me->AI())->SetCombatMovement(true, true);
754 continue;
755 }
756
757 TriggerCastFlags triggerFlags = TRIGGERED_NONE;
759 {
761 triggerFlags = TriggerCastFlags(e.action.cast.triggerFlags);
762 else
763 triggerFlags = TRIGGERED_FULL_MASK;
764 }
765
766 SpellCastResult result = me->CastSpell(target->ToUnit(), e.action.cast.spell, triggerFlags);
767 bool spellCastFailed = (result != SPELL_CAST_OK && result != SPELL_FAILED_SPELL_IN_PROGRESS);
768
770 {
771 if (result == SPELL_CAST_OK || result == SPELL_FAILED_SPELL_IN_PROGRESS)
772 {
773 CAST_AI(SmartAI, me->AI())->SetCombatMovement(false, true);
774 CAST_AI(SmartAI, me->AI())->SetCurrentRangeMode(
775 true, std::max(spellMaxRange - NOMINAL_MELEE_RANGE, 0.0f));
776 }
777 else if (result == SPELL_FAILED_OUT_OF_RANGE)
778 {
779 CAST_AI(SmartAI, me->AI())->SetCombatMovement(true, false);
780 CAST_AI(SmartAI, me->AI())->SetCurrentRangeMode(
781 true, std::max(spellMaxRange - NOMINAL_MELEE_RANGE, 0.0f));
782 }
783 else if (result != SPELL_FAILED_NOT_READY)
784 {
785 CAST_AI(SmartAI, me->AI())->SetCombatMovement(true, false);
786 CAST_AI(SmartAI, me->AI())->SetCurrentRangeMode(false, 0.f);
787 }
788 }
789
790 if (spellCastFailed)
791 failedSpellCast = true;
792 else
793 successfulSpellCast = true;
794
795 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_CAST: Unit {} casts spell {} on target {} with castflags {}",
796 me->GetGUID().ToString(), e.action.cast.spell, target->GetGUID().ToString(), e.action.cast.castFlags);
797 }
798 }
799
800 // If there is at least 1 failed cast and no successful casts at all, retry again on next loop
801 if (failedSpellCast && !successfulSpellCast)
802 {
803 RetryLater(e, true);
804 // Don't execute linked events
805 return;
806 }
807
808 break;
809 }
811 {
812 if (targets.empty())
813 break;
814
817
818 TriggerCastFlags triggerFlags = TRIGGERED_NONE;
820 {
822 {
823 triggerFlags = TriggerCastFlags(e.action.cast.triggerFlags);
824 }
825 else
826 {
827 triggerFlags = TRIGGERED_FULL_MASK;
828 }
829 }
830
831 for (WorldObject* target : targets)
832 {
833 Unit* uTarget = target->ToUnit();
834 if (!uTarget)
835 continue;
836
838 {
840 {
841 uTarget->InterruptNonMeleeSpells(false);
842 }
843
844 uTarget->CastSpell(uTarget, e.action.cast.spell, triggerFlags);
845 }
846 }
847 break;
848 }
850 {
851 // Can be used for area trigger cast
852 WorldObject* tempLastInvoker = GetLastInvoker(unit);
853 if (!tempLastInvoker)
854 break;
855
856 if (targets.empty())
857 break;
858
861
862 for (WorldObject* target : targets)
863 {
864 if (!IsUnit(target))
865 continue;
866
867 if (!IsUnit(tempLastInvoker))
868 continue;
869
870 if (!(e.action.cast.castFlags & SMARTCAST_AURA_NOT_PRESENT) || !target->ToUnit()->HasAura(e.action.cast.spell))
871 {
873 {
874 tempLastInvoker->ToUnit()->InterruptNonMeleeSpells(false);
875 }
876
877 TriggerCastFlags triggerFlags = TRIGGERED_NONE;
879 {
881 {
882 triggerFlags = TriggerCastFlags(e.action.cast.triggerFlags);
883 }
884 else
885 {
886 triggerFlags = TRIGGERED_FULL_MASK;
887 }
888 }
889
890 tempLastInvoker->ToUnit()->CastSpell(target->ToUnit(), e.action.cast.spell, triggerFlags);
891 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_INVOKER_CAST: Invoker {} casts spell {} on target {} with castflags {}",
892 tempLastInvoker->GetGUID().ToString(), e.action.cast.spell, target->GetGUID().ToString(), e.action.cast.castFlags);
893 }
894 else
895 {
896 LOG_DEBUG("scripts.ai", "Spell {} not cast because it has flag SMARTCAST_AURA_NOT_PRESENT and the target {} already has the aura",
897 e.action.cast.spell, target->GetGUID().ToString());
898 }
899 }
900 break;
901 }
903 {
904 for (WorldObject* target : targets)
905 {
906 if (IsUnit(target))
907 {
908 target->ToUnit()->AddAura(e.action.cast.spell, target->ToUnit());
909 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_ADD_AURA: Adding aura {} to unit {}",
910 e.action.cast.spell, target->GetGUID().ToString());
911 }
912 }
913 break;
914 }
916 {
917 for (WorldObject* target : targets)
918 {
919 if (IsGameObject(target))
920 {
921 GameObject* go = target->ToGameObject();
922
923 // Activate
925 {
927 }
928
930 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_ACTIVATE_GOBJECT. Gameobject {} activated", go->GetGUID().ToString());
931 }
932 }
933
934 break;
935 }
937 {
938 for (WorldObject* target : targets)
939 {
940 if (IsGameObject(target))
941 {
942 target->ToGameObject()->ResetDoorOrButton();
943 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_RESET_GOBJECT. Gameobject {} (entry: {}) reset",
944 target->GetGUID().ToString(), target->GetEntry());
945 }
946 }
947 break;
948 }
950 {
951 for (WorldObject* target : targets)
952 {
953 if (IsUnit(target))
954 {
955 target->ToUnit()->SetUInt32Value(UNIT_NPC_EMOTESTATE, e.action.emote.emote);
956 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_SET_EMOTE_STATE. Unit {} set emotestate to {}",
957 target->GetGUID().ToString(), e.action.emote.emote);
958 }
959 }
960 break;
961 }
963 {
964 for (WorldObject* target : targets)
965 {
966 if (IsUnit(target))
967 {
968 if (!e.action.unitFlag.type)
969 {
970 target->ToUnit()->SetFlag(UNIT_FIELD_FLAGS, e.action.unitFlag.flag);
971 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_SET_UNIT_FLAG. Unit {} added flag {} to UNIT_FIELD_FLAGS",
972 target->GetGUID().ToString(), e.action.unitFlag.flag);
973 }
974 else
975 {
976 target->ToUnit()->SetFlag(UNIT_FIELD_FLAGS_2, e.action.unitFlag.flag);
977 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_SET_UNIT_FLAG. Unit {} added flag {} to UNIT_FIELD_FLAGS_2",
978 target->GetGUID().ToString(), e.action.unitFlag.flag);
979 }
980 }
981 }
982 break;
983 }
985 {
986 for (WorldObject* target : targets)
987 {
988 if (IsUnit(target))
989 {
990 if (!e.action.unitFlag.type)
991 {
992 target->ToUnit()->RemoveFlag(UNIT_FIELD_FLAGS, e.action.unitFlag.flag);
993 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_REMOVE_UNIT_FLAG. Unit {} removed flag {} to UNIT_FIELD_FLAGS",
994 target->GetGUID().ToString(), e.action.unitFlag.flag);
995 }
996 else
997 {
998 target->ToUnit()->RemoveFlag(UNIT_FIELD_FLAGS_2, e.action.unitFlag.flag);
999 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction:: SMART_ACTION_REMOVE_UNIT_FLAG. Unit {} removed flag {} to UNIT_FIELD_FLAGS_2",
1000 target->GetGUID().ToString(), e.action.unitFlag.flag);
1001 }
1002 }
1003 }
1004 break;
1005 }
1007 {
1008 if (!IsSmart())
1009 break;
1010
1011 CAST_AI(SmartAI, me->AI())->SetAutoAttack(e.action.autoAttack.attack);
1012 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_AUTO_ATTACK: Creature: {} bool on = {}",
1014 break;
1015 }
1017 {
1018 if (!IsSmart())
1019 break;
1020
1021 bool move = e.action.combatMove.move;
1022 CAST_AI(SmartAI, me->AI())->SetCombatMovement(move, true);
1023 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_ALLOW_COMBAT_MOVEMENT: Creature {} bool on = {}",
1025 break;
1026 }
1028 {
1029 if (!GetBaseObject())
1030 break;
1031
1033 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_SET_EVENT_PHASE: Creature {} set event phase {}",
1034 GetBaseObject()->GetGUID().ToString(), e.action.setEventPhase.phase);
1035 break;
1036 }
1038 {
1039 if (!GetBaseObject())
1040 break;
1041
1044 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_INC_EVENT_PHASE: Creature {} inc event phase by {}, "
1045 "decrease by {}", GetBaseObject()->GetGUID().ToString(), e.action.incEventPhase.inc, e.action.incEventPhase.dec);
1046 break;
1047 }
1048 case SMART_ACTION_EVADE:
1049 {
1050 if (!GetBaseObject())
1051 break;
1052
1053 for (WorldObject* target : targets)
1054 if (IsCreature(target))
1055 if (target->ToCreature()->IsAIEnabled)
1056 target->ToCreature()->AI()->EnterEvadeMode();
1057
1058 break;
1059 }
1061 {
1062 // Xinef: do not allow to flee without control (stun, fear etc)
1064 break;
1065
1067 if (e.action.flee.withEmote)
1068 {
1070 sCreatureTextMgr->SendChatPacket(me, builder, CHAT_MSG_MONSTER_EMOTE);
1071 }
1072 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_FLEE_FOR_ASSIST: Creature {} DoFleeToGetAssistance", me->GetGUID().ToString());
1073 break;
1074 }
1076 {
1077 if (!me)
1078 break;
1079
1080 // Suppress evade during script-initiated combat stop so
1081 // JustExitedCombat does not trigger EnterEvadeMode.
1082 if (SmartAI* sai = CAST_AI(SmartAI, me->AI()))
1083 sai->SetSuppressEvade(true);
1084
1085 me->CombatStop(true);
1086
1087 if (SmartAI* sai = CAST_AI(SmartAI, me->AI()))
1088 sai->SetSuppressEvade(false);
1089
1090 break;
1091 }
1093 {
1094 for (WorldObject* target : targets)
1095 {
1096 if (!IsUnit(target))
1097 continue;
1098
1099 Unit* unitTarget = target->ToUnit();
1100 // If invoker was pet or charm
1101 Player* player = unitTarget->GetCharmerOrOwnerPlayerOrPlayerItself();
1102 if (player && GetBaseObject())
1103 {
1104 player->GroupEventHappens(e.action.quest.quest, GetBaseObject());
1105 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction: SMART_ACTION_CALL_GROUPEVENTHAPPENS: Player {}, group credit for quest {}",
1106 player->GetGUID().ToString(), e.action.quest.quest);
1107 }
1108
1109 // Special handling for vehicles
1110 if (Vehicle* vehicle = unitTarget->GetVehicleKit())
1111 {
1112 for (auto& Seat : vehicle->Seats)
1113 {
1114 if (Player* player = ObjectAccessor::GetPlayer(*unitTarget, Seat.second.Passenger.Guid))
1115 {
1116 player->GroupEventHappens(e.action.quest.quest, GetBaseObject());
1117 }
1118 }
1119 }
1120 }
1121 break;
1122 }
1124 {
1125 for (WorldObject* target : targets)
1126 {
1127 if (!IsUnit(target))
1128 continue;
1129
1130 if (e.action.removeAura.spell)
1131 {
1133 {
1134 if (Aura* aur = target->ToUnit()->GetAura(e.action.removeAura.spell))
1135 aur->ModCharges(-static_cast<int32>(e.action.removeAura.charges), AURA_REMOVE_BY_EXPIRE);
1136 }
1137 else
1138 target->ToUnit()->RemoveAurasDueToSpell(e.action.removeAura.spell);
1139 }
1140 else
1141 target->ToUnit()->RemoveAllAuras();
1142
1143 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction: SMART_ACTION_REMOVEAURASFROMSPELL: Unit {}, spell {}",
1144 target->GetGUID().ToString(), e.action.removeAura.spell);
1145 }
1146 break;
1147 }
1149 {
1150 if (!IsSmart())
1151 break;
1152
1154 {
1155 CAST_AI(SmartAI, me->AI())->StopFollow(false);
1156 break;
1157 }
1158
1159 for (WorldObject* target : targets)
1160 {
1161 if (IsUnit(target))
1162 {
1163 float angle = e.action.follow.angle > 6 ? (e.action.follow.angle * M_PI / 180.0f) : e.action.follow.angle;
1164 CAST_AI(SmartAI, me->AI())->SetFollow(target->ToUnit(), float(e.action.follow.dist) + 0.1f, angle, e.action.follow.credit, e.action.follow.entry, e.action.follow.creditType, e.action.follow.aliveState);
1165 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction: SMART_ACTION_FOLLOW: Creature {} following target {}",
1166 me->GetGUID().ToString(), target->GetGUID().ToString());
1167 break;
1168 }
1169 }
1170 break;
1171 }
1173 {
1174 if (!GetBaseObject())
1175 break;
1176
1177 std::vector<uint32> phases;
1178 std::copy_if(e.action.randomPhase.phases.begin(), e.action.randomPhase.phases.end(),
1179 std::back_inserter(phases), [](uint32 phase) { return phase != 0; });
1180
1182 SetPhase(phase);
1183 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction: SMART_ACTION_RANDOM_PHASE: Creature {} sets event phase to {}",
1184 GetBaseObject()->GetGUID().ToString(), phase);
1185 break;
1186 }
1188 {
1189 if (!GetBaseObject())
1190 break;
1191
1193 SetPhase(phase);
1194 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_RANDOM_PHASE_RANGE: Creature {} sets event phase to {}",
1195 GetBaseObject()->GetGUID().ToString(), phase);
1196 break;
1197 }
1199 {
1200 if (trigger && IsPlayer(unit))
1201 {
1203 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_CALL_KILLEDMONSTER: (trigger == true) Player {}, Killcredit: {}",
1205 }
1206 else if (e.target.type == SMART_TARGET_NONE || e.target.type == SMART_TARGET_SELF) // Loot recipient and his group members
1207 {
1208 if (!me)
1209 break;
1210
1211 if (Player* player = me->GetLootRecipient())
1212 {
1214 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_CALL_KILLEDMONSTER: Player {}, Killcredit: {}",
1216 }
1217 }
1218 else // Specific target type
1219 {
1220 for (WorldObject* target : targets)
1221 {
1222 if (!IsUnit(target))
1223 continue;
1224
1226 if (!player)
1227 continue;
1228
1230 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_CALL_KILLEDMONSTER: Player {}, Killcredit: {}",
1231 target->GetGUID().ToString(), e.action.killedMonster.creature);
1232 }
1233 }
1234 break;
1235 }
1237 {
1238 WorldObject* obj = GetBaseObject();
1239 if (!obj)
1240 obj = unit;
1241
1242 if (!obj)
1243 break;
1244
1245 InstanceScript* instance = obj->GetInstanceScript();
1246 if (!instance)
1247 {
1248 LOG_ERROR("scripts.ai.sai", "SmartScript: Event {} attempt to set instance data without instance script. EntryOrGuid {}", e.GetEventType(), e.entryOrGuid);
1249 break;
1250 }
1251
1252 switch (e.action.setInstanceData.type)
1253 {
1254 case 0:
1255 {
1257 LOG_DEBUG("scripts.ai.sai", "SmartScript::ProcessAction: SMART_ACTION_SET_INST_DATA: Field: {}, data: {}", e.action.setInstanceData.field, e.action.setInstanceData.data);
1258 } break;
1259 case 1:
1260 {
1262 LOG_DEBUG("scripts.ai.sai", "SmartScript::ProcessAction: SMART_ACTION_SET_INST_DATA: SetBossState BossId: {}, State: {} ({})", e.action.setInstanceData.field, e.action.setInstanceData.data, InstanceScript::GetBossStateName(e.action.setInstanceData.data));
1263 } break;
1264 default:
1265 {
1266 break;
1267 }
1268 }
1269 break;
1270 }
1272 {
1273 WorldObject* obj = GetBaseObject();
1274 if (!obj)
1275 obj = unit;
1276
1277 if (!obj)
1278 break;
1279
1280 InstanceScript* instance = obj->GetInstanceScript();
1281 if (!instance)
1282 {
1283 LOG_ERROR("sql.sql", "SmartScript: Event {} attempt to set instance data without instance script. EntryOrGuid {}", e.GetEventType(), e.entryOrGuid);
1284 break;
1285 }
1286
1287 if (targets.empty())
1288 break;
1289
1290 instance->SetGuidData(e.action.setInstanceData64.field, targets.front()->GetGUID());
1291 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction: SMART_ACTION_SET_INST_DATA64: Field: {}, data: {}",
1292 e.action.setInstanceData64.field, targets.front()->GetGUID().ToString());
1293 break;
1294 }
1296 {
1297 for (WorldObject* target : targets)
1298 if (IsCreature(target))
1299 target->ToCreature()->UpdateEntry(e.action.updateTemplate.creature, target->ToCreature()->GetCreatureData(), e.action.updateTemplate.updateLevel != 0);
1300 break;
1301 }
1302 case SMART_ACTION_DIE:
1303 {
1304 if (e.action.die.milliseconds)
1305 {
1306 if (me && !me->isDead())
1307 {
1309 {
1310 // We need to check again to see if we didn't die in the process.
1311 if (me && !me->isDead())
1312 {
1313 me->KillSelf();
1314 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_DIE: Creature {}", me->GetGUID().ToString());
1315 }
1317 }
1318 }
1319 else if (me && !me->isDead())
1320 {
1321 me->KillSelf();
1322 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_DIE: Creature {}", me->GetGUID().ToString());
1323 }
1324 break;
1325 }
1327 {
1328 if (targets.empty())
1329 break;
1330
1331 if (!me->GetMap()->IsDungeon())
1332 {
1333 ObjectVector units;
1334 GetWorldObjectsInDist(units, static_cast<float>(e.target.unitRange.maxDist));
1335
1336 if (!units.empty() && GetBaseObject())
1337 for (WorldObject* unit : units)
1338 if (IsPlayer(unit) && !unit->ToPlayer()->isDead())
1339 {
1340 me->EngageWithTarget(unit->ToPlayer());
1341 }
1342 }
1343 else
1344 {
1345 for (WorldObject* target : targets)
1346 {
1347 if (IsCreature(target))
1348 {
1349 target->ToCreature()->SetInCombatWithZone();
1350 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction: SMART_ACTION_SET_IN_COMBAT_WITH_ZONE: Creature {}, target: {}",
1351 me->GetGUID().ToString(), target->GetGUID().ToString());
1352 }
1353 }
1354 }
1355
1356 break;
1357 }
1359 {
1360 for (WorldObject* target : targets)
1361 {
1362 if (IsCreature(target))
1363 {
1364 target->ToCreature()->CallForHelp(float(e.action.callHelp.range));
1366 {
1368 sCreatureTextMgr->SendChatPacket(target, builder, CHAT_MSG_MONSTER_EMOTE);
1369 }
1370 LOG_DEBUG("scripts.ai", "SmartScript::ProcessAction: SMART_ACTION_CALL_FOR_HELP: Creature {}, target: {}",
1371 me->GetGUID().ToString(), target->GetGUID().ToString());
1372 }
1373 }
1374 break;
1375 }
1377 {
1378 if (me)
1379 {
1381 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_SET_SHEATH: Creature {}, State: {}",
1383 }
1384 break;
1385 }
1387 {
1388 for (WorldObject* target : targets)
1389 {
1391 {
1393 LOG_ERROR("sql.sql", "SmartScript: SMART_ACTION_FORCE_DESPAWN has removeObjectFromWorld set. delay and forceRespawnTimer ignored.");
1394
1395 if (Creature* creature = target->ToCreature())
1396 creature->AddObjectToRemoveList();
1397 else if (GameObject* go = target->ToGameObject())
1399 }
1400 else
1401 {
1402 Milliseconds despawnDelay(e.action.forceDespawn.delay);
1403
1404 // Wait at least one world update tick before despawn, so it doesn't break linked actions.
1405 if (despawnDelay <= 0ms)
1406 despawnDelay = 1ms;
1407
1408 Seconds forceRespawnTimer(e.action.forceDespawn.forceRespawnTimer);
1409 if (Creature* creature = target->ToCreature())
1410 creature->DespawnOrUnsummon(despawnDelay, forceRespawnTimer);
1411 else if (GameObject* go = target->ToGameObject())
1412 go->DespawnOrUnsummon(despawnDelay, forceRespawnTimer);
1413 }
1414 }
1415
1416 break;
1417 }
1419 {
1420 for (WorldObject* target : targets)
1421 {
1422 if (IsUnit(target))
1423 target->ToUnit()->SetPhaseMask(e.action.ingamePhaseMask.mask, true);
1424 else if (IsGameObject(target))
1425 target->ToGameObject()->SetPhaseMask(e.action.ingamePhaseMask.mask, true);
1426 }
1427 break;
1428 }
1430 {
1431 for (WorldObject* target : targets)
1432 {
1433 if (!IsUnit(target))
1434 continue;
1435
1437 {
1438 if (e.action.morphOrMount.creature > 0)
1439 {
1440 if (CreatureTemplate const* cInfo = sObjectMgr->GetCreatureTemplate(e.action.morphOrMount.creature))
1441 target->ToUnit()->Mount(ObjectMgr::ChooseDisplayId(cInfo)->CreatureDisplayID);
1442 }
1443 else
1444 target->ToUnit()->Mount(e.action.morphOrMount.model);
1445 }
1446 else
1447 target->ToUnit()->Dismount();
1448 }
1449 break;
1450 }
1452 {
1453 for (WorldObject* target : targets)
1454 {
1455 if (IsCreature(target))
1456 {
1457 SmartAI* ai = CAST_AI(SmartAI, target->ToCreature()->AI());
1458 if (!ai)
1459 continue;
1460
1461 if (e.action.invincHP.percent)
1462 ai->SetInvincibilityHpLevel(target->ToCreature()->CountPctFromMaxHealth(e.action.invincHP.percent));
1463 else
1465 }
1466 }
1467 break;
1468 }
1470 {
1471 for (WorldObject* target : targets)
1472 {
1473 if (Creature* cTarget = target->ToCreature())
1474 {
1475 CreatureAI* ai = cTarget->AI();
1476 // Make sure we check that the sender is either a creature or gameobject
1477 if (IsSmart(cTarget, true) && (me || go))
1478 {
1479 if (me)
1481 else
1482 ENSURE_AI(SmartAI, ai)->SetData(e.action.setData.field, e.action.setData.data, go);
1483 }
1484 else
1486 }
1487 else if (GameObject* oTarget = target->ToGameObject())
1488 {
1489 GameObjectAI* ai = oTarget->AI();
1490 // Make sure we check that the sender is either a creature or gameobject
1491 if (IsSmart(oTarget, true) && (me || go))
1492 {
1493 if (me)
1495 else
1497 }
1498 else
1500 }
1501 }
1502 break;
1503 }
1505 {
1506 WorldObject* invoker = me ? static_cast<WorldObject*>(me) : static_cast<WorldObject*>(go);
1507
1508 for (WorldObject* target : targets)
1509 {
1510 if (Creature* cTarget = target->ToCreature())
1511 {
1512 if (SmartAI* smartAI = CAST_AI(SmartAI, cTarget->AI()))
1513 {
1514 uint32 const newValue = smartAI->GetData(e.action.setData.field) + e.action.setData.data;
1515 smartAI->SetData(e.action.setData.field, newValue, invoker);
1516 }
1517 else
1518 LOG_ERROR("sql.sql", "SmartScript: Action target for SMART_ACTION_INC_DATA is not using SmartAI, skipping");
1519 }
1520 else if (GameObject* oTarget = target->ToGameObject())
1521 {
1522 if (SmartGameObjectAI* smartGOAI = CAST_AI(SmartGameObjectAI, oTarget->AI()))
1523 {
1524 uint32 const newValue = smartGOAI->GetData(e.action.setData.field) + e.action.setData.data;
1525 smartGOAI->SetData(e.action.setData.field, newValue, invoker);
1526 }
1527 else
1528 LOG_ERROR("sql.sql", "SmartScript: Action target for SMART_ACTION_INC_DATA is not using SmartGameObjectAI, skipping");
1529 }
1530 }
1531 break;
1532 }
1534 {
1535 for (WorldObject* target : targets)
1536 {
1537 if (IsCreature(target))
1538 {
1539 float x, y, z;
1540 target->ToCreature()->GetClosePoint(x, y, z, target->ToCreature()->GetObjectSize() / 3, (float)e.action.moveRandom.distance);
1541 target->ToCreature()->GetMotionMaster()->MovePoint(SMART_RANDOM_POINT, x, y, z);
1542 }
1543 }
1544 break;
1545 }
1547 {
1548 if (!me)
1549 break;
1550
1552 break;
1553 }
1555 {
1556 for (WorldObject* target : targets)
1557 if (IsUnit(target))
1558 target->ToUnit()->SetVisible(e.action.visibility.state);
1559
1560 break;
1561 }
1563 {
1564 for (WorldObject* target : targets)
1565 target->setActive(e.action.setActive.state);
1566 break;
1567 }
1569 {
1570 if (!me)
1571 break;
1572
1573 if (targets.empty())
1574 break;
1575
1576 // attack random target
1577 if (Unit* target = Acore::Containers::SelectRandomContainerElement(targets)->ToUnit())
1578 me->AI()->AttackStart(target);
1579 break;
1580 }
1582 {
1583 for (WorldObject* target : targets)
1584 if (Unit* unitTarget = target->ToUnit())
1585 unitTarget->AttackStop();
1586 break;
1587 }
1589 {
1591 bool preferUnit = flags.HasFlag(SmartActionSummonCreatureFlags::PreferUnit);
1592 WorldObject* summoner = preferUnit ? unit : Coalesce<WorldObject>(GetBaseObject(), unit);
1593 if (!summoner)
1594 break;
1595
1596 bool personalSpawn = flags.HasFlag(SmartActionSummonCreatureFlags::PersonalSpawn);
1597
1599 {
1600 float range = (float)e.target.randomPoint.range;
1601 Position randomPoint;
1602 Position srcPos = { e.target.x, e.target.y, e.target.z, e.target.o };
1603 for (uint32 i = 0; i < e.target.randomPoint.amount; i++)
1604 {
1605 if (e.target.randomPoint.self > 0)
1606 randomPoint = me->GetRandomPoint(me->GetPosition(), range);
1607 else
1608 randomPoint = me->GetRandomPoint(srcPos, range);
1609 if (Creature* summon = summoner->SummonCreature(e.action.summonCreature.creature, randomPoint, (TempSummonType)e.action.summonCreature.type, e.action.summonCreature.duration, 0, nullptr, personalSpawn))
1610 {
1611 if (unit && e.action.summonCreature.attackInvoker)
1612 summon->AI()->AttackStart(unit);
1614 summon->AI()->AttackStart(me);
1615 }
1616 }
1617 break;
1618 }
1619
1620 float x, y, z, o;
1621 for (WorldObject* target : targets)
1622 {
1623 target->GetPosition(x, y, z, o);
1624 x += e.target.x;
1625 y += e.target.y;
1626 z += e.target.z;
1627 o += e.target.o;
1628 if (Creature* summon = summoner->SummonCreature(e.action.summonCreature.creature, x, y, z, o, (TempSummonType)e.action.summonCreature.type, e.action.summonCreature.duration, nullptr, personalSpawn))
1629 {
1630 if (e.action.summonCreature.attackInvoker == 2) // pussywizard: proper attackInvoker implementation
1631 summon->AI()->AttackStart(unit);
1633 summon->AI()->AttackStart(target->ToUnit());
1635 summon->AI()->AttackStart(me);
1636 }
1637 }
1638
1640 break;
1641
1643 {
1644 if (unit && e.action.summonCreature.attackInvoker)
1645 summon->AI()->AttackStart(unit);
1647 summon->AI()->AttackStart(me);
1648 }
1649 break;
1650 }
1652 {
1653 if (!GetBaseObject())
1654 break;
1655
1656 if (!targets.empty())
1657 {
1658 float x, y, z, o;
1659 for (WorldObject* target : targets)
1660 {
1661 // xinef: allow gameobjects to summon gameobjects!
1662 //if (!IsUnit((*itr)))
1663 // continue;
1664
1665 target->GetPosition(x, y, z, o);
1666 x += e.target.x;
1667 y += e.target.y;
1668 z += e.target.z;
1669 o += e.target.o;
1672 else
1673 target->SummonGameObject(e.action.summonGO.entry, GetBaseObject()->GetPositionX(), GetBaseObject()->GetPositionY(), GetBaseObject()->GetPositionZ(), GetBaseObject()->GetOrientation(), 0, 0, 0, 0, e.action.summonGO.despawnTime);
1674 }
1675 }
1676
1678 break;
1679
1681 break;
1682 }
1684 {
1685 for (WorldObject* target : targets)
1686 {
1687 if (!IsUnit(target))
1688 continue;
1689
1690 Unit::Kill(target->ToUnit(), target->ToUnit());
1691 }
1692
1693 break;
1694 }
1696 {
1697 InstallTemplate(e);
1698 break;
1699 }
1701 {
1702 for (WorldObject* target : targets)
1703 {
1704 if (!IsPlayer(target))
1705 continue;
1706
1707 target->ToPlayer()->AddItem(e.action.item.entry, e.action.item.count);
1708 }
1709 break;
1710 }
1712 {
1713 for (WorldObject* target : targets)
1714 {
1715 if (!IsPlayer(target))
1716 continue;
1717
1718 target->ToPlayer()->DestroyItemCount(e.action.item.entry, e.action.item.count, true);
1719 }
1720 break;
1721 }
1723 {
1725 break;
1726 }
1728 {
1729 for (WorldObject* target : targets)
1730 {
1731 if (IsPlayer(target))
1732 target->ToPlayer()->TeleportTo(e.action.teleport.mapID, e.target.x, e.target.y, e.target.z, e.target.o);
1733 else if (IsCreature(target))
1734 target->ToCreature()->NearTeleportTo(e.target.x, e.target.y, e.target.z, e.target.o);
1735 }
1736 break;
1737 }
1739 {
1740 if (!IsSmart())
1741 break;
1742
1743 CAST_AI(SmartAI, me->AI())->SetFly(e.action.setFly.fly);
1744 // Xinef: Set speed if any
1745 if (e.action.setFly.speed)
1746 me->SetSpeed(MOVE_RUN, float(e.action.setFly.speed / 100.0f), true);
1747
1748 // Xinef: this wil be executed only if state is different
1750 break;
1751 }
1753 {
1754 for (WorldObject* target : targets)
1755 {
1756 if (IsCreature(target))
1757 {
1758 target->ToCreature()->SetWalk(e.action.setRun.run ? false : true);
1759 }
1760 }
1761
1762 break;
1763 }
1765 {
1766 if (!IsSmart())
1767 break;
1768
1769 CAST_AI(SmartAI, me->AI())->SetSwim(e.action.setSwim.swim);
1770 break;
1771 }
1773 {
1774 if (!targets.empty())
1775 {
1776 for (WorldObject* target : targets)
1777 {
1778 if (IsCreature(target))
1779 {
1780 if (SmartAI* ai = CAST_AI(SmartAI, target->ToCreature()->AI()))
1782 else
1783 LOG_ERROR("sql.sql", "SmartScript: Action target for SMART_ACTION_SET_COUNTER is not using SmartAI, skipping");
1784 }
1785 else if (IsGameObject(target))
1786 {
1787 if (SmartGameObjectAI* ai = CAST_AI(SmartGameObjectAI, target->ToGameObject()->AI()))
1789 else
1790 LOG_ERROR("sql.sql", "SmartScript: Action target for SMART_ACTION_SET_COUNTER is not using SmartGameObjectAI, skipping");
1791 }
1792 }
1793 }
1794 else
1796 break;
1797 }
1799 {
1800 if (!IsSmart())
1801 break;
1802
1803 ForcedMovement forcedMovement = static_cast<ForcedMovement>(e.action.wpStart.forcedMovement);
1804 uint32 entry = e.action.wpStart.pathID;
1805 bool repeat = e.action.wpStart.repeat != 0;
1806
1807 for (WorldObject* target : targets)
1808 {
1809 if (IsPlayer(target))
1810 {
1812 break;
1813 }
1814 }
1815
1817 CAST_AI(SmartAI, me->AI())->StartPath(forcedMovement, entry, repeat, unit);
1818
1819 uint32 quest = e.action.wpStart.quest;
1820 uint32 DespawnTime = e.action.wpStart.despawnTime;
1821 CAST_AI(SmartAI, me->AI())->mEscortQuestID = quest;
1822 CAST_AI(SmartAI, me->AI())->SetDespawnTime(DespawnTime);
1823 break;
1824 }
1826 {
1827 if (!IsSmart())
1828 break;
1829
1830 uint32 delay = e.action.wpPause.delay;
1831 CAST_AI(SmartAI, me->AI())->PausePath(delay, e.GetEventType() == SMART_EVENT_ESCORT_REACHED ? false : true);
1832 break;
1833 }
1835 {
1836 if (!IsSmart())
1837 break;
1838
1839 uint32 DespawnTime = e.action.wpStop.despawnTime;
1840 uint32 quest = e.action.wpStop.quest;
1841 bool fail = e.action.wpStop.fail;
1842 CAST_AI(SmartAI, me->AI())->StopPath(DespawnTime, quest, fail);
1843 break;
1844 }
1846 {
1847 if (!IsSmart())
1848 break;
1849
1850 CAST_AI(SmartAI, me->AI())->SetWPPauseTimer(0);
1851 break;
1852 }
1854 {
1855 if (!me)
1856 break;
1857
1858 if (e.action.orientation.random > 0)
1859 {
1860 float randomOri = frand(0.0f, 2 * M_PI);
1861 me->SetFacingTo(randomOri);
1863 me->SetOrientation(randomOri);
1864 break;
1865 }
1866
1868 {
1869 float turnOri = me->GetOrientation() + (static_cast<float>(e.action.orientation.turnAngle) * M_PI / 180.0f);
1870 me->SetFacingTo(turnOri);
1872 me->SetOrientation(turnOri);
1873 break;
1874 }
1875
1877 {
1881 }
1882 else if (e.GetTargetType() == SMART_TARGET_POSITION)
1883 {
1884 me->SetFacingTo(e.target.o);
1887 }
1888 else if (!targets.empty())
1889 {
1890 me->SetFacingToObject(*targets.begin());
1892 me->SetInFront(*targets.begin());
1893 }
1894
1895 break;
1896 }
1898 {
1899 for (WorldObject* target : targets)
1900 {
1901 if (!IsPlayer(target))
1902 continue;
1903
1904 target->ToPlayer()->SendMovieStart(e.action.movie.entry);
1905 }
1906 break;
1907 }
1909 {
1910 if (!IsSmart())
1911 break;
1912
1913 WorldObject* target = nullptr;
1914
1916
1917 switch (e.GetTargetType())
1918 {
1920 {
1921 G3D::Vector3 dest(e.target.x, e.target.y, e.target.z);
1923 if (TransportBase* trans = me->GetDirectTransport())
1924 trans->CalculatePassengerPosition(dest.x, dest.y, dest.z);
1925
1927 0.f, e.target.o, true, isForced, isControlled ? MOTION_SLOT_CONTROLLED : MOTION_SLOT_ACTIVE);
1928
1929 break;
1930 }
1932 {
1933 if (me)
1934 {
1935 float range = (float)e.target.randomPoint.range;
1936 Position srcPos = { e.target.x, e.target.y, e.target.z, e.target.o };
1937 Position randomPoint = me->GetRandomPoint(srcPos, range);
1940 randomPoint.m_positionX,
1941 randomPoint.m_positionY,
1942 randomPoint.m_positionZ,
1944 0.f, 0.f, true, isForced, isControlled ? MOTION_SLOT_CONTROLLED : MOTION_SLOT_ACTIVE
1945 );
1946
1947 }
1948
1949 break;
1950 }
1951 // Can use target floats as offset
1952 default:
1953 {
1954 // we want to move to random element
1955 if (targets.empty())
1956 return;
1957 else
1959
1960 float x, y, z;
1961 target->GetPosition(x, y, z);
1962
1964 target->GetNearPoint(me, x, y, z, target->GetCombatReach() + e.action.moveToPos.ContactDistance, 0, target->GetAngle(me));
1965 else if (e.action.moveToPos.ContactDistance)
1966 target->GetNearPoint(me, x, y, z, e.action.moveToPos.ContactDistance, 0, target->GetAngle(me));
1967
1969 0.f, 0.f, true, isForced, isControlled ? MOTION_SLOT_CONTROLLED : MOTION_SLOT_ACTIVE);
1970
1971 break;
1972 }
1973 }
1974
1975 break;
1976 }
1978 {
1979 for (WorldObject* target : targets)
1980 {
1981 if (IsCreature(target))
1982 {
1984
1985 Creature* ctarget = target->ToCreature();
1987 0.f, 0.f, true, isForced, isControlled ? MOTION_SLOT_CONTROLLED : MOTION_SLOT_ACTIVE);
1988 }
1989 }
1990
1991 break;
1992 }
1994 {
1995 for (WorldObject* target : targets)
1996 {
1997 if (IsCreature(target))
1998 target->ToCreature()->Respawn();
1999 else if (IsGameObject(target))
2000 {
2001 // do not modify respawndelay of already spawned gameobjects
2002 if (target->ToGameObject()->isSpawnedByDefault())
2003 target->ToGameObject()->Respawn();
2004 else
2006 }
2007 }
2008 break;
2009 }
2011 {
2012 for (WorldObject* target : targets)
2013 if (IsPlayer(target))
2014 target->ToPlayer()->PlayerTalkClass->SendCloseGossip();
2015 break;
2016 }
2017 case SMART_ACTION_EQUIP:
2018 {
2019 for (WorldObject* target : targets)
2020 {
2021 if (Creature* npc = target->ToCreature())
2022 {
2023 std::array<uint32, MAX_EQUIPMENT_ITEMS> slot;
2024 if (int8 equipId = static_cast<int8>(e.action.equip.entry))
2025 {
2026 EquipmentInfo const* eInfo = sObjectMgr->GetEquipmentInfo(npc->GetEntry(), equipId);
2027 if (!eInfo)
2028 {
2029 LOG_ERROR("sql.sql", "SmartScript: SMART_ACTION_EQUIP uses non-existent equipment info id {} for creature {}", equipId, npc->GetEntry());
2030 break;
2031 }
2032
2033 npc->SetCurrentEquipmentId(equipId);
2034
2035 std::copy(std::begin(eInfo->ItemEntry), std::end(eInfo->ItemEntry), std::begin(slot));
2036 }
2037 else
2038 std::copy(std::begin(e.action.equip.slots), std::end(e.action.equip.slots), std::begin(slot));
2039
2040 for (uint32 i = 0; i < MAX_EQUIPMENT_ITEMS; ++i)
2041 if (!e.action.equip.mask || (e.action.equip.mask & (1 << i)))
2042 npc->SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_ID + i, slot[i]);
2043 }
2044 }
2045 break;
2046 }
2048 {
2049 SmartEvent ne = SmartEvent();
2052 if (!ne.event_chance) ne.event_chance = 100;
2053
2058
2059 ne.event_flags = 0;
2062
2063 SmartAction ac = SmartAction();
2066
2068 ev.event = ne;
2069 ev.event_id = e.action.timeEvent.id;
2070 ev.target = e.target;
2071 ev.action = ac;
2072 InitTimer(ev);
2073 mStoredEvents.push_back(ev);
2074 break;
2075 }
2078
2079 // xinef: remove this event if not repeatable
2081 mRemIDs.push_back(e.action.timeEvent.id);
2082 break;
2084 mRemIDs.push_back(e.action.timeEvent.id);
2085 break;
2087 {
2088 for (WorldObject* target : targets)
2089 {
2090 if (IsCreature(target))
2091 {
2092 if (!meOrigGUID)
2094 if (!goOrigGUID)
2096 go = nullptr;
2097 me = target->ToCreature();
2098 break;
2099 }
2100 else if (IsGameObject(target))
2101 {
2102 if (!meOrigGUID)
2104 if (!goOrigGUID)
2106 go = target->ToGameObject();
2107 me = nullptr;
2108 break;
2109 }
2110 }
2111
2112 break;
2113 }
2116 break;
2118 OnReset();
2119 break;
2121 {
2122 if (!IsSmart())
2123 break;
2124
2125 float attackDistance = float(e.action.setRangedMovement.distance);
2126 float attackAngle = float(e.action.setRangedMovement.angle) / 180.0f * float(M_PI);
2127
2128 for (WorldObject* target : targets)
2129 if (Creature* creature = target->ToCreature())
2130 if (IsSmart(creature) && creature->GetVictim())
2131 if (!creature->HasUnitState(UNIT_STATE_NO_COMBAT_MOVEMENT))
2132 creature->GetMotionMaster()->MoveChase(creature->GetVictim(), attackDistance, attackAngle);
2133
2134 break;
2135 }
2137 {
2139 {
2140 LOG_ERROR("sql.sql", "SmartScript: Entry {} SourceType {} Event {} Action {} is using TARGET_NONE(0) for Script9 target. Please correct target_type in database.", e.entryOrGuid, e.GetScriptType(), e.GetEventType(), e.GetActionType());
2141 break;
2142 }
2143
2144 for (WorldObject* target : targets)
2145 {
2146 if (Creature* creature = target->ToCreature())
2147 {
2148 if (IsSmart(creature))
2149 CAST_AI(SmartAI, creature->AI())->SetScript9(e, e.action.timedActionList.id, GetLastInvoker());
2150 }
2151 else if (GameObject* go = target->ToGameObject())
2152 {
2153 if (IsSmart(go))
2155 }
2156 }
2157 break;
2158 }
2160 {
2161 for (WorldObject* target : targets)
2162 if (IsCreature(target))
2163 target->ToUnit()->ReplaceAllNpcFlags(NPCFlags(e.action.unitFlag.flag));
2164 break;
2165 }
2167 {
2168 for (WorldObject* target : targets)
2169 if (IsCreature(target))
2170 target->ToUnit()->SetNpcFlag(NPCFlags(e.action.unitFlag.flag));
2171 break;
2172 }
2174 {
2175 for (WorldObject* target : targets)
2176 if (IsCreature(target))
2177 target->ToUnit()->RemoveNpcFlag(NPCFlags(e.action.unitFlag.flag));
2178 break;
2179 }
2181 {
2182 if (targets.empty())
2183 break;
2184
2185 ObjectVector casters;
2187
2188 for (WorldObject* caster : casters)
2189 {
2190 if (!IsUnit(caster))
2191 continue;
2192
2193 Unit* casterUnit = caster->ToUnit();
2194
2195 bool interruptedSpell = false;
2196
2197 for (WorldObject* target : targets)
2198 {
2199 if (!IsUnit(target))
2200 continue;
2201
2203 {
2204 if (!interruptedSpell && e.action.crossCast.flags & SMARTCAST_INTERRUPT_PREVIOUS)
2205 {
2206 casterUnit->InterruptNonMeleeSpells(false);
2207 interruptedSpell = true;
2208 }
2209
2210 casterUnit->CastSpell(target->ToUnit(), e.action.crossCast.spell, (e.action.crossCast.flags & SMARTCAST_TRIGGERED) != 0);
2211 }
2212 else
2213 LOG_DEBUG("scripts.ai", "Spell {} not cast because it has flag SMARTCAST_AURA_NOT_PRESENT and the target ({}) already has the aura", e.action.crossCast.spell, target->GetGUID().ToString());
2214 }
2215 }
2216 break;
2217 }
2219 {
2220 std::vector<uint32> actionLists;
2222 std::back_inserter(actionLists), [](uint32 actionList) { return actionList != 0; });
2223
2226 {
2227 LOG_ERROR("sql.sql", "SmartScript: Entry {} SourceType {} Event {} Action {} is using TARGET_NONE(0) for Script9 target. Please correct target_type in database.", e.entryOrGuid, e.GetScriptType(), e.GetEventType(), e.GetActionType());
2228 break;
2229 }
2230
2231 for (WorldObject* target : targets)
2232 {
2233 if (Creature* creature = target->ToCreature())
2234 {
2235 if (IsSmart(creature))
2236 CAST_AI(SmartAI, creature->AI())->SetScript9(e, id, GetLastInvoker());
2237 }
2238 else if (GameObject* go = target->ToGameObject())
2239 {
2240 if (IsSmart(go))
2241 CAST_AI(SmartGameObjectAI, go->AI())->SetScript9(e, id, GetLastInvoker());
2242 }
2243 }
2244 break;
2245 }
2247 {
2250 {
2251 LOG_ERROR("sql.sql", "SmartScript: Entry {} SourceType {} Event {} Action {} is using TARGET_NONE(0) for Script9 target. Please correct target_type in database.", e.entryOrGuid, e.GetScriptType(), e.GetEventType(), e.GetActionType());
2252 break;
2253 }
2254
2255 for (WorldObject* target : targets)
2256 {
2257 if (Creature* creature = target->ToCreature())
2258 {
2259 if (IsSmart(creature))
2260 CAST_AI(SmartAI, creature->AI())->SetScript9(e, id, GetLastInvoker());
2261 }
2262 else if (GameObject* go = target->ToGameObject())
2263 {
2264 if (IsSmart(go))
2265 CAST_AI(SmartGameObjectAI, go->AI())->SetScript9(e, id, GetLastInvoker());
2266 }
2267 }
2268 break;
2269 }
2271 {
2272 for (WorldObject* target : targets)
2273 if (IsPlayer(target))
2274 target->ToPlayer()->ActivateTaxiPathTo(e.action.taxi.id);
2275 break;
2276 }
2278 {
2279 bool foundTarget = false;
2280
2281 for (WorldObject* target : targets)
2282 {
2283 if (IsCreature((target)))
2284 {
2285 foundTarget = true;
2286
2289 else
2290 target->ToCreature()->GetMotionMaster()->MoveIdle();
2291 }
2292 }
2293
2294 if (!foundTarget && me && IsCreature(me) && me->IsAlive())
2295 {
2298 else
2300 }
2301 break;
2302 }
2304 {
2305 for (WorldObject* target : targets)
2306 if (IsUnit(target))
2307 target->ToUnit()->SetByteFlag(UNIT_FIELD_BYTES_1, e.action.setunitByte.type, e.action.setunitByte.byte1);
2308 break;
2309 }
2311 {
2312 for (WorldObject* target : targets)
2313 if (IsUnit(target))
2314 target->ToUnit()->RemoveByteFlag(UNIT_FIELD_BYTES_1, e.action.delunitByte.type, e.action.delunitByte.byte1);
2315 break;
2316 }
2318 {
2319 for (WorldObject* target : targets)
2320 if (IsUnit(target))
2321 target->ToUnit()->InterruptNonMeleeSpells(e.action.interruptSpellCasting.withDelayed != 0, e.action.interruptSpellCasting.spell_id, e.action.interruptSpellCasting.withInstant != 0);
2322 break;
2323 }
2325 {
2326 for (WorldObject* target : targets)
2327 if (IsGameObject(target))
2328 target->ToGameObject()->SendCustomAnim(e.action.sendGoCustomAnim.anim);
2329 break;
2330 }
2332 {
2333 for (WorldObject* target : targets)
2334 if (IsUnit(target))
2335 target->ToUnit()->SetUInt32Value(UNIT_DYNAMIC_FLAGS, e.action.unitFlag.flag);
2336 break;
2337 }
2339 {
2340 for (WorldObject* target : targets)
2341 if (IsUnit(target))
2342 target->ToUnit()->SetFlag(UNIT_DYNAMIC_FLAGS, e.action.unitFlag.flag);
2343 break;
2344 }
2346 {
2347 for (WorldObject* target : targets)
2348 if (IsUnit(target))
2349 target->ToUnit()->RemoveFlag(UNIT_DYNAMIC_FLAGS, e.action.unitFlag.flag);
2350 break;
2351 }
2353 {
2355 {
2356 if (me)
2357 {
2358 float range = (float)e.target.randomPoint.range;
2359 Position srcPos = { e.target.x, e.target.y, e.target.z, e.target.o };
2360 Position randomPoint = me->GetRandomPoint(srcPos, range);
2361 me->GetMotionMaster()->MoveJump(randomPoint, (float)e.action.jump.speedxy, (float)e.action.jump.speedz);
2362 }
2363
2364 break;
2365 }
2366
2367 if (targets.empty())
2368 break;
2369
2370 // xinef: my implementation
2371 if (e.action.jump.selfJump)
2372 {
2374 if (me)
2375 me->GetMotionMaster()->MoveJump(target->GetPositionX() + e.target.x, target->GetPositionY() + e.target.y, target->GetPositionZ() + e.target.z, (float)e.action.jump.speedxy, (float)e.action.jump.speedz);
2376 }
2377 else
2378 {
2379 for (WorldObject* target : targets)
2380 if (WorldObject* obj = (target))
2381 {
2382 if (Creature* creature = obj->ToCreature())
2383 creature->GetMotionMaster()->MoveJump(e.target.x, e.target.y, e.target.z, (float)e.action.jump.speedxy, (float)e.action.jump.speedz);
2384 }
2385 }
2386
2387 break;
2388 }
2390 {
2391 for (WorldObject* target : targets)
2392 if (IsGameObject(target))
2393 target->ToGameObject()->SetLootState((LootState)e.action.setGoLootState.state);
2394 break;
2395 }
2397 {
2398 for (WorldObject* target : targets)
2399 if (IsGameObject(target))
2400 target->ToGameObject()->SetGoState((GOState)e.action.goState.state);
2401 break;
2402 }
2404 {
2405 WorldObject* ref = GetBaseObject();
2406
2407 if (!ref)
2408 ref = unit;
2409
2410 if (!ref)
2411 break;
2412
2413 ObjectVector const* storedTargets = GetStoredTargetVector(e.action.sendTargetToTarget.id, *ref);
2414 if (!storedTargets)
2415 break;
2416
2417 for (WorldObject* target : targets)
2418 {
2419 if (IsCreature(target))
2420 {
2421 if (SmartAI* ai = CAST_AI(SmartAI, target->ToCreature()->AI()))
2422 ai->GetScript()->StoreTargetList(ObjectVector(*storedTargets), e.action.sendTargetToTarget.id); // store a copy of target list
2423 else
2424 LOG_ERROR("sql.sql", "SmartScript: Action target for SMART_ACTION_SEND_TARGET_TO_TARGET is not using SmartAI, skipping");
2425 }
2426 else if (IsGameObject(target))
2427 {
2429 ai->GetScript()->StoreTargetList(ObjectVector(*storedTargets), e.action.sendTargetToTarget.id); // store a copy of target list
2430 else
2431 LOG_ERROR("sql.sql", "SmartScript: Action target for SMART_ACTION_SEND_TARGET_TO_TARGET is not using SmartGameObjectAI, skipping");
2432 }
2433 }
2434 break;
2435 }
2437 {
2438 if (!GetBaseObject())
2439 break;
2440
2441 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction:: SMART_ACTION_SEND_GOSSIP_MENU: gossipMenuId {}, gossipNpcTextId {}",
2443
2444 for (WorldObject* target : targets)
2445 if (Player* player = target->ToPlayer())
2446 {
2449 else
2450 ClearGossipMenuFor(player);
2451
2453 }
2454
2455 break;
2456 }
2458 {
2459 if (!targets.empty())
2460 {
2461 float x, y, z, o;
2462 for (WorldObject* target : targets)
2463 if (IsCreature(target))
2464 {
2466 {
2467 target->ToCreature()->GetRespawnPosition(x, y, z, &o);
2468 target->ToCreature()->SetHomePosition(x, y, z, o);
2469 }
2470 else
2471 target->ToCreature()->SetHomePosition(target->GetPositionX(), target->GetPositionY(), target->GetPositionZ(), target->GetOrientation());
2472 }
2473 }
2474 else if (me && e.GetTargetType() == SMART_TARGET_POSITION)
2475 {
2477 {
2478 float x, y, z, o;
2479 me->GetRespawnPosition(x, y, z, &o);
2480 me->SetHomePosition(x, y, z, o);
2481 }
2482 else
2484 }
2485 break;
2486 }
2488 {
2489 for (WorldObject* target : targets)
2490 if (IsCreature(target))
2491 target->ToCreature()->SetRegeneratingHealth(e.action.setHealthRegen.regenHealth);
2492
2493 break;
2494 }
2496 {
2497 for (WorldObject* target : targets)
2498 if (IsCreature(target))
2499 target->ToCreature()->SetControlled(e.action.setRoot.root != 0, UNIT_STATE_ROOT);
2500 break;
2501 }
2503 {
2504 for (WorldObject* target : targets)
2505 if (IsGameObject(target))
2506 target->ToGameObject()->SetUInt32Value(GAMEOBJECT_FLAGS, e.action.goFlag.flag);
2507 break;
2508 }
2510 {
2511 for (WorldObject* target : targets)
2512 if (IsGameObject(target))
2513 target->ToGameObject()->SetFlag(GAMEOBJECT_FLAGS, e.action.goFlag.flag);
2514 break;
2515 }
2517 {
2518 for (WorldObject* target : targets)
2519 if (IsGameObject(target))
2520 target->ToGameObject()->RemoveFlag(GAMEOBJECT_FLAGS, e.action.goFlag.flag);
2521 break;
2522 }
2524 {
2525 std::list<TempSummon*> summonList;
2527
2528 for (std::list<TempSummon*>::const_iterator itr = summonList.begin(); itr != summonList.end(); ++itr)
2529 {
2530 if (unit && e.action.creatureGroup.attackInvoker)
2531 (*itr)->AI()->AttackStart(unit);
2533 (*itr)->AI()->AttackStart(me);
2534 }
2535
2536 break;
2537 }
2539 {
2540 for (WorldObject* target : targets)
2541 if (IsUnit(target))
2542 target->ToUnit()->SetPower(Powers(e.action.power.powerType), e.action.power.newPower);
2543 break;
2544 }
2546 {
2547 for (WorldObject* target : targets)
2548 if (IsUnit(target))
2549 target->ToUnit()->SetPower(Powers(e.action.power.powerType), target->ToUnit()->GetPower(Powers(e.action.power.powerType)) + e.action.power.newPower);
2550 break;
2551 }
2553 {
2554 for (WorldObject* target : targets)
2555 if (IsUnit(target))
2556 target->ToUnit()->SetPower(Powers(e.action.power.powerType), target->ToUnit()->GetPower(Powers(e.action.power.powerType)) - e.action.power.newPower);
2557 break;
2558 }
2560 {
2561 uint32 eventId = e.action.gameEventStop.id;
2562 if (!sGameEventMgr->IsActiveEvent(eventId))
2563 {
2564 LOG_ERROR("scripts.ai.sai", "SmartScript::ProcessAction: At case SMART_ACTION_GAME_EVENT_STOP, inactive event (id: {})", eventId);
2565 break;
2566 }
2567 sGameEventMgr->StopEvent(eventId, true);
2568 break;
2569 }
2571 {
2572 uint32 eventId = e.action.gameEventStart.id;
2573 if (sGameEventMgr->IsActiveEvent(eventId))
2574 {
2575 LOG_ERROR("scripts.ai.sai", "SmartScript::ProcessAction: At case SMART_ACTION_GAME_EVENT_START, already activated event (id: {})", eventId);
2576 break;
2577 }
2578 sGameEventMgr->StartEvent(eventId, true);
2579 break;
2580 }
2582 {
2583 PathSource pathSource = static_cast<PathSource>(e.action.startClosestWaypoint.pathSource);
2584
2585 if (pathSource != PathSource::WAYPOINT_MGR && pathSource != PathSource::SMART_WAYPOINT_MGR)
2586 {
2587 LOG_ERROR("scripts.ai.sai", "SmartScript::ProcessAction: SMART_ACTION_START_CLOSEST_WAYPOINT: Invalid PathSource {} for entryOrGuid {} source_type {} event_id {} link {}",
2588 static_cast<uint32>(pathSource), e.entryOrGuid, e.source_type, e.event_id, e.link);
2589 break;
2590 }
2591
2592 float distanceToClosest = std::numeric_limits<float>::max();
2593 uint32 closestWpId = 0;
2594
2595 for (WorldObject* target : targets)
2596 {
2597 if (Creature* creature = target->ToCreature())
2598 {
2599 if (IsSmart(creature))
2600 {
2601 for (uint32 pathId = e.action.startClosestWaypoint.pathId1; pathId <= e.action.startClosestWaypoint.pathId2; ++pathId)
2602 {
2603 WaypointPath const* path = nullptr;
2604
2605 switch (pathSource)
2606 {
2608 path = sSmartWaypointMgr->GetPath(pathId);
2609 break;
2611 path = sWaypointMgr->GetPath(pathId);
2612 break;
2613 }
2614
2615 if (!path || path->Nodes.empty())
2616 continue;
2617
2618 {
2619 WaypointNode const& wpData = path->Nodes[0];
2620 float distToThisPath = creature->GetExactDistSq(wpData.X, wpData.Y, wpData.Z);
2621
2622 if (distToThisPath < distanceToClosest)
2623 {
2624 distanceToClosest = distToThisPath;
2625 closestWpId = pathId;
2626 }
2627 }
2628 }
2629
2630 if (closestWpId)
2631 {
2632 bool repeat = e.action.startClosestWaypoint.repeat;
2634
2635 CAST_AI(SmartAI, creature->AI())->StartPath(forcedMovement, closestWpId, repeat, nullptr, pathSource);
2636 }
2637 }
2638 }
2639 }
2640 break;
2641 }
2643 {
2644 for (WorldObject* target : targets)
2645 if (IsUnit(target))
2646 target->ToUnit()->ExitVehicle();
2647
2648 break;
2649 }
2651 {
2652 for (WorldObject* target : targets)
2653 if (IsUnit(target))
2654 {
2656 target->ToUnit()->SendMovementFlagUpdate();
2657 }
2658
2659 break;
2660 }
2662 {
2663 for (WorldObject* target : targets)
2664 if (IsCreature(target))
2665 target->ToCreature()->m_CombatDistance = e.action.combatDistance.dist;
2666
2667 break;
2668 }
2670 {
2671 for (WorldObject* const target : targets)
2672 if (IsCreature(target))
2673 target->ToCreature()->m_SightDistance = e.action.sightDistance.dist;
2674 break;
2675 }
2676 case SMART_ACTION_FLEE:
2677 {
2678 for (WorldObject* const target : targets)
2679 if (IsCreature(target))
2680 target->ToCreature()->GetMotionMaster()->MoveFleeing(me, e.action.flee.withEmote);
2681 break;
2682 }
2684 {
2685 if (!me->CanHaveThreatList())
2686 break;
2687 for (WorldObject* const target : targets)
2688 if (IsUnit(target))
2689 me->GetThreatMgr().AddThreat(target->ToUnit(), float(e.action.threat.threatINC) - float(e.action.threat.threatDEC), nullptr, true, true);
2690 break;
2691 }
2693 {
2694 for (WorldObject* const target : targets)
2695 if (IsCreature(target))
2696 target->ToCreature()->LoadEquipment(e.action.loadEquipment.id, e.action.loadEquipment.force != 0);
2697 break;
2698 }
2700 {
2703 break;
2704 }
2706 {
2707 for (WorldObject* const target : targets)
2708 if (IsUnit(target))
2709 target->ToUnit()->Dismount();
2710 break;
2711 }
2713 {
2714 for (WorldObject* target : targets)
2715 if (IsUnit(target))
2716 target->ToUnit()->SetHover(e.action.setHover.state);
2717 break;
2718 }
2720 {
2721 for (WorldObject* target : targets)
2722 if (IsUnit(target))
2723 target->ToUnit()->ApplySpellImmune(e.action.immunity.id, e.action.immunity.type, e.action.immunity.value, true);
2724
2725 break;
2726 }
2728 {
2729 for (WorldObject* target : targets)
2730 if (IsUnit(target))
2731 target->ToUnit()->ApplySpellImmune(e.action.immunity.id, e.action.immunity.type, e.action.immunity.value, false);
2732 break;
2733 }
2734 case SMART_ACTION_FALL:
2735 {
2736 for (WorldObject* target : targets)
2737 if (IsUnit(target))
2738 target->ToUnit()->GetMotionMaster()->MoveFall();
2739
2740 break;
2741 }
2743 {
2745 break;
2746 }
2748 {
2749 for (WorldObject* const target : targets)
2750 if (IsUnit(target))
2751 target->ToUnit()->RemoveAllGameObjects();
2752 break;
2753 }
2755 {
2756 for (WorldObject* const target : targets)
2757 {
2758 if (IsUnit(target))
2759 {
2761 target->ToUnit()->StopMoving();
2763 target->ToUnit()->GetMotionMaster()->MovementExpired();
2764 }
2765 }
2766 break;
2767 }
2769 {
2770 for (WorldObject* target : targets)
2771 if (IsUnit(target))
2772 target->ToUnit()->AddUnitState(UNIT_STATE_NO_ENVIRONMENT_UPD);
2773
2774 break;
2775 }
2777 {
2778 for (WorldObject* target : targets)
2779 if (IsUnit(target))
2780 if (Player* player = target->ToUnit()->GetCharmerOrOwnerPlayerOrPlayerItself())
2781 {
2783 break;
2784 }
2785
2786 break;
2787 }
2789 {
2790 if (me && me->FindMap())
2791 me->FindMap()->LoadGrid(e.target.x, e.target.y);
2792 else if (go && go->FindMap())
2793 go->FindMap()->LoadGrid(e.target.x, e.target.y);
2794 break;
2795 }
2797 {
2798 std::string text = sObjectMgr->GetAcoreString(e.action.playerTalk.textId, DEFAULT_LOCALE);
2799
2800 if (!targets.empty())
2801 for (WorldObject* target : targets)
2802 if (IsPlayer(target))
2803 !e.action.playerTalk.flag ? target->ToPlayer()->Say(text, LANG_UNIVERSAL) : target->ToPlayer()->Yell(text, LANG_UNIVERSAL);
2804
2805 break;
2806 }
2808 {
2809 if (!me)
2810 break;
2811
2812 for (WorldObject* target : targets)
2813 {
2814 if (IsUnit(target))
2815 {
2817 {
2819 }
2820
2822 {
2823 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(e.action.castCustom.spell);
2824 CustomSpellValues values;
2825 if (e.action.castCustom.bp1)
2827 if (e.action.castCustom.bp2)
2829 if (e.action.castCustom.bp3)
2832
2833 float spellMaxRange = me->GetSpellMaxRangeForTarget(target->ToUnit(), spellInfo);
2835 {
2836 if (result == SPELL_CAST_OK || result == SPELL_FAILED_SPELL_IN_PROGRESS)
2837 {
2838 CAST_AI(SmartAI, me->AI())->SetCombatMovement(false, true);
2839 CAST_AI(SmartAI, me->AI())->SetCurrentRangeMode(
2840 true, std::max(spellMaxRange - NOMINAL_MELEE_RANGE, 0.0f));
2841 }
2842 else if (result == SPELL_FAILED_OUT_OF_RANGE)
2843 {
2844 CAST_AI(SmartAI, me->AI())->SetCombatMovement(true, false);
2845 CAST_AI(SmartAI, me->AI())->SetCurrentRangeMode(
2846 true, std::max(spellMaxRange - NOMINAL_MELEE_RANGE, 0.0f));
2847 }
2848 else if (result != SPELL_FAILED_NOT_READY)
2849 {
2850 CAST_AI(SmartAI, me->AI())->SetCombatMovement(true, false);
2851 CAST_AI(SmartAI, me->AI())->SetCurrentRangeMode(false, 0.f);
2852 }
2853 }
2854 }
2855 }
2856 }
2857 break;
2858 }
2860 {
2861 if (!me)
2862 break;
2863
2864 if (targets.empty())
2865 break;
2866
2868
2869 float a = static_cast<float>(e.action.summonVortex.a);
2870 float k = static_cast<float>(e.action.summonVortex.k) / 1000.0f;
2871 float r_max = static_cast<float>(e.action.summonVortex.r_max);
2872 float delta_phi = M_PI * static_cast<float>(e.action.summonVortex.phi_delta) / 180.0f;
2873
2874 // r(phi) = a * e ^ (k * phi)
2875 // r(phi + delta_phi) = a * e ^ (k * (phi + delta_phi))
2876 // r(phi + delta_phi) = a * e ^ (k * phi) * e ^ (k * delta_phi)
2877 // r(phi + delta_phi) = r(phi) * e ^ (k * delta_phi)
2878 float factor = std::exp(k * delta_phi);
2879
2880 // r(0) = a * e ^ (k * 0) = a * e ^ 0 = a * 1 = a
2881 float summonRadius = a;
2882
2883 for (WorldObject* target : targets)
2884 {
2885 // Offset by orientation, should not count into radius calculation,
2886 // but is needed for vortex direction (polar coordinates)
2887 float phi = target->GetOrientation();
2888
2889 do
2890 {
2891 Position summonPosition(*target);
2892 summonPosition.RelocatePolarOffset(phi, summonRadius);
2893
2895
2896 phi += delta_phi;
2897 summonRadius *= factor;
2898 } while (summonRadius <= r_max);
2899 }
2900
2901 break;
2902 }
2904 {
2905 if (!me)
2906 break;
2907
2909
2910 float distInARow = static_cast<float>(e.action.coneSummon.distanceBetweenSummons);
2911 float coneAngle = static_cast<float>(e.action.coneSummon.coneAngle) * M_PI / 180.0f;
2912
2913 for (uint32 radius = 0; radius <= e.action.coneSummon.coneLength; radius += e.action.coneSummon.distanceBetweenRings)
2914 {
2915 float deltaAngle = 0.0f;
2916 if (radius > 0)
2917 deltaAngle = distInARow / radius;
2918
2919 uint32 count = 1;
2920 if (deltaAngle > 0)
2921 count += coneAngle / deltaAngle;
2922
2923 float currentAngle = -static_cast<float>(count) * deltaAngle / 2.0f;
2924
2926 currentAngle += G3D::fuzzyGt(e.target.o, 0.0f) ? (e.target.o - me->GetOrientation()) : 0.0f;
2927 else if (!targets.empty())
2928 {
2929 currentAngle += (me->GetAngle(targets.front()) - me->GetOrientation());
2930 }
2931
2932 for (uint32 index = 0; index < count; ++index)
2933 {
2934 Position spawnPosition(*me);
2935 spawnPosition.RelocatePolarOffset(currentAngle, radius);
2936 currentAngle += deltaAngle;
2937
2939 }
2940 }
2941
2942 break;
2943 }
2945 {
2946 for (WorldObject* target : targets)
2947 {
2948 if (Player* playerTarget = target->ToPlayer())
2949 {
2950 playerTarget->RemoveArenaSpellCooldowns();
2951 playerTarget->RemoveAurasDueToSpell(57724); // Spell Shaman Debuff - Sated (Heroism)
2952 playerTarget->RemoveAurasDueToSpell(57723); // Spell Shaman Debuff - Exhaustion (Bloodlust)
2953 playerTarget->RemoveAurasDueToSpell(2825); // Bloodlust
2954 playerTarget->RemoveAurasDueToSpell(32182); // Heroism
2955 }
2956 }
2957
2958 break;
2959 }
2961 {
2964 {
2965 if (targets.empty())
2966 break;
2967
2968 for (WorldObject* objTarget : targets)
2969 {
2970 if (Creature const* unitTarget = objTarget->ToCreature())
2971 {
2972 if (unitTarget->IsAIEnabled)
2973 {
2974 unitTarget->AI()->DoAction(actionId);
2975 }
2976 }
2977 else if (GameObject const* gobjTarget = objTarget->ToGameObject())
2978 {
2979 gobjTarget->AI()->DoAction(actionId);
2980 }
2981 }
2982
2983 }
2984 else
2985 {
2986 InstanceScript* instanceScript = nullptr;
2987 if (WorldObject* baseObj = GetBaseObject())
2988 {
2989 instanceScript = baseObj->GetInstanceScript();
2990 }
2991 // Action is triggered by AreaTrigger
2992 else if (trigger && IsPlayer(unit))
2993 {
2994 instanceScript = unit->GetInstanceScript();
2995 }
2996
2997 if (instanceScript)
2998 {
2999 instanceScript->DoAction(actionId);
3000 }
3001 }
3002 break;
3003 }
3005 {
3006 if (!IsSmart())
3007 break;
3008
3009 CAST_AI(SmartAI, me->AI())->SetEvadeDisabled(e.action.disableEvade.disable != 0);
3010 break;
3011 }
3013 {
3014 for (WorldObject* const target : targets)
3015 {
3016 if (IsCreature(target))
3018 }
3019 break;
3020 }
3022 {
3023 for (WorldObject* target : targets)
3024 if (Unit* targetUnit = target->ToUnit())
3025 targetUnit->SetHealth(targetUnit->CountPctFromMaxHealth(e.action.setHealthPct.percent));
3026 break;
3027 }
3029 {
3030 uint32 speedInteger = e.action.movementSpeed.speedInteger;
3031 uint32 speedFraction = e.action.movementSpeed.speedFraction;
3032 float speed = float(speedInteger) + float(speedFraction) / std::pow(10, std::floor(std::log10(float(speedFraction ? speedFraction : 1)) + 1));
3033
3034 for (WorldObject* target : targets)
3035 if (IsCreature(target))
3036 target->ToCreature()->SetSpeed(UnitMoveType(e.action.movementSpeed.movementType), speed);
3037
3038 break;
3039 }
3041 {
3042 for (WorldObject* target : targets)
3043 {
3044 if (!IsPlayer(target))
3045 continue;
3046
3048 }
3049 break;
3050 }
3052 {
3053 WorldObject* obj = GetBaseObject();
3054 if (!obj)
3055 break;
3056
3059 e.action.groupSpawn.force != 0);
3060 break;
3061 }
3063 {
3064 WorldObject* obj = GetBaseObject();
3065 if (!obj)
3066 break;
3067
3069 e.action.groupSpawn.ignoreRespawn != 0); // reuse ignoreRespawn as deleteRespawnTimes
3070 break;
3071 }
3073 {
3074 for (WorldObject* target : targets)
3075 {
3076 ObjectGuid guidToSend = me ? me->GetGUID() : go->GetGUID();
3077
3079 {
3080 if (WorldObject* invoker = GetLastInvoker())
3081 {
3082 guidToSend = invoker->GetGUID();
3083 }
3084 }
3085
3086 if (Creature* creature = target->ToCreature())
3087 {
3088 creature->AI()->SetGUID(guidToSend, e.action.setGuid.index);
3089 }
3090 else if (GameObject* object = target->ToGameObject())
3091 {
3092 object->AI()->SetGUID(guidToSend, e.action.setGuid.index);
3093 }
3094 }
3095 break;
3096 }
3098 {
3099 // Enable Scripted Spawns
3100 switch (e.action.scriptSpawn.state)
3101 {
3102 case 0: // Disable Respawn
3103 {
3104 for (WorldObject* target : targets)
3105 {
3106 if (Creature* c = target->ToCreature())
3107 {
3108 CAST_AI(SmartAI, c->AI())->SetCanRespawn(false);
3110 c->DespawnOrUnsummon();
3111 }
3112 }
3113 break;
3114 }
3115 case 1: // Respawn Once
3116 {
3117 for (WorldObject* target : targets)
3118 {
3119 if (Creature* c = target->ToCreature())
3120 {
3121 CAST_AI(SmartAI, c->AI())->SetCanRespawn(true);
3122 c->Respawn(true);
3123 CAST_AI(SmartAI, c->AI())->SetCanRespawn(false);
3124 }
3125 }
3126 break;
3127 }
3128 case 2: // Enable Respawning
3129 {
3130 for (WorldObject* target : targets)
3131 {
3132 if (Creature* c = target->ToCreature())
3133 {
3134 CAST_AI(SmartAI, c->AI())->SetCanRespawn(true);
3135
3136 // If 0, respawn immediately
3139 else
3140 c->Respawn(true);
3141
3142 // If 0, use DB values
3144 c->SetRespawnDelay(e.action.scriptSpawn.respawnDelay);
3145
3146 // If 0, use default
3148 c->SetCorpseDelay(e.action.scriptSpawn.corpseDelay);
3149 }
3150 }
3151 break;
3152 }
3153 default:
3154 break;
3155 }
3156 break;
3157 }
3159 {
3160 float scale = static_cast<float>(e.action.setScale.scale) / 100.0f;
3161
3162 for (WorldObject* target : targets)
3163 {
3164 if (IsUnit(target))
3165 target->ToUnit()->SetObjectScale(scale);
3166 else if (IsGameObject(target))
3167 target->ToGameObject()->SetObjectScale(scale);
3168 }
3169 break;
3170 }
3172 {
3173 if (!me)
3174 break;
3175
3177
3178 float startAngle = me->GetOrientation() + (static_cast<float>(e.action.radialSummon.startAngle) * M_PI / 180.0f);
3179 float stepAngle = static_cast<float>(e.action.radialSummon.stepAngle) * M_PI / 180.0f;
3180
3181 if (e.action.radialSummon.dist)
3182 {
3183 for (uint32 itr = 0; itr < e.action.radialSummon.repetitions; itr++)
3184 {
3185 Position summonPos = me->GetPosition();
3186 summonPos.RelocatePolarOffset(itr * stepAngle, static_cast<float>(e.action.radialSummon.dist));
3188 }
3189 break;
3190 }
3191
3192 for (uint32 itr = 0; itr < e.action.radialSummon.repetitions; itr++)
3193 {
3194 float currentAngle = startAngle + (itr * stepAngle);
3196 }
3197
3198 break;
3199 }
3201 {
3202 for (WorldObject* target : targets)
3203 {
3204 if (IsUnit(target))
3205 {
3208 }
3209 }
3210 break;
3211 }
3213 {
3215 {
3216 for (WorldObject* target : targets)
3217 if (IsCreature(target))
3218 target->ToCreature()->GetMotionMaster()->Clear();
3219
3220 break;
3221 }
3222
3223 std::stable_sort(targets.begin(), targets.end(), [](WorldObject const* left, WorldObject const* right)
3224 {
3225 if (!left->IsCreature())
3226 return false;
3227
3228 if (!right->IsCreature())
3229 return true;
3230
3231 return left->ToCreature()->GetSpawnId() < right->ToCreature()->GetSpawnId();
3232 });
3233
3234 uint8 membCount = targets.size();
3235 uint8 itr = 1;
3236 float dist = float(e.action.followGroup.dist / 100);
3237 auto moveFollower = [this, &e](Creature* follower, float followDist, float followAngle)
3238 {
3240 follower->GetMotionMaster()->MoveFormation(me, followDist, followAngle, 0, 0);
3241 else
3242 follower->GetMotionMaster()->MoveFollow(me, followDist, followAngle);
3243 };
3244
3245 switch (e.action.followGroup.followType)
3246 {
3247 case FOLLOW_TYPE_CIRCLE:
3248 {
3249 float angle = (membCount > 4 ? (M_PI * 2)/membCount : (M_PI / 2)); // 90 degrees is the maximum angle
3250 for (WorldObject* target : targets)
3251 {
3252 if (IsCreature(target))
3253 {
3254 moveFollower(target->ToCreature(), dist, angle * (itr - 1));
3255 itr++;
3256 }
3257 }
3258 break;
3259 }
3261 {
3262 for (WorldObject* target : targets)
3263 {
3264 if (IsCreature(target))
3265 {
3266 moveFollower(target->ToCreature(), dist, (M_PI / 2.0f) + (M_PI / membCount) * (itr - 1));
3267 itr++;
3268 }
3269 }
3270 break;
3271 }
3273 {
3274 for (WorldObject* target : targets)
3275 {
3276 if (IsCreature(target))
3277 {
3278 moveFollower(target->ToCreature(), dist, M_PI + (M_PI / 2.0f) + (M_PI / membCount) * (itr - 1));
3279 itr++;
3280 }
3281 }
3282 break;
3283 }
3284 case FOLLOW_TYPE_LINE:
3285 {
3286 for (WorldObject* target : targets)
3287 {
3288 if (IsCreature(target))
3289 {
3290 moveFollower(target->ToCreature(), dist * (((itr - 1) / 2) + 1), itr % 2 ? 0.f : M_PI);
3291 itr++;
3292 }
3293 }
3294 break;
3295 }
3296 case FOLLOW_TYPE_COLUMN:
3297 {
3298 for (WorldObject* target : targets)
3299 {
3300 if (IsCreature(target))
3301 {
3302 moveFollower(target->ToCreature(), dist * (((itr - 1) / 2) + 1), itr % 2 ? (M_PI / 2) : (M_PI * 1.5f));
3303 itr++;
3304 }
3305 }
3306 break;
3307 }
3309 {
3310 for (WorldObject* target : targets)
3311 {
3312 if (IsCreature(target))
3313 {
3314 moveFollower(target->ToCreature(), dist * (((itr - 1) / 2) + 1), itr % 2 ? M_PI - (M_PI / 4) : M_PI + (M_PI / 4));
3315 itr++;
3316 }
3317 }
3318 break;
3319 }
3321 {
3322 for (WorldObject* target : targets)
3323 {
3324 if (IsCreature(target))
3325 {
3326 moveFollower(target->ToCreature(), dist * itr, M_PI);
3327 itr++;
3328 }
3329 }
3330 break;
3331 }
3332 default:
3333 break;
3334 }
3335
3336 break;
3337 }
3339 {
3340 switch (e.action.orientationTarget.type)
3341 {
3342 case 0: // Reset
3343 {
3344 for (WorldObject* target : targets)
3345 target->ToCreature()->SetFacingTo((target->ToCreature()->HasUnitMovementFlag(MOVEMENTFLAG_ONTRANSPORT) && target->ToCreature()->GetTransGUID() ? target->ToCreature()->GetTransportHomePosition() : target->ToCreature()->GetHomePosition()).GetOrientation());
3346
3347 break;
3348 }
3349 case 1: // Target target.o
3350 {
3351 for (WorldObject* target : targets)
3352 target->ToCreature()->SetFacingTo(e.target.o);
3353
3354 break;
3355 }
3356 case 2: // Target source
3357 {
3358 for (WorldObject* target : targets)
3359 target->ToCreature()->SetFacingToObject(me);
3360
3361 break;
3362 }
3363 case 3: // Target parameters
3364 {
3365 ObjectVector facingTargets;
3367
3368 for (WorldObject* facingTarget : facingTargets)
3369 for (WorldObject* target : targets)
3370 target->ToCreature()->SetFacingToObject(facingTarget);
3371
3372 break;
3373 }
3374 default:
3375 break;
3376 }
3377 break;
3378 }
3380 {
3381 if (e.action.wpData.pathId)
3382 {
3383 for (WorldObject* target : targets)
3384 {
3385 if (IsCreature(target))
3386 {
3387 target->ToCreature()->LoadPath(e.action.wpData.pathId);
3389 }
3390 }
3391 }
3392
3393 break;
3394 }
3396 {
3398 {
3399 for (WorldObject* target : targets)
3400 {
3401 if (IsCreature(target))
3402 {
3404 target->ToCreature()->LoadPath(path);
3406 }
3407 }
3408 }
3409
3410 break;
3411 }
3413 {
3414 for (WorldObject* target : targets)
3415 if (IsUnit(target))
3416 target->ToUnit()->StopMoving();
3417
3418 break;
3419 }
3421 {
3422 for (WorldObject* target : targets)
3423 if (IsUnit(target))
3424 target->ToUnit()->PauseMovement(e.action.move.timer);
3425
3426 break;
3427 }
3429 {
3430 for (WorldObject* target : targets)
3431 if (IsUnit(target))
3432 target->ToUnit()->ResumeMovement(e.action.move.timer);
3433
3434 break;
3435 }
3437 {
3438 sWorldState->HandleExternalEvent(static_cast<WorldStateEvent>(e.action.worldStateScript.eventId), e.action.worldStateScript.param);
3439 break;
3440 }
3442 {
3443 for (WorldObject* target : targets)
3444 if (IsCreature(target))
3445 {
3446 target->ToCreature()->SetReputationRewardDisabled(static_cast<bool>(e.action.reward.reputation));
3447 target->ToCreature()->SetLootRewardDisabled(static_cast<bool>(e.action.reward.loot));
3448 }
3449 break;
3450 }
3452 {
3453 for (WorldObject* target : targets)
3454 if (IsUnit(target))
3455 target->ToUnit()->SetAnimTier(AnimTier(e.action.animTier.animTier));
3456 break;
3457 }
3459 {
3460 for (WorldObject* target : targets)
3461 {
3462 if (Creature* creature = target->ToCreature())
3463 {
3464 creature->SetGossipMenuId(e.action.setGossipMenu.gossipMenuId);
3465 LOG_DEBUG("sql.sql", "SmartScript::ProcessAction: SMART_ACTION_SET_GOSSIP_MENU: Creature {} set gossip menu to {}",
3466 creature->GetGUID().ToString(), e.action.setGossipMenu.gossipMenuId);
3467 }
3468 }
3469 break;
3470 }
3472 {
3473 if (!GetBaseObject())
3474 break;
3475
3477 break;
3478 }
3479 default:
3480 LOG_ERROR("sql.sql", "SmartScript::ProcessAction: Entry {} SourceType {}, Event {}, Unhandled Action type {}", e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType());
3481 break;
3482 }
3483
3484 if (e.link && e.link != e.event_id)
3485 {
3486 auto linked = FindLinkedEvent(e.link);
3487 if (linked.has_value())
3488 {
3489 auto& linkedEvent = linked.value().get();
3490 if (linkedEvent.GetEventType() == SMART_EVENT_LINK)
3491 executionStack.emplace_back(SmartScriptFrame{ linkedEvent, unit, var0, var1, bvar, spell, gob });
3492 else
3493 LOG_ERROR("sql.sql", "SmartScript::ProcessAction: Entry {} SourceType {}, Event {}, Link Event {} found but has wrong type (should be 61, is {}).", e.entryOrGuid, e.GetScriptType(), e.event_id, e.link, linkedEvent.GetEventType());
3494 }
3495 else
3496 LOG_ERROR("sql.sql", "SmartScript::ProcessAction: Entry {} SourceType {}, Event {}, Link Event {} not found, skipped.", e.entryOrGuid, e.GetScriptType(), e.event_id, e.link);
3497 }
3498}
npc
Definition BattlegroundSA.h:47
#define DEFAULT_LOCALE
Definition Common.h:139
#define MAX_EQUIPMENT_ITEMS
Definition CreatureData.h:36
@ TEXT_RANGE_NORMAL
Definition CreatureTextMgr.h:30
std::int8_t int8
Definition Define.h:105
std::chrono::milliseconds Milliseconds
Milliseconds shorthand typedef.
Definition Duration.h:27
std::chrono::seconds Seconds
Seconds shorthand typedef.
Definition Duration.h:30
#define sGameEventMgr
Definition GameEventMgr.h:204
GOState
Definition GameObjectData.h:707
LootState
Definition GameObject.h:109
@ GO_READY
Definition GameObject.h:111
EncounterState
Definition InstanceScript.h:57
@ BROADCAST_TEXT_CALL_FOR_HELP
Definition Language.h:24
@ BROADCAST_TEXT_FLEE_FOR_ASSIST
Definition Language.h:25
@ MOTION_SLOT_CONTROLLED
Definition MotionMaster.h:66
@ MOTION_SLOT_ACTIVE
Definition MotionMaster.h:65
PathSource
Definition MotionMaster.h:95
@ SMART_WAYPOINT_MGR
ForcedMovement
Definition MotionMaster.h:85
@ FORCED_MOVEMENT_NONE
Definition MotionMaster.h:86
AnimTier
Definition MotionMaster.h:101
#define NOMINAL_MELEE_RANGE
Definition ObjectDefines.h:47
#define sObjectMgr
Definition ObjectMgr.h:1731
TempSummonType
Definition Object.h:49
@ TEMPSUMMON_TIMED_DESPAWN
Definition Object.h:52
@ TEMPSUMMON_CORPSE_DESPAWN
Definition Object.h:54
float frand(float min, float max)
Definition Random.cpp:57
uint32 urand(uint32 min, uint32 max)
Definition Random.cpp:44
void SendGossipMenuFor(Player *player, uint32 npcTextID, ObjectGuid const &guid)
Definition ScriptedGossip.cpp:45
void ClearGossipMenuFor(Player *player)
Definition ScriptedGossip.cpp:22
@ GAMEOBJECT_TYPE_DOOR
Definition SharedDefines.h:1564
@ POWER_MANA
Definition SharedDefines.h:257
@ CHAT_MSG_MONSTER_EMOTE
Definition SharedDefines.h:3401
@ CHAT_MSG_ADDON
Definition SharedDefines.h:3384
@ LANG_UNIVERSAL
Definition SharedDefines.h:723
@ LANG_ADDON
Definition SharedDefines.h:741
@ SPELL_ATTR2_IGNORE_LINE_OF_SIGHT
Definition SharedDefines.h:446
@ TEAM_NEUTRAL
Definition SharedDefines.h:750
SpellCastResult
Definition SharedDefines.h:936
@ SPELL_FAILED_OUT_OF_RANGE
Definition SharedDefines.h:1034
@ SPELL_FAILED_NOT_READY
Definition SharedDefines.h:1004
@ SPELL_CAST_OK
Definition SharedDefines.h:1126
@ SPELL_FAILED_SPELL_IN_PROGRESS
Definition SharedDefines.h:1042
@ SMART_EVENT_FLAG_TEMP_IGNORE_CHANCE_ROLL
Definition SmartScriptMgr.h:1976
SMARTAI_TARGETS
Definition SmartScriptMgr.h:1549
@ SMART_TARGET_RANDOM_POINT
Definition SmartScriptMgr.h:1588
#define sSmartWaypointMgr
Definition SmartScriptMgr.h:2282
SMART_ACTION
Definition SmartScriptMgr.h:541
@ SMART_ACTION_REMOVE_TIMED_EVENT
Definition SmartScriptMgr.h:616
@ SMART_ACTION_NONE
Definition SmartScriptMgr.h:542
@ SMART_ACTION_SET_GO_FLAG
Definition SmartScriptMgr.h:646
@ SMART_ACTION_UPDATE_TEMPLATE
Definition SmartScriptMgr.h:578
@ SMART_ACTION_SET_HEALTH_REGEN
Definition SmartScriptMgr.h:644
@ SMART_ACTION_SET_GOSSIP_MENU
Definition SmartScriptMgr.h:727
@ SMART_ACTION_ACTIVATE_GOBJECT
Definition SmartScriptMgr.h:551
@ SMART_ACTION_GAME_EVENT_START
Definition SmartScriptMgr.h:654
@ SMART_ACTION_CALL_RANDOM_RANGE_TIMED_ACTIONLIST
Definition SmartScriptMgr.h:630
@ SMART_ACTION_REMOVE_UNIT_FIELD_BYTES_1
Definition SmartScriptMgr.h:633
@ SMART_ACTION_SET_INST_DATA64
Definition SmartScriptMgr.h:577
@ SMART_ACTION_SET_FACTION
Definition SmartScriptMgr.h:544
@ SMART_ACTION_THREAT_SINGLE_PCT
Definition SmartScriptMgr.h:555
@ SMART_ACTION_OFFER_QUEST
Definition SmartScriptMgr.h:549
@ SMART_ACTION_REMOVE_ALL_GAMEOBJECTS
Definition SmartScriptMgr.h:668
@ SMART_ACTION_RISE_UP
Definition SmartScriptMgr.h:656
@ SMART_ACTION_SET_INGAME_PHASE_MASK
Definition SmartScriptMgr.h:586
@ SMART_ACTION_SET_UNIT_FIELD_BYTES_1
Definition SmartScriptMgr.h:632
@ SMART_ACTION_CLOSE_GOSSIP
Definition SmartScriptMgr.h:614
@ SMART_ACTION_DISABLE_EVADE
Definition SmartScriptMgr.h:659
@ SMART_ACTION_INC_DATA
Definition SmartScriptMgr.h:729
@ SMART_ACTION_CONE_SUMMON
Definition SmartScriptMgr.h:706
@ SMART_ACTION_ADD_GO_FLAG
Definition SmartScriptMgr.h:647
@ SMART_ACTION_ESCORT_START
Definition SmartScriptMgr.h:595
@ SMART_ACTION_ADD_DYNAMIC_FLAG
Definition SmartScriptMgr.h:637
@ SMART_ACTION_KILL_UNIT
Definition SmartScriptMgr.h:593
@ SMART_ACTION_LOAD_EQUIPMENT
Definition SmartScriptMgr.h:666
@ SMART_ACTION_CALL_AREAEXPLOREDOREVENTHAPPENS
Definition SmartScriptMgr.h:557
@ SMART_ACTION_ATTACK_START
Definition SmartScriptMgr.h:591
@ SMART_ACTION_MOVEMENT_RESUME
Definition SmartScriptMgr.h:723
@ SMART_ACTION_SET_UNIT_FLAG
Definition SmartScriptMgr.h:560
@ SMART_ACTION_NO_ENVIRONMENT_UPDATE
Definition SmartScriptMgr.h:699
@ SMART_ACTION_CALL_GROUPEVENTHAPPENS
Definition SmartScriptMgr.h:568
@ SMART_ACTION_MOUNT_TO_ENTRY_OR_MODEL
Definition SmartScriptMgr.h:585
@ SMART_ACTION_INVOKER_CAST
Definition SmartScriptMgr.h:676
@ SMART_ACTION_MOVEMENT_STOP
Definition SmartScriptMgr.h:721
@ SMART_ACTION_SET_SCALE
Definition SmartScriptMgr.h:714
@ SMART_ACTION_JUMP_TO_POS
Definition SmartScriptMgr.h:639
@ SMART_ACTION_CALL_RANDOM_TIMED_ACTIONLIST
Definition SmartScriptMgr.h:629
@ SMART_ACTION_SEND_GOSSIP_MENU
Definition SmartScriptMgr.h:640
@ SMART_ACTION_SET_COUNTER
Definition SmartScriptMgr.h:605
@ SMART_ACTION_FLEE_FOR_ASSIST
Definition SmartScriptMgr.h:567
@ SMART_ACTION_EQUIP
Definition SmartScriptMgr.h:613
@ SMART_ACTION_SET_ROOT
Definition SmartScriptMgr.h:645
@ SMART_ACTION_ATTACK_STOP
Definition SmartScriptMgr.h:711
@ SMART_ACTION_SUMMON_GO
Definition SmartScriptMgr.h:592
@ SMART_ACTION_SET_HOVER
Definition SmartScriptMgr.h:693
@ SMART_ACTION_SIMPLE_TALK
Definition SmartScriptMgr.h:626
@ SMART_ACTION_STOP_MOTION
Definition SmartScriptMgr.h:698
@ SMART_ACTION_VORTEX_SUMMON
Definition SmartScriptMgr.h:708
@ SMART_ACTION_WORLD_SCRIPT
Definition SmartScriptMgr.h:724
@ SMART_ACTION_MUSIC
Definition SmartScriptMgr.h:702
@ SMART_ACTION_SET_ORIENTATION_TARGET
Definition SmartScriptMgr.h:718
@ SMART_ACTION_SPAWN_SPAWNGROUP
Definition SmartScriptMgr.h:673
@ SMART_ACTION_SET_UNIT_MOVEMENT_FLAGS
Definition SmartScriptMgr.h:690
@ SMART_ACTION_ADD_AURA
Definition SmartScriptMgr.h:617
@ SMART_ACTION_THREAT_ALL_PCT
Definition SmartScriptMgr.h:556
@ SMART_ACTION_WAYPOINT_START
Definition SmartScriptMgr.h:719
@ SMART_ACTION_ESCORT_STOP
Definition SmartScriptMgr.h:597
@ SMART_ACTION_RESPAWN_TARGET
Definition SmartScriptMgr.h:612
@ SMART_ACTION_FOLLOW_GROUP
Definition SmartScriptMgr.h:717
@ SMART_ACTION_SOUND
Definition SmartScriptMgr.h:546
@ SMART_ACTION_ESCORT_PAUSE
Definition SmartScriptMgr.h:596
@ SMART_ACTION_MOVE_TO_POS_TARGET
Definition SmartScriptMgr.h:687
@ SMART_ACTION_SET_MOVEMENT_SPEED
Definition SmartScriptMgr.h:678
@ SMART_ACTION_PLAY_CINEMATIC
Definition SmartScriptMgr.h:677
@ SMART_ACTION_ADD_NPC_FLAG
Definition SmartScriptMgr.h:624
@ SMART_ACTION_EVADE
Definition SmartScriptMgr.h:566
@ SMART_ACTION_FAIL_QUEST
Definition SmartScriptMgr.h:548
@ SMART_ACTION_INTERRUPT_SPELL
Definition SmartScriptMgr.h:634
@ SMART_ACTION_ADD_POWER
Definition SmartScriptMgr.h:651
@ SMART_ACTION_SET_ANIM_TIER
Definition SmartScriptMgr.h:726
@ SMART_ACTION_REMOVE_DYNAMIC_FLAG
Definition SmartScriptMgr.h:638
@ SMART_ACTION_RANDOM_SOUND
Definition SmartScriptMgr.h:657
@ SMART_ACTION_RANDOM_MUSIC
Definition SmartScriptMgr.h:703
@ SMART_ACTION_SET_COMBAT_DISTANCE
Definition SmartScriptMgr.h:691
@ SMART_ACTION_SET_POWER
Definition SmartScriptMgr.h:650
@ SMART_ACTION_SEND_TARGET_TO_TARGET
Definition SmartScriptMgr.h:642
@ SMART_ACTION_REMOVE_POWER
Definition SmartScriptMgr.h:652
@ SMART_ACTION_ADD_IMMUNITY
Definition SmartScriptMgr.h:694
@ SMART_ACTION_SET_DYNAMIC_FLAG
Definition SmartScriptMgr.h:636
@ SMART_ACTION_FALL
Definition SmartScriptMgr.h:696
@ SMART_ACTION_GO_SET_GO_STATE
Definition SmartScriptMgr.h:660
@ SMART_ACTION_CUSTOM_CAST
Definition SmartScriptMgr.h:705
@ SMART_ACTION_REMOVE_ITEM
Definition SmartScriptMgr.h:599
@ SMART_ACTION_SEND_GO_CUSTOM_ANIM
Definition SmartScriptMgr.h:635
@ SMART_ACTION_MORPH_TO_ENTRY_OR_MODEL
Definition SmartScriptMgr.h:545
@ SMART_ACTION_REMOVE_UNIT_FLAG
Definition SmartScriptMgr.h:561
@ SMART_ACTION_RANDOM_PHASE
Definition SmartScriptMgr.h:572
@ SMART_ACTION_SET_EMOTE_STATE
Definition SmartScriptMgr.h:559
@ SMART_ACTION_CROSS_CAST
Definition SmartScriptMgr.h:628
@ SMART_ACTION_GAME_EVENT_STOP
Definition SmartScriptMgr.h:653
@ SMART_ACTION_SCRIPTED_SPAWN
Definition SmartScriptMgr.h:713
@ SMART_ACTION_ESCORT_RESUME
Definition SmartScriptMgr.h:607
@ SMART_ACTION_CALL_SCRIPT_RESET
Definition SmartScriptMgr.h:620
@ SMART_ACTION_CU_ENCOUNTER_START
Definition SmartScriptMgr.h:709
@ SMART_ACTION_COMBAT_STOP
Definition SmartScriptMgr.h:569
@ SMART_ACTION_EXIT_VEHICLE
Definition SmartScriptMgr.h:689
@ SMART_ACTION_SET_HEALTH_PCT
Definition SmartScriptMgr.h:680
@ SMART_ACTION_AUTO_ATTACK
Definition SmartScriptMgr.h:562
@ SMART_ACTION_SET_INVINCIBILITY_HP_LEVEL
Definition SmartScriptMgr.h:584
@ SMART_ACTION_SET_VISIBILITY
Definition SmartScriptMgr.h:589
@ SMART_ACTION_RANDOM_PHASE_RANGE
Definition SmartScriptMgr.h:573
@ SMART_ACTION_MOVEMENT_PAUSE
Definition SmartScriptMgr.h:722
@ SMART_ACTION_GO_SET_LOOT_STATE
Definition SmartScriptMgr.h:641
@ SMART_ACTION_PLAYER_TALK
Definition SmartScriptMgr.h:707
@ SMART_ACTION_SELF_CAST
Definition SmartScriptMgr.h:627
@ SMART_ACTION_SET_SWIM
Definition SmartScriptMgr.h:603
@ SMART_ACTION_SET_SIGHT_DIST
Definition SmartScriptMgr.h:663
@ SMART_ACTION_SET_INST_DATA
Definition SmartScriptMgr.h:576
@ SMART_ACTION_REMOVE_GO_FLAG
Definition SmartScriptMgr.h:648
@ SMART_ACTION_LOAD_GRID
Definition SmartScriptMgr.h:701
@ SMART_ACTION_CALL_FOR_HELP
Definition SmartScriptMgr.h:581
@ SMART_ACTION_SUMMON_RADIAL
Definition SmartScriptMgr.h:715
@ SMART_ACTION_ADD_THREAT
Definition SmartScriptMgr.h:665
@ SMART_ACTION_DISMOUNT
Definition SmartScriptMgr.h:692
@ SMART_ACTION_TELEPORT
Definition SmartScriptMgr.h:604
@ SMART_ACTION_PLAYMOVIE
Definition SmartScriptMgr.h:610
@ SMART_ACTION_TRIGGER_RANDOM_TIMED_EVENT
Definition SmartScriptMgr.h:667
@ SMART_ACTION_FOLLOW
Definition SmartScriptMgr.h:571
@ SMART_ACTION_PLAY_EMOTE
Definition SmartScriptMgr.h:547
@ SMART_ACTION_DESPAWN_SPAWNGROUP
Definition SmartScriptMgr.h:674
@ SMART_ACTION_SET_CORPSE_DELAY
Definition SmartScriptMgr.h:658
@ SMART_ACTION_WAYPOINT_DATA_RANDOM
Definition SmartScriptMgr.h:720
@ SMART_ACTION_SET_GUID
Definition SmartScriptMgr.h:712
@ SMART_ACTION_SET_SHEATH
Definition SmartScriptMgr.h:582
@ SMART_ACTION_SET_ORIENTATION
Definition SmartScriptMgr.h:608
@ SMART_ACTION_SET_NPC_FLAG
Definition SmartScriptMgr.h:623
@ SMART_ACTION_MOVE_TO_POS
Definition SmartScriptMgr.h:611
@ SMART_ACTION_RANDOM_EMOTE
Definition SmartScriptMgr.h:552
@ SMART_ACTION_INC_EVENT_PHASE
Definition SmartScriptMgr.h:565
@ SMART_ACTION_CREATE_TIMED_EVENT
Definition SmartScriptMgr.h:609
@ SMART_ACTION_SET_EVENT_FLAG_RESET
Definition SmartScriptMgr.h:697
@ SMART_ACTION_SUMMON_GAMEOBJECT_GROUP
Definition SmartScriptMgr.h:728
@ SMART_ACTION_DIE
Definition SmartScriptMgr.h:579
@ SMART_ACTION_RESET_SCRIPT_BASE_OBJECT
Definition SmartScriptMgr.h:619
@ SMART_ACTION_REMOVE_NPC_FLAG
Definition SmartScriptMgr.h:625
@ SMART_ACTION_SET_FLY
Definition SmartScriptMgr.h:602
@ SMART_ACTION_INSTALL_AI_TEMPLATE
Definition SmartScriptMgr.h:600
@ SMART_ACTION_SUMMON_CREATURE
Definition SmartScriptMgr.h:554
@ SMART_ACTION_CALL_TIMED_ACTIONLIST
Definition SmartScriptMgr.h:622
@ SMART_ACTION_SET_IN_COMBAT_WITH_ZONE
Definition SmartScriptMgr.h:580
@ SMART_ACTION_DO_ACTION
Definition SmartScriptMgr.h:710
@ SMART_ACTION_SET_HOME_POS
Definition SmartScriptMgr.h:643
@ SMART_ACTION_ADD_ITEM
Definition SmartScriptMgr.h:598
@ SMART_ACTION_SET_ACTIVE
Definition SmartScriptMgr.h:590
@ SMART_ACTION_SET_RANGED_MOVEMENT
Definition SmartScriptMgr.h:621
@ SMART_ACTION_ACTIVATE_TAXI
Definition SmartScriptMgr.h:594
@ SMART_ACTION_START_CLOSEST_WAYPOINT
Definition SmartScriptMgr.h:655
@ SMART_ACTION_SUMMON_CREATURE_GROUP
Definition SmartScriptMgr.h:649
@ SMART_ACTION_REMOVE_IMMUNITY
Definition SmartScriptMgr.h:695
@ SMART_ACTION_PLAY_SPELL_VISUAL
Definition SmartScriptMgr.h:716
@ SMART_ACTION_SET_REACT_STATE
Definition SmartScriptMgr.h:550
@ SMART_ACTION_DISABLE_REWARD
Definition SmartScriptMgr.h:725
@ SMART_ACTION_RANDOM_MOVE
Definition SmartScriptMgr.h:631
@ SMART_ACTION_OVERRIDE_SCRIPT_BASE_OBJECT
Definition SmartScriptMgr.h:618
@ SMART_ACTION_TRIGGER_TIMED_EVENT
Definition SmartScriptMgr.h:615
@ SMART_ACTION_REMOVEAURASFROMSPELL
Definition SmartScriptMgr.h:570
@ SMART_ACTION_FLEE
Definition SmartScriptMgr.h:664
@ SMART_ACTION_ZONE_UNDER_ATTACK
Definition SmartScriptMgr.h:700
@ FOLLOW_TYPE_CIRCLE
Definition SmartScriptMgr.h:1996
@ FOLLOW_TYPE_SEMI_CIRCLE_BEHIND
Definition SmartScriptMgr.h:1997
@ FOLLOW_TYPE_SEMI_CIRCLE_FRONT
Definition SmartScriptMgr.h:1998
@ FOLLOW_TYPE_COLUMN
Definition SmartScriptMgr.h:2000
@ FOLLOW_TYPE_SINGLE_FILE
Definition SmartScriptMgr.h:2002
@ FOLLOW_TYPE_ANGULAR
Definition SmartScriptMgr.h:2001
@ FOLLOW_TYPE_LINE
Definition SmartScriptMgr.h:1999
SMART_EVENT
Definition SmartScriptMgr.h:98
@ SMART_EVENT_TIMED_EVENT_TRIGGERED
Definition SmartScriptMgr.h:158
@ SMART_EVENT_ESCORT_REACHED
Definition SmartScriptMgr.h:139
@ SMART_EVENT_LINK
Definition SmartScriptMgr.h:160
uint32 SAIBool
Definition SmartScriptMgr.h:31
SmartActionSummonCreatureFlags
Definition SmartScriptMgr.h:735
@ SMART_ESCORT_TARGETS
Definition SmartScriptMgr.h:40
@ SMARTCAST_TRIGGERED
Definition SmartScriptMgr.h:1982
@ SMARTCAST_ENABLE_COMBAT_MOVE_ON_LOS
Definition SmartScriptMgr.h:1990
@ SMARTCAST_COMBAT_MOVE
Definition SmartScriptMgr.h:1987
@ SMARTCAST_INTERRUPT_PREVIOUS
Definition SmartScriptMgr.h:1981
@ SMARTCAST_AURA_NOT_PRESENT
Definition SmartScriptMgr.h:1986
@ SMARTCAST_THREATLIST_NOT_SINGLE
Definition SmartScriptMgr.h:1988
@ SMARTCAST_TARGET_POWER_MANA
Definition SmartScriptMgr.h:1989
@ AURA_REMOVE_BY_EXPIRE
Definition SpellAuraDefines.h:395
@ SPELLVALUE_BASE_POINT1
Definition SpellDefines.h:122
@ SPELLVALUE_BASE_POINT2
Definition SpellDefines.h:123
@ SPELLVALUE_BASE_POINT0
Definition SpellDefines.h:121
TriggerCastFlags
Definition SpellDefines.h:140
@ TRIGGERED_FULL_MASK
Will return SPELL_FAILED_DONT_REPORT in CheckCast functions.
Definition SpellDefines.h:158
@ TRIGGERED_NONE
Definition SpellDefines.h:141
#define sSpellMgr
Definition SpellMgr.h:847
#define CAST_AI(a, b)
Definition UnitAI.h:26
#define ENSURE_AI(a, b)
Definition UnitAI.h:27
@ MOVEMENTFLAG_ONTRANSPORT
Definition UnitDefines.h:381
NPCFlags
Non Player Character flags.
Definition UnitDefines.h:320
SheathState
Definition UnitDefines.h:128
@ UNIT_STATE_LOST_CONTROL
Definition UnitDefines.h:219
@ UNIT_STATE_ROOT
Definition UnitDefines.h:183
@ UNIT_STATE_NO_ENVIRONMENT_UPD
Definition UnitDefines.h:201
@ UNIT_STATE_NO_COMBAT_MOVEMENT
Definition UnitDefines.h:204
UnitMoveType
Definition UnitDefines.h:355
@ MOVE_RUN
Definition UnitDefines.h:357
@ UNIT_FLAG_SILENCED
Definition UnitDefines.h:270
ReactStates
Definition Unit.h:566
@ UNIT_FIELD_FLAGS_2
Definition UpdateFields.h:118
@ UNIT_VIRTUAL_ITEM_SLOT_ID
Definition UpdateFields.h:116
@ UNIT_FIELD_FLAGS
Definition UpdateFields.h:117
@ UNIT_NPC_EMOTESTATE
Definition UpdateFields.h:140
@ UNIT_FIELD_BYTES_1
Definition UpdateFields.h:131
@ UNIT_DYNAMIC_FLAGS
Definition UpdateFields.h:136
@ GAMEOBJECT_FLAGS
Definition UpdateFields.h:399
#define sWaypointMgr
Definition WaypointMgr.h:54
#define sWorldState
Definition WorldState.h:377
WorldStateEvent
Definition WorldState.h:42
Say
Definition boss_broodlord_lashlayer.cpp:29
Seats
Definition boss_flame_leviathan.cpp:167
Definition ChatTextBuilder.h:31
Definition SpellAuras.h:88
void StartCinematic(uint32 const cinematicSequenceId)
Definition CinematicMgr.cpp:31
Definition CreatureAI.h:69
void Talk(uint8 id, WorldObject const *whisperTarget=nullptr, Milliseconds delay=0ms)
Causes the creature to talk/say the text assigned to their entry in the creature_text database table.
Definition CreatureAI.cpp:67
void SetReputationRewardDisabled(bool disable)
Definition Creature.h:378
void SetHomePosition(float x, float y, float z, float o)
Definition Creature.h:347
void Respawn(bool force=false)
Definition Creature.cpp:2044
void GetRespawnPosition(float &x, float &y, float &z, float *ori=nullptr, float *dist=nullptr) const
Definition Creature.cpp:3108
void GetHomePosition(float &x, float &y, float &z, float &ori) const
Definition Creature.h:349
void SendZoneUnderAttackMessage(Player *attacker)
Send a message to LocalDefense channel for players opposition team in the zone.
Definition Creature.cpp:2872
void GetTransportHomePosition(float &x, float &y, float &z, float &ori) const
Definition Creature.h:354
void DoFleeToGetAssistance()
Definition Creature.cpp:1090
bool IsRooted() const
Definition Creature.h:89
void SetCorpseDelay(uint32 delay)
Definition Creature.h:74
void SetLootRewardDisabled(bool disable)
Definition Creature.h:380
void SetReactState(ReactStates state)
A creature can have 3 ReactStates : Agressive, Passive, Neutral.
Definition Creature.h:100
void LoadPath(uint32 pathid)
Definition Creature.h:358
Definition SpellDefines.h:173
void AddSpellMod(SpellValueMod mod, int32 value)
Definition SpellDefines.h:175
Definition EnumFlag.h:66
void AddEventAtOffset(BasicEvent *event, Milliseconds offset, uint8 eventGroup=0)
Definition EventProcessor.h:108
Definition GameObjectAI.h:33
virtual void SetData(uint32, uint32)
Definition GameObjectAI.h:62
void UseDoorOrButton(uint32 time_to_restore=0, bool alternative=false, Unit *user=nullptr)
Definition GameObject.cpp:1429
bool isSpawnedByDefault() const
Definition GameObject.h:197
void SetLootState(LootState s, Unit *unit=nullptr)
Definition GameObject.cpp:2484
void SetRespawnTime(int32 respawn)
Definition GameObject.cpp:1288
GameobjectTypes GetGoType() const
Definition GameObject.h:204
void Respawn()
Definition GameObject.cpp:1303
void DespawnOrUnsummon(Milliseconds delay=0ms, Seconds forcedRespawnTime=0s)
Definition GameObject.cpp:928
void CastSpell(Unit *target, uint32 spell)
Definition GameObject.cpp:2099
virtual bool SetBossState(uint32 id, EncounterState state)
Definition InstanceScript.cpp:400
virtual void DoAction(int32)
Definition InstanceScript.h:286
static std::string GetBossStateName(uint8 state)
Definition InstanceScript.cpp:844
Definition LinkedList.h:139
bool IsEmpty() const
Definition LinkedList.h:97
Definition MapRefMgr.h:26
iterator begin()
Definition MapRefMgr.h:36
iterator end()
Definition MapRefMgr.h:37
bool SpawnGroupSpawn(uint32 groupId, bool ignoreRespawn=false, bool force=false)
Definition Map.cpp:2642
void LoadGrid(float x, float y)
Definition Map.cpp:216
PlayerList const & GetPlayers() const
Definition Map.h:335
bool SpawnGroupDespawn(uint32 groupId, bool deleteRespawnTimes=false)
Definition Map.cpp:2726
void MoveFormation(Unit *leader, float dist, float angle, uint32 point1, uint32 point2)
Definition MotionMaster.cpp:471
void MovePoint(uint32 id, Position const &pos, ForcedMovement forcedMovement=FORCED_MOVEMENT_NONE, float speed=0.f, bool generatePath=true, bool forceDestination=true, std::optional< AnimTier > animTier=std::nullopt)
Definition MotionMaster.h:241
void MoveWaypoint(uint32 path_id, bool repeatable, PathSource pathSource=PathSource::WAYPOINT_MGR)
Move the unit following a specific path. Doesn't work with UNIT_FLAG_DISABLE_MOVE.
Definition MotionMaster.cpp:1014
void MovementExpired(bool reset=true)
Definition MotionMaster.h:207
void MoveJump(Position const &pos, float speedXY, float speedZ, uint32 id=0)
Definition MotionMaster.h:257
void MoveIdle()
Definition MotionMaster.cpp:235
void MoveFollow(Unit *target, float dist, float angle, MovementSlot slot=MOTION_SLOT_ACTIVE, bool inheritWalkState=true, bool inheritSpeed=true)
The unit will follow this target. Doesn't work with UNIT_FLAG_DISABLE_MOVE.
Definition MotionMaster.cpp:448
void MoveRandom(float wanderDistance=0.0f)
Enable a random movement in desired range around the unit. Doesn't work with UNIT_FLAG_DISABLE_MOVE.
Definition MotionMaster.cpp:245
static ObjectGuid const Empty
Definition ObjectGuid.h:123
std::string ToString() const
Definition ObjectGuid.cpp:48
static CreatureModel const * ChooseDisplayId(CreatureTemplate const *cinfo, CreatureData const *data=nullptr)
Definition ObjectMgr.cpp:1644
bool HasFlag(uint16 index, uint32 flag) const
Definition Object.cpp:880
virtual void SetObjectScale(float scale)
Definition Object.h:127
Definition GossipDef.h:259
CinematicMgr & GetCinematicMgr()
Definition Player.h:1403
void GroupEventHappens(uint32 questId, WorldObject const *pEventObject)
Definition PlayerQuest.cpp:1892
void PrepareGossipMenu(WorldObject *source, uint32 menuId=0, bool showQuests=false)
Definition PlayerGossip.cpp:32
void RewardPlayerAndGroupAtEvent(uint32 creature_id, WorldObject *pRewardSource)
Definition Player.cpp:13046
Definition QuestDef.h:210
void SetInvincibilityHpLevel(uint32 level)
Definition SmartAI.h:189
void SetData(uint32 id, uint32 value) override
Definition SmartAI.h:167
void IncPhase(uint32 p)
Definition SmartScript.cpp:5672
void StoreTargetList(ObjectVector const &targets, uint32 id)
Definition SmartScript.h:93
void RetryLater(SmartScriptHolder &e, bool ignoreChanceRoll=false)
Definition SmartScript.cpp:5352
void StoreCounter(uint32 id, uint32 value, uint32 reset, uint32 subtract)
Definition SmartScript.h:108
std::optional< std::reference_wrapper< SmartScriptHolder > > FindLinkedEvent(uint32 link)
Definition SmartScript.h:269
std::deque< SmartScriptFrame > executionStack
Definition SmartScript.h:286
void SetPhaseReset(bool allow)
Definition SmartScript.h:205
void GetTargets(ObjectVector &targets, SmartScriptHolder const &e, WorldObject *invoker=nullptr) const
Definition SmartScript.cpp:3627
void OnReset()
Definition SmartScript.cpp:131
void InstallTemplate(SmartScriptHolder const &e)
Definition SmartScript.cpp:3515
ObjectGuid goOrigGUID
Definition SmartScript.h:229
void DecPhase(uint32 p)
Definition SmartScript.cpp:5678
ObjectGuid meOrigGUID
Definition SmartScript.h:227
Definition SpellInfo.h:340
SpellSchoolMask GetSchoolMask() const
Definition SpellInfo.cpp:1921
bool HasAttribute(SpellAttr0 attribute) const
Definition SpellInfo.h:441
int32 CalcPowerCost(WorldObject const *caster, SpellSchoolMask schoolMask, Spell *spell=nullptr) const
Definition SpellInfo.cpp:2829
void ModifyThreatByPercent(Unit *target, int32 percent)
Definition ThreatManager.h:150
size_t GetThreatListSize() const
Definition ThreatManager.cpp:298
Definition VehicleDefines.h:130
virtual void SetData(uint32, uint32)
Definition UnitAI.h:219
virtual void AttackStart(Unit *)
Definition UnitAI.cpp:29
uint8 getGender() const
Definition Unit.h:849
void SetFacingToObject(WorldObject *object, Milliseconds timed=0ms)
Definition Unit.cpp:16078
void SetFacingTo(float ori)
Definition Unit.cpp:16068
float GetSpeed(UnitMoveType mtype) const
Definition Unit.cpp:11047
void InterruptNonMeleeSpells(bool withDelayed, uint32 spellid=0, bool withInstant=true, bool bySelf=false)
Definition Unit.cpp:4047
float GetSpellMinRangeForTarget(Unit const *target, SpellInfo const *spellInfo) const
Definition Unit.cpp:11509
Player * GetCharmerOrOwnerPlayerOrPlayerItself() const
Definition Unit.cpp:7503
static void Kill(Unit *killer, Unit *victim, bool durabilityLoss=true, WeaponAttackType attackType=BASE_ATTACK, SpellInfo const *spellProto=nullptr, Spell const *spell=nullptr)
Definition Unit.cpp:13580
MotionMaster * GetMotionMaster()
Definition Unit.h:1761
void SetUnitMovementFlags(uint32 f)
Definition Unit.h:777
SpellCastResult CastCustomSpell(Unit *victim, uint32 spellId, int32 const *bp0, int32 const *bp1, int32 const *bp2, bool triggered, Item *castItem=nullptr, AuraEffect const *triggeredByAura=nullptr, ObjectGuid originalCaster=ObjectGuid::Empty)
Definition Unit.cpp:1429
bool IsAlive() const
Definition Unit.h:1796
void StopMoving()
Definition Unit.cpp:12639
void SendPlaySpellVisual(uint32 id)
Definition Unit.cpp:14795
bool HasAura(uint32 spellId, ObjectGuid casterGUID=ObjectGuid::Empty, ObjectGuid itemCasterGUID=ObjectGuid::Empty, uint8 reqEffMask=0) const
Definition Unit.cpp:5764
virtual void SetSheath(SheathState sheathed)
Definition Unit.h:1780
float GetSpellMaxRangeForTarget(Unit const *target, SpellInfo const *spellInfo) const
Definition Unit.cpp:11489
bool HasUnitMovementFlag(uint32 f) const
Definition Unit.h:775
TransportBase * GetDirectTransport() const
Definition Unit.cpp:14651
void SendMovementFlagUpdate(bool self=false)
Definition Unit.cpp:12693
void EngageWithTarget(Unit *who)
Definition Unit.cpp:7306
SpellCastResult CastSpell(SpellCastTargets const &targets, SpellInfo const *spellInfo, CustomSpellValues const *value, TriggerCastFlags triggerFlags=TRIGGERED_NONE, Item *castItem=nullptr, AuraEffect const *triggeredByAura=nullptr, ObjectGuid originalCaster=ObjectGuid::Empty)
Definition Unit.cpp:1372
void RemoveAurasDueToSpell(uint32 spellId, ObjectGuid casterGUID=ObjectGuid::Empty, uint8 reqEffMask=0, AuraRemoveMode removeMode=AURA_REMOVE_BY_DEFAULT)
Definition Unit.cpp:4936
void SetSpeed(UnitMoveType mtype, float rate, bool forced=false)
Definition Unit.cpp:11052
ThreatManager & GetThreatMgr()
Definition Unit.h:957
ObjectGuid GetTransGUID() const override
Definition Unit.cpp:14640
bool IsAIEnabled
Definition Unit.h:2102
bool HasUnitState(const uint32 f) const
Definition Unit.h:737
float GetPowerPct(Powers power) const
Definition Unit.h:1143
void SetDisableGravity(bool disable)
Definition Unit.cpp:16119
float GetMeleeRange(Unit const *target) const
Definition Unit.cpp:807
uint32 GetPower(Powers power) const
Definition Unit.h:1141
void CombatStop(bool includingCast=false, bool mutualPvP=true)
Definition Unit.cpp:7273
void KillSelf(bool durabilityLoss=true, WeaponAttackType attackType=BASE_ATTACK, SpellInfo const *spellProto=nullptr, Spell const *spell=nullptr)
Definition Unit.h:1240
bool CanHaveThreatList(bool skipAliveCheck=false) const
Definition Unit.cpp:11179
void SetInFront(WorldObject const *target)
Definition Unit.cpp:16062
bool isDead() const
Definition Unit.h:1798
Definition Vehicle.h:28
Map * FindMap() const
Definition Object.h:638
bool IsWithinLOSInMap(WorldObject const *obj, VMAP::ModelIgnoreFlags ignoreFlags=VMAP::ModelIgnoreFlags::Nothing, LineOfSightChecks checks=LINEOFSIGHT_ALL_CHECKS, Optional< float > collisionHeight={ }, Optional< float > combatReach={ }) const
Definition Object.cpp:1412
void GetNearPoint(WorldObject const *searcher, float &x, float &y, float &z, float searcher_size, float distance2d, float absAngle, float controlZ=0, Position const *startPos=nullptr) const
Definition Object.cpp:2752
void SummonGameObjectGroup(uint8 group, std::list< GameObject * > *list=nullptr)
Definition Object.cpp:2544
std::string const & GetName() const
Definition Object.h:535
void AddObjectToRemoveList()
Definition Object.cpp:2232
EventProcessor m_Events
Definition Object.h:749
TempSummon * SummonCreature(uint32 id, Position const &pos, TempSummonType spwtype=TEMPSUMMON_MANUAL_DESPAWN, uint32 despwtime=0, uint32 vehId=0, SummonPropertiesEntry const *properties=nullptr, bool visibleBySummonerOnly=false) const
Definition Object.cpp:2453
float GetDistance(WorldObject const *obj) const
Definition Object.cpp:1304
uint32 GetAreaId() const
Definition Object.cpp:3179
uint32 GetZoneId() const
Definition Object.cpp:3171
GameObject * SummonGameObject(uint32 entry, float x, float y, float z, float ang, float rotation0, float rotation1, float rotation2, float rotation3, uint32 respawnTime, bool checkTransport=true, GOSummonType summonType=GO_SUMMON_TIMED_OR_CORPSE_DESPAWN)
Definition Object.cpp:2467
void SummonCreatureGroup(uint8 group, std::list< TempSummon * > *list=nullptr)
Definition Object.cpp:2530
virtual float GetCombatReach() const
Definition Object.h:513
void GetRandomPoint(Position const &srcPos, float distance, float &rand_x, float &rand_y, float &rand_z) const
Definition Object.cpp:1567
Creature * SummonTrigger(float x, float y, float z, float ang, uint32 dur, bool setLevel=false, CreatureAI *(*GetAI)(Creature *)=nullptr)
Definition Object.cpp:2502
Player session in the World.
Definition WorldSession.h:430
virtual void SetData(uint32, uint32)
Definition ZoneScript.h:52
virtual void SetGuidData(uint32, ObjectGuid)
Definition ZoneScript.h:45
auto SelectRandomContainerElement(C const &container) -> typename std::add_const< decltype(*std::begin(container))>::type &
Definition Containers.h:133
std::string ToString(Type &&val, Params &&... params)
Definition StringConvert.h:250
Definition ObjectAccessor.h:61
Player * GetPlayer(Map const *, ObjectGuid const &guid)
Definition ObjectAccessor.cpp:244
Definition CreatureData.h:170
uint32 CreatureDisplayID
Definition CreatureData.h:180
float DisplayScale
Definition CreatureData.h:181
Definition CreatureData.h:360
uint32 ItemEntry[MAX_EQUIPMENT_ITEMS]
Definition CreatureData.h:361
Definition Position.h:27
float GetAngle(Position const *pos) const
Definition Position.cpp:85
float m_positionZ
Definition Position.h:57
float m_positionX
Definition Position.h:55
float GetPositionZ() const
Definition Position.h:123
float m_positionY
Definition Position.h:56
float GetOrientation() const
Definition Position.h:124
void SetOrientation(float orientation)
Definition Position.h:116
float GetPositionX() const
Definition Position.h:121
void GetPosition(float &x, float &y) const
Definition Position.h:126
float GetPositionY() const
Definition Position.h:122
void RelocatePolarOffset(float angle, float dist, float z=0.0f)
Definition Position.cpp:34
Definition SmartScriptMgr.h:746
struct SmartAction::@75::@98 combatMove
uint32 followState
Definition SmartScriptMgr.h:1455
uint32 visualId
Definition SmartScriptMgr.h:1450
uint32 targetParam2
Definition SmartScriptMgr.h:850
struct SmartAction::@75::@100 incEventPhase
struct SmartAction::@75::@106 killedMonster
SAIBool disableForceDestination
Definition SmartScriptMgr.h:1207
std::array< uint32, SMART_ACTION_PARAM_COUNT > emotes
Definition SmartScriptMgr.h:833
uint32 forcedMovement
Definition SmartScriptMgr.h:1032
uint32 repeatMax
Definition SmartScriptMgr.h:1109
uint32 phaseMin
Definition SmartScriptMgr.h:935
uint32 targetsLimit
Definition SmartScriptMgr.h:841
struct SmartAction::@75::@181 movementSpeed
struct SmartAction::@75::@186 setScale
SAIBool transport
Definition SmartScriptMgr.h:1203
struct SmartAction::@75::@192 wpDataRandom
struct SmartAction::@75::@82 randomSound
struct SmartAction::@75::@120 summonGO
uint32 startAngle
Definition SmartScriptMgr.h:1443
SAIBool reset
Definition SmartScriptMgr.h:1094
std::array< uint32, SMART_ACTION_PARAM_COUNT > actionLists
Definition SmartScriptMgr.h:1157
struct SmartAction::@75::@185 scriptSpawn
uint32 delay
Definition SmartScriptMgr.h:756
struct SmartAction::@75::@163 startClosestWaypoint
uint32 random
Definition SmartScriptMgr.h:1338
uint32 quickChange
Definition SmartScriptMgr.h:1337
uint32 targetParam4
Definition SmartScriptMgr.h:1467
uint32 dist
Definition SmartScriptMgr.h:920
uint32 group
Definition SmartScriptMgr.h:1260
SAIBool disable
Definition SmartScriptMgr.h:1392
struct SmartAction::@75::@180 corpseDelay
struct SmartAction::@75::@194 worldStateScript
struct SmartAction::@75::@111 callHelp
uint32 spell
Definition SmartScriptMgr.h:838
uint32 minHP
Definition SmartScriptMgr.h:987
SAIBool force
Definition SmartScriptMgr.h:1314
struct SmartAction::@75::@177 summonVortex
uint32 flags
Definition SmartScriptMgr.h:847
struct SmartAction::@75::@97 autoAttack
SAIBool loot
Definition SmartScriptMgr.h:1510
uint32 distanceBetweenSummons
Definition SmartScriptMgr.h:1353
uint32 data
Definition SmartScriptMgr.h:947
struct SmartAction::@75::@105 randomPhaseRange
uint32 entry
Definition SmartScriptMgr.h:922
struct SmartAction::@75::@91 crossCast
struct SmartAction::@75::@129 setSwim
uint32 quest
Definition SmartScriptMgr.h:817
struct SmartAction::@75::@150 moveToPosTarget
struct SmartAction::@75::@172 orientation
struct SmartAction::@75::@78 simpleTalk
uint32 triggerFlags
Definition SmartScriptMgr.h:840
struct SmartAction::@75::@87 questOffer
uint32 bp1
Definition SmartScriptMgr.h:1368
uint32 distance
Definition SmartScriptMgr.h:780
SAIBool removeObjectFromWorld
Definition SmartScriptMgr.h:982
uint32 min
Definition SmartScriptMgr.h:1106
uint32 spawnTimerMax
Definition SmartScriptMgr.h:1427
uint32 subtract
Definition SmartScriptMgr.h:1095
struct SmartAction::@75::@110 die
uint32 a
Definition SmartScriptMgr.h:1377
struct SmartAction::@75::@151 sendGossipMenu
struct SmartAction::@75::@104 randomPhase
struct SmartAction::@75::@198 setGossipMenu
struct SmartAction::@75::@133 timeEvent
SAIBool invokerGUID
Definition SmartScriptMgr.h:1419
struct SmartAction::@75::@191 wpData
uint32 percent
Definition SmartScriptMgr.h:988
uint32 dec
Definition SmartScriptMgr.h:904
uint32 milliseconds
Definition SmartScriptMgr.h:964
struct SmartAction::@75::@125 item
uint32 summonEntry
Definition SmartScriptMgr.h:1350
struct SmartAction::@75::@84 randomMusic
uint32 followType
Definition SmartScriptMgr.h:1456
uint32 instanceTarget
Definition SmartScriptMgr.h:1387
struct SmartAction::@75::@196 reward
uint32 credit
Definition SmartScriptMgr.h:923
uint32 controlled
Definition SmartScriptMgr.h:1204
uint32 alternative
Definition SmartScriptMgr.h:856
uint32 targetParam1
Definition SmartScriptMgr.h:849
uint32 mapID
Definition SmartScriptMgr.h:1087
uint32 stopMovement
Definition SmartScriptMgr.h:1344
struct SmartAction::@75::@134 movie
struct SmartAction::@75::@94 summonCreature
uint32 charges
Definition SmartScriptMgr.h:915
struct SmartAction::@75::@113 forceDespawn
struct SmartAction::@75::@103 follow
uint32 model
Definition SmartScriptMgr.h:773
uint32 duration
Definition SmartScriptMgr.h:754
SAIBool attackInvoker
Definition SmartScriptMgr.h:869
SAIBool useTalkTarget
Definition SmartScriptMgr.h:755
SAIBool run
Definition SmartScriptMgr.h:1070
struct SmartAction::@75::@200 groupSpawn
struct SmartAction::@75::@176 castCustom
uint32 value
Definition SmartScriptMgr.h:1093
struct SmartAction::@75::@140 timedActionList
uint32 movementExpired
Definition SmartScriptMgr.h:1345
struct SmartAction::@75::@117 moveRandom
uint32 targetParam3
Definition SmartScriptMgr.h:851
uint32 respawnDelay
Definition SmartScriptMgr.h:1428
SAIBool swim
Definition SmartScriptMgr.h:1082
uint32 combatReach
Definition SmartScriptMgr.h:1206
uint32 sound2
Definition SmartScriptMgr.h:786
struct SmartAction::@75::@188 spellVisual
uint32 spawnPos
Definition SmartScriptMgr.h:1308
struct SmartAction::@75::@92 activateObject
struct SmartAction::@75::@167 setHomePos
struct SmartAction::@75::@161 gameEventStop
uint32 pathId2
Definition SmartScriptMgr.h:1284
uint32 creature
Definition SmartScriptMgr.h:772
struct SmartAction::@75::@190 orientationTarget
uint32 spawnTimerMin
Definition SmartScriptMgr.h:1426
struct SmartAction::@75::@132 storeTargets
struct SmartAction::@75::@114 invincHP
uint32 angle
Definition SmartScriptMgr.h:921
uint32 field
Definition SmartScriptMgr.h:946
struct SmartAction::@75::@199 gameobjectGroup
uint32 range
Definition SmartScriptMgr.h:861
struct SmartAction::@75::@95 threatPCT
struct SmartAction::@75::@89 randomEmote
struct SmartAction::@75::@162 gameEventStart
uint32 flag
Definition SmartScriptMgr.h:1127
uint32 sound3
Definition SmartScriptMgr.h:787
uint32 targetsummon
Definition SmartScriptMgr.h:1021
struct SmartAction::@75::@145 jump
uint32 chance
Definition SmartScriptMgr.h:1110
struct SmartAction::@75::@131 setCounter
uint32 state
Definition SmartScriptMgr.h:828
struct SmartAction::@75::@90 cast
struct SmartAction::@75::@108 setInstanceData64
uint32 sound1
Definition SmartScriptMgr.h:785
struct SmartAction::@75::@80 morphOrMount
struct SmartAction::@75::@116 setData
uint32 forceRespawnTimer
Definition SmartScriptMgr.h:981
uint32 speed
Definition SmartScriptMgr.h:1076
uint32 sound4
Definition SmartScriptMgr.h:788
struct SmartAction::@75::@147 flee
uint32 targetType
Definition SmartScriptMgr.h:848
uint32 repetitions
Definition SmartScriptMgr.h:1442
struct SmartAction::@75::@174 coneSummon
uint32 aliveState
Definition SmartScriptMgr.h:925
SAIBool onlySelf
Definition SmartScriptMgr.h:779
uint32 attackScriptOwner
Definition SmartScriptMgr.h:870
uint32 speedxy
Definition SmartScriptMgr.h:1180
uint32 pointId
Definition SmartScriptMgr.h:1202
SAIBool attack
Definition SmartScriptMgr.h:888
uint32 repeatMin
Definition SmartScriptMgr.h:1108
struct SmartAction::@75::@122 wpStart
uint32 scale
Definition SmartScriptMgr.h:1435
SAIBool fly
Definition SmartScriptMgr.h:1075
uint32 textGroupID
Definition SmartScriptMgr.h:753
uint32 castFlags
Definition SmartScriptMgr.h:839
struct SmartAction::@75::@179 disableEvade
std::array< uint32, SMART_ACTION_PARAM_COUNT > phases
Definition SmartScriptMgr.h:930
SAIBool dontDespawn
Definition SmartScriptMgr.h:1430
uint32 turnAngle
Definition SmartScriptMgr.h:1339
uint32 textId
Definition SmartScriptMgr.h:1360
uint32 gossipMenuId
Definition SmartScriptMgr.h:1218
uint32 speedz
Definition SmartScriptMgr.h:1181
SAIBool repeat
Definition SmartScriptMgr.h:1034
struct SmartAction::@75::@173 stopMotion
uint32 gossipNpcTextId
Definition SmartScriptMgr.h:1219
uint32 mask
Definition SmartScriptMgr.h:993
uint32 pathId1
Definition SmartScriptMgr.h:1283
uint32 phi_delta
Definition SmartScriptMgr.h:1380
uint32 count
Definition SmartScriptMgr.h:1055
struct SmartAction::@75::@112 setSheath
uint32 inc
Definition SmartScriptMgr.h:903
uint32 phaseMax
Definition SmartScriptMgr.h:936
struct SmartAction::@75::@130 teleport
uint32 timer
Definition SmartScriptMgr.h:1397
uint32 ContactDistance
Definition SmartScriptMgr.h:1205
struct SmartAction::@75::@79 faction
PathSource pathSource
Definition SmartScriptMgr.h:1287
struct SmartAction::@75::@135 equip
uint32 k
Definition SmartScriptMgr.h:1378
uint32 distanceBetweenRings
Definition SmartScriptMgr.h:1352
uint32 coneLength
Definition SmartScriptMgr.h:1354
uint32 counterId
Definition SmartScriptMgr.h:1092
SAIBool withEmote
Definition SmartScriptMgr.h:970
struct SmartAction::@75::@146 movementFlag
uint32 param
Definition SmartScriptMgr.h:1492
uint32 max
Definition SmartScriptMgr.h:1107
uint32 selfJump
Definition SmartScriptMgr.h:1182
struct SmartAction::@75::@183 cinematic
uint32 maxId
Definition SmartScriptMgr.h:1320
uint32 r_max
Definition SmartScriptMgr.h:1379
struct SmartAction::@75::@136 unitFlag
uint32 speedFraction
Definition SmartScriptMgr.h:1404
struct SmartAction::@75::@88 react
struct SmartAction::@75::@119 setActive
struct SmartAction::@75::@159 creatureGroup
SAIBool fail
Definition SmartScriptMgr.h:1049
struct SmartAction::@75::@124 wpStop
SAIBool directAdd
Definition SmartScriptMgr.h:823
uint32 bp2
Definition SmartScriptMgr.h:1369
uint32 disableGravity
Definition SmartScriptMgr.h:1077
uint32 sound
Definition SmartScriptMgr.h:778
uint32 threatINC
Definition SmartScriptMgr.h:876
uint32 coneAngle
Definition SmartScriptMgr.h:1355
uint32 summonDuration
Definition SmartScriptMgr.h:1351
struct SmartAction::@75::@148 RespawnTarget
struct SmartAction::@75::@175 playerTalk
uint32 threatDEC
Definition SmartScriptMgr.h:877
SAIBool reputation
Definition SmartScriptMgr.h:1509
uint32 ignoreRespawn
Definition SmartScriptMgr.h:1531
uint32 stepAngle
Definition SmartScriptMgr.h:1444
struct SmartAction::@75::@153 sendTargetToTarget
uint32 reactState
Definition SmartScriptMgr.h:1037
uint32 speedInteger
Definition SmartScriptMgr.h:1403
struct SmartAction::@75::@77 talk
uint32 index
Definition SmartScriptMgr.h:1420
struct SmartAction::@75::@123 wpPause
struct SmartAction::@75::@83 music
uint32 actionId
Definition SmartScriptMgr.h:1385
struct SmartAction::@75::@169 randomTimedEvent
uint32 despawnTime
Definition SmartScriptMgr.h:1020
struct SmartAction::@75::@128 setFly
uint32 goRespawnTime
Definition SmartScriptMgr.h:1197
struct SmartAction::@75::@115 ingamePhaseMask
uint32 factionID
Definition SmartScriptMgr.h:767
uint32 eventId
Definition SmartScriptMgr.h:1491
uint32 groupId
Definition SmartScriptMgr.h:1530
struct SmartAction::@75::@189 followGroup
uint32 pathId
Definition SmartScriptMgr.h:1472
SAIBool move
Definition SmartScriptMgr.h:893
struct SmartAction::@75::@178 doAction
struct SmartAction::@75::@149 moveToPos
std::array< uint32, MAX_EQUIPMENT_ITEMS > slots
Definition SmartScriptMgr.h:1122
struct SmartAction::@75::@127 setRun
struct SmartAction::@75::@187 radialSummon
struct SmartAction::@75::@99 setEventPhase
struct SmartAction::@75::@107 setInstanceData
uint32 questID
Definition SmartScriptMgr.h:822
uint32 bp3
Definition SmartScriptMgr.h:1370
uint32 pathID
Definition SmartScriptMgr.h:1033
uint32 emote
Definition SmartScriptMgr.h:812
struct SmartAction::@75::@102 removeAura
uint32 id
Definition SmartScriptMgr.h:1027
uint32 minId
Definition SmartScriptMgr.h:1319
uint32 phase
Definition SmartScriptMgr.h:898
uint32 sheath
Definition SmartScriptMgr.h:975
uint32 isNegative
Definition SmartScriptMgr.h:1386
uint32 creditType
Definition SmartScriptMgr.h:924
struct SmartAction::@75::@141 randTimedActionList
struct SmartAction::@75::@154 setRangedMovement
struct SmartAction::@75::@184 setGuid
Definition SmartScriptMgr.h:205
uint32 repeatMin
Definition SmartScriptMgr.h:216
uint32 repeatMax
Definition SmartScriptMgr.h:217
bool runOnce
Definition SmartScriptMgr.h:2033
uint32 link
Definition SmartScriptMgr.h:2016
bool IsAreatriggerScript() const
Definition SmartScriptMgr.h:2028
uint32 event_id
Definition SmartScriptMgr.h:2015
int32 entryOrGuid
Definition SmartScriptMgr.h:2013
uint32 GetScriptType() const
Definition SmartScriptMgr.h:2023
uint32 GetTargetType() const
Definition SmartScriptMgr.h:2026
uint32 GetActionType() const
Definition SmartScriptMgr.h:2025
struct SmartTarget::@201::@205 unitRange
float o
Definition SmartScriptMgr.h:1613
uint32 maxDist
Definition SmartScriptMgr.h:1619
uint32 range
Definition SmartScriptMgr.h:1740
float x
Definition SmartScriptMgr.h:1613
uint32 self
Definition SmartScriptMgr.h:1742
uint32 amount
Definition SmartScriptMgr.h:1741
struct SmartTarget::@201::@222 randomPoint
float y
Definition SmartScriptMgr.h:1613
float z
Definition SmartScriptMgr.h:1613
Definition WaypointDefines.h:37
float X
Definition WaypointDefines.h:48
float Z
Definition WaypointDefines.h:48
float Y
Definition WaypointDefines.h:48
Definition WaypointDefines.h:60
std::vector< WaypointNode > Nodes
Definition WaypointDefines.h:68

References SmartAction::a, SmartScriptHolder::action, SmartAction::actionId, SmartAction::actionLists, SmartAction::activateObject, EventProcessor::AddEventAtOffset(), WorldObject::AddObjectToRemoveList(), CustomSpellValues::AddSpellMod(), ThreatManager::AddThreat(), Creature::AI(), GameObject::AI(), SmartAction::aliveState, SmartAction::alternative, SmartTarget::amount, SmartAction::angle, SmartAction::anim, SmartAction::animTier, SmartAction::attack, SmartAction::attackInvoker, SmartAction::attackScriptOwner, UnitAI::AttackStart(), AURA_REMOVE_BY_EXPIRE, SmartAction::autoAttack, MapRefMgr::begin(), SmartAction::bp1, SmartAction::bp2, SmartAction::bp3, BROADCAST_TEXT_CALL_FOR_HELP, BROADCAST_TEXT_FLEE_FOR_ASSIST, SmartAction::byte1, SpellInfo::CalcPowerCost(), SmartAction::callHelp, Unit::CanHaveThreatList(), SmartAction::cast, CAST_AI, SmartAction::castCustom, Unit::CastCustomSpell(), SmartAction::castFlags, Unit::CastSpell(), GameObject::CastSpell(), SmartAction::chance, SmartAction::charges, CHAT_MSG_ADDON, CHAT_MSG_MONSTER_EMOTE, ObjectMgr::ChooseDisplayId(), SmartAction::cinematic, ClearGossipMenuFor(), SmartAction::combatDistance, SmartAction::combatMove, SmartAction::combatReach, Unit::CombatStop(), SmartAction::coneAngle, SmartAction::coneLength, SmartAction::coneSummon, SmartAction::ContactDistance, SmartAction::controlled, SmartAction::corpseDelay, SmartAction::count, SmartAction::counterId, CreateSmartEvent(), SmartAction::creature, CreatureModel::CreatureDisplayID, SmartAction::creatureGroup, SmartAction::credit, SmartAction::creditType, SmartAction::crossCast, SmartAction::data, SmartAction::dec, DecPhase(), DEFAULT_LOCALE, SmartAction::delay, SmartAction::delunitByte, GameObject::DespawnOrUnsummon(), SmartAction::despawnTime, SmartAction::die, SmartAction::directAdd, SmartAction::disable, SmartAction::disableEvade, SmartAction::disableForceDestination, SmartAction::disableGravity, CreatureModel::DisplayScale, SmartAction::dist, SmartAction::distance, SmartAction::distanceBetweenRings, SmartAction::distanceBetweenSummons, SmartAction::doAction, InstanceScript::DoAction(), Creature::DoFleeToGetAssistance(), SmartAction::dontDespawn, SmartAction::duration, SmartAction::emote, SmartAction::emotes, ObjectGuid::Empty, MapRefMgr::end(), Unit::EngageWithTarget(), ENSURE_AI, SmartAction::entry, SmartScriptHolder::entryOrGuid, SmartAction::equip, SmartScriptHolder::event, SmartEvent::event_chance, SmartEvent::event_flags, SmartScriptHolder::event_id, SmartAction::eventId, executionStack, SmartAction::faction, SmartAction::factionID, SmartAction::fail, SmartAction::field, FindLinkedEvent(), WorldObject::FindMap(), SmartAction::flag, SmartAction::flags, SmartAction::flee, SmartAction::fly, SmartAction::follow, FOLLOW_TYPE_ANGULAR, FOLLOW_TYPE_CIRCLE, FOLLOW_TYPE_COLUMN, FOLLOW_TYPE_LINE, FOLLOW_TYPE_SEMI_CIRCLE_BEHIND, FOLLOW_TYPE_SEMI_CIRCLE_FRONT, FOLLOW_TYPE_SINGLE_FILE, SmartAction::followGroup, SmartAction::followState, SmartAction::followType, SmartAction::force, FORCED_MOVEMENT_NONE, SmartAction::forceDespawn, SmartAction::forcedMovement, SmartAction::forceRespawnTimer, frand(), SmartAction::gameEventStart, SmartAction::gameEventStop, GAMEOBJECT_FLAGS, GAMEOBJECT_TYPE_DOOR, SmartAction::gameobjectGroup, SmartScriptHolder::GetActionType(), Position::GetAngle(), WorldObject::GetAreaId(), GetBaseObject(), InstanceScript::GetBossStateName(), Unit::GetCharmerOrOwnerPlayerOrPlayerItself(), WorldObject::GetCombatReach(), Unit::GetDirectTransport(), WorldObject::GetDistance(), Object::GetEntry(), SmartScriptHolder::GetEventType(), Unit::getGender(), GameObject::GetGoType(), Object::GetGUID(), Creature::GetHomePosition(), WorldObject::GetInstanceScript(), GetLastInvoker(), Creature::GetLootRecipient(), WorldObject::GetMap(), Unit::GetMeleeRange(), ThreatManager::GetModifiableThreatList(), Unit::GetMotionMaster(), WorldObject::GetName(), WorldObject::GetNearPoint(), Position::GetOrientation(), ObjectAccessor::GetPlayer(), Map::GetPlayers(), Position::GetPosition(), Position::GetPositionX(), Position::GetPositionY(), Position::GetPositionZ(), Unit::GetPower(), Unit::GetPowerPct(), WorldObject::GetRandomPoint(), Creature::GetRespawnPosition(), SpellInfo::GetSchoolMask(), SmartScriptHolder::GetScriptType(), Unit::GetSpeed(), Unit::GetSpellMaxRangeForTarget(), Unit::GetSpellMinRangeForTarget(), GetStoredTargetVector(), GetTargets(), SmartScriptHolder::GetTargetType(), ThreatManager::GetThreatListSize(), Unit::GetThreatMgr(), Unit::GetTransGUID(), Creature::GetTransportHomePosition(), Unit::GetVehicleKit(), GetWorldObjectsInDist(), WorldObject::GetZoneId(), go, GO_READY, SmartAction::goFlag, goOrigGUID, SmartAction::goRespawnTime, SmartAction::gossipMenuId, SmartAction::gossipNpcTextId, SmartAction::goState, SmartAction::group, Player::GroupEventHappens(), SmartAction::groupId, SmartAction::groupSpawn, SpellInfo::HasAttribute(), Unit::HasAura(), EnumFlag< T >::HasFlag(), Object::HasFlag(), Unit::HasUnitMovementFlag(), Unit::HasUnitState(), SmartAction::id, SmartAction::ignoreRespawn, SmartAction::immunity, SmartAction::inc, SmartAction::incEventPhase, IncPhase(), SmartAction::index, SmartAction::ingamePhaseMask, InitTimer(), InstallTemplate(), SmartAction::instanceTarget, Unit::InterruptNonMeleeSpells(), SmartAction::interruptSpellCasting, SmartAction::invincHP, SmartAction::invokerGUID, Unit::IsAlive(), SmartScriptHolder::IsAreatriggerScript(), IsCreature(), Unit::isDead(), Map::IsDungeon(), LinkedListHead::IsEmpty(), IsGameObject(), SmartAction::isNegative, IsPlayer(), Creature::IsRooted(), IsSmart(), IsUnit(), Unit::IsVehicle(), WorldObject::IsWithinLOSInMap(), SmartAction::item, EquipmentInfo::ItemEntry, SmartAction::jump, SmartAction::k, Unit::Kill(), SmartAction::killedMonster, Unit::KillSelf(), LANG_ADDON, LANG_UNIVERSAL, SmartScriptHolder::link, SmartAction::loadEquipment, Map::LoadGrid(), LOG_DEBUG, LOG_ERROR, SmartAction::loot, VMAP::M2, WorldObject::m_Events, Position::m_positionX, Position::m_positionY, Position::m_positionZ, SmartAction::mapID, SmartAction::mask, SmartEvent::max, SmartAction::max, MAX_EQUIPMENT_ITEMS, SmartTarget::maxDist, SmartAction::maxId, me, meOrigGUID, SmartAction::milliseconds, SmartEvent::min, SmartAction::min, SmartAction::minHP, SmartAction::minId, SmartEvent::minMaxRepeat, mLastInvoker, mLastTextID, SmartAction::model, ThreatManager::ModifyThreatByPercent(), SmartAction::morphOrMount, MOTION_SLOT_ACTIVE, MOTION_SLOT_CONTROLLED, SmartAction::move, MOVE_RUN, MotionMaster::MoveFollow(), MotionMaster::MoveFormation(), MotionMaster::MoveIdle(), MotionMaster::MoveJump(), SmartAction::movementExpired, SmartAction::movementFlag, MOVEMENTFLAG_ONTRANSPORT, SmartAction::movementSpeed, SmartAction::movementType, MotionMaster::MovePoint(), SmartAction::moveRandom, MotionMaster::MoveRandom(), SmartAction::moveToPos, SmartAction::moveToPosTarget, SmartAction::movie, mRemIDs, mStoredEvents, mTalkerEntry, mTextTimer, mUseTextTimer, SmartAction::music, SmartAction::newPower, WaypointPath::Nodes, NOMINAL_MELEE_RANGE, SmartTarget::o, SmartAction::onlySelf, OnReset(), SmartAction::orientation, SmartAction::orientationTarget, SmartAction::param, SmartAction::pathID, SmartAction::pathId, SmartAction::pathId1, SmartAction::pathId2, SmartAction::pathSource, SmartAction::percent, PersonalSpawn, SmartAction::phase, SmartAction::phaseMax, SmartAction::phaseMin, SmartAction::phases, SmartAction::phi_delta, SmartAction::playerTalk, SmartAction::pointId, SmartAction::power, POWER_MANA, SmartAction::powerType, PreferUnit, ProcessEventsFor(), SmartAction::quest, SmartAction::questID, SmartAction::questOffer, SmartAction::quickChange, SmartAction::r_max, SmartAction::radialSummon, SmartAction::random, SmartAction::randomEmote, SmartAction::randomMusic, SmartAction::randomPhase, SmartAction::randomPhaseRange, SmartTarget::randomPoint, Acore::Containers::RandomResize(), SmartAction::randomSound, SmartAction::randomTimedEvent, SmartAction::randTimedActionList, SmartAction::range, SmartTarget::range, SmartAction::react, SmartAction::reactState, SmartAction::regenHealth, Position::RelocatePolarOffset(), SmartAction::removeAura, Unit::RemoveAurasDueToSpell(), SmartAction::removeObjectFromWorld, SmartAction::repeat, SmartEvent::repeatMax, SmartAction::repeatMax, SmartEvent::repeatMin, SmartAction::repeatMin, SmartAction::repetitions, SmartAction::reputation, SmartAction::reset, ResetBaseObject(), SmartAction::respawnDelay, SmartAction::RespawnTarget, RetryLater(), SmartAction::reward, Player::RewardPlayerAndGroupAtEvent(), SmartAction::root, SmartAction::run, SmartScriptHolder::runOnce, SmartAction::scale, sCreatureTextMgr, SmartAction::scriptSpawn, Acore::Containers::SelectRandomContainerElement(), SmartTarget::self, SmartAction::selfJump, SmartAction::sendGoCustomAnim, SmartAction::sendGossipMenu, SendGossipMenuFor(), Unit::SendPlaySpellVisual(), PlayerMenu::SendQuestGiverQuestDetails(), SmartAction::sendTargetToTarget, Creature::SendZoneUnderAttackMessage(), SmartAction::setActive, InstanceScript::SetBossState(), SmartAction::setCounter, GameObjectAI::SetData(), UnitAI::SetData(), SmartAction::setData, ZoneScript::SetData(), Unit::SetDisableGravity(), SmartAction::setEventPhase, Unit::SetFacingTo(), Unit::SetFacingToObject(), SmartAction::setFly, SmartAction::setGoLootState, SmartAction::setGossipMenu, SmartAction::setGuid, ZoneScript::SetGuidData(), SmartAction::setHealthPct, SmartAction::setHealthRegen, SmartAction::setHomePos, Creature::SetHomePosition(), SmartAction::setHover, Unit::SetInFront(), SmartAction::setInstanceData, SmartAction::setInstanceData64, SmartAI::SetInvincibilityHpLevel(), GameObject::SetLootState(), Position::SetOrientation(), SetPhase(), SetPhaseReset(), SmartAction::setRangedMovement, Creature::SetReactState(), SmartAction::setRoot, SmartAction::setRun, SmartAction::setScale, SetScript9(), SmartAction::setSheath, Unit::SetSheath(), Unit::SetSpeed(), SmartAction::setSwim, SmartAction::setunitByte, sGameEventMgr, SmartAction::sheath, SmartAction::sightDistance, SmartAction::simpleTalk, SmartAction::slots, SMART_ACTION_ACTIVATE_GOBJECT, SMART_ACTION_ACTIVATE_TAXI, SMART_ACTION_ADD_AURA, SMART_ACTION_ADD_DYNAMIC_FLAG, SMART_ACTION_ADD_GO_FLAG, SMART_ACTION_ADD_IMMUNITY, SMART_ACTION_ADD_ITEM, SMART_ACTION_ADD_NPC_FLAG, SMART_ACTION_ADD_POWER, SMART_ACTION_ADD_THREAT, SMART_ACTION_ALLOW_COMBAT_MOVEMENT, SMART_ACTION_ATTACK_START, SMART_ACTION_ATTACK_STOP, SMART_ACTION_AUTO_ATTACK, SMART_ACTION_CALL_AREAEXPLOREDOREVENTHAPPENS, SMART_ACTION_CALL_FOR_HELP, SMART_ACTION_CALL_GROUPEVENTHAPPENS, SMART_ACTION_CALL_KILLEDMONSTER, SMART_ACTION_CALL_RANDOM_RANGE_TIMED_ACTIONLIST, SMART_ACTION_CALL_RANDOM_TIMED_ACTIONLIST, SMART_ACTION_CALL_SCRIPT_RESET, SMART_ACTION_CALL_TIMED_ACTIONLIST, SMART_ACTION_CAST, SMART_ACTION_CLOSE_GOSSIP, SMART_ACTION_COMBAT_STOP, SMART_ACTION_CONE_SUMMON, SMART_ACTION_CREATE_TIMED_EVENT, SMART_ACTION_CROSS_CAST, SMART_ACTION_CU_ENCOUNTER_START, SMART_ACTION_CUSTOM_CAST, SMART_ACTION_DESPAWN_SPAWNGROUP, SMART_ACTION_DIE, SMART_ACTION_DISABLE_EVADE, SMART_ACTION_DISABLE_REWARD, SMART_ACTION_DISMOUNT, SMART_ACTION_DO_ACTION, SMART_ACTION_EQUIP, SMART_ACTION_ESCORT_PAUSE, SMART_ACTION_ESCORT_RESUME, SMART_ACTION_ESCORT_START, SMART_ACTION_ESCORT_STOP, SMART_ACTION_EVADE, SMART_ACTION_EXIT_VEHICLE, SMART_ACTION_FAIL_QUEST, SMART_ACTION_FALL, SMART_ACTION_FLEE, SMART_ACTION_FLEE_FOR_ASSIST, SMART_ACTION_FOLLOW, SMART_ACTION_FOLLOW_GROUP, SMART_ACTION_FORCE_DESPAWN, SMART_ACTION_GAME_EVENT_START, SMART_ACTION_GAME_EVENT_STOP, SMART_ACTION_GO_SET_GO_STATE, SMART_ACTION_GO_SET_LOOT_STATE, SMART_ACTION_INC_DATA, SMART_ACTION_INC_EVENT_PHASE, SMART_ACTION_INSTALL_AI_TEMPLATE, SMART_ACTION_INTERRUPT_SPELL, SMART_ACTION_INVOKER_CAST, SMART_ACTION_JUMP_TO_POS, SMART_ACTION_KILL_UNIT, SMART_ACTION_LOAD_EQUIPMENT, SMART_ACTION_LOAD_GRID, SMART_ACTION_MORPH_TO_ENTRY_OR_MODEL, SMART_ACTION_MOUNT_TO_ENTRY_OR_MODEL, SMART_ACTION_MOVE_FORWARD, SMART_ACTION_MOVE_TO_POS, SMART_ACTION_MOVE_TO_POS_TARGET, SMART_ACTION_MOVEMENT_PAUSE, SMART_ACTION_MOVEMENT_RESUME, SMART_ACTION_MOVEMENT_STOP, SMART_ACTION_MUSIC, SMART_ACTION_NO_ENVIRONMENT_UPDATE, SMART_ACTION_NONE, SMART_ACTION_OFFER_QUEST, SMART_ACTION_OVERRIDE_SCRIPT_BASE_OBJECT, SMART_ACTION_PLAY_CINEMATIC, SMART_ACTION_PLAY_EMOTE, SMART_ACTION_PLAY_SPELL_VISUAL, SMART_ACTION_PLAYER_TALK, SMART_ACTION_PLAYMOVIE, SMART_ACTION_RANDOM_EMOTE, SMART_ACTION_RANDOM_MOVE, SMART_ACTION_RANDOM_MUSIC, SMART_ACTION_RANDOM_PHASE, SMART_ACTION_RANDOM_PHASE_RANGE, SMART_ACTION_RANDOM_SOUND, SMART_ACTION_REMOVE_ALL_GAMEOBJECTS, SMART_ACTION_REMOVE_DYNAMIC_FLAG, SMART_ACTION_REMOVE_GO_FLAG, SMART_ACTION_REMOVE_IMMUNITY, SMART_ACTION_REMOVE_ITEM, SMART_ACTION_REMOVE_NPC_FLAG, SMART_ACTION_REMOVE_POWER, SMART_ACTION_REMOVE_TIMED_EVENT, SMART_ACTION_REMOVE_UNIT_FIELD_BYTES_1, SMART_ACTION_REMOVE_UNIT_FLAG, SMART_ACTION_REMOVEAURASFROMSPELL, SMART_ACTION_RESET_GOBJECT, SMART_ACTION_RESET_SCRIPT_BASE_OBJECT, SMART_ACTION_RESPAWN_TARGET, SMART_ACTION_RISE_UP, SMART_ACTION_SCRIPTED_SPAWN, SMART_ACTION_SELF_CAST, SMART_ACTION_SEND_GO_CUSTOM_ANIM, SMART_ACTION_SEND_GOSSIP_MENU, SMART_ACTION_SEND_TARGET_TO_TARGET, SMART_ACTION_SET_ACTIVE, SMART_ACTION_SET_ANIM_TIER, SMART_ACTION_SET_COMBAT_DISTANCE, SMART_ACTION_SET_CORPSE_DELAY, SMART_ACTION_SET_COUNTER, SMART_ACTION_SET_DATA, SMART_ACTION_SET_DYNAMIC_FLAG, SMART_ACTION_SET_EMOTE_STATE, SMART_ACTION_SET_EVENT_FLAG_RESET, SMART_ACTION_SET_EVENT_PHASE, SMART_ACTION_SET_FACTION, SMART_ACTION_SET_FLY, SMART_ACTION_SET_GO_FLAG, SMART_ACTION_SET_GOSSIP_MENU, SMART_ACTION_SET_GUID, SMART_ACTION_SET_HEALTH_PCT, SMART_ACTION_SET_HEALTH_REGEN, SMART_ACTION_SET_HOME_POS, SMART_ACTION_SET_HOVER, SMART_ACTION_SET_IN_COMBAT_WITH_ZONE, SMART_ACTION_SET_INGAME_PHASE_MASK, SMART_ACTION_SET_INST_DATA, SMART_ACTION_SET_INST_DATA64, SMART_ACTION_SET_INVINCIBILITY_HP_LEVEL, SMART_ACTION_SET_MOVEMENT_SPEED, SMART_ACTION_SET_NPC_FLAG, SMART_ACTION_SET_ORIENTATION, SMART_ACTION_SET_ORIENTATION_TARGET, SMART_ACTION_SET_POWER, SMART_ACTION_SET_RANGED_MOVEMENT, SMART_ACTION_SET_REACT_STATE, SMART_ACTION_SET_ROOT, SMART_ACTION_SET_RUN, SMART_ACTION_SET_SCALE, SMART_ACTION_SET_SHEATH, SMART_ACTION_SET_SIGHT_DIST, SMART_ACTION_SET_SWIM, SMART_ACTION_SET_UNIT_FIELD_BYTES_1, SMART_ACTION_SET_UNIT_FLAG, SMART_ACTION_SET_UNIT_MOVEMENT_FLAGS, SMART_ACTION_SET_VISIBILITY, SMART_ACTION_SIMPLE_TALK, SMART_ACTION_SOUND, SMART_ACTION_SPAWN_SPAWNGROUP, SMART_ACTION_START_CLOSEST_WAYPOINT, SMART_ACTION_STOP_MOTION, SMART_ACTION_STORE_TARGET_LIST, SMART_ACTION_SUMMON_CREATURE, SMART_ACTION_SUMMON_CREATURE_GROUP, SMART_ACTION_SUMMON_GAMEOBJECT_GROUP, SMART_ACTION_SUMMON_GO, SMART_ACTION_SUMMON_RADIAL, SMART_ACTION_TALK, SMART_ACTION_TELEPORT, SMART_ACTION_THREAT_ALL_PCT, SMART_ACTION_THREAT_SINGLE_PCT, SMART_ACTION_TRIGGER_RANDOM_TIMED_EVENT, SMART_ACTION_TRIGGER_TIMED_EVENT, SMART_ACTION_UPDATE_TEMPLATE, SMART_ACTION_VORTEX_SUMMON, SMART_ACTION_WAYPOINT_DATA_RANDOM, SMART_ACTION_WAYPOINT_START, SMART_ACTION_WORLD_SCRIPT, SMART_ACTION_ZONE_UNDER_ATTACK, SMART_ESCORT_TARGETS, SMART_EVENT_ESCORT_REACHED, SMART_EVENT_FLAG_NOT_REPEATABLE, SMART_EVENT_FLAG_TEMP_IGNORE_CHANCE_ROLL, SMART_EVENT_LINK, SMART_EVENT_TIMED_EVENT_TRIGGERED, SMART_EVENT_UPDATE, SMART_EVENT_UPDATE_IC, SMART_RANDOM_POINT, SMART_TARGET_FORMATION, SMART_TARGET_NONE, SMART_TARGET_POSITION, SMART_TARGET_RANDOM_POINT, SMART_TARGET_SELF, SMART_WAYPOINT_MGR, SMARTCAST_AURA_NOT_PRESENT, SMARTCAST_COMBAT_MOVE, SMARTCAST_ENABLE_COMBAT_MOVE_ON_LOS, SMARTCAST_INTERRUPT_PREVIOUS, SMARTCAST_TARGET_POWER_MANA, SMARTCAST_THREATLIST_NOT_SINGLE, SMARTCAST_TRIGGERED, sObjectMgr, SmartAction::sound, SmartAction::sound1, SmartAction::sound2, SmartAction::sound3, SmartAction::sound4, SmartScriptHolder::source_type, Map::SpawnGroupDespawn(), Map::SpawnGroupSpawn(), SmartAction::spawnPos, SmartAction::spawnTimerMax, SmartAction::spawnTimerMin, SmartAction::speed, SmartAction::speedFraction, SmartAction::speedInteger, SmartAction::speedxy, SmartAction::speedz, SmartAction::spell, SPELL_ATTR2_IGNORE_LINE_OF_SIGHT, SPELL_CAST_OK, SPELL_FAILED_NOT_READY, SPELL_FAILED_OUT_OF_RANGE, SPELL_FAILED_SPELL_IN_PROGRESS, SmartAction::spell_id, SPELLVALUE_BASE_POINT0, SPELLVALUE_BASE_POINT1, SPELLVALUE_BASE_POINT2, SmartAction::spellVisual, sSmartWaypointMgr, sSpellMgr, SmartAction::startAngle, SmartAction::startClosestWaypoint, SmartAction::state, SmartAction::stepAngle, SmartAction::stopMotion, SmartAction::stopMovement, StoreCounter(), StoreTargetList(), SmartAction::storeTargets, SmartAction::subtract, SmartAction::summonCreature, WorldObject::SummonCreature(), WorldObject::SummonCreatureGroup(), SmartAction::summonDuration, SmartAction::summonEntry, WorldObject::SummonGameObject(), WorldObject::SummonGameObjectGroup(), SmartAction::summonGO, WorldObject::SummonTrigger(), SmartAction::summonVortex, sWaypointMgr, SmartAction::swim, sWorldState, CreatureAI::Talk(), SmartAction::talk, SmartScriptHolder::target, SmartAction::targetParam1, SmartAction::targetParam2, SmartAction::targetParam3, SmartAction::targetParam4, SmartAction::targetsLimit, SmartAction::targetsummon, SmartAction::targetType, SmartAction::taxi, TEAM_NEUTRAL, SmartAction::teleport, TEMPSUMMON_CORPSE_DESPAWN, TEMPSUMMON_TIMED_DESPAWN, TEXT_RANGE_NORMAL, SmartAction::textGroupID, SmartAction::textId, SmartAction::threat, SmartAction::threatDEC, SmartAction::threatINC, SmartAction::threatPCT, SmartAction::timedActionList, SmartAction::timeEvent, SmartAction::timer, Object::ToCreature(), Object::ToGameObject(), Object::ToPlayer(), ObjectGuid::ToString(), Object::ToUnit(), SmartAction::transport, trigger, TRIGGERED_FULL_MASK, TRIGGERED_NONE, SmartAction::triggerFlags, SmartAction::turnAngle, SmartEvent::type, SmartAction::type, SmartTarget::type, UNIT_DYNAMIC_FLAGS, UNIT_FIELD_BYTES_1, UNIT_FIELD_FLAGS, UNIT_FIELD_FLAGS_2, UNIT_FLAG_SILENCED, UNIT_NPC_EMOTESTATE, UNIT_STATE_LOST_CONTROL, UNIT_STATE_NO_COMBAT_MOVEMENT, UNIT_STATE_NO_ENVIRONMENT_UPD, UNIT_STATE_ROOT, UNIT_VIRTUAL_ITEM_SLOT_ID, SmartAction::unitFlag, SmartTarget::unitRange, SmartAction::updateLevel, SmartAction::updateTemplate, urand(), GameObject::UseDoorOrButton(), SmartAction::useTalkTarget, SmartAction::value, SmartAction::visibility, SmartAction::visualId, WAYPOINT_MGR, SmartAction::withDelayed, SmartAction::withEmote, SmartAction::withInstant, SmartAction::worldStateScript, SmartAction::wpData, SmartAction::wpDataRandom, SmartAction::wpPause, SmartAction::wpStart, SmartAction::wpStop, SmartTarget::x, WaypointNode::X, SmartTarget::y, WaypointNode::Y, SmartTarget::z, and WaypointNode::Z.

Referenced by ProcessEvent(), and ProcessTimedAction().

◆ ProcessEvent()

void SmartScript::ProcessEvent ( SmartScriptHolder &  e,
Unit *  unit = nullptr,
uint32  var0 = 0,
uint32  var1 = 0,
bool  bvar = false,
SpellInfo const *  spell = nullptr,
GameObject *  gob = nullptr 
)
4305{
4306 if (!e.active && e.GetEventType() != SMART_EVENT_LINK)
4307 return;
4308
4310 return;
4311
4313 return;
4314
4315 switch (e.GetEventType())
4316 {
4317 case SMART_EVENT_LINK://special handling
4318 ProcessAction(e, unit, var0, var1, bvar, spell, gob);
4319 break;
4320 //called from Update tick
4321 case SMART_EVENT_UPDATE:
4323 break;
4325 if (me && me->IsEngaged())
4326 return;
4328 break;
4330 if (!me || !me->IsEngaged())
4331 return;
4333 break;
4335 {
4336 if (!me || !me->IsEngaged() || !me->GetMaxHealth())
4337 return;
4338 uint32 perc = (uint32)me->GetHealthPct();
4339 if (perc > e.event.minMaxRepeat.max || perc < e.event.minMaxRepeat.min)
4340 return;
4342 break;
4343 }
4345 {
4346 if (!me || !me->IsEngaged() || !me->GetVictim() || !me->GetVictim()->GetMaxHealth())
4347 return;
4348 uint32 perc = (uint32)me->GetVictim()->GetHealthPct();
4349 if (perc > e.event.minMaxRepeat.max || perc < e.event.minMaxRepeat.min)
4350 return;
4352 break;
4353 }
4355 {
4356 if (!me || !me->IsEngaged() || !me->GetMaxPower(POWER_MANA))
4357 return;
4359 if (perc > e.event.minMaxRepeat.max || perc < e.event.minMaxRepeat.min)
4360 return;
4362 break;
4363 }
4365 {
4366 if (!me || !me->IsEngaged() || !me->GetVictim() || !me->GetVictim()->GetMaxPower(POWER_MANA))
4367 return;
4369 if (perc > e.event.minMaxRepeat.max || perc < e.event.minMaxRepeat.min)
4370 return;
4372 break;
4373 }
4374 case SMART_EVENT_RANGE:
4375 {
4376 if (!me || !me->IsEngaged() || !me->GetVictim())
4377 return;
4378
4381 else
4382 RecalcTimer(e, 1200, 1200); // make it predictable
4383
4384 break;
4385 }
4387 {
4388 if (!me || !me->IsEngaged())
4389 return;
4390
4391 Unit* victim = me->GetVictim();
4392
4393 if (!victim || !victim->IsNonMeleeSpellCast(false, false, true))
4394 return;
4395
4396 if (e.event.targetCasting.spellId > 0)
4397 if (Spell* currSpell = victim->GetCurrentSpell(CURRENT_GENERIC_SPELL))
4398 if (currSpell->m_spellInfo->Id != e.event.targetCasting.spellId)
4399 return;
4400
4402 break;
4403 }
4405 {
4406 if (!me || !me->IsEngaged())
4407 return;
4408
4410 if (!target || !target->IsInCombat())
4411 {
4412 // Xinef: if there are at least two same npcs, they will perform the same action immediately even if this is useless...
4413 RecalcTimer(e, 1000, 3000);
4414 return;
4415 }
4417 break;
4418 }
4420 {
4421 if (!me || !me->IsEngaged())
4422 return;
4423
4424 std::vector<Creature*> creatures;
4426 if (creatures.empty())
4427 {
4428 // Xinef: if there are at least two same npcs, they will perform the same action immediately even if this is useless...
4429 RecalcTimer(e, 1000, 3000);
4430 return;
4431 }
4433 break;
4434 }
4436 {
4438 {
4439 return;
4440 }
4441
4442 std::vector<Creature*> creatures;
4444
4445 if (creatures.empty())
4446 return;
4447
4449 break;
4450 }
4452 {
4453 if (!me)
4454 return;
4455 uint32 count = me->GetAuraCount(e.event.aura.spell);
4456 if ((!e.event.aura.count && !count) || (e.event.aura.count && count >= e.event.aura.count))
4458 break;
4459 }
4461 {
4462 if (!me || !me->GetVictim())
4463 return;
4465 if (count < e.event.aura.count)
4466 return;
4468 break;
4469 }
4471 {
4472 if (bvar == (e.event.charm.onRemove != 1))
4473 ProcessAction(e, unit, var0, var1, bvar, spell, gob);
4474 break;
4475 }
4476 //no params
4477 case SMART_EVENT_AGGRO:
4478 case SMART_EVENT_DEATH:
4479 case SMART_EVENT_EVADE:
4492 case SMART_EVENT_RESET:
4496 ProcessAction(e, unit, var0, var1, bvar, spell, gob);
4497 break;
4498
4500 switch (e.event.gossipHello.filter)
4501 {
4502 case 0:
4503 // no filter set, always execute action
4504 break;
4505 case 1:
4506 // GossipHello only filter set, skip action if reportUse
4507 if (var0)
4508 {
4509 return;
4510 }
4511 break;
4512 case 2:
4513 // reportUse only filter set, skip action if GossipHello
4514 if (!var0)
4515 {
4516 return;
4517 }
4518 break;
4519 default:
4520 // Ignore any other value
4521 break;
4522 }
4523
4524 ProcessAction(e, unit, var0, var1, bvar, spell, gob);
4525 break;
4527 {
4528 if (!me)
4529 return;
4530
4531 if (Unit* victim = me->GetVictim())
4532 {
4534 if (!victim->HasInArc(static_cast<float>(M_PI), me))
4536 }
4537
4538 break;
4539 }
4541 {
4542 if (!me)
4543 return;
4544
4545 if (Unit* victim = me->GetVictim())
4546 if ((!e.event.meleeRange.invert && me->IsWithinMeleeRange(victim, static_cast<float>(e.event.meleeRange.dist))) ||
4547 (e.event.meleeRange.invert && !me->IsWithinMeleeRange(victim, static_cast<float>(e.event.meleeRange.dist))))
4549
4550 break;
4551 }
4553 if (e.event.emote.emote == var0)
4554 {
4555 ProcessAction(e, unit);
4556 RecalcTimer(e, e.event.emote.cooldownMin, e.event.emote.cooldownMax);
4557 }
4558 break;
4559 case SMART_EVENT_KILL:
4560 {
4561 if (!me || !unit)
4562 return;
4563 if (e.event.kill.playerOnly && !unit->IsPlayer())
4564 return;
4565 if (e.event.kill.creature && unit->GetEntry() != e.event.kill.creature)
4566 return;
4568 ProcessAction(e, unit);
4569 break;
4570 }
4573 {
4574 if (!spell)
4575 return;
4576 if ((!e.event.spellHit.spell || spell->Id == e.event.spellHit.spell) &&
4577 (!e.event.spellHit.school || (spell->SchoolMask & e.event.spellHit.school)))
4578 {
4580 ProcessAction(e, unit, 0, 0, bvar, spell);
4581 }
4582 break;
4583 }
4585 {
4586 if (!me || me->IsEngaged())
4587 return;
4588 //can trigger if closer than fMaxAllowedRange
4589 float range = (float)e.event.los.maxDist;
4590
4591 //if range is ok and we are actually in LOS
4592 if (me->IsWithinDistInMap(unit, range) && me->IsWithinLOSInMap(unit))
4593 {
4595 //if friendly event&&who is not hostile OR hostile event&&who is hostile
4596 if ((hostilityMode == SmartEvent::LOSHostilityMode::Any) ||
4597 (hostilityMode == SmartEvent::LOSHostilityMode::NotHostile && !me->IsHostileTo(unit)) ||
4598 (hostilityMode == SmartEvent::LOSHostilityMode::Hostile && me->IsHostileTo(unit)))
4599 {
4600 if (e.event.los.playerOnly && !unit->IsPlayer())
4601 return;
4603 ProcessAction(e, unit);
4604 }
4605 }
4606 break;
4607 }
4608 case SMART_EVENT_IC_LOS:
4609 {
4610 if (!me || !me->IsEngaged())
4611 return;
4612 //can trigger if closer than fMaxAllowedRange
4613 float range = (float)e.event.los.maxDist;
4614
4615 //if range is ok and we are actually in LOS
4616 if (me->IsWithinDistInMap(unit, range) && me->IsWithinLOSInMap(unit))
4617 {
4619 //if friendly event&&who is not hostile OR hostile event&&who is hostile
4620 if ((hostilityMode == SmartEvent::LOSHostilityMode::Any) ||
4621 (hostilityMode == SmartEvent::LOSHostilityMode::NotHostile && !me->IsHostileTo(unit)) ||
4622 (hostilityMode == SmartEvent::LOSHostilityMode::Hostile && me->IsHostileTo(unit)))
4623 {
4624 if (e.event.los.playerOnly && !unit->IsPlayer())
4625 return;
4627 ProcessAction(e, unit);
4628 }
4629 }
4630 break;
4631 }
4633 {
4634 if (!GetBaseObject())
4635 return;
4637 return;
4639 return;
4640 ProcessAction(e);
4641 break;
4642 }
4646 {
4647 if (!IsCreature(unit))
4648 return;
4649 if (e.event.summoned.creature && unit->GetEntry() != e.event.summoned.creature)
4650 return;
4652 ProcessAction(e, unit);
4653 break;
4654 }
4657 {
4658 if (var0 > e.event.minMaxRepeat.max || var0 < e.event.minMaxRepeat.min)
4659 return;
4661 ProcessAction(e, unit);
4662 break;
4663 }
4665 {
4666 if (e.event.minMaxRepeat.rangeMin) // health check mode
4667 {
4668 if (!me || !me->IsEngaged() || !me->GetMaxHealth())
4669 return;
4671 return;
4672 ProcessAction(e, unit);
4673 }
4674 else
4675 {
4676 if (var0 > e.event.minMaxRepeat.max || var0 < e.event.minMaxRepeat.min)
4677 return;
4679 ProcessAction(e, unit);
4680 }
4681 break;
4682 }
4684 {
4685 if ((e.event.movementInform.type && var0 != e.event.movementInform.type) || (e.event.movementInform.id && var1 != e.event.movementInform.id))
4686 return;
4688 return;
4689 ProcessAction(e, unit, var0, var1);
4690 break;
4691 }
4694 {
4695 if (e.event.waypoint.pathID && var0 != e.event.waypoint.pathID)
4696 return;
4697 ProcessAction(e, unit, var0);
4698 break;
4699 }
4705 {
4706 if (!me || (e.event.waypoint.pointID && var0 != e.event.waypoint.pointID) || (e.event.waypoint.pathID && GetPathId() != e.event.waypoint.pathID))
4707 return;
4708 ProcessAction(e, unit);
4709 break;
4710 }
4712 {
4713 if (e.event.summoned.creature && e.event.summoned.creature != var0)
4714 return;
4716 ProcessAction(e, unit, var0);
4717 break;
4718 }
4720 {
4722 return;
4724 ProcessAction(e, unit, var0);
4725 break;
4726 }
4729 {
4730 if (e.event.quest.quest && var0 != e.event.quest.quest)
4731 return;
4732 RecalcTimer(e, e.event.quest.cooldownMin, e.event.quest.cooldownMax);
4733 ProcessAction(e, unit, var0);
4734 break;
4735 }
4737 {
4739 return;
4740 ProcessAction(e, unit, var0);
4741 break;
4742 }
4744 {
4745 if (e.event.areatrigger.id && var0 != e.event.areatrigger.id)
4746 return;
4747 ProcessAction(e, unit, var0);
4748 break;
4749 }
4751 {
4753 return;
4754 ProcessAction(e, unit, var0);
4755 break;
4756 }
4758 {
4759 if (e.event.dataSet.id != var0 || e.event.dataSet.value != var1)
4760 return;
4762 ProcessAction(e, unit, var0, var1, false, nullptr, gob);
4763 break;
4764 }
4767 {
4768 if (!unit)
4769 return;
4771 ProcessAction(e, unit);
4772 break;
4773 }
4775 {
4776 if (e.event.timedEvent.id == var0)
4777 ProcessAction(e, unit);
4778 break;
4779 }
4781 {
4782 LOG_DEBUG("sql.sql", "SmartScript: Gossip Select: menu {} action {}", var0, var1); //little help for scripters
4783 if (e.event.gossip.sender != var0 || e.event.gossip.action != var1)
4784 return;
4785 ProcessAction(e, unit, var0, var1);
4786 break;
4787 }
4789 {
4791 return;
4792
4793 ProcessAction(e);
4794 break;
4795 }
4798 {
4799 if (e.event.gameEvent.gameEventId != var0)
4800 return;
4801 ProcessAction(e, nullptr, var0);
4802 break;
4803 }
4805 {
4806 if (e.event.goStateChanged.state != var0)
4807 return;
4808 ProcessAction(e, unit, var0, var1);
4809 break;
4810 }
4812 {
4813 if (e.event.eventInform.eventId != var0)
4814 return;
4815 ProcessAction(e, nullptr, var0);
4816 break;
4817 }
4819 {
4820 if (e.event.doAction.eventId != var0)
4821 return;
4823 ProcessAction(e, unit, var0);
4824 break;
4825 }
4827 {
4828 if (!me || !me->IsEngaged())
4829 return;
4830
4831 Unit* unitTarget = nullptr;
4832 switch (e.GetTargetType())
4833 {
4841 {
4842 ObjectVector targets;
4843 GetTargets(targets, e);
4844 for (WorldObject* target : targets)
4845 {
4846 if (IsUnit(target) && me->IsFriendlyTo(target->ToUnit()) && target->ToUnit()->IsAlive() && target->ToUnit()->IsInCombat())
4847 {
4848 uint32 healthPct = uint32(target->ToUnit()->GetHealthPct());
4849 if (healthPct > e.event.friendlyHealthPct.hpPct)
4850 {
4851 continue;
4852 }
4853
4854 unitTarget = target->ToUnit();
4855 break;
4856 }
4857 }
4858
4859 break;
4860 }
4861 case SMART_TARGET_SELF:
4864 break;
4865 default:
4866 return;
4867 }
4868
4869 if (!unitTarget)
4870 return;
4871
4873 break;
4874 }
4876 {
4877 if (!me)
4878 return;
4879
4880 WorldObject* creature = nullptr;
4881
4882 if (e.event.distance.guid != 0)
4883 {
4884 creature = FindCreatureNear(me, e.event.distance.guid);
4885
4886 if (!creature)
4887 return;
4888
4889 if (!me->IsInRange(creature, 0, (float)e.event.distance.dist))
4890 return;
4891 }
4892 else if (e.event.distance.entry != 0)
4893 {
4894 std::list<Creature*> list;
4896
4897 if (!list.empty())
4898 creature = list.front();
4899 }
4900
4901 if (creature)
4903
4904 break;
4905 }
4907 {
4908 if (!me)
4909 return;
4910
4911 WorldObject* gameobject = nullptr;
4912
4913 if (e.event.distance.guid != 0)
4914 {
4915 gameobject = FindGameObjectNear(me, e.event.distance.guid);
4916
4917 if (!gameobject)
4918 return;
4919
4920 if (!me->IsInRange(gameobject, 0, (float)e.event.distance.dist))
4921 return;
4922 }
4923 else if (e.event.distance.entry != 0)
4924 {
4925 std::list<GameObject*> list;
4927
4928 if (!list.empty())
4929 gameobject = list.front();
4930 }
4931
4932 if (gameobject)
4934
4935 break;
4936 }
4938 if (e.event.counter.id != var0 || GetCounterValue(e.event.counter.id) != e.event.counter.value)
4939 return;
4940
4942 break;
4944 {
4945 uint32 playerCount = 0;
4946 ObjectVector targets;
4947 GetWorldObjectsInDist(targets, static_cast<float>(e.event.nearPlayer.radius));
4948
4949 if (!targets.empty())
4950 {
4951 for (WorldObject* target : targets)
4952 if (IsPlayer(target) && !target->ToPlayer()->IsGameMaster())
4953 playerCount++;
4954
4955 if (playerCount >= e.event.nearPlayer.minCount)
4956 ProcessAction(e, unit);
4957 }
4959 break;
4960 }
4962 {
4963 uint32 playerCount = 0;
4964 ObjectVector targets;
4965 GetWorldObjectsInDist(targets, static_cast<float>(e.event.nearPlayerNegation.radius));
4966
4967 if (!targets.empty())
4968 {
4969 for (WorldObject* target : targets)
4970 if (IsPlayer(target) && !target->ToPlayer()->IsGameMaster())
4971 playerCount++;
4972
4973 if (playerCount < e.event.nearPlayerNegation.maxCount)
4974 ProcessAction(e, unit);
4975 }
4977 break;
4978 }
4980 {
4981 uint32 unitCount = 0;
4982 ObjectVector targets;
4983 GetWorldObjectsInDist(targets, static_cast<float>(e.event.nearUnit.range));
4984
4985 if (!targets.empty())
4986 {
4987 if (e.event.nearUnit.type)
4988 {
4989 for (WorldObject* target : targets)
4990 {
4991 if (IsGameObject(target) && target->GetEntry() == e.event.nearUnit.entry)
4992 unitCount++;
4993 }
4994 }
4995 else
4996 {
4997 for (WorldObject* target : targets)
4998 {
4999 if (IsCreature(target) && target->GetEntry() == e.event.nearUnit.entry)
5000 unitCount++;
5001 }
5002 }
5003
5004 if (unitCount >= e.event.nearUnit.count)
5005 ProcessAction(e, unit);
5006 }
5008 break;
5009 }
5011 {
5012 uint32 unitCount = 0;
5013 ObjectVector targets;
5014 GetWorldObjectsInDist(targets, static_cast<float>(e.event.nearUnitNegation.range));
5015
5016 if (!targets.empty())
5017 {
5019 {
5020 for (WorldObject* target : targets)
5021 {
5022 if (IsGameObject(target) && target->GetEntry() == e.event.nearUnitNegation.entry)
5023 unitCount++;
5024 }
5025 }
5026 else
5027 {
5028 for (WorldObject* target : targets)
5029 {
5030 if (IsCreature(target) && target->GetEntry() == e.event.nearUnitNegation.entry)
5031 unitCount++;
5032 }
5033 }
5034
5035 if (unitCount < e.event.nearUnitNegation.count)
5036 ProcessAction(e, unit);
5037 }
5039 break;
5040 }
5042 {
5043 if (!me || !me->IsEngaged())
5044 return;
5045
5046 for (ThreatReference const* ref : me->GetThreatMgr().GetUnsortedThreatList())
5047 {
5048 if (Unit* target = ref->GetVictim())
5049 {
5050 if (!IsPlayer(target) || !target->IsNonMeleeSpellCast(false, false, true))
5051 continue;
5052
5053 if (!(me->IsInRange(target, (float)e.event.minMaxRepeat.rangeMin, (float)e.event.minMaxRepeat.rangeMax)))
5054 continue;
5055
5056 ProcessAction(e, target);
5058 return;
5059 }
5060 }
5061
5062 // No targets found
5064
5065 break;
5066 }
5068 {
5069 if (!me || !me->IsEngaged())
5070 return;
5071
5072 for (ThreatReference const* ref : me->GetThreatMgr().GetUnsortedThreatList())
5073 {
5074 if (Unit* target = ref->GetVictim())
5075 {
5076 if (!(me->IsInRange(target, (float)e.event.minMaxRepeat.rangeMin, (float)e.event.minMaxRepeat.rangeMax)))
5077 continue;
5078
5079 ProcessAction(e, target);
5081 return;
5082 }
5083 }
5084
5085 // If no targets are found and it's off cooldown, check again
5086 RecalcTimer(e, 1200, 1200);
5087 break;
5088 }
5091 {
5092 if (!me || (e.event.wpData.pointId && var0 != e.event.wpData.pointId) || (e.event.wpData.pathId && me->GetWaypointPath() != e.event.wpData.pathId))
5093 return;
5094 ProcessAction(e, unit);
5095 break;
5096 }
5097 default:
5098 LOG_ERROR("sql.sql", "SmartScript::ProcessEvent: Unhandled Event type {}", e.GetEventType());
5099 break;
5100 }
5101}
@ SMART_EVENT_FLAG_WHILE_CHARMED
Definition SmartScriptMgr.h:1970
@ SMART_SCRIPT_RESPAWN_CONDITION_AREA
Definition SmartScriptMgr.h:536
@ SMART_SCRIPT_RESPAWN_CONDITION_MAP
Definition SmartScriptMgr.h:535
@ SMART_EVENT_EVADE
Definition SmartScriptMgr.h:106
@ SMART_EVENT_ACTION_DONE
Definition SmartScriptMgr.h:171
@ SMART_EVENT_SUMMON_DESPAWNED
Definition SmartScriptMgr.h:134
@ SMART_EVENT_SPELLHIT
Definition SmartScriptMgr.h:107
@ SMART_EVENT_RECEIVE_EMOTE
Definition SmartScriptMgr.h:121
@ SMART_EVENT_QUEST_FAIL
Definition SmartScriptMgr.h:150
@ SMART_EVENT_RECEIVE_HEAL
Definition SmartScriptMgr.h:152
@ SMART_EVENT_CHARMED_TARGET
Definition SmartScriptMgr.h:129
@ SMART_EVENT_TARGET_MANA_PCT
Definition SmartScriptMgr.h:117
@ SMART_EVENT_QUEST_COMPLETION
Definition SmartScriptMgr.h:148
@ SMART_EVENT_HEALTH_PCT
Definition SmartScriptMgr.h:101
@ SMART_EVENT_ESCORT_START
Definition SmartScriptMgr.h:138
@ SMART_EVENT_EVENT_PHASE_CHANGE
Definition SmartScriptMgr.h:165
@ SMART_EVENT_AREATRIGGER_ONTRIGGER
Definition SmartScriptMgr.h:145
@ SMART_EVENT_ON_SPELLCLICK
Definition SmartScriptMgr.h:172
@ SMART_EVENT_ESCORT_PAUSED
Definition SmartScriptMgr.h:154
@ SMART_EVENT_ESCORT_RESUMED
Definition SmartScriptMgr.h:155
@ SMART_EVENT_PASSENGER_REMOVED
Definition SmartScriptMgr.h:127
@ SMART_EVENT_INSTANCE_PLAYER_ENTER
Definition SmartScriptMgr.h:144
@ SMART_EVENT_ESCORT_ENDED
Definition SmartScriptMgr.h:157
@ SMART_EVENT_REACHED_HOME
Definition SmartScriptMgr.h:120
@ SMART_EVENT_TRANSPORT_ADDCREATURE
Definition SmartScriptMgr.h:141
@ SMART_EVENT_REWARD_QUEST
Definition SmartScriptMgr.h:119
@ SMART_EVENT_GO_EVENT_INFORM
Definition SmartScriptMgr.h:170
@ SMART_EVENT_JUST_SUMMONED
Definition SmartScriptMgr.h:153
@ SMART_EVENT_CHARMED
Definition SmartScriptMgr.h:128
@ SMART_EVENT_SPELLHIT_TARGET
Definition SmartScriptMgr.h:130
@ SMART_EVENT_GAME_EVENT_START
Definition SmartScriptMgr.h:167
@ SMART_EVENT_KILL
Definition SmartScriptMgr.h:104
@ SMART_EVENT_TRANSPORT_REMOVE_PLAYER
Definition SmartScriptMgr.h:142
@ SMART_EVENT_ESCORT_STOPPED
Definition SmartScriptMgr.h:156
@ SMART_EVENT_GOSSIP_HELLO
Definition SmartScriptMgr.h:163
@ SMART_EVENT_GOSSIP_SELECT
Definition SmartScriptMgr.h:161
@ SMART_EVENT_CORPSE_REMOVED
Definition SmartScriptMgr.h:135
@ SMART_EVENT_SUMMONED_UNIT_EVADE
Definition SmartScriptMgr.h:196
@ SMART_EVENT_PASSENGER_BOARDED
Definition SmartScriptMgr.h:126
@ SMART_EVENT_TRANSPORT_ADDPLAYER
Definition SmartScriptMgr.h:140
@ SMART_EVENT_WAYPOINT_ENDED
Definition SmartScriptMgr.h:198
@ SMART_EVENT_ACCEPTED_QUEST
Definition SmartScriptMgr.h:118
@ SMART_EVENT_COUNTER_SET
Definition SmartScriptMgr.h:176
@ SMART_EVENT_FRIENDLY_MISSING_BUFF
Definition SmartScriptMgr.h:115
@ SMART_EVENT_WAYPOINT_REACHED
Definition SmartScriptMgr.h:197
@ SMART_EVENT_TARGET_BUFFED
Definition SmartScriptMgr.h:123
@ SMART_EVENT_RESPAWN
Definition SmartScriptMgr.h:110
@ SMART_EVENT_QUEST_ACCEPTED
Definition SmartScriptMgr.h:146
@ SMART_EVENT_FRIENDLY_HEALTH
Definition SmartScriptMgr.h:113
@ SMART_EVENT_QUEST_REWARDED
Definition SmartScriptMgr.h:149
@ SMART_EVENT_DEATH
Definition SmartScriptMgr.h:105
@ SMART_EVENT_TRANSPORT_RELOCATE
Definition SmartScriptMgr.h:143
@ SMART_EVENT_GAME_EVENT_END
Definition SmartScriptMgr.h:168
@ SMART_EVENT_DAMAGED
Definition SmartScriptMgr.h:131
@ SMART_EVENT_FOLLOW_COMPLETED
Definition SmartScriptMgr.h:164
@ SMART_EVENT_QUEST_OBJ_COMPLETION
Definition SmartScriptMgr.h:147
@ SMART_EVENT_SUMMONED_UNIT_DIES
Definition SmartScriptMgr.h:183
@ SMART_EVENT_FRIENDLY_IS_CC
Definition SmartScriptMgr.h:114
@ SMART_EVENT_AGGRO
Definition SmartScriptMgr.h:103
@ SMART_EVENT_TARGET_HEALTH_PCT
Definition SmartScriptMgr.h:111
@ SMART_EVENT_VICTIM_CASTING
Definition SmartScriptMgr.h:112
@ SMART_EVENT_DAMAGED_TARGET
Definition SmartScriptMgr.h:132
@ SMART_EVENT_HAS_AURA
Definition SmartScriptMgr.h:122
@ SMART_EVENT_SUMMONED_UNIT
Definition SmartScriptMgr.h:116
@ CURRENT_GENERIC_SPELL
Definition Unit.h:557
uint32 GetWaypointPath() const
Definition Creature.h:357
uint32 GetCounterValue(uint32 id)
Definition SmartScript.h:134
void DoFindFriendlyMissingBuff(std::vector< Creature * > &creatures, float range, uint32 spellid) const
Definition SmartScript.cpp:5573
void DoFindFriendlyCC(std::vector< Creature * > &creatures, float range) const
Definition SmartScript.cpp:5563
void ProcessAction(SmartScriptHolder &e, Unit *unit=nullptr, uint32 var0=0, uint32 var1=0, bool bvar=false, SpellInfo const *spell=nullptr, GameObject *gob=nullptr)
Definition SmartScript.cpp:185
static bool IsCharmedCreature(WorldObject *obj)
Definition SmartScript.cpp:5656
uint32 GetPathId() const
Definition SmartScript.h:63
Unit * DoSelectLowestHpFriendly(float range, uint32 MinHPDiff) const
Definition SmartScript.cpp:5536
bool IsInPhase(uint32 p) const
Definition SmartScript.cpp:5702
Unit * DoSelectLowestHpPercentFriendly(float range, uint32 minHpPct, uint32 maxHpPct) const
Definition SmartScript.cpp:5549
void ProcessTimedAction(SmartScriptHolder &e, uint32 const &min, uint32 const &max, Unit *unit=nullptr, uint32 var0=0, uint32 var1=0, bool bvar=false, SpellInfo const *spell=nullptr, GameObject *gob=nullptr)
Definition SmartScript.cpp:3500
Definition Spell.h:298
float GetHealthPct() const
Definition Unit.h:1116
bool IsNonMeleeSpellCast(bool withDelayed, bool skipChanneled=false, bool skipAutorepeat=false, bool isAutoshoot=false, bool skipInstant=true) const
Definition Unit.cpp:4017
uint32 GetMaxHealth() const
Definition Unit.h:1115
bool IsWithinMeleeRange(Unit const *obj, float dist=0.f) const
Definition Unit.cpp:790
uint32 GetAuraCount(uint32 spellId) const
Definition Unit.cpp:5725
uint32 GetMaxPower(Powers power) const
Definition Unit.h:1142
bool IsFriendlyTo(Unit const *unit) const
Definition Unit.cpp:7043
bool HealthBelowPctDamaged(int32 pct, uint32 damage) const
Definition Unit.h:1123
bool IsHostileTo(Unit const *unit) const
Definition Unit.cpp:7038
bool IsInCombat() const
Definition Unit.h:941
Spell * GetCurrentSpell(CurrentSpellTypes spellType) const
Definition Unit.h:1581
void GetGameObjectListWithEntryInGrid(std::list< GameObject * > &lList, uint32 uiEntry, float fMaxSearchRange) const
Definition Object.cpp:2605
void GetCreatureListWithEntryInGrid(std::list< Creature * > &lList, uint32 uiEntry, float fMaxSearchRange) const
Definition Object.cpp:2619
bool IsWithinDistInMap(WorldObject const *obj, float dist2compare, bool is3D=true, bool incOwnRadius=true, bool incTargetRadius=true) const
Definition Object.cpp:1386
bool HasInArc(float arcangle, Position const *pos, float targetRadius=0.0f) const
Definition Position.cpp:148
struct SmartEvent::@30::@69 nearPlayerNegation
uint32 map
Definition SmartScriptMgr.h:253
uint32 pointId
Definition SmartScriptMgr.h:508
uint32 invert
Definition SmartScriptMgr.h:494
uint32 entry
Definition SmartScriptMgr.h:447
struct SmartEvent::@30::@61 gameEvent
uint32 id
Definition SmartScriptMgr.h:339
LOSHostilityMode
Definition SmartScriptMgr.h:524
uint32 cooldownMax
Definition SmartScriptMgr.h:225
struct SmartEvent::@30::@53 instancePlayerEnter
uint32 pointID
Definition SmartScriptMgr.h:353
uint32 radius
Definition SmartScriptMgr.h:273
uint32 maxDist
Definition SmartScriptMgr.h:244
struct SmartEvent::@30::@51 transportAddCreature
uint32 sender
Definition SmartScriptMgr.h:397
struct SmartEvent::@30::@45 aura
struct SmartEvent::@30::@57 gossipHello
uint32 school
Definition SmartScriptMgr.h:233
uint32 rangeMin
Definition SmartScriptMgr.h:218
uint32 eventId
Definition SmartScriptMgr.h:424
struct SmartEvent::@30::@34 spellHit
struct SmartEvent::@30::@35 los
uint32 guid
Definition SmartScriptMgr.h:446
struct SmartEvent::@30::@49 dataSet
uint32 dist
Definition SmartScriptMgr.h:448
struct SmartEvent::@30::@48 movementInform
uint32 spellId
Definition SmartScriptMgr.h:267
uint32 emote
Definition SmartScriptMgr.h:310
struct SmartEvent::@30::@72 nearUnitNegation
uint32 hpPct
Definition SmartScriptMgr.h:440
uint32 filter
Definition SmartScriptMgr.h:392
uint32 hostilityMode
Hostility mode of the event. 0: hostile, 1: not hostile, 2: any.
Definition SmartScriptMgr.h:243
uint32 hpDeficit
Definition SmartScriptMgr.h:272
struct SmartEvent::@30::@33 kill
struct SmartEvent::@30::@71 meleeRange
uint32 area
Definition SmartScriptMgr.h:254
uint32 count
Definition SmartScriptMgr.h:318
uint32 onlyInCombat
Definition SmartScriptMgr.h:291
struct SmartEvent::@30::@41 missingBuff
struct SmartEvent::@30::@50 waypoint
uint32 value
Definition SmartScriptMgr.h:346
struct SmartEvent::@30::@42 summoned
uint32 pathID
Definition SmartScriptMgr.h:354
SAIBool playerOnly
Definition SmartScriptMgr.h:226
struct SmartEvent::@30::@54 areatrigger
struct SmartEvent::@30::@60 eventPhaseChange
uint32 pathId
Definition SmartScriptMgr.h:340
uint32 creatureEntry
Definition SmartScriptMgr.h:382
struct SmartEvent::@30::@65 friendlyHealthPct
struct SmartEvent::@30::@58 gossip
uint32 action
Definition SmartScriptMgr.h:398
struct SmartEvent::@30::@64 doAction
struct SmartEvent::@30::@46 charm
struct SmartEvent::@30::@63 eventInform
struct SmartEvent::@30::@38 targetCasting
uint32 spell
Definition SmartScriptMgr.h:232
uint32 maxCount
Definition SmartScriptMgr.h:471
uint32 gameEventId
Definition SmartScriptMgr.h:414
uint32 textGroupID
Definition SmartScriptMgr.h:381
uint32 cooldownMin
Definition SmartScriptMgr.h:224
uint32 onRemove
Definition SmartScriptMgr.h:325
struct SmartEvent::@30::@73 wpData
uint32 quest
Definition SmartScriptMgr.h:303
struct SmartEvent::@30::@67 counter
uint32 state
Definition SmartScriptMgr.h:419
struct SmartEvent::@30::@36 respawn
struct SmartEvent::@30::@56 timedEvent
struct SmartEvent::@30::@39 friendlyHealth
uint32 rangeMax
Definition SmartScriptMgr.h:219
uint32 team
Definition SmartScriptMgr.h:369
uint32 range
Definition SmartScriptMgr.h:483
uint32 minCount
Definition SmartScriptMgr.h:462
struct SmartEvent::@30::@37 minMax
struct SmartEvent::@30::@55 textOver
struct SmartEvent::@30::@40 friendlyCC
struct SmartEvent::@30::@62 goStateChanged
uint32 creature
Definition SmartScriptMgr.h:227
uint32 phasemask
Definition SmartScriptMgr.h:409

References SmartEvent::action, SmartScriptHolder::active, SmartEvent::Any, SmartEvent::area, SmartEvent::areatrigger, SmartEvent::aura, SmartEvent::charm, SmartEvent::cooldownMax, SmartEvent::cooldownMin, SmartEvent::count, SmartEvent::counter, SmartEvent::creature, SmartEvent::creatureEntry, CURRENT_GENERIC_SPELL, SmartEvent::dataSet, SmartEvent::dist, SmartEvent::distance, SmartEvent::doAction, DoFindFriendlyCC(), DoFindFriendlyMissingBuff(), DoSelectLowestHpFriendly(), DoSelectLowestHpPercentFriendly(), SmartEvent::emote, SmartEvent::entry, SmartScriptHolder::event, SmartEvent::event_flags, SmartEvent::event_phase_mask, SmartEvent::eventId, SmartEvent::eventInform, SmartEvent::eventPhaseChange, SmartEvent::filter, FindCreatureNear(), FindGameObjectNear(), SmartEvent::friendlyCC, SmartEvent::friendlyHealth, SmartEvent::friendlyHealthPct, SmartEvent::gameEvent, SmartEvent::gameEventId, Unit::GetAuraCount(), GetBaseObject(), GetCounterValue(), WorldObject::GetCreatureListWithEntryInGrid(), Unit::GetCurrentSpell(), Object::GetEntry(), SmartScriptHolder::GetEventType(), WorldObject::GetGameObjectListWithEntryInGrid(), Unit::GetHealthPct(), Unit::GetMaxHealth(), Unit::GetMaxPower(), GetPathId(), Unit::GetPowerPct(), GetTargets(), SmartScriptHolder::GetTargetType(), Unit::GetThreatMgr(), ThreatManager::GetUnsortedThreatList(), Unit::GetVictim(), Creature::GetWaypointPath(), GetWorldObjectsInDist(), SmartEvent::gossip, SmartEvent::gossipHello, SmartEvent::goStateChanged, SmartEvent::guid, Unit::HealthBelowPctDamaged(), SmartEvent::Hostile, SmartEvent::hostilityMode, SmartEvent::hpDeficit, SmartEvent::hpPct, SmartEvent::id, SpellInfo::Id, SmartEvent::instancePlayerEnter, SmartEvent::invert, IsCharmedCreature(), IsCreature(), Creature::IsEngaged(), Unit::IsFriendlyTo(), IsGameObject(), Unit::IsHostileTo(), Unit::IsInCombat(), IsInPhase(), WorldObject::IsInRange(), Unit::IsNonMeleeSpellCast(), Object::IsPlayer(), IsPlayer(), IsUnit(), WorldObject::IsWithinDistInMap(), WorldObject::IsWithinLOSInMap(), Unit::IsWithinMeleeRange(), SmartEvent::kill, LOG_DEBUG, LOG_ERROR, SmartEvent::los, SmartEvent::map, SmartEvent::max, SmartEvent::maxCount, SmartEvent::maxDist, me, SmartEvent::meleeRange, SmartEvent::min, SmartEvent::minCount, SmartEvent::minMax, SmartEvent::minMaxRepeat, SmartEvent::missingBuff, SmartEvent::movementInform, SmartEvent::nearPlayer, SmartEvent::nearPlayerNegation, SmartEvent::nearUnit, SmartEvent::nearUnitNegation, SmartEvent::NotHostile, SmartEvent::onlyInCombat, SmartEvent::onRemove, SmartEvent::pathId, SmartEvent::pathID, SmartEvent::phasemask, SmartEvent::playerOnly, SmartEvent::pointID, SmartEvent::pointId, POWER_MANA, ProcessAction(), ProcessTimedAction(), SmartEvent::quest, SmartEvent::radius, SmartEvent::range, SmartEvent::rangeMax, SmartEvent::rangeMin, RecalcTimer(), SmartEvent::repeat, SmartEvent::repeatMax, SmartEvent::repeatMin, SmartEvent::respawn, SmartScriptHolder::runOnce, SmartEvent::school, SpellInfo::SchoolMask, Acore::Containers::SelectRandomContainerElement(), SmartEvent::sender, SMART_EVENT_ACCEPTED_QUEST, SMART_EVENT_ACTION_DONE, SMART_EVENT_AGGRO, SMART_EVENT_AI_INIT, SMART_EVENT_AREA_CASTING, SMART_EVENT_AREA_RANGE, SMART_EVENT_AREATRIGGER_ONTRIGGER, SMART_EVENT_CHARMED, SMART_EVENT_CHARMED_TARGET, SMART_EVENT_CORPSE_REMOVED, SMART_EVENT_COUNTER_SET, SMART_EVENT_DAMAGED, SMART_EVENT_DAMAGED_TARGET, SMART_EVENT_DATA_SET, SMART_EVENT_DEATH, SMART_EVENT_DISTANCE_CREATURE, SMART_EVENT_DISTANCE_GAMEOBJECT, SMART_EVENT_ESCORT_ENDED, SMART_EVENT_ESCORT_PAUSED, SMART_EVENT_ESCORT_REACHED, SMART_EVENT_ESCORT_RESUMED, SMART_EVENT_ESCORT_START, SMART_EVENT_ESCORT_STOPPED, SMART_EVENT_EVADE, SMART_EVENT_EVENT_PHASE_CHANGE, SMART_EVENT_FLAG_NOT_REPEATABLE, SMART_EVENT_FLAG_WHILE_CHARMED, SMART_EVENT_FOLLOW_COMPLETED, SMART_EVENT_FRIENDLY_HEALTH, SMART_EVENT_FRIENDLY_HEALTH_PCT, SMART_EVENT_FRIENDLY_IS_CC, SMART_EVENT_FRIENDLY_MISSING_BUFF, SMART_EVENT_GAME_EVENT_END, SMART_EVENT_GAME_EVENT_START, SMART_EVENT_GO_EVENT_INFORM, SMART_EVENT_GO_STATE_CHANGED, SMART_EVENT_GOSSIP_HELLO, SMART_EVENT_GOSSIP_SELECT, SMART_EVENT_HAS_AURA, SMART_EVENT_HEALTH_PCT, SMART_EVENT_IC_LOS, SMART_EVENT_INSTANCE_PLAYER_ENTER, SMART_EVENT_IS_BEHIND_TARGET, SMART_EVENT_IS_IN_MELEE_RANGE, SMART_EVENT_JUST_CREATED, SMART_EVENT_JUST_SUMMONED, SMART_EVENT_KILL, SMART_EVENT_LINK, SMART_EVENT_MANA_PCT, SMART_EVENT_MOVEMENTINFORM, SMART_EVENT_NEAR_PLAYERS, SMART_EVENT_NEAR_PLAYERS_NEGATION, SMART_EVENT_NEAR_UNIT, SMART_EVENT_NEAR_UNIT_NEGATION, SMART_EVENT_ON_SPELLCLICK, SMART_EVENT_OOC_LOS, SMART_EVENT_PASSENGER_BOARDED, SMART_EVENT_PASSENGER_REMOVED, SMART_EVENT_QUEST_ACCEPTED, SMART_EVENT_QUEST_COMPLETION, SMART_EVENT_QUEST_FAIL, SMART_EVENT_QUEST_OBJ_COMPLETION, SMART_EVENT_QUEST_REWARDED, SMART_EVENT_RANGE, SMART_EVENT_REACHED_HOME, SMART_EVENT_RECEIVE_EMOTE, SMART_EVENT_RECEIVE_HEAL, SMART_EVENT_RESET, SMART_EVENT_RESPAWN, SMART_EVENT_REWARD_QUEST, SMART_EVENT_SPELLHIT, SMART_EVENT_SPELLHIT_TARGET, SMART_EVENT_SUMMON_DESPAWNED, SMART_EVENT_SUMMONED_UNIT, SMART_EVENT_SUMMONED_UNIT_DIES, SMART_EVENT_SUMMONED_UNIT_EVADE, SMART_EVENT_TARGET_BUFFED, SMART_EVENT_TARGET_HEALTH_PCT, SMART_EVENT_TARGET_MANA_PCT, SMART_EVENT_TEXT_OVER, SMART_EVENT_TIMED_EVENT_TRIGGERED, SMART_EVENT_TRANSPORT_ADDCREATURE, SMART_EVENT_TRANSPORT_ADDPLAYER, SMART_EVENT_TRANSPORT_RELOCATE, SMART_EVENT_TRANSPORT_REMOVE_PLAYER, SMART_EVENT_UPDATE, SMART_EVENT_UPDATE_IC, SMART_EVENT_UPDATE_OOC, SMART_EVENT_VICTIM_CASTING, SMART_EVENT_WAYPOINT_ENDED, SMART_EVENT_WAYPOINT_REACHED, SMART_SCRIPT_RESPAWN_CONDITION_AREA, SMART_SCRIPT_RESPAWN_CONDITION_MAP, SMART_TARGET_ACTION_INVOKER, SMART_TARGET_CLOSEST_CREATURE, SMART_TARGET_CLOSEST_PLAYER, SMART_TARGET_CREATURE_DISTANCE, SMART_TARGET_CREATURE_GUID, SMART_TARGET_CREATURE_RANGE, SMART_TARGET_PLAYER_DISTANCE, SMART_TARGET_PLAYER_RANGE, SMART_TARGET_SELF, SmartEvent::spell, SmartEvent::spellHit, SmartEvent::spellId, SmartEvent::state, SmartEvent::summoned, SmartEvent::targetCasting, SmartEvent::team, SmartEvent::textGroupID, SmartEvent::textOver, SmartEvent::timedEvent, SmartEvent::timer, Object::ToUnit(), SmartEvent::transportAddCreature, SmartEvent::type, SmartEvent::value, SmartEvent::waypoint, and SmartEvent::wpData.

Referenced by ProcessEventsFor(), and UpdateTimer().

◆ ProcessEventsFor()

void SmartScript::ProcessEventsFor ( SMART_EVENT  e,
Unit *  unit = nullptr,
uint32  var0 = 0,
uint32  var1 = 0,
bool  bvar = false,
SpellInfo const *  spell = nullptr,
GameObject *  gob = nullptr 
)
158{
159 for (SmartAIEventList::iterator i = mEvents.begin(); i != mEvents.end(); ++i)
160 {
161 SMART_EVENT eventType = SMART_EVENT((*i).GetEventType());
162 if (eventType == SMART_EVENT_LINK)//special handling
163 continue;
164
165 if (eventType == e)
166 {
167 ConditionList conds = sConditionMgr->GetConditionsForSmartEvent((*i).entryOrGuid, (*i).event_id, (*i).source_type);
168 ConditionSourceInfo info = ConditionSourceInfo(unit, GetBaseObject(), me ? me->GetVictim() : nullptr);
169
170 if (sConditionMgr->IsObjectMeetToConditions(info, conds))
171 {
172 ASSERT(executionStack.empty());
173 executionStack.emplace_back(SmartScriptFrame{ *i, unit, var0, var1, bvar, spell, gob });
174 while (!executionStack.empty())
175 {
176 auto [stack_holder , stack_unit, stack_var0, stack_var1, stack_bvar, stack_spell, stack_gob] = executionStack.back();
177 executionStack.pop_back();
178 ProcessEvent(stack_holder, stack_unit, stack_var0, stack_var1, stack_bvar, stack_spell, stack_gob);
179 }
180 }
181 }
182 }
183}
#define sConditionMgr
Definition ConditionMgr.h:296
std::list< Condition * > ConditionList
Definition ConditionMgr.h:240
#define ASSERT
Definition Errors.h:68
void ProcessEvent(SmartScriptHolder &e, Unit *unit=nullptr, uint32 var0=0, uint32 var1=0, bool bvar=false, SpellInfo const *spell=nullptr, GameObject *gob=nullptr)
Definition SmartScript.cpp:4304
Definition ConditionMgr.h:185

References ASSERT, executionStack, GetBaseObject(), Unit::GetVictim(), me, mEvents, ProcessEvent(), sConditionMgr, and SMART_EVENT_LINK.

Referenced by SmartAI::CorpseRemoved(), SmartAI::DamageDealt(), SmartAI::DamageTaken(), SmartGameObjectAI::Destroyed(), SmartAI::DoAction(), SmartAI::EndPath(), SmartAI::EnterEvadeMode(), SmartGameObjectAI::EventInform(), SmartGameObjectAI::GossipHello(), SmartGameObjectAI::GossipSelect(), SmartAI::HealReceived(), SmartAI::InitializeAI(), SmartGameObjectAI::InitializeAI(), SmartAI::IsSummonedBy(), SmartAI::JustDied(), SmartAI::JustEngagedWith(), SmartAI::JustReachedHome(), SmartAI::JustRespawned(), SmartAI::JustSummoned(), SmartGameObjectAI::JustSummoned(), SmartAI::KilledUnit(), SmartAI::MovementInform(), SmartAI::MovepointReached(), SmartAI::OnCharmed(), SmartGameObjectAI::OnGameEvent(), OnInitialize(), OnMoveInLineOfSight(), OnReset(), SmartAI::OnSpellClick(), SmartGameObjectAI::OnStateChanged(), SmartTrigger::OnTrigger(), OnUpdate(), SmartAI::PassengerBoarded(), SmartAI::PathEndReached(), SmartAI::PausePath(), ProcessAction(), SmartGameObjectAI::QuestAccept(), SmartGameObjectAI::QuestReward(), SmartAI::ReceiveEmote(), SmartGameObjectAI::Reset(), SmartAI::SetData(), SmartGameObjectAI::SetData(), SetPhase(), SmartAI::sGossipHello(), SmartAI::sGossipSelect(), SmartAI::sOnGameEvent(), SmartAI::SpellHit(), SmartGameObjectAI::SpellHit(), SmartAI::SpellHitTarget(), SmartAI::sQuestAccept(), SmartAI::sQuestReward(), SmartAI::StartPath(), SmartAI::StopFollow(), SmartAI::StopPath(), StoreCounter(), SmartAI::SummonedCreatureDespawn(), SmartGameObjectAI::SummonedCreatureDespawn(), SmartAI::SummonedCreatureDies(), SmartGameObjectAI::SummonedCreatureDies(), SmartAI::SummonedCreatureEvade(), SmartGameObjectAI::SummonedCreatureEvade(), SmartAI::UpdatePath(), SmartAI::WaypointPathEnded(), and SmartAI::WaypointReached().

◆ ProcessTimedAction()

void SmartScript::ProcessTimedAction ( SmartScriptHolder &  e,
uint32 const &  min,
uint32 const &  max,
Unit *  unit = nullptr,
uint32  var0 = 0,
uint32  var1 = 0,
bool  bvar = false,
SpellInfo const *  spell = nullptr,
GameObject *  gob = nullptr 
)
3501{
3502 // xinef: extended by selfs victim
3503 ConditionList const conds = sConditionMgr->GetConditionsForSmartEvent(e.entryOrGuid, e.event_id, e.source_type);
3504 ConditionSourceInfo info = ConditionSourceInfo(unit, GetBaseObject(), me ? me->GetVictim() : nullptr);
3505
3506 if (sConditionMgr->IsObjectMeetToConditions(info, conds))
3507 {
3508 ProcessAction(e, unit, var0, var1, bvar, spell, gob);
3509 RecalcTimer(e, min, max);
3510 }
3511 else
3512 RecalcTimer(e, 5000, 5000);
3513}

References SmartScriptHolder::entryOrGuid, SmartScriptHolder::event_id, GetBaseObject(), Unit::GetVictim(), me, ProcessAction(), RecalcTimer(), sConditionMgr, and SmartScriptHolder::source_type.

Referenced by ProcessEvent().

◆ RaisePriority()

void SmartScript::RaisePriority ( SmartScriptHolder &  e)
private
5342{
5343 e.timer = 1200;
5344 // Change priority only if it's set to default, otherwise keep the current order of events
5346 {
5348 mEventSortingRequired = true;
5349 }
5350}
uint32 timer
Definition SmartScriptMgr.h:2030
uint32 priority
Definition SmartScriptMgr.h:2031

References SmartScriptHolder::DEFAULT_PRIORITY, mCurrentPriority, mEventSortingRequired, SmartScriptHolder::priority, and SmartScriptHolder::timer.

Referenced by RetryLater(), and UpdateTimer().

◆ RecalcTimer()

void SmartScript::RecalcTimer ( SmartScriptHolder &  e,
uint32  min,
uint32  max 
)
static
5137{
5138 // min/max was checked at loading!
5139 e.timer = urand(uint32(min), uint32(max));
5140 e.active = e.timer ? false : true;
5141}

References SmartScriptHolder::active, SmartScriptHolder::timer, and urand().

Referenced by InitTimer(), ProcessEvent(), and ProcessTimedAction().

◆ RemoveCreatureSummon()

void SmartScript::RemoveCreatureSummon ( ObjectGuid const &  guid)
5718{
5719 _summonList.erase(guid);
5720}

References _summonList.

Referenced by SmartAI::SummonedCreatureDespawn().

◆ RemoveStoredEvent()

void SmartScript::RemoveStoredEvent ( uint32  id)
inlineprivate
255 {
256 if (!mStoredEvents.empty())
257 {
258 for (SmartAIEventStoredList::iterator i = mStoredEvents.begin(); i != mStoredEvents.end(); ++i)
259 {
260 if (i->event_id == id)
261 {
262 mStoredEvents.erase(i);
263 return;
264 }
265 }
266 }
267 }

References mStoredEvents.

Referenced by OnUpdate().

◆ ResetBaseObject()

void SmartScript::ResetBaseObject ( )
inline
167 {
168 WorldObject* lookupRoot = me;
169 if (!lookupRoot)
170 lookupRoot = go;
171
172 if (lookupRoot)
173 {
174 if (meOrigGUID)
175 {
176 if (Creature* m = ObjectAccessor::GetCreature(*lookupRoot, meOrigGUID))
177 {
178 me = m;
179 go = nullptr;
180 }
181 }
182
183 if (goOrigGUID)
184 {
186 {
187 me = nullptr;
188 go = o;
189 }
190 }
191 }
192
195 }
GameObject * GetGameObject(WorldObject const &u, ObjectGuid const &guid)
Definition ObjectAccessor.cpp:208
Creature * GetCreature(WorldObject const &u, ObjectGuid const &guid)
Definition ObjectAccessor.cpp:234

References ObjectGuid::Clear(), ObjectAccessor::GetCreature(), ObjectAccessor::GetGameObject(), go, goOrigGUID, me, and meOrigGUID.

Referenced by OnReset(), and ProcessAction().

◆ RetryLater()

void SmartScript::RetryLater ( SmartScriptHolder &  e,
bool  ignoreChanceRoll = false 
)
private
5353{
5354 RaisePriority(e);
5355
5356 // This allows to retry the action later without rolling again the chance roll (which might fail and end up not executing the action)
5357 if (ignoreChanceRoll)
5359
5360 e.runOnce = false;
5361}
void RaisePriority(SmartScriptHolder &e)
Definition SmartScript.cpp:5341

References SmartScriptHolder::event, SmartEvent::event_flags, RaisePriority(), SmartScriptHolder::runOnce, and SMART_EVENT_FLAG_TEMP_IGNORE_CHANCE_ROLL.

Referenced by ProcessAction().

◆ SetPathId()

void SmartScript::SetPathId ( uint32  id)
inline
62{ mPathId = id; }

References mPathId.

Referenced by SmartAI::EndPath(), and SmartAI::LoadPath().

◆ SetPhase()

void SmartScript::SetPhase ( uint32  p)
private
5691{
5692 uint32 oldPhase = mEventPhase;
5693
5694 mEventPhase = p;
5695
5696 if (oldPhase != mEventPhase)
5697 {
5699 }
5700}

References mEventPhase, ProcessEventsFor(), and SMART_EVENT_EVENT_PHASE_CHANGE.

Referenced by DecPhase(), IncPhase(), OnReset(), and ProcessAction().

◆ SetPhaseReset()

void SmartScript::SetPhaseReset ( bool  allow)
inline
205{ _allowPhaseReset = allow; }

References _allowPhaseReset.

Referenced by ProcessAction().

◆ SetScript9()

void SmartScript::SetScript9 ( SmartScriptHolder &  e,
uint32  entry 
)
5596{
5597 //do NOT clear mTimedActionList if it's being iterated because it will invalidate the iterator and delete
5598 // any SmartScriptHolder contained like the "e" parameter passed to this function
5600 {
5601 LOG_ERROR("scripts.ai.sai", "Entry {} SourceType {} Event {} Action {} is trying to overwrite timed action list from a timed action, this is not allowed!.", e.entryOrGuid, e.GetScriptType(), e.GetEventType(), e.GetActionType());
5602 return;
5603 }
5604
5605 // Do NOT allow to start a new actionlist if a previous one is already running, unless explicitly allowed. We need to always finish the current actionlist
5607 {
5608 return;
5609 }
5610
5611 mTimedActionList.clear();
5613 if (mTimedActionList.empty())
5614 return;
5615 for (SmartAIEventList::iterator i = mTimedActionList.begin(); i != mTimedActionList.end(); ++i)
5616 {
5617 i->enableTimed = i == mTimedActionList.begin();//enable processing only for the first action
5618
5619 if (e.action.timedActionList.timerType == 0)
5620 i->event.type = SMART_EVENT_UPDATE_OOC;
5621 else if (e.action.timedActionList.timerType == 1)
5622 i->event.type = SMART_EVENT_UPDATE_IC;
5623 else if (e.action.timedActionList.timerType > 1)
5624 i->event.type = SMART_EVENT_UPDATE;
5625
5626 InitTimer((*i));
5627 }
5628}
@ SMART_SCRIPT_TYPE_TIMED_ACTIONLIST
Definition SmartScriptMgr.h:1812
SAIBool allowOverride
Definition SmartScriptMgr.h:1152
uint32 timerType
Definition SmartScriptMgr.h:1151

References SmartScriptHolder::action, SmartAction::allowOverride, SmartScriptHolder::entryOrGuid, SmartScriptHolder::GetActionType(), SmartScriptHolder::GetEventType(), SmartScriptHolder::GetScriptType(), InitTimer(), isProcessingTimedActionList, LOG_ERROR, mTimedActionList, SMART_EVENT_UPDATE, SMART_EVENT_UPDATE_IC, SMART_EVENT_UPDATE_OOC, SMART_SCRIPT_TYPE_TIMED_ACTIONLIST, sSmartScriptMgr, SmartAction::timedActionList, and SmartAction::timerType.

Referenced by ProcessAction(), SmartAI::SetScript9(), and SmartGameObjectAI::SetScript9().

◆ SortEvents()

void SmartScript::SortEvents ( SmartAIEventList &  events)
private
5337{
5338 std::sort(events.begin(), events.end());
5339}
events
Definition boss_sartura.cpp:43

Referenced by OnUpdate().

◆ StoreCounter()

void SmartScript::StoreCounter ( uint32  id,
uint32  value,
uint32  reset,
uint32  subtract 
)
inline
109 {
110 CounterMap::iterator itr = mCounterList.find(id);
111 if (itr != mCounterList.end())
112 {
113 if (!reset && !subtract)
114 {
115 itr->second += value;
116 }
117 else if (subtract)
118 {
119 itr->second -= value;
120 }
121 else
122 {
123 itr->second = value;
124 }
125 }
126 else
127 {
128 mCounterList.insert(std::make_pair(id, value));
129 }
130
132 }

References mCounterList, ProcessEventsFor(), and SMART_EVENT_COUNTER_SET.

Referenced by ProcessAction().

◆ StoreTargetList()

void SmartScript::StoreTargetList ( ObjectVector const &  targets,
uint32  id 
)
inline
94 {
95 // insert or replace
96 _storedTargets.erase(id);
97 _storedTargets.emplace(id, ObjectGuidVector(targets));
98 }
Definition SmartScriptMgr.h:2048

References _storedTargets.

Referenced by ProcessAction().

◆ UpdateTimer()

void SmartScript::UpdateTimer ( SmartScriptHolder &  e,
uint32 const  diff 
)
5144{
5145 if (e.GetEventType() == SMART_EVENT_LINK)
5146 return;
5147
5149 return;
5150
5151 if (e.GetEventType() == SMART_EVENT_UPDATE_IC && (!me || !me->IsEngaged()))
5152 return;
5153
5154 if (e.GetEventType() == SMART_EVENT_UPDATE_OOC && (me && me->IsEngaged()))//can be used with me=nullptr (go script)
5155 return;
5156
5157 if (e.timer < diff)
5158 {
5159 // delay spell cast for another AI tick if another spell is being cast
5161 {
5162 uint32 flags = (e.GetActionType() == SMART_ACTION_CAST)
5164 : e.action.castCustom.flags;
5165 if (!(flags & SMARTCAST_INTERRUPT_PREVIOUS))
5166 {
5168 {
5169 RaisePriority(e);
5170 return;
5171 }
5172 }
5173 }
5174
5175 // Delay flee for assist event if casting
5177 {
5178 e.timer = 1200;
5179 return;
5180 } // @TODO: Can't these be handled by the action themselves instead? Less expensive
5181
5182 e.active = true;//activate events with cooldown
5183 switch (e.GetEventType())//process ONLY timed events
5184 {
5189 case SMART_EVENT_UPDATE:
5196 case SMART_EVENT_RANGE:
5210 {
5211 ASSERT(executionStack.empty());
5212 executionStack.emplace_back(SmartScriptFrame{ e, nullptr, 0, 0, false, nullptr, nullptr });
5213 while (!executionStack.empty())
5214 {
5215 auto [stack_holder, stack_unit, stack_var0, stack_var1, stack_bvar, stack_spell, stack_gob] = executionStack.back();
5216 executionStack.pop_back();
5217 ProcessEvent(stack_holder, stack_unit, stack_var0, stack_var1, stack_bvar, stack_spell, stack_gob);
5218 }
5220 {
5221 e.enableTimed = false;//disable event if it is in an ActionList and was processed once
5222 for (SmartAIEventList::iterator i = mTimedActionList.begin(); i != mTimedActionList.end(); ++i)
5223 {
5224 //find the first event which is not the current one and enable it
5225 if (i->event_id > e.event_id)
5226 {
5227 i->enableTimed = true;
5228 break;
5229 }
5230 }
5231 }
5232 break;
5233 }
5234 }
5235
5237 {
5238 // Reset priority to default one only if the event hasn't been rescheduled again to next loop
5239 if (e.timer > 1)
5240 {
5241 // Re-sort events if this was moved to the top of the queue
5242 mEventSortingRequired = true;
5243 // Reset priority to default one
5245 }
5246 }
5247 }
5248 else
5249 e.timer -= diff;
5250}
bool IsActionPreventedByCasting() const
Definition Unit.cpp:4110
bool enableTimed
Definition SmartScriptMgr.h:2034

References SmartScriptHolder::action, SmartScriptHolder::active, ASSERT, SmartAction::cast, SmartAction::castCustom, SmartAction::castFlags, SmartScriptHolder::DEFAULT_PRIORITY, SmartScriptHolder::enableTimed, SmartScriptHolder::event, SmartScriptHolder::event_id, SmartEvent::event_phase_mask, executionStack, SmartAction::flags, SmartScriptHolder::GetActionType(), SmartScriptHolder::GetEventType(), SmartScriptHolder::GetScriptType(), Unit::IsActionPreventedByCasting(), Creature::IsEngaged(), IsInPhase(), me, mEventSortingRequired, mTimedActionList, SmartScriptHolder::priority, ProcessEvent(), RaisePriority(), SMART_ACTION_CAST, SMART_ACTION_CUSTOM_CAST, SMART_ACTION_FLEE_FOR_ASSIST, SMART_EVENT_AREA_CASTING, SMART_EVENT_AREA_RANGE, SMART_EVENT_DISTANCE_CREATURE, SMART_EVENT_DISTANCE_GAMEOBJECT, SMART_EVENT_FRIENDLY_HEALTH, SMART_EVENT_FRIENDLY_HEALTH_PCT, SMART_EVENT_FRIENDLY_IS_CC, SMART_EVENT_FRIENDLY_MISSING_BUFF, SMART_EVENT_HAS_AURA, SMART_EVENT_HEALTH_PCT, SMART_EVENT_IS_BEHIND_TARGET, SMART_EVENT_IS_IN_MELEE_RANGE, SMART_EVENT_LINK, SMART_EVENT_MANA_PCT, SMART_EVENT_NEAR_PLAYERS, SMART_EVENT_NEAR_PLAYERS_NEGATION, SMART_EVENT_NEAR_UNIT, SMART_EVENT_NEAR_UNIT_NEGATION, SMART_EVENT_RANGE, SMART_EVENT_TARGET_BUFFED, SMART_EVENT_TARGET_HEALTH_PCT, SMART_EVENT_TARGET_MANA_PCT, SMART_EVENT_UPDATE, SMART_EVENT_UPDATE_IC, SMART_EVENT_UPDATE_OOC, SMART_EVENT_VICTIM_CASTING, SMART_SCRIPT_TYPE_TIMED_ACTIONLIST, SMARTCAST_INTERRUPT_PREVIOUS, and SmartScriptHolder::timer.

Referenced by OnUpdate().

Member Data Documentation

◆ _allowPhaseReset

bool SmartScript::_allowPhaseReset
private

◆ _storedTargets

ObjectVectorMap SmartScript::_storedTargets
private

◆ _summonList

GuidUnorderedSet SmartScript::_summonList
private

◆ executionStack

std::deque<SmartScriptFrame> SmartScript::executionStack
private

◆ go

◆ goOrigGUID

ObjectGuid SmartScript::goOrigGUID
private

Referenced by ProcessAction(), and ResetBaseObject().

◆ isProcessingTimedActionList

bool SmartScript::isProcessingTimedActionList
private

Referenced by OnUpdate(), SetScript9(), and SmartScript().

◆ mCounterList

CounterMap SmartScript::mCounterList

◆ mCurrentPriority

uint32 SmartScript::mCurrentPriority
private

Referenced by RaisePriority(), and SmartScript().

◆ me

◆ meOrigGUID

ObjectGuid SmartScript::meOrigGUID
private

Referenced by ProcessAction(), and ResetBaseObject().

◆ mEventPhase

uint32 SmartScript::mEventPhase
private

◆ mEvents

◆ mEventSortingRequired

bool SmartScript::mEventSortingRequired
private

◆ mInstallEvents

SmartAIEventList SmartScript::mInstallEvents
private

Referenced by AddEvent(), and InstallEvents().

◆ mLastInvoker

◆ mLastTextID

uint32 SmartScript::mLastTextID
private

◆ mPathId

uint32 SmartScript::mPathId
private

Referenced by GetPathId(), SetPathId(), and SmartScript().

◆ mRemIDs

std::list<uint32> SmartScript::mRemIDs
private

Referenced by OnUpdate(), and ProcessAction().

◆ mScriptType

SmartScriptType SmartScript::mScriptType
private

◆ mStoredDecimals

std::unordered_map<int32, int32> SmartScript::mStoredDecimals
private

◆ mStoredEvents

SmartAIEventStoredList SmartScript::mStoredEvents
private

◆ mTalkerEntry

uint32 SmartScript::mTalkerEntry
private

◆ mTemplate

SMARTAI_TEMPLATE SmartScript::mTemplate
private

Referenced by InstallTemplate(), and SmartScript().

◆ mTextTimer

uint32 SmartScript::mTextTimer
private

◆ mTimedActionList

SmartAIEventList SmartScript::mTimedActionList
private

Referenced by OnUpdate(), SetScript9(), and UpdateTimer().

◆ mUseTextTimer

bool SmartScript::mUseTextTimer
private

◆ trigger

AreaTrigger const* SmartScript::trigger
private

The documentation for this class was generated from the following files: