Project SkyFire Core
SkyFire 5.4.8 server core API documentation
Loading...
Searching...
No Matches
zone_howling_fjord.cpp
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/* ScriptData
7SDName: Sholazar_Basin
8SD%Complete: 100
9SDComment: Quest support: 11253, 11241.
10SDCategory: howling_fjord
11EndScriptData */
12
13/* ContentData
14npc_plaguehound_tracker
15npc_apothecary_hanes
16EndContentData */
17
18#include "ScriptMgr.h"
19#include "ScriptedCreature.h"
20#include "ScriptedGossip.h"
21#include "ScriptedEscortAI.h"
22#include "Player.h"
23
24/*######
25## npc_apothecary_hanes
26######*/
36
38{
39public:
40 npc_apothecary_hanes() : CreatureScript("npc_apothecary_hanes") { }
41
42 bool OnQuestAccept(Player* player, Creature* creature, Quest const* quest) OVERRIDE
43 {
44 if (quest->GetQuestId() == QUEST_TRAIL_OF_FIRE)
45 {
46 switch (player->GetTeam())
47 {
48 case ALLIANCE:
49 creature->setFaction(FACTION_ESCORTEE_A);
50 break;
51 case HORDE:
52 creature->setFaction(FACTION_ESCORTEE_H);
53 break;
54 }
55 CAST_AI(npc_escortAI, (creature->AI()))->Start(true, false, player->GetGUID());
56 }
57 return true;
58 }
59
61 {
64
66 {
67 SetDespawnAtFar(false);
68 PotTimer = 10000; //10 sec cooldown on potion
69 }
70
71 void JustDied(Unit* /*killer*/) OVERRIDE
72 {
73 if (Player* player = GetPlayerForEscort())
74 player->FailQuest(QUEST_TRAIL_OF_FIRE);
75 }
76
78 {
79 if (HealthBelowPct(75))
80 {
81 if (PotTimer <= diff)
82 {
83 DoCast(me, 17534, true);
84 PotTimer = 10000;
85 } else PotTimer -= diff;
86 }
87 if (GetAttack() && UpdateVictim())
89 }
90
92 {
93 Player* player = GetPlayerForEscort();
94 if (!player)
95 return;
96
97 switch (waypointId)
98 {
99 case 1:
100 me->SetReactState(REACT_AGGRESSIVE);
101 SetRun(true);
102 break;
103 case 23:
105 me->DespawnOrUnsummon();
106 break;
107 case 5:
108 if (Unit* Trigger = me->FindNearestCreature(NPC_HANES_FIRE_TRIGGER, 10.0f))
109 Trigger->CastSpell(Trigger, SPELL_COSMETIC_LOW_POLY_FIRE, false);
110 SetRun(false);
111 break;
112 case 6:
113 if (Unit* Trigger = me->FindNearestCreature(NPC_HANES_FIRE_TRIGGER, 10.0f))
114 Trigger->CastSpell(Trigger, SPELL_COSMETIC_LOW_POLY_FIRE, false);
115 SetRun(true);
116 break;
117 case 8:
118 if (Unit* Trigger = me->FindNearestCreature(NPC_HANES_FIRE_TRIGGER, 10.0f))
119 Trigger->CastSpell(Trigger, SPELL_COSMETIC_LOW_POLY_FIRE, false);
120 SetRun(false);
121 break;
122 case 9:
123 if (Unit* Trigger = me->FindNearestCreature(NPC_HANES_FIRE_TRIGGER, 10.0f))
124 Trigger->CastSpell(Trigger, SPELL_COSMETIC_LOW_POLY_FIRE, false);
125 break;
126 case 10:
127 SetRun(true);
128 break;
129 case 13:
130 SetRun(false);
131 break;
132 case 14:
133 if (Unit* Trigger = me->FindNearestCreature(NPC_HANES_FIRE_TRIGGER, 10.0f))
134 Trigger->CastSpell(Trigger, SPELL_COSMETIC_LOW_POLY_FIRE, false);
135 SetRun(true);
136 break;
137 }
138 }
139 };
140
142 {
143 return new npc_Apothecary_HanesAI(creature);
144 }
145};
146
147/*######
148## npc_plaguehound_tracker
149######*/
150
155
157{
158public:
159 npc_plaguehound_tracker() : CreatureScript("npc_plaguehound_tracker") { }
160
162 {
164
166 {
167 uint64 summonerGUID = 0;
168
169 if (me->IsSummon())
170 if (Unit* summoner = me->ToTempSummon()->GetSummoner())
171 if (summoner->GetTypeId() == TypeID::TYPEID_PLAYER)
172 summonerGUID = summoner->GetGUID();
173
174 if (!summonerGUID)
175 return;
176
177 me->SetWalk(true);
178 Start(false, false, summonerGUID);
179 }
180
182 {
183 if (waypointId != 26)
184 return;
185
186 me->DespawnOrUnsummon();
187 }
188 };
189
191 {
192 return new npc_plaguehound_trackerAI(creature);
193 }
194};
195
196/*######
197## npc_razael_and_lyana
198######*/
199
200#define GOSSIP_RAZAEL_REPORT "High Executor Anselm wants a report on the situation."
201#define GOSSIP_LYANA_REPORT "High Executor Anselm requests your report."
202
213
215{
216public:
217 npc_razael_and_lyana() : CreatureScript("npc_razael_and_lyana") { }
218
219 bool OnGossipHello(Player* player, Creature* creature) OVERRIDE
220 {
221 if (creature->IsQuestGiver())
222 player->PrepareQuestMenu(creature->GetGUID());
223
224 if (player->GetQuestStatus(QUEST_REPORTS_FROM_THE_FIELD) == QUEST_STATUS_INCOMPLETE)
225 switch (creature->GetEntry())
226 {
227 case NPC_RAZAEL:
228 if (!player->GetReqKillOrCastCurrentCount(QUEST_REPORTS_FROM_THE_FIELD, NPC_RAZAEL))
229 {
231 player->SEND_GOSSIP_MENU(GOSSIP_TEXTID_RAZAEL1, creature->GetGUID());
232 return true;
233 }
234 break;
235 case NPC_LYANA:
236 if (!player->GetReqKillOrCastCurrentCount(QUEST_REPORTS_FROM_THE_FIELD, NPC_LYANA))
237 {
239 player->SEND_GOSSIP_MENU(GOSSIP_TEXTID_LYANA1, creature->GetGUID());
240 return true;
241 }
242 break;
243 }
244 player->SEND_GOSSIP_MENU(player->GetGossipTextId(creature), creature->GetGUID());
245 return true;
246 }
247
248 bool OnGossipSelect(Player* player, Creature* creature, uint32 /*sender*/, uint32 action) OVERRIDE
249 {
250 player->PlayerTalkClass->ClearMenus();
251 switch (action)
252 {
253 case GOSSIP_ACTION_INFO_DEF + 1:
254 player->SEND_GOSSIP_MENU(GOSSIP_TEXTID_RAZAEL2, creature->GetGUID());
255 player->TalkedToCreature(NPC_RAZAEL, creature->GetGUID());
256 break;
257 case GOSSIP_ACTION_INFO_DEF + 2:
258 player->SEND_GOSSIP_MENU(GOSSIP_TEXTID_LYANA2, creature->GetGUID());
259 player->TalkedToCreature(NPC_LYANA, creature->GetGUID());
260 break;
261 }
262 return true;
263 }
264};
265
266/*######
267## npc_daegarn
268######*/
269
271{
273
274 NPC_FIRJUS = 24213,
276 NPC_YOROS = 24214,
277 NPC_OLUF = 23931,
278
279 NPC_PRISONER_1 = 24253, // looks the same but has different abilities
282};
283
284static float afSummon[] = {838.81f, -4678.06f, -94.182f};
285static float afCenter[] = {801.88f, -4721.87f, -96.143f};
286
288{
289public:
290 npc_daegarn() : CreatureScript("npc_daegarn") { }
291
292 bool OnQuestAccept(Player* player, Creature* creature, const Quest* quest) OVERRIDE
293 {
294 if (quest->GetQuestId() == QUEST_DEFEAT_AT_RING)
295 {
296 if (npc_daegarnAI* pDaegarnAI = CAST_AI(npc_daegarn::npc_daegarnAI, creature->AI()))
297 pDaegarnAI->StartEvent(player->GetGUID());
298 }
299
300 return true;
301 }
302
304 struct npc_daegarnAI : public ScriptedAI
305 {
306 npc_daegarnAI(Creature* creature) : ScriptedAI(creature) { }
307
310
312 {
313 bEventInProgress = false;
314 uiPlayerGUID = 0;
315 }
316
317 void StartEvent(uint64 uiGUID)
318 {
320 return;
321
322 uiPlayerGUID = uiGUID;
323
325 }
326
328 {
330 {
331 if (player->IsAlive())
332 {
333 summon->SetWalk(false);
334 summon->GetMotionMaster()->MovePoint(0, afCenter[0], afCenter[1], afCenter[2]);
335 summon->AI()->AttackStart(player);
336 return;
337 }
338 }
339
340 Reset();
341 }
342
344 {
346 }
347
348 void SummonedCreatureDies(Creature* summoned, Unit* /*killer*/) OVERRIDE
349 {
350 uint32 uiEntry = 0;
351
352 // will eventually reset the event if something goes wrong
353 switch (summoned->GetEntry())
354 {
355 case NPC_FIRJUS: uiEntry = NPC_JLARBORN; break;
356 case NPC_JLARBORN: uiEntry = NPC_YOROS; break;
357 case NPC_YOROS: uiEntry = NPC_OLUF; break;
358 case NPC_OLUF: Reset(); return;
359 }
360
361 SummonGladiator(uiEntry);
362 }
363 };
364
366 {
367 return new npc_daegarnAI(creature);
368 }
369};
370
@ IN_MILLISECONDS
Definition Common.h:125
std::uint32_t uint32
Definition Define.h:77
#define OVERRIDE
Definition Define.h:60
std::uint64_t uint64
Definition Define.h:76
@ GOSSIP_ICON_CHAT
Definition GossipDef.h:46
@ TYPEID_PLAYER
Definition Object.h:55
@ TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT
Definition Object.h:71
@ QUEST_STATUS_INCOMPLETE
Definition QuestDef.h:89
#define CAST_AI(a, b)
@ GOSSIP_SENDER_MAIN
@ GOSSIP_ACTION_INFO_DEF
@ ALLIANCE
@ HORDE
@ REACT_AGGRESSIVE
Definition Unit.h:1158
bool UpdateVictim()
CreatureScript(const char *name)
static Player * GetPlayer(WorldObject const &, uint64 guid)
void GroupEventHappens(uint32 questId, WorldObject const *pEventObject)
void DoMeleeAttackIfReady()
Definition UnitAI.cpp:28
void DoCast(uint32 spellId)
Definition UnitAI.cpp:110
Definition Unit.h:1367
bool OnQuestAccept(Player *player, Creature *creature, Quest const *quest) OVERRIDE
CreatureAI * GetAI(Creature *creature) const OVERRIDE
bool OnQuestAccept(Player *player, Creature *creature, const Quest *quest) OVERRIDE
CreatureAI * GetAI(Creature *creature) const OVERRIDE
CreatureAI * GetAI(Creature *creature) const OVERRIDE
bool OnGossipHello(Player *player, Creature *creature) OVERRIDE
bool OnGossipSelect(Player *player, Creature *creature, uint32, uint32 action) OVERRIDE
Creature * me
bool HealthBelowPct(uint32 pct) const
ScriptedAI(Creature *creature)
void UpdateEscortAI(const uint32 diff) OVERRIDE
void WaypointReached(uint32 waypointId) OVERRIDE
void SummonedCreatureDies(Creature *summoned, Unit *) OVERRIDE
void SummonGladiator(uint32 uiEntry)
void JustSummoned(Creature *summon) OVERRIDE
bool GetAttack() const
void SetDespawnAtFar(bool despawn)
Player * GetPlayerForEscort()
void SetRun(bool on=true)
npc_escortAI(Creature *creature)
void Start(bool isActiveAttacker=true, bool run=false, uint64 playerGUID=0, Quest const *quest=NULL, bool instantRespawn=false, bool canLoopPath=false, bool resetWaypoints=true)
@ FACTION_ESCORTEE_A
@ FACTION_ESCORTEE_H
@ FACTION_ESCORTEE_A
@ FACTION_ESCORTEE_H
@ NPC_HANES_FIRE_TRIGGER
@ QUEST_TRAIL_OF_FIRE
@ SPELL_COSMETIC_LOW_POLY_FIRE
@ NPC_APOTHECARY_HANES
void AddSC_howling_fjord()
#define GOSSIP_LYANA_REPORT
@ GOSSIP_TEXTID_LYANA1
@ GOSSIP_TEXTID_RAZAEL2
@ GOSSIP_TEXTID_LYANA2
@ GOSSIP_TEXTID_RAZAEL1
@ QUEST_REPORTS_FROM_THE_FIELD
static float afCenter[]
@ QUEST_SNIFF_OUT_ENEMY
static float afSummon[]
#define GOSSIP_RAZAEL_REPORT
@ QUEST_DEFEAT_AT_RING
@ NPC_PRISONER_3
@ NPC_PRISONER_2
@ NPC_PRISONER_1