Project SkyFire Core
SkyFire 5.4.8 server core API documentation
Loading...
Searching...
No Matches
ThreatManager.h
Go to the documentation of this file.
1/*
2* This file is part of Project SkyFire https://www.projectskyfire.org.
3* See LICENSE.md file for Copyright information
4*/
5
6#ifndef SF_THREATMANAGER
7#define SF_THREATMANAGER
8
9#include "Common.h"
11#include "SharedDefines.h"
12#include "ThreatCalcHelper.h"
13#include "UnitEvents.h"
14
15#include <list>
16
17//==============================================================
18
19class Unit;
20class Creature;
21class ThreatManager;
22class SpellInfo;
23
24#define THREAT_UPDATE_INTERVAL 1 * IN_MILLISECONDS // Server should send threat update to client periodically each second
25
26//==============================================================
27class HostileReference : public Reference<Unit, ThreatManager>
28{
29public:
30 HostileReference(Unit* refUnit, ThreatManager* threatManager, float threat);
31
32 //=================================================
33 void addThreat(float modThreat);
34
35 void setThreat(float threat) { addThreat(threat - getThreat()); }
36
37 void addThreatPercent(int32 percent);
38
39 float getThreat() const { return iThreat; }
40
41 bool isOnline() const { return iOnline; }
42
43 // The Unit might be in water and the creature can not enter the water, but has range attack
44 // in this case online = true, but accessible = false
45 bool isAccessible() const { return iAccessible; }
46
47 // used for temporary setting a threat and reducting it later again.
48 // the threat modification is stored
49 void setTempThreat(float threat)
50 {
51 addTempThreat(threat - getThreat());
52 }
53
54 void addTempThreat(float threat)
55 {
56 iTempThreatModifier = threat;
57 if (iTempThreatModifier != 0.0f)
59 }
60
62 {
63 if (iTempThreatModifier != 0.0f)
64 {
67 }
68 }
69
71
72 //=================================================
73 // check, if source can reach target and set the status
74 void updateOnlineStatus();
75
77
79 //=================================================
80
81 bool operator == (const HostileReference& hostileRef) const { return hostileRef.getUnitGuid() == getUnitGuid(); }
82
83 //=================================================
84
85 uint64 getUnitGuid() const { return iUnitGuid; }
86
87 //=================================================
88 // reference is not needed anymore. realy delete it !
89
90 void removeReference();
91
92 //=================================================
93
95
96 //=================================================
97
98 // Tell our refTo (target) object that we have a link
100
101 // Tell our refTo (taget) object, that the link is cut
103
104 // Tell our refFrom (source) object, that the link is cut (Target destroyed)
106private:
107 // Inform the source, that the status of that reference was changed
108 void fireStatusChanged(ThreatRefStatusChangeEvent& threatRefStatusChangeEvent);
109
111private:
112 float iThreat;
113 float iTempThreatModifier; // used for taunt
117};
118
119//==============================================================
120class ThreatManager;
121
123{
124 friend class ThreatManager;
125
126public:
127 typedef std::list<HostileReference*> StorageType;
128
129 ThreatContainer() : iDirty(false) { }
130
132
133 HostileReference* addThreat(Unit* victim, float threat);
134
135 void modifyThreatPercent(Unit* victim, int32 percent);
136
137 HostileReference* selectNextVictim(Creature* attacker, HostileReference* currentVictim) const;
138
139 void setDirty(bool isDirty) { iDirty = isDirty; }
140
141 bool isDirty() const { return iDirty; }
142
143 bool empty() const
144 {
145 return iThreatList.empty();
146 }
147
149 {
150 return iThreatList.empty() ? NULL : iThreatList.front();
151 }
152
154
155 StorageType const& getThreatList() const { return iThreatList; }
156
157private:
158 void remove(HostileReference* hostileRef)
159 {
160 iThreatList.remove(hostileRef);
161 }
162
164 {
165 iThreatList.push_back(hostileRef);
166 }
167
168 void clearReferences();
169
170 // Sort the list if necessary
171 void update();
172
174 bool iDirty;
175};
176
177//=================================================
178
180{
181public:
182 friend class HostileReference;
183
184 explicit ThreatManager(Unit* owner);
185
187
188 void clearReferences();
189
190 void addThreat(Unit* victim, float threat, SpellSchoolMask schoolMask = SPELL_SCHOOL_MASK_NORMAL, SpellInfo const* threatSpell = NULL);
191
192 void doAddThreat(Unit* victim, float threat);
193
194 void modifyThreatPercent(Unit* victim, int32 percent);
195
196 float getThreat(Unit* victim, bool alsoSearchOfflineList = false);
197
198 bool isThreatListEmpty() const { return iThreatContainer.empty(); }
199
200 void processThreatEvent(ThreatRefStatusChangeEvent* threatRefStatusChangeEvent);
201
202 bool isNeedUpdateToClient(uint32 time);
203
205
206 Unit* GetOwner() const { return iOwner; }
207
209
210 void tauntApply(Unit* taunter);
211 void tauntFadeOut(Unit* taunter);
212
213 void setCurrentVictim(HostileReference* hostileRef);
214
215 void setDirty(bool isDirty) { iThreatContainer.setDirty(isDirty); }
216
217 // Reset all aggro without modifying the threadlist.
218 void resetAllAggro();
219
220 // Reset all aggro of unit in threadlist satisfying the predicate.
221 template<class PREDICATE> void resetAggro(PREDICATE predicate)
222 {
223 ThreatContainer::StorageType& threatList = iThreatContainer.iThreatList;
224 if (threatList.empty())
225 return;
226
227 for (ThreatContainer::StorageType::iterator itr = threatList.begin(); itr != threatList.end(); ++itr)
228 {
229 HostileReference* ref = (*itr);
230
231 if (predicate(ref->getTarget()))
232 {
233 ref->setThreat(0);
234 setDirty(true);
235 }
236 }
237 }
238
239 // methods to access the lists from the outside to do some dirty manipulation (scriping and such)
240 // I hope they are used as little as possible.
241 ThreatContainer::StorageType const& getThreatList() const { return iThreatContainer.getThreatList(); }
245private:
246 void _addThreat(Unit* victim, float threat);
247
253};
254
255//=================================================
256
257namespace Skyfire
258{
259 // Binary predicate for sorting HostileReferences based on threat value
261 {
262 public:
263 ThreatOrderPred(bool ascending = false) : m_ascending(ascending) { }
264 bool operator() (HostileReference const* a, HostileReference const* b) const
265 {
266 return m_ascending ? a->getThreat() < b->getThreat() : a->getThreat() > b->getThreat();
267 }
268 private:
269 const bool m_ascending;
270 };
271}
272#endif
std::int32_t int32
Definition Define.h:73
std::uint32_t uint32
Definition Define.h:77
std::uint64_t uint64
Definition Define.h:76
SpellSchoolMask
@ SPELL_SCHOOL_MASK_NORMAL
bool isOnline() const
HostileReference(Unit *refUnit, ThreatManager *threatManager, float threat)
void setOnlineOfflineState(bool isOnline)
bool operator==(const HostileReference &hostileRef) const
void addTempThreat(float threat)
HostileReference * next()
void setAccessibleState(bool isAccessible)
void setTempThreat(float threat)
bool isAccessible() const
void addThreat(float modThreat)
uint64 getUnitGuid() const
float getThreat() const
void fireStatusChanged(ThreatRefStatusChangeEvent &threatRefStatusChangeEvent)
void addThreatPercent(int32 percent)
float getTempThreatModifier() const
void setThreat(float threat)
TO * getTarget() const
Definition Reference.h:81
Reference< TO, FROM > * next()
Definition Reference.h:70
bool operator()(HostileReference const *a, HostileReference const *b) const
ThreatOrderPred(bool ascending=false)
HostileReference * getReferenceByTarget(Unit *victim) const
void setDirty(bool isDirty)
HostileReference * addThreat(Unit *victim, float threat)
friend class ThreatManager
bool isDirty() const
StorageType iThreatList
HostileReference * getMostHated() const
void modifyThreatPercent(Unit *victim, int32 percent)
std::list< HostileReference * > StorageType
StorageType const & getThreatList() const
bool empty() const
void addReference(HostileReference *hostileRef)
HostileReference * selectNextVictim(Creature *attacker, HostileReference *currentVictim) const
void remove(HostileReference *hostileRef)
ThreatContainer & getOnlineContainer()
ThreatManager(Unit *owner)
void tauntFadeOut(Unit *taunter)
Unit * getHostilTarget()
float getThreat(Unit *victim, bool alsoSearchOfflineList=false)
void setDirty(bool isDirty)
HostileReference * getCurrentVictim() const
ThreatContainer::StorageType const & getThreatList() const
ThreatContainer iThreatOfflineContainer
ThreatContainer iThreatContainer
void modifyThreatPercent(Unit *victim, int32 percent)
HostileReference * iCurrentVictim
void addThreat(Unit *victim, float threat, SpellSchoolMask schoolMask=SPELL_SCHOOL_MASK_NORMAL, SpellInfo const *threatSpell=NULL)
void setCurrentVictim(HostileReference *hostileRef)
bool isThreatListEmpty() const
void processThreatEvent(ThreatRefStatusChangeEvent *threatRefStatusChangeEvent)
void tauntApply(Unit *taunter)
void _addThreat(Unit *victim, float threat)
void resetAggro(PREDICATE predicate)
ThreatContainer::StorageType const & getOfflineThreatList() const
friend class HostileReference
bool isNeedUpdateToClient(uint32 time)
Unit * GetOwner() const
void doAddThreat(Unit *victim, float threat)
ThreatContainer & getOfflineContainer()
Definition Unit.h:1367