void UpdateEscortAI(const uint32 uiDiff) { if (uiPhase) { if (uiTimer <= uiDiff) { switch(uiPhase) { case 1: DoScriptText(SAY_BLASTMASTER_1, me); NextStep(1500, true); break; case 2: SetEscortPaused(false); NextStep(0, false, 0); break; case 3: DoScriptText(SAY_BLASTMASTER_2, me); SetEscortPaused(false); NextStep(0, false, 0); break; case 4: DoScriptText(SAY_BLASTMASTER_3, me); NextStep(3000, true); break; case 5: DoScriptText(SAY_BLASTMASTER_4, me); NextStep(3000, true); break; case 6: SetInFace(true); DoScriptText(SAY_BLASTMASTER_5, me); Summon(1); if (pInstance) if (GameObject* pGo = GameObject::GetGameObject((*me), pInstance->GetData64(DATA_GO_CAVE_IN_RIGHT))) pInstance->HandleGameObject(NULL, true, pGo); NextStep(3000, true); break; case 7: DoScriptText(SAY_BLASTMASTER_6, me); SetEscortPaused(false); NextStep(0, false, 0); break; case 8: me->HandleEmoteCommand(EMOTE_STATE_WORK); NextStep(25000, true); break; case 9: Summon(2); NextStep(0, false); break; case 10: Summon(4); NextStep(0, false); break; case 11: DoScriptText(SAY_BLASTMASTER_17, me); NextStep(5000, true); break; case 12: DoScriptText(SAY_BLASTMASTER_18, me); NextStep(5000, true); break; case 13: DoScriptText(SAY_BLASTMASTER_20, me); CaveDestruction(true); NextStep(8000, true); break; case 14: DoScriptText(SAY_BLASTMASTER_21, me); NextStep(8500, true); break; case 15: DoScriptText(SAY_BLASTMASTER_22, me); NextStep(2000, true); break; case 16: DoScriptText(SAY_BLASTMASTER_23, me); SetInFace(false); if (pInstance) if (GameObject* pGo = GameObject::GetGameObject((*me), pInstance->GetData64(DATA_GO_CAVE_IN_LEFT))) pInstance->HandleGameObject(NULL, true, pGo); NextStep(2000, true); break; case 17: SetEscortPaused(false); DoScriptText(SAY_BLASTMASTER_24, me); Summon(6); NextStep(0, false); break; case 18: Summon(7); NextStep(0, false); break; case 19: SetInFace(false); Summon(8); DoScriptText(SAY_BLASTMASTER_25, me); NextStep(0, false); break; case 20: DoScriptText(SAY_BLASTMASTER_27, me); NextStep(2000, true); break; case 21: Summon(9); NextStep(0, false); break; case 22: CaveDestruction(false); DoScriptText(SAY_BLASTMASTER_20, me); NextStep(0, false); break; } } else uiTimer -= uiDiff; } if (!UpdateVictim()) return; DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 uiDiff) { if (!m_creature->SelectHostileTarget() || !m_creature->getVictim()) { if (m_uiEquipTimer) { // decrease the cooldown in between equipment change phases if (m_uiEquipTimer > uiDiff) { m_uiEquipTimer -= uiDiff; return; } else m_uiEquipTimer = 0; } switch(m_uiPhase) { case PHASE_EQUIP_START: PhaseEquipStart(); break; case PHASE_EQUIP_PROCESS: PhaseEquipProcess(); break; case PHASE_EQUIP_END: PhaseEquipEnd(); break; } return; } // the normal combat phases switch(m_uiPhase) { case PHASE_1: { if (m_creature->GetHealthPercent() < 66.0f) { if (DoCastSpellIfCan(m_creature, SPELL_SMITE_STOMP) == CAST_OK) { DoScriptText(SAY_PHASE_2, m_creature); m_uiPhase = PHASE_EQUIP_START; m_uiEquipTimer = 2500; // will clear getVictim (m_attacking) m_creature->AttackStop(true); m_creature->RemoveAurasDueToSpell(SPELL_NIBLE_REFLEXES); } return; } break; } case PHASE_2: { if (m_creature->GetHealthPercent() < 33.0f) { if (DoCastSpellIfCan(m_creature, SPELL_SMITE_STOMP) == CAST_OK) { DoScriptText(SAY_PHASE_3, m_creature); m_uiPhase = PHASE_EQUIP_START; m_uiEquipTimer = 2500; m_creature->AttackStop(true); m_creature->RemoveAurasDueToSpell(SPELL_THRASH); } return; } break; } case PHASE_3: { if (m_uiSlamTimer < uiDiff) { if (DoCastSpellIfCan(m_creature->getVictim(), SPELL_SMITE_SLAM) == CAST_OK) m_uiSlamTimer = 11000; } else m_uiSlamTimer -= uiDiff; break; } } DoMeleeAttackIfReady(); }
void PetAI::UpdateAI(uint32 diff) { if (!me->isAlive() || !me->GetCharmInfo()) return; Unit* owner = me->GetCharmerOrOwner(); if (m_updateAlliesTimer <= diff) // UpdateAllies self set update timer UpdateAllies(); else m_updateAlliesTimer -= diff; if (me->getVictim() && me->getVictim()->isAlive()) { // is only necessary to stop casting, the pet must not exit combat if (me->getVictim()->HasBreakableByDamageCrowdControlAura(me)) { me->InterruptNonMeleeSpells(false); return; } if (_needToStop()) { sLog->outDebug(LOG_FILTER_GENERAL, "Pet AI stopped attacking [guid=%u]", me->GetGUIDLow()); _stopAttack(); return; } // Check before attacking to prevent pets from leaving stay position if (me->GetCharmInfo()->HasCommandState(COMMAND_STAY)) { if (me->GetCharmInfo()->IsCommandAttack() || (me->GetCharmInfo()->IsAtStay() && me->IsWithinMeleeRange(me->getVictim()))) DoMeleeAttackIfReady(); } else DoMeleeAttackIfReady(); } else { if (me->HasReactState(REACT_AGGRESSIVE) || me->GetCharmInfo()->IsAtStay()) { // Every update we need to check targets only in certain cases // Aggressive - Allow auto select if owner or pet don't have a target // Stay - Only pick from pet or owner targets / attackers so targets won't run by // while chasing our owner. Don't do auto select. // All other cases (ie: defensive) - Targets are assigned by AttackedBy(), OwnerAttackedBy(), OwnerAttacked(), etc. Unit* nextTarget = SelectNextTarget(me->HasReactState(REACT_AGGRESSIVE)); if (nextTarget) AttackStart(nextTarget); else HandleReturnMovement(); } else HandleReturnMovement(); } // Autocast (casted only in combat or persistent spells in any state) if (!me->HasUnitState(UNIT_STATE_CASTING)) { typedef std::vector<std::pair<Unit*, Spell*> > TargetSpellList; TargetSpellList targetSpellStore; for (uint8 i = 0; i < me->GetPetAutoSpellSize(); ++i) { uint32 spellID = me->GetPetAutoSpellOnPos(i); if (!spellID) continue; SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spellID); if (!spellInfo) continue; if (me->GetCharmInfo() && me->GetCharmInfo()->GetGlobalCooldownMgr().HasGlobalCooldown(spellInfo)) continue; if (spellInfo->IsPositive()) { if (spellInfo->CanBeUsedInCombat()) { // check spell cooldown if (me->HasSpellCooldown(spellInfo->Id)) continue; // Check if we're in combat or commanded to attack if (!me->isInCombat() && !me->GetCharmInfo()->IsCommandAttack()) continue; } Spell* spell = new Spell(me, spellInfo, TRIGGERED_NONE, 0); bool spellUsed = false; // Some spells can target enemy or friendly (DK Ghoul's Leap) // Check for enemy first (pet then owner) Unit* target = me->getAttackerForHelper(); if (!target && owner) target = owner->getAttackerForHelper(); if (target) { if (CanAttack(target) && spell->CanAutoCast(target)) { targetSpellStore.push_back(std::make_pair(target, spell)); spellUsed = true; } } if (spellInfo->HasEffect(SPELL_EFFECT_JUMP_DEST)) continue; // Pets must only jump to target // No enemy, check friendly if (!spellUsed) { for (std::set<uint64>::const_iterator tar = m_AllySet.begin(); tar != m_AllySet.end(); ++tar) { Unit* ally = ObjectAccessor::GetUnit(*me, *tar); //only buff targets that are in combat, unless the spell can only be cast while out of combat if (!ally) continue; if (spell->CanAutoCast(ally)) { targetSpellStore.push_back(std::make_pair(ally, spell)); spellUsed = true; break; } } } // No valid targets at all if (!spellUsed) delete spell; } else if (me->getVictim() && CanAttack(me->getVictim()) && spellInfo->CanBeUsedInCombat()) { Spell* spell = new Spell(me, spellInfo, TRIGGERED_NONE, 0); if (spell->CanAutoCast(me->getVictim())) targetSpellStore.push_back(std::make_pair(me->getVictim(), spell)); else delete spell; } } //found units to cast on to if (!targetSpellStore.empty()) { uint32 index = urand(0, targetSpellStore.size() - 1); Spell* spell = targetSpellStore[index].second; Unit* target = targetSpellStore[index].first; targetSpellStore.erase(targetSpellStore.begin() + index); SpellCastTargets targets; targets.SetUnitTarget(target); if (!me->HasInArc(M_PI, target)) { me->SetInFront(target); if (target && target->GetTypeId() == TYPEID_PLAYER) me->SendUpdateToPlayer(target->ToPlayer()); if (owner && owner->GetTypeId() == TYPEID_PLAYER) me->SendUpdateToPlayer(owner->ToPlayer()); } me->AddCreatureSpellCooldown(spell->m_spellInfo->Id); spell->prepare(&targets); } // deleted cached Spell objects for (TargetSpellList::const_iterator itr = targetSpellStore.begin(); itr != targetSpellStore.end(); ++itr) delete itr->second; } // Update speed as needed to prevent dropping too far behind and despawning me->UpdateSpeed(MOVE_RUN, true); me->UpdateSpeed(MOVE_WALK, true); me->UpdateSpeed(MOVE_FLIGHT, true); }
void UpdateAI(uint32 diff) { m_events.Update(diff); while (uint32 eventId = m_events.ExecuteEvent()) { switch (eventId) { case 1: { // if (GameObject* door = ObjectAccessor::GetGameObject(*me, m_instance->GetData64(DATA_FACTORY_DOOR))) // door->UseDoorOrButton(); m_events.ScheduleEvent(1, 10000); break; } } } if (!UpdateVictim()) return; if (phase == 1) { if (SpellTimer <= diff) { switch (urand(0, 1)) { case 0: if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(me, SPELL_FIST_OF_FLAME); Talk(SAY_FISTS_OF_FLAME); break; case 1: if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(me, SPELL_FIST_OF_FROST); Talk(SAY_FISTS_OF_FROST); break; } SpellTimer = urand(10 * IN_MILLISECONDS, 25 * IN_MILLISECONDS); } else SpellTimer -= diff; if (HealthBelowPct(50)) { phase = 2; DoCast(me, SPELL_ARCANE_POWER); Talk(SAY_ARCANE_POWER); } DoMeleeAttackIfReady(); } else { if (SpellTimer <= diff) { DoCast(me, urand(1, 2) == 1 ? SPELL_FROST_BLOSSOM : SPELL_FIRE_BLOSSOM); SpellTimer = urand(10 * IN_MILLISECONDS, 25 * IN_MILLISECONDS); } else SpellTimer -= diff; } if (PhaseChangeTimer <= diff && Phase == PHASE_NORMAL) { if (PhaseChangeTimer <= diff) { me->SetReactState(REACT_AGGRESSIVE); elemental_fists = 20000; blinkTimer = 12000; Phase = PHASE_NORMAL; } else PhaseChangeTimer -= diff; if (elemental_fists <= diff && Phase == PHASE_NORMAL) { if (elemental_fists <= diff) { DoCast(me, elemental_fists); me->MonsterYell(SAY_FLAME, LANG_UNIVERSAL, NULL); elemental_fists = 20000; } else elemental_fists -= diff; } if (blinkTimer <= diff && Phase == PHASE_NORMAL) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 1, 10.0f, true)) DoCast(me, SPELL_BLINK); blinkTimer = 12000; } else blinkTimer -= diff; DoMeleeAttackIfReady(); } }
void UpdateAI(const uint32 diff) { if (TalkTimer) { if (!TalkSequence) { me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE + UNIT_FLAG_NOT_SELECTABLE); me->InterruptNonMeleeSpells(true); me->RemoveAllAuras(); me->DeleteThreatList(); me->CombatStop(); ++TalkSequence; } if (TalkTimer <= diff) { if (isFriendly) GoodEnding(); else BadEnding(); ++TalkSequence; } else TalkTimer -= diff; } else { if (bJustReset) { if (ResetTimer <= diff) { me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE|UNIT_FLAG_NOT_SELECTABLE); me->SetDisableGravity(false); me->SetVisible(true); me->SetStandState(UNIT_STAND_STATE_SLEEP); ResetTimer = 10000; bJustReset = false; } else ResetTimer -= diff; return; } if (!UpdateVictim()) return; if (CheckTimer <= diff) { if (me->GetDistance(CENTER_X, CENTER_Y, DRAGON_REALM_Z) >= 75) { me->AI()->EnterEvadeMode(); return; } if (HealthBelowPct(10) && !isEnraged) { if (Creature* Sath = Unit::GetCreature(*me, SathGUID)) Sath->AI()->DoAction(DO_ENRAGE); DoAction(DO_ENRAGE); } if (!isBanished && HealthBelowPct(1)) { if (Creature* Sath = Unit::GetCreature(*me, SathGUID)) { if (Sath->HasAura(SPELL_BANISH)) { Sath->DealDamage(Sath, Sath->GetHealth()); return; } else DoAction(DO_BANISH); } else { sLog->outError(LOG_FILTER_TSCR, "Didn't find Shathrowar. Kalecgos event reseted."); EnterEvadeMode(); return; } } CheckTimer = 1000; } else CheckTimer -= diff; if (ArcaneBuffetTimer <= diff) { DoCastAOE(SPELL_ARCANE_BUFFET); ArcaneBuffetTimer = 8000; } else ArcaneBuffetTimer -= diff; if (FrostBreathTimer <= diff) { DoCastAOE(SPELL_FROST_BREATH); FrostBreathTimer = 15000; } else FrostBreathTimer -= diff; if (TailLashTimer <= diff) { DoCastAOE(SPELL_TAIL_LASH); TailLashTimer = 15000; } else TailLashTimer -= diff; if (WildMagicTimer <= diff) { DoCastAOE(WildMagic[rand()%6]); WildMagicTimer = 20000; } else WildMagicTimer -= diff; if (SpectralBlastTimer <= diff) { ThreatContainer::StorageType const& m_threatlist = me->getThreatManager().getThreatList(); std::list<Unit*> targetList; for (ThreatContainer::StorageType::const_iterator itr = m_threatlist.begin(); itr!= m_threatlist.end(); ++itr) { Unit* target = (*itr)->getTarget(); if (target && target->GetTypeId() == TYPEID_PLAYER && target->GetGUID() != me->getVictim()->GetGUID() && target->GetPositionZ() > me->GetPositionZ() - 5 && !target->HasAura(AURA_SPECTRAL_EXHAUSTION)) { targetList.push_back(target); } } if (targetList.empty()) { SpectralBlastTimer = 1000; return; } std::list<Unit*>::const_iterator i = targetList.begin(); advance(i, rand()%targetList.size()); if ((*i)) { (*i)->CastSpell((*i), SPELL_SPECTRAL_BLAST, true); SpectralBlastTimer = 20000+rand()%5000; } else SpectralBlastTimer = 1000; } else SpectralBlastTimer -= diff; DoMeleeAttackIfReady(); } }
void UpdateAI(uint32 diff) { EnterEvadeIfOutOfCombatArea(); if (!UpdateVictim()) return; events.Update(diff); if (me->HasUnitState(UNIT_STATE_CASTING)) return; switch (events.ExecuteEvent()) { case EVENT_SPELL_SHOCK_BLAST: me->CastSpell(me->GetVictim(), SPELL_SHOCK_BLAST, false); events.ScheduleEvent(EVENT_SPELL_SHOCK_BLAST, urand(10000, 20000)); break; case EVENT_SPELL_STATIC_CHARGE: if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 40.0f)) me->CastSpell(target, SPELL_STATIC_CHARGE, false); events.ScheduleEvent(EVENT_SPELL_STATIC_CHARGE, 20000); break; case EVENT_SPELL_ENTANGLE: me->CastSpell(me, SPELL_ENTANGLE, false); events.ScheduleEvent(EVENT_SPELL_ENTANGLE, 30000); break; case EVENT_CHECK_HEALTH: if (me->HealthBelowPct(71)) { Talk(SAY_PHASE2); me->SetReactState(REACT_PASSIVE); me->GetMotionMaster()->MovePoint(POINT_HOME, me->GetHomePosition().GetPositionX(), me->GetHomePosition().GetPositionY(), me->GetHomePosition().GetPositionZ(), true, true); break; } events.ScheduleEvent(EVENT_CHECK_HEALTH, 1000); break; case EVENT_SPELL_FORKED_LIGHTNING: if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 60.0f)) me->CastSpell(target, SPELL_FORKED_LIGHTNING, false); events.ScheduleEvent(EVENT_SPELL_FORKED_LIGHTNING, urand(2500, 5000)); break; case EVENT_SUMMON_A: me->CastSpell(me, SPELL_SUMMON_ENCHANTED_ELEMENTAL, true); events.ScheduleEvent(EVENT_SUMMON_A, 2500); break; case EVENT_SUMMON_B: me->CastSpell(me, SPELL_SUMMON_COILFANG_ELITE, true); events.ScheduleEvent(EVENT_SUMMON_B, 45000); break; case EVENT_SUMMON_C: me->CastSpell(me, SPELL_SUMMON_COILFANG_STRIDER, true); events.ScheduleEvent(EVENT_SUMMON_C, 60000); break; case EVENT_SUMMON_D: me->CastSpell(me, SPELL_SUMMON_TAINTED_ELEMENTAL, true); events.ScheduleEvent(EVENT_SUMMON_D, 50000); break; case EVENT_CHECK_HEALTH2: if (!me->HasAura(SPELL_MAGIC_BARRIER)) { Talk(SAY_PHASE3); me->SetReactState(REACT_AGGRESSIVE); me->GetMotionMaster()->MoveChase(me->GetVictim()); events.Reset(); events.ScheduleEvent(EVENT_SPELL_SHOCK_BLAST, 10000); events.ScheduleEvent(EVENT_SPELL_STATIC_CHARGE, 15000); events.ScheduleEvent(EVENT_SPELL_ENTANGLE, 20000); events.ScheduleEvent(EVENT_SUMMON_SPOREBAT, 5000); break; } events.ScheduleEvent(EVENT_CHECK_HEALTH2, 1000); break; case EVENT_SUMMON_SPOREBAT: me->CastSpell(me, SPELL_SUMMON_TOXIC_SPOREBAT, true); events.ScheduleEvent(EVENT_SUMMON_SPOREBAT, 20000 - 1000*std::min(count++, 16)); break; } if (me->GetReactState() != REACT_AGGRESSIVE || !me->isAttackReady()) return; if (!me->IsWithinMeleeRange(me->GetVictim())) { me->resetAttackTimer(); me->SetSheath(SHEATH_STATE_RANGED); me->CastSpell(me->GetVictim(), roll_chance_i(33) ? SPELL_MULTI_SHOT : SPELL_SHOOT, false); if (roll_chance_i(15)) Talk(SAY_BOWSHOT); } else { me->SetSheath(SHEATH_STATE_MELEE); DoMeleeAttackIfReady(); } }
void UpdateAI(const uint32 diff) { if (!UpdateVictim()) return; //BrainWashTotem_Timer if (BrainWashTotem_Timer <= diff) { DoCast(me, SPELL_BRAINWASHTOTEM); BrainWashTotem_Timer = 18000 + rand()%8000; } else BrainWashTotem_Timer -= diff; //HealingWard_Timer if (HealingWard_Timer <= diff) { //DoCast(me, SPELL_POWERFULLHEALINGWARD); me->SummonCreature(14987, me->GetPositionX()+3, me->GetPositionY()-2, me->GetPositionZ(), 0, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,30000); HealingWard_Timer = 14000 + rand()%6000; } else HealingWard_Timer -= diff; //Hex_Timer if (Hex_Timer <= diff) { DoCast(me->getVictim(), SPELL_HEX); if (DoGetThreat(me->getVictim())) DoModifyThreatPercent(me->getVictim(),-80); Hex_Timer = 12000 + rand()%8000; } else Hex_Timer -= diff; //Casting the delusion curse with a shade. So shade will attack the same target with the curse. if (Delusions_Timer <= diff) { if (Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0)) { DoCast(pTarget, SPELL_DELUSIONSOFJINDO); Creature *Shade = me->SummonCreature(14986, pTarget->GetPositionX(), pTarget->GetPositionY(), pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Shade) Shade->AI()->AttackStart(pTarget); } Delusions_Timer = 4000 + rand()%8000; } else Delusions_Timer -= diff; //Teleporting a random gamer and spawning 9 skeletons that will attack this gamer if (Teleport_Timer <= diff) { Unit *pTarget = NULL; pTarget = SelectUnit(SELECT_TARGET_RANDOM,0); if (pTarget && pTarget->GetTypeId() == TYPEID_PLAYER) { DoTeleportPlayer(pTarget, -11583.7783f,-1249.4278f,77.5471f,4.745f); if (DoGetThreat(me->getVictim())) DoModifyThreatPercent(pTarget,-100); Creature *Skeletons; Skeletons = me->SummonCreature(14826, pTarget->GetPositionX()+2, pTarget->GetPositionY(), pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Skeletons) Skeletons->AI()->AttackStart(pTarget); Skeletons = me->SummonCreature(14826, pTarget->GetPositionX()-2, pTarget->GetPositionY(), pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Skeletons) Skeletons->AI()->AttackStart(pTarget); Skeletons = me->SummonCreature(14826, pTarget->GetPositionX()+4, pTarget->GetPositionY(), pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Skeletons) Skeletons->AI()->AttackStart(pTarget); Skeletons = me->SummonCreature(14826, pTarget->GetPositionX()-4, pTarget->GetPositionY(), pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Skeletons) Skeletons->AI()->AttackStart(pTarget); Skeletons = me->SummonCreature(14826, pTarget->GetPositionX(), pTarget->GetPositionY()+2, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Skeletons) Skeletons->AI()->AttackStart(pTarget); Skeletons = me->SummonCreature(14826, pTarget->GetPositionX(), pTarget->GetPositionY()-2, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Skeletons) Skeletons->AI()->AttackStart(pTarget); Skeletons = me->SummonCreature(14826, pTarget->GetPositionX(), pTarget->GetPositionY()+4, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Skeletons) Skeletons->AI()->AttackStart(pTarget); Skeletons = me->SummonCreature(14826, pTarget->GetPositionX(), pTarget->GetPositionY()-4, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Skeletons) Skeletons->AI()->AttackStart(pTarget); Skeletons = me->SummonCreature(14826, pTarget->GetPositionX()+3, pTarget->GetPositionY(), pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000); if (Skeletons) Skeletons->AI()->AttackStart(pTarget); } Teleport_Timer = 15000 + rand()%8000; } else Teleport_Timer -= diff; DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 diff) { //Return since we have no target if (!UpdateVictim()) return; switch (Phase) { case SKELETAL: if (uiCurseOfLifeTimer < diff) { if (Unit* pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(pTarget, HEROIC(SPELL_CURSE_OF_LIFE, H_SPELL_CURSE_OF_LIFE)); uiCurseOfLifeTimer = urand(10000,15000); } else uiCurseOfLifeTimer -= diff; if (uiShadowVolleyTimer < diff) { DoCastVictim(HEROIC(SPELL_SHADOW_VOLLEY,H_SPELL_SHADOW_VOLLEY)); uiShadowVolleyTimer = urand(8000,10000); } else uiShadowVolleyTimer -= diff; if (uiRainOfFireTimer < diff) { DoCastAOE(HEROIC(SPELL_RAIN_OF_FIRE,H_SPELL_RAIN_OF_FIRE)); uiRainOfFireTimer = urand(14000,18000); } else uiRainOfFireTimer -= diff; if (uiPhaseTimer < diff) { DoCast(SPELL_DECAY_FLESH); Phase = GOING_FLESH; uiPhaseTimer = 6000; } else uiPhaseTimer -= diff; DoMeleeAttackIfReady(); break; case GOING_FLESH: if (uiPhaseTimer < diff) { DoScriptText(RAND(SAY_FLESH_1,SAY_FLESH_2),m_creature); m_creature->SetDisplayId(MODEL_FLESH); std::list<HostilReference*>& threatlist = m_creature->getThreatManager().getThreatList(); for (std::list<HostilReference*>::iterator itr = threatlist.begin(); itr != threatlist.end(); ++itr) { Unit *pTemp = Unit::GetUnit((*m_creature),(*itr)->getUnitGuid()); if (pTemp && pTemp->GetTypeId() == TYPEID_PLAYER) { m_creature->AddAura(SPELL_GIFT_OF_THARON_JA,pTemp); pTemp->SetDisplayId(MODEL_SKELETON); } } uiPhaseTimer = 20000; uiLightningBreathTimer = urand(3000,4000); uiEyeBeamTimer = urand(4000,8000); uiPoisonCloudTimer = urand(6000,7000); Phase = FLESH; } else uiPhaseTimer -= diff; break; case FLESH: if (uiLightningBreathTimer < diff) { if (Unit* pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(pTarget, HEROIC(SPELL_LIGHTNING_BREATH, H_SPELL_LIGHTNING_BREATH)); uiLightningBreathTimer = urand(6000,7000); } else uiLightningBreathTimer -= diff; if (uiEyeBeamTimer < diff) { if (Unit* pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(pTarget, HEROIC(SPELL_EYE_BEAM, H_SPELL_EYE_BEAM)); uiEyeBeamTimer = urand(4000,6000); } else uiEyeBeamTimer -= diff; if (uiPoisonCloudTimer < diff) { DoCastAOE(HEROIC(SPELL_POISON_CLOUD,H_SPELL_POISON_CLOUD)); uiPoisonCloudTimer = urand(10000,12000); } else uiPoisonCloudTimer -= diff; if (uiPhaseTimer < diff) { DoCast(SPELL_RETURN_FLESH); Phase = GOING_SKELETAL; uiPhaseTimer = 6000; } else uiPhaseTimer -= diff; DoMeleeAttackIfReady(); break; case GOING_SKELETAL: if (uiPhaseTimer < diff) { DoScriptText(RAND(SAY_SKELETON_1,SAY_SKELETON_2), m_creature); m_creature->DeMorph(); Phase = SKELETAL; uiPhaseTimer = 20000; uiCurseOfLifeTimer = 1000; uiRainOfFireTimer = urand(14000,18000); uiShadowVolleyTimer = urand(8000,10000); std::list<HostilReference*>& threatlist = m_creature->getThreatManager().getThreatList(); for (std::list<HostilReference*>::iterator itr = threatlist.begin(); itr != threatlist.end(); ++itr) { Unit *pTemp = Unit::GetUnit((*m_creature),(*itr)->getUnitGuid()); if (pTemp && pTemp->GetTypeId() == TYPEID_PLAYER) { if (pTemp->HasAura(SPELL_GIFT_OF_THARON_JA)) pTemp->RemoveAura(SPELL_GIFT_OF_THARON_JA); pTemp->DeMorph(); } } } else uiPhaseTimer -= diff; break; } }
void UpdateAI(const uint32 diff) { if (!UpdateVictim()) return; if (me->getVictim() && me->isAlive()) { if (!CombatStart) { //At combat Start Mandokir is mounted so we must unmount it first me->Dismount(); //And summon his raptor me->SummonCreature(14988, me->getVictim()->GetPositionX(), me->getVictim()->GetPositionY(), me->getVictim()->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 35000); CombatStart = true; } if (Watch_Timer <= diff) //Every 20 Sec Mandokir will check this { if (WatchTarget) //If someone is watched and If the Position of the watched target is different from the one stored, or are attacking, mandokir will charge him { Unit* unit = Unit::GetUnit(*me, WatchTarget); if (unit && ( targetX != unit->GetPositionX() || targetY != unit->GetPositionY() || targetZ != unit->GetPositionZ() || unit->isInCombat())) { if (me->IsWithinMeleeRange(unit)) { DoCast(unit, 24316); } else { DoCast(unit, SPELL_CHARGE); //me->SendMonsterMove(unit->GetPositionX(), unit->GetPositionY(), unit->GetPositionZ(), 0, true, 1); AttackStart(unit); } } } someWatched = false; Watch_Timer = 20000; } else Watch_Timer -= diff; if ((Watch_Timer < 8000) && !someWatched) //8 sec(cast time + expire time) before the check for the watch effect mandokir will cast watch debuff on a random target { if (Unit* p = SelectTarget(SELECT_TARGET_RANDOM, 0)) { DoScriptText(SAY_WATCH, me, p); DoCast(p, SPELL_WATCH); WatchTarget = p->GetGUID(); someWatched = true; endWatch = true; } } if ((Watch_Timer < 1000) && endWatch) //1 sec before the debuf expire, store the target position { Unit* unit = Unit::GetUnit(*me, WatchTarget); if (unit) { targetX = unit->GetPositionX(); targetY = unit->GetPositionY(); targetZ = unit->GetPositionZ(); } endWatch = false; } if (!someWatched) { //Cleave if (Cleave_Timer <= diff) { DoCast(me->getVictim(), SPELL_CLEAVE); Cleave_Timer = 7000; } else Cleave_Timer -= diff; //Whirlwind if (Whirlwind_Timer <= diff) { DoCast(me, SPELL_WHIRLWIND); Whirlwind_Timer = 18000; } else Whirlwind_Timer -= diff; //If more then 3 targets in melee range mandokir will cast fear if (Fear_Timer <= diff) { TargetInRange = 0; std::list<HostileReference*>::const_iterator i = me->getThreatManager().getThreatList().begin(); for (; i != me->getThreatManager().getThreatList().end(); ++i) { Unit* unit = Unit::GetUnit(*me, (*i)->getUnitGuid()); if (unit && me->IsWithinMeleeRange(unit)) ++TargetInRange; } if (TargetInRange > 3) DoCast(me->getVictim(), SPELL_FEAR); Fear_Timer = 4000; } else Fear_Timer -=diff; //Mortal Strike if target below 50% hp if (me->getVictim() && me->getVictim()->HealthBelowPct(50)) { if (MortalStrike_Timer <= diff) { DoCast(me->getVictim(), SPELL_MORTAL_STRIKE); MortalStrike_Timer = 15000; } else MortalStrike_Timer -= diff; } } //Checking if Ohgan is dead. If yes Mandokir will enrage. if (Check_Timer <= diff) { if (instance) { if (instance->GetData(DATA_OHGAN) == DONE) { if (!RaptorDead) { DoCast(me, SPELL_ENRAGE); RaptorDead = true; } } } Check_Timer = 1000; } else Check_Timer -= diff; DoMeleeAttackIfReady(); } }
void UpdateAI(const uint32 diff) { if (!me->isInCombat()) // sometimes isincombat but !incombat, faction bug? return; if (Berserk_Timer <= diff) { me->CastSpell(me, SPELL_BERSERK, true); Berserk_Timer = 60000; } else Berserk_Timer -= diff; if (ForceMove) { if (ForceTimer <= diff) { me->GetMotionMaster()->MovePoint(0, waypoint[cur_wp][0], waypoint[cur_wp][1], waypoint[cur_wp][2]); ForceTimer = 5000; } else ForceTimer -= diff; } if (WaitEvent) { if (WaitTimer) { if (WaitTimer <= diff) { if (AfterMoving) { me->GetMotionMaster()->MoveIdle(); AfterMoving = false; } switch (WaitEvent) { case WE_PLATFORM: Platforms_Move_Timer = 30000+rand()%5000; break; case WE_QUILL: me->CastSpell(me, SPELL_FLAME_QUILLS, true); Platforms_Move_Timer = 1; WaitTimer = 10000; WaitEvent = WE_DUMMY; return; case WE_DIE: ForceMove = false; me->SetUInt32Value(UNIT_FIELD_BYTES_1, UNIT_STAND_STATE_DEAD); WaitTimer = 5000; WaitEvent = WE_REVIVE; return; case WE_REVIVE: me->SetUInt32Value(UNIT_FIELD_BYTES_1, UNIT_STAND_STATE_STAND); me->SetHealth(me->GetMaxHealth()); me->SetSpeed(MOVE_RUN, DefaultMoveSpeedRate); me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE); DoZoneInCombat(); me->CastSpell(me, SPELL_REBIRTH, true); pInstance->SetData(DATA_ALAREVENT, SPECIAL); // proszeq MeltArmor_Timer = 60000; Charge_Timer = 7000; DiveBomb_Timer = 40000+rand()%5000; FlamePatch_Timer = 30000; Phase1 = false; break; case WE_METEOR: me->ApplySpellImmune(0, IMMUNITY_SCHOOL, SPELL_SCHOOL_MASK_FIRE, false); me->CastSpell(me, SPELL_DIVE_BOMB_VISUAL, false); WaitEvent = WE_DIVE; WaitTimer = 4000; return; case WE_DIVE: if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0)) { me->RemoveAurasDueToSpell(SPELL_DIVE_BOMB_VISUAL); me->CastSpell(pTarget, SPELL_DIVE_BOMB, true); float dist = me->GetDistance(pTarget->GetPositionX(), pTarget->GetPositionY(), pTarget->GetPositionZ()); if (dist < 5.0f) dist = 5.0f; WaitTimer = 1000 + floor(dist / 80 * 1000.0f); me->GetMap()->CreatureRelocation(me, pTarget->GetPositionX(), pTarget->GetPositionY(), pTarget->GetPositionZ(),0.0f); me->StopMoving(); WaitEvent = WE_LAND; } else { EnterEvadeMode(); return; } case WE_LAND: WaitEvent = WE_SUMMON; WaitTimer = 4000; for (uint8 i = 0; i < 2; ++i) DoSpawnCreature(CREATURE_EMBER_OF_ALAR, 0, 0, 0, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 5000); return; case WE_SUMMON: //for (uint8 i = 0; i < 2; ++i) //DoSpawnCreature(CREATURE_EMBER_OF_ALAR, 0, 0, 0, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 5000); me->SetFloatValue(UNIT_FIELD_BOUNDINGRADIUS, 10); me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); me->SetDisplayId(me->GetNativeDisplayId()); me->CastSpell(me, SPELL_REBIRTH_2, true); break; case WE_DUMMY: default: break; } WaitEvent = WE_NONE; WaitTimer = 0; } else WaitTimer -= diff; } return; } if (Phase1) { if (me->getThreatManager().getThreatList().empty()) { EnterEvadeMode(); return; } if (Platforms_Move_Timer <= diff) { if (cur_wp == 4) { cur_wp = 0; WaitEvent = WE_PLATFORM; } else { if (rand()%5) // next platform { DoSpawnCreature(CREATURE_EMBER_OF_ALAR, 0, 0, 0, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 5000); if (cur_wp == 3) cur_wp = 0; else cur_wp++; WaitEvent = WE_PLATFORM; } else // flame quill { cur_wp = 4; WaitEvent = WE_QUILL; } } ForceMove = true; ForceTimer = 5000; me->GetMotionMaster()->MovePoint(0, waypoint[cur_wp][0], waypoint[cur_wp][1], waypoint[cur_wp][2]); WaitTimer = 0; return; } else Platforms_Move_Timer -= diff; } else { if (Charge_Timer <= diff) { Unit* pTarget= SelectTarget(SELECT_TARGET_RANDOM, 1, 100, true); if (pTarget) DoCast(pTarget, SPELL_CHARGE); Charge_Timer = 30000+rand()%20000; } else Charge_Timer -= diff; if (MeltArmor_Timer <= diff) { DoCast(me->getVictim(), SPELL_MELT_ARMOR); MeltArmor_Timer = 60000; } else MeltArmor_Timer -= diff; if (DiveBomb_Timer <= diff) { me->AttackStop(); me->GetMotionMaster()->MovePoint(6, waypoint[4][0], waypoint[4][1], waypoint[4][2]); me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); me->SetFloatValue(UNIT_FIELD_BOUNDINGRADIUS, 50); WaitEvent = WE_METEOR; WaitTimer = 0; DiveBomb_Timer = 30000+rand()%30000; return; } else DiveBomb_Timer -= diff; if (FlamePatch_Timer <= diff) { if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0)) { Creature* Summoned = me->SummonCreature(CREATURE_FLAME_PATCH_ALAR, pTarget->GetPositionX(), pTarget->GetPositionY(), pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN, 120000); if (Summoned) { Summoned->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); Summoned->SetFloatValue(OBJECT_FIELD_SCALE_X, Summoned->GetFloatValue(OBJECT_FIELD_SCALE_X)*2.5f); Summoned->SetDisplayId(11686); Summoned->setFaction(me->getFaction()); Summoned->SetLevel(me->getLevel()); Summoned->CastSpell(Summoned, SPELL_FLAME_PATCH, false); } } FlamePatch_Timer = 30000+rand()%20000; //30 sec to cooldown } else FlamePatch_Timer -= diff; } DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 uiDiff) { if (m_bShades && m_uiShades_Timer < uiDiff) { //Become unbanished again m_creature->setFaction(14); m_creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); m_bShades = false; } else if (m_bShades) { m_uiShades_Timer -= uiDiff; //Do nothing while banished return; } //Return since we have no target if (!m_creature->SelectHostileTarget() || !m_creature->getVictim()) return; //Sleep_Timer if (m_uiSleep_Timer < uiDiff) { if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0)) DoCast(pTarget, SPELL_SLEEP); m_uiSleep_Timer = urand(8000, 15000); } else m_uiSleep_Timer -= uiDiff; //NoxiousBreath_Timer if (m_uiNoxiousBreath_Timer < uiDiff) { DoCast(m_creature->getVictim(), SPELL_NOXIOUSBREATH); m_uiNoxiousBreath_Timer = urand(14000, 20000); } else m_uiNoxiousBreath_Timer -= uiDiff; //Tailsweep every 2 seconds if (m_uiTailSweep_Timer < uiDiff) { DoCast(m_creature, SPELL_TAILSWEEP); m_uiTailSweep_Timer = 2000; } else m_uiTailSweep_Timer -= uiDiff; //MarkOfNature_Timer //if (m_uiMarkOfNature_Timer < uiDiff) //{ // DoCast(m_creature->getVictim(), SPELL_MARKOFNATURE); // m_uiMarkOfNature_Timer = 45000; //} //else //m_uiMarkOfNature_Timer -= uiDiff; //ArcaneBlast_Timer if (m_uiArcaneBlast_Timer < uiDiff) { DoCast(m_creature->getVictim(), SPELL_ARCANEBLAST); m_uiArcaneBlast_Timer = urand(7000, 12000); } else m_uiArcaneBlast_Timer -= uiDiff; //BellowingRoar_Timer if (m_uiBellowingRoar_Timer < uiDiff) { DoCast(m_creature->getVictim(), SPELL_BELLOWINGROAR); m_uiBellowingRoar_Timer = urand(20000, 30000); } else m_uiBellowingRoar_Timer -= uiDiff; //Summon 3 Shades at 75%, 50% and 25% (if bShades is true we already left in line 117, no need to check here again) if (!m_bShades && (m_creature->GetHealth()*100 / m_creature->GetMaxHealth()) <= (100-(25*m_uiShadesSummoned))) { if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0)) { //Inturrupt any spell casting m_creature->InterruptNonMeleeSpells(false); //horrible workaround, need to fix m_creature->setFaction(35); m_creature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); DoScriptText(SAY_SUMMONSHADE, m_creature); int iSize = sizeof(m_auiSpellSummonShade) / sizeof(uint32); for(int i = 0; i < iSize; ++i) m_creature->CastSpell(pTarget, m_auiSpellSummonShade[i], true); ++m_uiShadesSummoned; // prevent casting twice at same health m_bShades = true; } m_uiShades_Timer = 60000; } DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 uiDiff) { if (!pEntered) { if (m_uiFlyPoint_Timer <= uiDiff) { switch (point_id) { case 21: float x,y,z; m_creature->GetClosePoint(x, y, z, m_creature->GetObjectBoundingRadius(), 15.0f, 0.0f); if (Creature* pTemp = m_creature->SummonCreature(NPC_HEAD, x, y, z, 0, TEMPSUMMON_CORPSE_DESPAWN, 0)) HeadGUID = pTemp->GetGUID(); else { error_log("Headless Horsemann could't summon his head so abording the event"); m_creature->ForcedDespawn(); } pEntered = true; break; default: m_creature->SendMonsterMove(FlightPoint[point_id][0], FlightPoint[point_id][1], FlightPoint[point_id][2], SPLINETYPE_NORMAL, SPLINEFLAG_WALKMODE,999); ++point_id; break; } m_uiFlyPoint_Timer = 1000; }else m_uiFlyPoint_Timer -= uiDiff; } if (!m_pInstance) return; Creature* pHead = m_creature->GetMap()->GetCreature(HeadGUID); if (pEntered && !pHead) { error_log("Debug: Headless Horseman aggroed but no Head of Horseman found so abording!"); m_creature->ForcedDespawn(); } switch (m_pInstance->GetData(TYPE_HALLOWSEND_EVENT)) { //Phase 1a case 0: if (!m_creature->HasAura(SPELL_HEAD)) DoCast(m_creature,SPELL_HEAD,false); if (((m_creature->GetHealth()*100) / (m_creature->GetMaxHealth())) <= 1) m_pInstance->SetData(TYPE_HALLOWSEND_EVENT,1); if (m_uiCleave_Timer <= uiDiff) { m_creature->CastSpell(m_creature->getVictim(),SPELL_CLEAVE_PROC,false); m_uiCleave_Timer = 5000; }else m_uiCleave_Timer -= uiDiff; DoMeleeAttackIfReady(); break; //Phase 1b case 1: if (m_creature->HasAura(SPELL_HEAD)) { m_creature->RemoveAurasDueToSpell(SPELL_HEAD); m_creature->CastSpell(pHead,SPELL_SEND_HEAD,false); } ApplyRegenAuras(); if (Unit* pTarget = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM, 0)) if (pHead->AI()) pHead->AI()->AttackStart(pTarget); if ((pHead->GetHealth()*100) / (pHead->GetMaxHealth()) <= 66) { RemoveRegenAuras(); if ((m_creature->GetHealth()*100) / (m_creature->GetMaxHealth()) < 100) m_pInstance->SetData(TYPE_HALLOWSEND_EVENT,2); else m_pInstance->SetData(TYPE_HALLOWSEND_EVENT,0); pHead->SetHealth(pHead->GetMaxHealth()*0.7); } break; //Phase 2a case 2: if (((m_creature->GetHealth()*100) / (m_creature->GetMaxHealth())) <= 1) m_pInstance->SetData(TYPE_HALLOWSEND_EVENT,3); if (m_uiConflageration_Timer <= uiDiff) { if (Unit* pTarget = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM, 0)) { DoScriptText(SAY_CONFLAGRATION,m_creature); pTarget->CastSpell(pTarget,SPELL_CONFLAGRATION,false); } m_uiConflageration_Timer = 15000; }else m_uiConflageration_Timer -= uiDiff; DoMeleeAttackIfReady(); break; //Phase 2b case 3: if (m_creature->HasAura(SPELL_HEAD)) { m_creature->RemoveAurasDueToSpell(SPELL_HEAD); m_creature->CastSpell(pHead,SPELL_SEND_HEAD,false); } ApplyRegenAuras(); if (Unit* pTarget = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM, 0)) if (pHead->AI()) pHead->AI()->AttackStart(pTarget); if ((pHead->GetHealth()*100) / (pHead->GetMaxHealth()) <= 33) { RemoveRegenAuras(); if ((m_creature->GetHealth()*100) / (m_creature->GetMaxHealth()) < 100) m_pInstance->SetData(TYPE_HALLOWSEND_EVENT,4); else m_pInstance->SetData(TYPE_HALLOWSEND_EVENT,2); pHead->SetHealth(pHead->GetMaxHealth()*0.4); } break; //Phase 3a case 4: if ((m_creature->GetHealth()*100) / (m_creature->GetMaxHealth()) <= 1) { if (Unit* pTarget = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM, 0)) if (pHead->AI()) pHead->AI()->AttackStart(pTarget); m_pInstance->SetData(TYPE_HALLOWSEND_EVENT,5); } if (m_uiPumpkinSprout_Timer <= uiDiff) { if (Unit* pTarget = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM, 0)) { DoScriptText(SAY_SPROUTING_PUMPKINS,m_creature); m_creature->CastSpell(pTarget,SPELL_SUMMON_PUMPKIN,false); } m_uiPumpkinSprout_Timer = 30000; }else m_uiPumpkinSprout_Timer -= uiDiff; DoMeleeAttackIfReady(); break; //Phase 3b case 5: if (m_creature->HasAura(SPELL_HEAD)) { m_creature->RemoveAurasDueToSpell(SPELL_HEAD); m_creature->CastSpell(pHead,SPELL_SEND_HEAD,false); } ApplyRegenAuras(); if (((m_creature->GetHealth()*100) / (m_creature->GetMaxHealth())) == 100) { RemoveRegenAuras(); m_pInstance->SetData(TYPE_HALLOWSEND_EVENT,4); } break; // Head or body died case 6: if (m_creature->isAlive()) m_creature->DealDamage(m_creature, m_creature->GetMaxHealth(),NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false); break; default: break; } }
void UpdateAI(uint32 diff) override { if (!UpdateVictim()) return; // Pounding if (Pounding_Timer <= diff) { DoCastVictim(SPELL_POUNDING); Talk(SAY_POUNDING); Pounding_Timer = 15000; //cast time(3000) + cooldown time(12000) } else Pounding_Timer -= diff; // Arcane Orb if (ArcaneOrb_Timer <= diff) { Unit* target = NULL; std::list<HostileReference*> t_list = me->getThreatManager().getThreatList(); std::vector<Unit*> target_list; for (std::list<HostileReference*>::const_iterator itr = t_list.begin(); itr!= t_list.end(); ++itr) { target = ObjectAccessor::GetUnit(*me, (*itr)->getUnitGuid()); if (!target) continue; // exclude pets & totems, 18 yard radius minimum if (target->GetTypeId() == TYPEID_PLAYER && target->IsAlive() && !target->IsWithinDist(me, 18, false)) target_list.push_back(target); target = NULL; } if (!target_list.empty()) target = *(target_list.begin() + rand32() % target_list.size()); else target = me->GetVictim(); if (target) me->CastSpell(target, SPELL_ARCANE_ORB, false, NULL, NULL); ArcaneOrb_Timer = 3000; } else ArcaneOrb_Timer -= diff; // Single Target knock back, reduces aggro if (KnockAway_Timer <= diff) { DoCastVictim(SPELL_KNOCK_AWAY); //Drop 25% aggro if (DoGetThreat(me->GetVictim())) DoModifyThreatPercent(me->GetVictim(), -25); KnockAway_Timer = 30000; } else KnockAway_Timer -= diff; //Berserk if (Berserk_Timer < diff && !Enraged) { DoCast(me, SPELL_BERSERK); Enraged = true; } else Berserk_Timer -= diff; DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 diff) { if (uiCheckTimer <= diff) { if (CheckPlayersInDistance()) { if (!me->isInCombat()) { SummonAdds(); } } else if (me->isInCombat()) { Summons.DespawnAll(); EnterEvadeMode(); } uiCheckTimer = 2*IN_MILLISECONDS; } else uiCheckTimer -= diff; //Return since we have no target if (!UpdateVictim()) return; if (!bClosedDoor) { if (uiSummonTimer <= diff) { SummonAdds(); uiSummonTimer = 5*IN_MILLISECONDS; } else uiSummonTimer -= diff; if (uiDoorsTimer <= diff) { bClosedDoor = true; } else uiDoorsTimer -= diff; } if (me->HasUnitState(UNIT_STATE_CASTING)) return; if (uiPierceTimer <= diff) { DoCast(me->getVictim(), SPELL_PIERCE_ARMOR); uiPierceTimer = 8*IN_MILLISECONDS; } else uiPierceTimer -= diff; if (uiAcidTimer <= diff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(target, SPELL_ACID_CLOUD); uiAcidTimer = urand(20*IN_MILLISECONDS, 30*IN_MILLISECONDS); } else uiAcidTimer -= diff; if (uiLeechTimer <= diff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(target, SPELL_LEECH_POISON); uiLeechTimer = urand(11*IN_MILLISECONDS, 14*IN_MILLISECONDS); } else uiLeechTimer -= diff; if (uiGrabTimer <= diff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0)) // Draws all players (and attacking Mobs) to itself. DoCast(target, SPELL_WEB_GRAB); uiGrabTimer = urand(15*IN_MILLISECONDS, 30*IN_MILLISECONDS); } else uiGrabTimer -= diff; DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 diff) { if (!UpdateCombatState()) return; events.Update(diff); if (Phase == 1) { while (uint32 eventId = events.GetEvent()) { switch(eventId) { case EVENT_WASTE: DoSummon(NPC_WASTE, Pos[RAND(0,3,6,9)]); events.RepeatEvent(urand(2000,5000)); break; case EVENT_ABOMIN: if (nAbomination < 8) { DoSummon(NPC_ABOMINATION, Pos[RAND(1,4,7,10)]); nAbomination++; events.RepeatEvent(20000); } else events.PopEvent(); break; case EVENT_WEAVER: if (nWeaver < 8) { DoSummon(NPC_WEAVER, Pos[RAND(0,3,6,9)]); nWeaver++; events.RepeatEvent(25000); } else events.PopEvent(); break; case EVENT_TRIGGER: if (GameObject *pKTTrigger = me->GetMap()->GetGameObject(KTTriggerGUID)) pKTTrigger->SetPhaseMask(2, true); events.PopEvent(); break; case EVENT_PHASE: events.Reset(); DoScriptText(RAND(SAY_AGGRO_1,SAY_AGGRO_2,SAY_AGGRO_3), me); spawns.DespawnAll(); me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE | UNIT_FLAG_DISABLE_MOVE | UNIT_FLAG_NOT_SELECTABLE); me->CastStop(); DoStartMovement(me->getVictim()); events.ScheduleEvent(EVENT_BOLT, urand(5000,10000)); events.ScheduleEvent(EVENT_NOVA, 15000); events.ScheduleEvent(EVENT_DETONATE, urand(30000,40000)); events.ScheduleEvent(EVENT_FISSURE, urand(10000,30000)); events.ScheduleEvent(EVENT_BLAST, urand(60000,120000)); if (getDifficulty() == RAID_DIFFICULTY_25MAN_NORMAL) events.ScheduleEvent(EVENT_CHAIN, urand(30000,60000)); Phase = 2; break; default: events.PopEvent(); break; } } } else { //start phase 3 when we are 45% health if (Phase != 3) { if (HealthBelowPct(45)) { Phase = 3 ; DoScriptText(SAY_REQUEST_AID, me); //here Lich King should respond to KelThuzad but I don't know which Creature to make talk //so for now just make Kelthuzad says it. DoScriptText(SAY_ANSWER_REQUEST, me); for (uint8 i = 0; i <= 3; ++i) { if (GameObject *pPortal = me->GetMap()->GetGameObject(PortalsGUID[i])) { if (pPortal->getLootState() == GO_READY) pPortal->UseDoorOrButton(); } } } } else if (nGuardiansOfIcecrownCount < RAID_MODE(2,4)) { if (uiGuardiansOfIcecrownTimer <= diff) { // TODO : Add missing text if (Creature* pGuardian = DoSummon(NPC_ICECROWN, Pos[RAND(2,5,8,11)])) pGuardian->SetFloatValue(UNIT_FIELD_COMBATREACH, 2); ++nGuardiansOfIcecrownCount; uiGuardiansOfIcecrownTimer = 5000; } else uiGuardiansOfIcecrownTimer -= diff; } if (me->hasUnitState(UNIT_STAT_CASTING)) return; if (uint32 eventId = events.GetEvent()) { switch(eventId) { case EVENT_BOLT: DoCastVictim(RAID_MODE(SPELL_FROST_BOLT,H_SPELL_FROST_BOLT)); events.RepeatEvent(urand(5000,10000)); break; case EVENT_NOVA: DoCastAOE(RAID_MODE(SPELL_FROST_BOLT_AOE,H_SPELL_FROST_BOLT_AOE)); events.RepeatEvent(urand(15000,30000)); break; case EVENT_CHAIN: { uint32 count = urand(1,3); for (uint8 i = 1; i <= count; i++) { Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 1, 200, true); if (pTarget && !pTarget->isCharmed() && (chained.find(pTarget->GetGUID()) == chained.end())) { DoCast(pTarget, SPELL_CHAINS_OF_KELTHUZAD); float scale = pTarget->GetFloatValue(OBJECT_FIELD_SCALE_X); chained.insert(std::make_pair(pTarget->GetGUID(), scale)); pTarget->SetFloatValue(OBJECT_FIELD_SCALE_X, scale * 2); events.ScheduleEvent(EVENT_CHAINED_SPELL, 2000); //core has 2000ms to set unit flag charm } } if (!chained.empty()) DoScriptText(RAND(SAY_CHAIN_1,SAY_CHAIN_2), me); events.RepeatEvent(urand(100000,180000)); break; } case EVENT_CHAINED_SPELL: { std::map<uint64, float>::iterator itr; for (itr = chained.begin(); itr != chained.end();) { if (Unit* player = Unit::GetPlayer(*me, (*itr).first)) { if (!player->isCharmed()) { player->SetFloatValue(OBJECT_FIELD_SCALE_X, (*itr).second); std::map<uint64, float>::iterator next = itr; ++next; chained.erase(itr); itr = next; continue; } if (Unit *pTarget = SelectTarget(SELECT_TARGET_TOPAGGRO, 0, NotCharmedTargetSelector())) { switch(player->getClass()) { case CLASS_DRUID: if (urand(0,1)) player->CastSpell(pTarget, SPELL_MOONFIRE, false); else player->CastSpell(me, SPELL_LIFEBLOOM, false); break; case CLASS_HUNTER: player->CastSpell(pTarget, RAND(SPELL_MULTI_SHOT, SPELL_VOLLEY), false); break; case CLASS_MAGE: player->CastSpell(pTarget, RAND(SPELL_FROST_FIREBOLT, SPELL_ARCANE_MISSILES), false); break; case CLASS_WARLOCK: player->CastSpell(pTarget, RAND(SPELL_CURSE_OF_AGONY, SPELL_SHADOW_BOLT), true); break; case CLASS_WARRIOR: player->CastSpell(pTarget, RAND(SPELL_BLADESTORM, SPELL_CLEAVE), false); break; case CLASS_PALADIN: if (urand(0,1)) player->CastSpell(pTarget, SPELL_HAMMER_OF_JUSTICE, false); else player->CastSpell(me, SPELL_HOLY_SHOCK, false); break; case CLASS_PRIEST: if (urand(0,1)) player->CastSpell(pTarget, SPELL_VAMPIRIC_TOUCH, false); else player->CastSpell(me, SPELL_RENEW, false); break; case CLASS_SHAMAN: if (urand(0,1)) player->CastSpell(pTarget, SPELL_EARTH_SHOCK, false); else player->CastSpell(me, SPELL_HEALING_WAVE, false); break; case CLASS_ROGUE: player->CastSpell(pTarget, RAND(SPELL_HEMORRHAGE, SPELL_MUTILATE), false); break; case CLASS_DEATH_KNIGHT: if (urand(0,1)) player->CastSpell(pTarget, SPELL_PLAGUE_STRIKE, true); else player->CastSpell(pTarget, SPELL_HOWLING_BLAST, true); break; } } } ++itr; } if (chained.empty()) events.PopEvent(); else events.RepeatEvent(5000); break; } case EVENT_DETONATE: { std::vector<Unit*> unitList; std::list<HostileReference*> *threatList = &me->getThreatManager().getThreatList(); for (std::list<HostileReference*>::const_iterator itr = threatList->begin(); itr != threatList->end(); ++itr) { if ((*itr)->getTarget()->GetTypeId() == TYPEID_PLAYER && (*itr)->getTarget()->getPowerType() == POWER_MANA && (*itr)->getTarget()->GetPower(POWER_MANA)) unitList.push_back((*itr)->getTarget()); } if (!unitList.empty()) { std::vector<Unit*>::const_iterator itr = unitList.begin(); advance(itr, rand()%unitList.size()); DoCast(*itr, SPELL_MANA_DETONATION); DoScriptText(RAND(SAY_SPECIAL_1,SAY_SPECIAL_2,SAY_SPECIAL_3), me); } events.RepeatEvent(urand(20000,50000)); break; } case EVENT_FISSURE: if (Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0)) DoCast(pTarget, SPELL_SHADOW_FISURE); events.RepeatEvent(urand(10000,45000)); break; case EVENT_BLAST: if (Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, RAID_MODE(1,0), 0, true)) DoCast(pTarget, SPELL_FROST_BLAST); if (rand()%2) DoScriptText(SAY_FROST_BLAST, me); events.RepeatEvent(urand(30000,90000)); break; default: events.PopEvent(); break; } } DoMeleeAttackIfReady(); } }
void UpdateAI(const uint32 diff) { if (!UpdateVictim()) return; events.Update(diff); if (me->HasUnitState(UNIT_STATE_CASTING)) return; while (uint32 eventId = events.ExecuteEvent()) { switch (eventId) { case EVENT_UNHOLY_SHOT: if (Unit* pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 0.0f, true)) DoCast(pTarget, SPELL_UNHOLY_SHOT); events.ScheduleEvent(EVENT_UNHOLY_SHOT, urand(10000, 20000)); break; case EVENT_SHRIEK_OF_THE_HIGHBORNE: if (Unit* pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 0.0f, true)) DoCast(pTarget, SPELL_SHRIEK_OF_THE_HIGHBORNE); events.ScheduleEvent(EVENT_SHRIEK_OF_THE_HIGHBORNE, urand(15000, 21000)); break; case EVENT_TELEPORT: events.CancelEvent(EVENT_UNHOLY_SHOT); events.CancelEvent(EVENT_SHRIEK_OF_THE_HIGHBORNE); me->SetReactState(REACT_PASSIVE); me->AttackStop(); me->InterruptNonMeleeSpells(false); DoCast(me, SPELL_TELEPORT, true); events.ScheduleEvent(EVENT_TELEPORT_1, 2000); break; case EVENT_TELEPORT_1: Talk(SAY_SPELL); DoCast(me, SPELL_CALL_OF_THE_HIGHBORNE, true); for (uint8 i = 0; i < 8; ++i) me->SummonCreature(NPC_GHOUL_1, ghoulPos[i]); events.ScheduleEvent(EVENT_DEATH_GRIP, 3000); events.ScheduleEvent(EVENT_SPAWN_GHOUL, 3000); break; case EVENT_DEATH_GRIP: DoCastAOE(SPELL_DEATH_GRIP_AOE); break; case EVENT_SPAWN_GHOUL: { deadghouls = 0; Unit* _first = NULL; Unit* _prev = NULL; for (uint8 i = 1; i < 8; ++i) { if (Creature* pGhoul = me->SummonCreature(NPC_RISEN_GHOUL, ghoulPos[i])) { if (_prev) { _prev->CastSpell(pGhoul, SPELL_WRACKING_PAIN_ANY, true); _prev->GetAI()->SetGUID(pGhoul->GetGUID(), DATA_GUID); } _prev = pGhoul; if (i == 1) _first = pGhoul; } } if (_first) { _prev->CastSpell(_first, SPELL_WRACKING_PAIN_ANY, true); _prev->GetAI()->SetGUID(_first->GetGUID(), DATA_GUID); } summons.DespawnEntry(NPC_GHOUL_1); break; } case EVENT_START: me->RemoveAura(SPELL_CALL_OF_THE_HIGHBORNE); me->SetReactState(REACT_AGGRESSIVE); me->GetMotionMaster()->MoveChase(me->getVictim()); events.ScheduleEvent(EVENT_UNHOLY_SHOT, urand(5000, 20000)); events.ScheduleEvent(EVENT_SHRIEK_OF_THE_HIGHBORNE, urand(5000, 20000)); events.ScheduleEvent(EVENT_TELEPORT, 40000); break; default: break; } } DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 diff) { if(!pInstance) return; if(!inCombat && !me->IsNonMeleeSpellCasted(false)) { if(m_uiChannelTimer <= diff) { DoCast(pDummyTarget, SPELL_CHANNEL_SPELL); m_uiChannelTimer = 1*IN_MILLISECONDS; } else m_uiChannelTimer -= diff; } if(!UpdateVictim()) return; switch(uiStage) { case 0: if(HealthBelowPct(67)) uiStage = 1; break; case 1: me->InterruptNonMeleeSpells(true); if(Is25ManRaid()) { DoCast(SPELL_SUMMON_CLONE); DoScriptText(-1999981, me); } uiStage = 2; break; case 2: if(me->IsNonMeleeSpellCasted(false)) return; DoCast(SPELL_REPELLING_WAVE); uiStage = 3; case 3: if(HealthBelowPct(51)) uiStage = 4; break; case 4: me->InterruptNonMeleeSpells(true); if(!Is25ManRaid()) { DoCast(SPELL_SUMMON_CLONE); DoScriptText(-1999981, me); } uiStage = 5; break; case 5: if(me->IsNonMeleeSpellCasted(false)) return; DoCast(SPELL_REPELLING_WAVE); uiStage = 6; case 6: if(HealthBelowPct(34)) uiStage = 7; break; case 7: me->InterruptNonMeleeSpells(true); if(Is25ManRaid()) { DoCast(SPELL_SUMMON_CLONE); DoScriptText(-1999981, me); } uiStage = 8; break; case 8: if(me->IsNonMeleeSpellCasted(false)) return; DoCast(SPELL_REPELLING_WAVE); uiStage = 9; case 9: default: break; } if(m_uiEnevatingTimer <= diff) { DoCast(SPELL_ENERVATING_BRAND); m_uiEnevatingTimer = urand(10*IN_MILLISECONDS, 25*IN_MILLISECONDS); } else m_uiEnevatingTimer -= diff; if(m_uiSaberLashTimer <= diff) { DoCast(SPELL_SABER_LASH); m_uiSaberLashTimer = urand(10*IN_MILLISECONDS, 15*IN_MILLISECONDS); } else m_uiSaberLashTimer -= diff; DoMeleeAttackIfReady(); }
void UpdateAI(uint32 diff) override { if (!UpdateVictim()) return; events.Update(diff); if (me->HasUnitState(UNIT_STATE_CASTING)) return; while (uint32 eventId = events.ExecuteEvent()) { switch (eventId) { case EVENT_JET: Talk(EMOTE_JETS); DoCast(me, SPELL_FLAME_JETS); events.ScheduleEvent(EVENT_JET, urand(35000, 40000)); break; case EVENT_SLAG_POT: if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 1, 100, true)) { Talk(SAY_SLAG_POT); _slagPotGUID = target->GetGUID(); DoCast(target, SPELL_GRAB); events.DelayEvents(3000); events.ScheduleEvent(EVENT_GRAB_POT, 500); } events.ScheduleEvent(EVENT_SLAG_POT, RAID_MODE(30000, 15000)); break; case EVENT_GRAB_POT: if (Unit* slagPotTarget = ObjectAccessor::GetUnit(*me, _slagPotGUID)) { slagPotTarget->EnterVehicle(me, 0); events.CancelEvent(EVENT_GRAB_POT); events.ScheduleEvent(EVENT_CHANGE_POT, 1000); } break; case EVENT_CHANGE_POT: if (Unit* slagPotTarget = ObjectAccessor::GetUnit(*me, _slagPotGUID)) { DoCast(slagPotTarget, SPELL_SLAG_POT, true); slagPotTarget->EnterVehicle(me, 1); events.CancelEvent(EVENT_CHANGE_POT); events.ScheduleEvent(EVENT_END_POT, 10000); } break; case EVENT_END_POT: if (Unit* slagPotTarget = ObjectAccessor::GetUnit(*me, _slagPotGUID)) { slagPotTarget->ExitVehicle(); slagPotTarget = NULL; _slagPotGUID.Clear(); events.CancelEvent(EVENT_END_POT); } break; case EVENT_SCORCH: Talk(SAY_SCORCH); if (Unit* target = me->GetVictim()) me->SummonCreature(NPC_GROUND_SCORCH, target->GetPositionX(), target->GetPositionY(), target->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN, 45000); DoCast(SPELL_SCORCH); events.ScheduleEvent(EVENT_SCORCH, 25000); break; case EVENT_CONSTRUCT: Talk(SAY_SUMMON); DoSummon(NPC_IRON_CONSTRUCT, ConstructSpawnPosition[urand(0, CONSTRUCT_SPAWN_POINTS - 1)], 30000, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT); DoCast(SPELL_STRENGHT); DoCast(me, SPELL_ACTIVATE_CONSTRUCT); events.ScheduleEvent(EVENT_CONSTRUCT, RAID_MODE(40000, 30000)); break; case EVENT_BERSERK: DoCast(me, SPELL_BERSERK, true); Talk(SAY_BERSERK); break; } } DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 uiDiff) { if (!UpdateVictim()) return; if (m_uiSummonInfernalEruptionTimer <= uiDiff) { DoScriptText(EMOTE_INFERNAL_ERUPTION, me); DoScriptText(SAY_INFERNAL_ERUPTION, me); DoCast(SPELL_INFERNAL_ERUPTION); m_uiSummonInfernalEruptionTimer = 2*MINUTE*IN_MILLISECONDS; } else m_uiSummonInfernalEruptionTimer -= uiDiff; if (m_uiSummonNetherPortalTimer <= uiDiff) { DoScriptText(EMOTE_NETHER_PORTAL, me); DoScriptText(SAY_NETHER_PORTAL, me); DoCast(SPELL_NETHER_PORTAL); m_uiSummonNetherPortalTimer = 2*MINUTE*IN_MILLISECONDS; } else m_uiSummonNetherPortalTimer -= uiDiff; if (m_uiFelFireballTimer <= uiDiff) { DoCastVictim(SPELL_FEL_FIREBALL); m_uiFelFireballTimer = urand(10*IN_MILLISECONDS, 15*IN_MILLISECONDS); } else m_uiFelFireballTimer -= uiDiff; if (m_uiFelLightningTimer <= uiDiff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM)) DoCast(target, SPELL_FEL_LIGHTING); m_uiFelLightningTimer = urand(10*IN_MILLISECONDS, 15*IN_MILLISECONDS); } else m_uiFelLightningTimer -= uiDiff; if (m_uiIncinerateFleshTimer <= uiDiff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 1, 0, true)) { DoScriptText(EMOTE_INCINERATE, me, target); DoScriptText(SAY_INCINERATE, me); DoCast(target, SPELL_INCINERATE_FLESH); } m_uiIncinerateFleshTimer = urand(20*IN_MILLISECONDS, 25*IN_MILLISECONDS); } else m_uiIncinerateFleshTimer -= uiDiff; if (m_uiNetherPowerTimer <= uiDiff) { me->CastCustomSpell(SPELL_NETHER_POWER, SPELLVALUE_AURA_STACK, RAID_MODE<uint32>(5,10,5,10), me, true); m_uiNetherPowerTimer = 40*IN_MILLISECONDS; } else m_uiNetherPowerTimer -= uiDiff; if (m_uiLegionFlameTimer <= uiDiff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 1, 0, true)) { DoScriptText(EMOTE_LEGION_FLAME, me, target); DoCast(target, SPELL_LEGION_FLAME); } m_uiLegionFlameTimer = 30*IN_MILLISECONDS; } else m_uiLegionFlameTimer -= uiDiff; if (GetDifficulty() == RAID_DIFFICULTY_25MAN_HEROIC && m_uiTouchOfJaraxxusTimer <= uiDiff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0)) DoCast(target, SPELL_TOUCH_OF_JARAXXUS); m_uiTouchOfJaraxxusTimer = urand(10*IN_MILLISECONDS, 15*IN_MILLISECONDS); } else m_uiTouchOfJaraxxusTimer -= uiDiff; DoMeleeAttackIfReady(); }
void UpdateAI(uint32 uiDiff) override { //Return since we have no target if (!UpdateVictim()) return; // Change stance if (m_uiChangeStance_Timer <= uiDiff) { //wait for current spell to finish before change stance if (me->IsNonMeleeSpellCast(false)) return; DoRemoveStanceAura(m_uiStance); int uiTempStance = rand32() % (3 - 1); if (uiTempStance >= m_uiStance) ++uiTempStance; m_uiStance = uiTempStance; switch (m_uiStance) { case STANCE_DEFENSIVE: Talk(SAY_DEFENSIVE_STANCE); Talk(EMOTE_DEFENSIVE_STANCE); DoCast(me, SPELL_DEFENSIVE_STANCE); SetEquipmentSlots(false, EQUIP_SWORD, EQUIP_SHIELD, EQUIP_NO_CHANGE); break; case STANCE_BERSERKER: Talk(SAY_BERSEKER_STANCE); Talk(EMOTE_BERSEKER_STANCE); DoCast(me, SPELL_BERSEKER_STANCE); SetEquipmentSlots(false, EQUIP_SWORD, EQUIP_SWORD, EQUIP_NO_CHANGE); break; case STANCE_BATTLE: Talk(SAY_BATTLE_STANCE); Talk(EMOTE_BATTLE_STANCE); DoCast(me, SPELL_BATTLE_STANCE); SetEquipmentSlots(false, EQUIP_MACE, EQUIP_UNEQUIP, EQUIP_NO_CHANGE); break; } m_uiChangeStance_Timer = urand(20000, 25000); return; } else m_uiChangeStance_Timer -= uiDiff; switch (m_uiStance) { case STANCE_DEFENSIVE: { if (m_uiReflection_Timer <= uiDiff) { DoCast(me, SPELL_SPELL_REFLECTION); m_uiReflection_Timer = urand(8000, 9000); } else m_uiReflection_Timer -= uiDiff; if (m_uiKnockAway_Timer <= uiDiff) { DoCast(me, SPELL_KNOCK_AWAY); m_uiKnockAway_Timer = urand(20000, 21000); } else m_uiKnockAway_Timer -= uiDiff; if (m_uiPummel_Timer <= uiDiff) { DoCastVictim(SPELL_PUMMEL); m_uiPummel_Timer = urand(10000, 11000); } else m_uiPummel_Timer -= uiDiff; if (m_uiIronform_Timer <= uiDiff) { DoCast(me, SPELL_IRONFORM); m_uiIronform_Timer = urand(25000, 26000); } else m_uiIronform_Timer -= uiDiff; break; } case STANCE_BERSERKER: { if (m_uiIntercept_Timer <= uiDiff) { //not much point is this, better random target and more often? DoCastVictim(SPELL_INTERCEPT); m_uiIntercept_Timer = urand(45000, 46000); } else m_uiIntercept_Timer -= uiDiff; if (m_uiWhirlwind_Timer <= uiDiff) { DoCast(me, SPELL_WHIRLWIND); m_uiWhirlwind_Timer = urand(10000, 11000); } else m_uiWhirlwind_Timer -= uiDiff; if (m_uiCleave_Timer <= uiDiff) { DoCastVictim(SPELL_CLEAVE); m_uiCleave_Timer = urand(8000, 9000); } else m_uiCleave_Timer -= uiDiff; break; } case STANCE_BATTLE: { if (m_uiMortalStrike_Timer <= uiDiff) { DoCastVictim(SPELL_MORTAL_STRIKE); m_uiMortalStrike_Timer = urand(20000, 21000); } else m_uiMortalStrike_Timer -= uiDiff; if (m_uiSlam_Timer <= uiDiff) { DoCastVictim(SPELL_SLAM); m_uiSlam_Timer = urand(15000, 16000); } else m_uiSlam_Timer -= uiDiff; break; } } DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 diff) { if (Invisible && Invisible_Timer <= diff) { //Become visible again me->setFaction(14); me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); //Noxxion model me->SetDisplayId(11172); Invisible = false; //me->m_canMove = true; } else if (Invisible) { Invisible_Timer -= diff; //Do nothing while invisible return; } //Return since we have no target if (!UpdateVictim()) return; //ToxicVolley_Timer if (ToxicVolley_Timer <= diff) { DoCast(me->getVictim(), SPELL_TOXICVOLLEY); ToxicVolley_Timer = 9000; } else ToxicVolley_Timer -= diff; //Uppercut_Timer if (Uppercut_Timer <= diff) { DoCast(me->getVictim(), SPELL_UPPERCUT); Uppercut_Timer = 12000; } else Uppercut_Timer -= diff; //Adds_Timer if (!Invisible && Adds_Timer <= diff) { //Interrupt any spell casting //me->m_canMove = true; me->InterruptNonMeleeSpells(false); me->setFaction(35); me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); // Invisible Model me->SetDisplayId(11686); SummonAdds(me->getVictim()); SummonAdds(me->getVictim()); SummonAdds(me->getVictim()); SummonAdds(me->getVictim()); SummonAdds(me->getVictim()); Invisible = true; Invisible_Timer = 15000; Adds_Timer = 40000; } else Adds_Timer -= diff; DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 diff) { //Return since we have no target if (!m_creature->SelectHostileTarget() || !m_creature->getVictim()) return; if (Teleport) { if (Teleport_Timer <= diff) { m_creature->NearTeleportTo(LOCX, LOCY, LOCZ, 0.0f); float ranX = LOCX; float ranY = LOCY; float ranZ = LOCZ; std::vector<ObjectGuid> vGuids; m_creature->FillGuidsListFromThreatList(vGuids); for (std::vector<ObjectGuid>::const_iterator itr = vGuids.begin();itr != vGuids.end(); ++itr) { Unit* target = m_creature->GetMap()->GetUnit(*itr); if (target && target->GetTypeId() == TYPEID_PLAYER) { target->GetRandomPoint(LOCX,LOCY,LOCZ,3.0f,ranX,ranY,ranZ); DoTeleportPlayer(target,ranX,ranY,ranZ,m_creature->GetAngle(m_creature->GetPositionX(),m_creature->GetPositionY())); } } Teleport = false; DoCastSpellIfCan(m_creature->getVictim(), m_bIsRegularMode ? SPELL_RAIN_OF_FIRE : SPELL_RAIN_OF_FIRE_H); Teleport_Timer = 1000; }else Teleport_Timer -= diff; } if (ShadowBoltVolley_Timer < diff) { DoCastSpellIfCan(m_creature->getVictim(), SPELL_SHADOW_BOLT_VOLLEY); ShadowBoltVolley_Timer = urand(15000, 30000); }else ShadowBoltVolley_Timer -= diff; if (DrawShadows_Timer < diff) { DoCastSpellIfCan(m_creature,SPELL_DRAW_SHADOWS); DrawShadows_Timer = 30000; Teleport = true; }else DrawShadows_Timer -= diff; if (VoidTraveler_Timer < diff) { DoScriptText(SAY_HELP, m_creature); switch(urand(0, 4)) { case 0: DoCastSpellIfCan(m_creature, SPELL_SUMMON_VOIDWALKER_A, CAST_TRIGGERED); break; case 1: DoCastSpellIfCan(m_creature, SPELL_SUMMON_VOIDWALKER_B, CAST_TRIGGERED); break; case 2: DoCastSpellIfCan(m_creature, SPELL_SUMMON_VOIDWALKER_C, CAST_TRIGGERED); break; case 3: DoCastSpellIfCan(m_creature, SPELL_SUMMON_VOIDWALKER_D, CAST_TRIGGERED); break; case 4: DoCastSpellIfCan(m_creature, SPELL_SUMMON_VOIDWALKER_E, CAST_TRIGGERED); break; } //faster rate when below (X) health? VoidTraveler_Timer = 35000; }else VoidTraveler_Timer -= diff; if (!m_bIsRegularMode) { if (Banish_Timer < diff) { if (Unit* target = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM, 1)) DoCastSpellIfCan(target,SPELL_BANISH_H); Banish_Timer = 35000; }else Banish_Timer -= diff; } DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 diff) { if (!UpdateVictim()) { if (phase == PHASE_FLIGHT && !me->IsInEvadeMode()) EnterEvadeMode(); return; } events.Update(diff); if (me->IsNonMeleeSpellCasted(false)) return; if (phase == PHASE_GROUND) { switch(events.ExecuteEvent()) { case EVENT_BERSERK: DoScriptText(YELL_BERSERK, me); DoCast(me, SPELL_BERSERK, true); events.ScheduleEvent(EVENT_BERSERK, 10000); break; case EVENT_CLEAVE: DoCast(me->getVictim(), SPELL_CLEAVE, false); events.ScheduleEvent(EVENT_CLEAVE, urand(5000, 10000)); break; case EVENT_CORROSION: DoCast(me->getVictim(), SPELL_CORROSION, false); events.ScheduleEvent(EVENT_CORROSION, urand(20000, 30000)); break; case EVENT_GAS_NOVA: DoCast(me, SPELL_GAS_NOVA, false); events.ScheduleEvent(EVENT_GAS_NOVA, urand(20000, 25000)); break; case EVENT_ENCAPSULATE: if (Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 150, true)) DoCast(pTarget, SPELL_ENCAPSULATE_CHANNEL, false); events.ScheduleEvent(EVENT_ENCAPSULATE, urand(25000, 30000)); break; case EVENT_FLIGHT: EnterPhase(PHASE_FLIGHT); break; default: DoMeleeAttackIfReady(); break; } } if (phase == PHASE_FLIGHT) { switch(events.ExecuteEvent()) { case EVENT_BERSERK: DoScriptText(YELL_BERSERK, me); DoCast(me, SPELL_BERSERK, true); break; case EVENT_FLIGHT_SEQUENCE: HandleFlightSequence(); break; case EVENT_SUMMON_FOG: { float x, y, z; me->GetPosition(x, y, z); me->UpdateGroundPositionZ(x, y, z); if (Creature *Fog = me->SummonCreature(MOB_VAPOR_TRAIL, x, y, z, 0, TEMPSUMMON_TIMED_DESPAWN, 10000)) { Fog->RemoveAurasDueToSpell(SPELL_TRAIL_TRIGGER); Fog->CastSpell(Fog, SPELL_FOG_TRIGGER, true); me->CastSpell(Fog, SPELL_FOG_FORCE, true); } } events.ScheduleEvent(EVENT_SUMMON_FOG, 1000); break; } } }
void UpdateAI(const uint32 diff) { if (!UpdateVictim()) return; if (DelayTimer && DelayTimer > 5000) DelayEventStart(); else DelayTimer+=diff; switch (Phase) { case PHASE_UNDERGROUND: if (ImpaleTimer <= diff) { switch (ImpalePhase) { case IMPALE_PHASE_TARGET: if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) { if (Creature* impaleTarget = DoSummonImpaleTarget(target)) impaleTarget->CastSpell(impaleTarget, SPELL_IMPALE_SHAKEGROUND, true); ImpaleTimer = 3*IN_MILLISECONDS; ImpalePhase = IMPALE_PHASE_ATTACK; } break; case IMPALE_PHASE_ATTACK: if (Creature* impaleTarget = Unit::GetCreature(*me, ImpaleTarget)) { impaleTarget->CastSpell(impaleTarget, SPELL_IMPALE_SPIKE, false); impaleTarget->RemoveAurasDueToSpell(SPELL_IMPALE_SHAKEGROUND); } ImpalePhase = IMPALE_PHASE_DMG; ImpaleTimer = 1*IN_MILLISECONDS; break; case IMPALE_PHASE_DMG: if (Creature* impaleTarget = Unit::GetCreature(*me, ImpaleTarget)) me->CastSpell(impaleTarget, SPELL_IMPALE_DMG, true); ImpalePhase = IMPALE_PHASE_TARGET; ImpaleTimer = 9*IN_MILLISECONDS; break; } } else ImpaleTimer -= diff; if (!GuardianSummoned) { for (uint8 i = 0; i < 2; ++i) { if (Creature* Guardian = me->SummonCreature(CREATURE_GUARDIAN, SpawnPointGuardian[i], TEMPSUMMON_CORPSE_DESPAWN, 0)) { Guardian->AddThreat(me->getVictim(), 0.0f); DoZoneInCombat(Guardian); } } GuardianSummoned = true; } if (!VenomancerSummoned) { if (VenomancerTimer <= diff) { if (UndergroundPhase > 1) { for (uint8 i = 0; i < 2; ++i) { if (Creature* Venomancer = me->SummonCreature(CREATURE_VENOMANCER, SpawnPoint[i], TEMPSUMMON_CORPSE_DESPAWN, 0)) { Venomancer->AddThreat(me->getVictim(), 0.0f); DoZoneInCombat(Venomancer); } } VenomancerSummoned = true; } } else VenomancerTimer -= diff; } if (!DatterSummoned) { if (DatterTimer <= diff) { if (UndergroundPhase > 2) { for (uint8 i = 0; i < 2; ++i) { if (Creature* Datter = me->SummonCreature(CREATURE_DATTER, SpawnPoint[i], TEMPSUMMON_CORPSE_DESPAWN, 0)) { Datter->AddThreat(me->getVictim(), 0.0f); DoZoneInCombat(Datter); } } DatterSummoned = true; } } else DatterTimer -= diff; if (me->HasAura(SPELL_LEECHING_SWARM)) me->RemoveAurasDueToSpell(SPELL_LEECHING_SWARM); } if (UndergroundTimer <= diff) { me->RemoveAura(SPELL_SUBMERGE); me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE|UNIT_FLAG_NOT_SELECTABLE); Phase = PHASE_MELEE; } else UndergroundTimer -= diff; break; case PHASE_MELEE: if (((UndergroundPhase == 0 && HealthBelowPct(75)) || (UndergroundPhase == 1 && HealthBelowPct(50)) || (UndergroundPhase == 2 && HealthBelowPct(25))) && !me->HasUnitState(UNIT_STATE_CASTING)) { GuardianSummoned = false; VenomancerSummoned = false; DatterSummoned = false; UndergroundTimer = 40*IN_MILLISECONDS; VenomancerTimer = 25*IN_MILLISECONDS; DatterTimer = 32*IN_MILLISECONDS; ImpalePhase = 0; ImpaleTimer = 9*IN_MILLISECONDS; DoCast(me, SPELL_SUBMERGE, false); me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE|UNIT_FLAG_NOT_SELECTABLE); Phase = PHASE_UNDERGROUND; ++UndergroundPhase; } if (Channeling == true) { for (uint8 i = 0; i < 8; ++i) DoCast(me->getVictim(), SPELL_SUMMON_CARRION_BEETLES, true); Channeling = false; } else if (CarrionBeetlesTimer <= diff) { Channeling = true; DoCastVictim(SPELL_CARRION_BEETLES); CarrionBeetlesTimer = 25*IN_MILLISECONDS; } else CarrionBeetlesTimer -= diff; if (LeechingSwarmTimer <= diff) { DoCast(me, SPELL_LEECHING_SWARM, true); LeechingSwarmTimer = 19*IN_MILLISECONDS; } else LeechingSwarmTimer -= diff; if (PoundTimer <= diff) { if (Unit* target = me->getVictim()) { if (Creature* pImpaleTarget = DoSummonImpaleTarget(target)) me->CastSpell(pImpaleTarget, SPELL_POUND, false); } PoundTimer = 16500; } else PoundTimer -= diff; DoMeleeAttackIfReady(); break; } }
void UpdateAI(const uint32 diff) { if (!me->HasAura(AURA_SPECTRAL_INVISIBILITY)) me->CastSpell(me, AURA_SPECTRAL_INVISIBILITY, true); if (!UpdateVictim()) return; if (CheckTimer <= diff) { Creature* Kalec = Unit::GetCreature(*me, KalecGUID); if (!Kalec || (Kalec && !Kalec->isAlive())) { if (Creature* Kalecgos = Unit::GetCreature(*me, KalecgosGUID)) Kalecgos->AI()->EnterEvadeMode(); return; } if (HealthBelowPct(10) && !isEnraged) { if (Creature* Kalecgos = Unit::GetCreature(*me, KalecgosGUID)) Kalecgos->AI()->DoAction(DO_ENRAGE); DoAction(DO_ENRAGE); } Creature* Kalecgos = Unit::GetCreature(*me, KalecgosGUID); if (Kalecgos) { if (!Kalecgos->isInCombat()) { me->AI()->EnterEvadeMode(); return; } } if (!isBanished && HealthBelowPct(1)) { if (Kalecgos) { if (Kalecgos->HasAura(SPELL_BANISH)) { me->DealDamage(me, me->GetHealth()); return; } else DoAction(DO_BANISH); } else { me->MonsterTextEmote(EMOTE_UNABLE_TO_FIND, 0); EnterEvadeMode(); return; } } CheckTimer = 1000; } else CheckTimer -= diff; if (ResetThreat <= diff) { ThreatContainer::StorageType threatlist = me->getThreatManager().getThreatList(); for (ThreatContainer::StorageType::const_iterator itr = threatlist.begin(); itr != threatlist.end(); ++itr) { if (Unit* unit = Unit::GetUnit(*me, (*itr)->getUnitGuid())) if (unit->GetPositionZ() > me->GetPositionZ() + 5) me->getThreatManager().modifyThreatPercent(unit, -100); } ResetThreat = 1000; } else ResetThreat -= diff; if (ShadowBoltTimer <= diff) { if (!(rand()%5))Talk(SAY_SATH_SPELL1); DoCast(me, SPELL_SHADOW_BOLT); ShadowBoltTimer = 7000+(rand()%3000); } else ShadowBoltTimer -= diff; if (AgonyCurseTimer <= diff) { Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 1); if (!target) target = me->getVictim(); DoCast(target, SPELL_AGONY_CURSE); AgonyCurseTimer = 20000; } else AgonyCurseTimer -= diff; if (CorruptionStrikeTimer <= diff) { if (!(rand()%5))Talk(SAY_SATH_SPELL2); DoCast(me->getVictim(), SPELL_CORRUPTION_STRIKE); CorruptionStrikeTimer = 13000; } else CorruptionStrikeTimer -= diff; DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 diff) { if (!UpdateVictim()) return; if (StormCount) { Unit *pTarget = Unit::GetUnit(*me, CloudGUID); if (!pTarget || !pTarget->isAlive()) { EnterEvadeMode(); return; } else if (Unit* Cyclone = Unit::GetUnit(*me, CycloneGUID)) Cyclone->CastSpell(pTarget, 25160, true); // keep casting or... if (StormSequenceTimer <= diff) HandleStormSequence(pTarget); else StormSequenceTimer -= diff; return; } if (Enrage_Timer <= diff) { me->MonsterYell(SAY_ONENRAGE, LANG_UNIVERSAL, NULL); DoPlaySoundToSet(me, SOUND_ONENRAGE); DoCast(me, SPELL_BERSERK, true); Enrage_Timer = 600000; } else Enrage_Timer -= diff; if (StaticDisruption_Timer <= diff) { Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM, 1); if (!pTarget) pTarget = me->getVictim(); TargetGUID = pTarget->GetGUID(); DoCast(pTarget, SPELL_STATIC_DISRUPTION, false); me->SetInFront(me->getVictim()); StaticDisruption_Timer = (10+rand()%8)*1000; // < 20s /*if (float dist = me->IsWithinDist3d(pTarget->GetPositionX(), pTarget->GetPositionY(), pTarget->GetPositionZ(), 5.0f) dist = 5.0f; SDisruptAOEVisual_Timer = 1000 + floor(dist / 30 * 1000.0f);*/ } else StaticDisruption_Timer -= diff; if (GustOfWind_Timer <= diff) { Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM, 1); if (!pTarget) pTarget = me->getVictim(); DoCast(pTarget, SPELL_GUST_OF_WIND); GustOfWind_Timer = (20+rand()%10)*1000; //20 to 30 seconds(bosskillers) } else GustOfWind_Timer -= diff; if (CallLighting_Timer <= diff) { DoCast(me->getVictim(), SPELL_CALL_LIGHTNING); CallLighting_Timer = (12 + rand()%5)*1000; //totaly random timer. can't find any info on this } else CallLighting_Timer -= diff; if (!isRaining && ElectricalStorm_Timer < 8000 + rand()%5000) { SetWeather(WEATHER_STATE_HEAVY_RAIN, 0.9999f); isRaining = true; } if (ElectricalStorm_Timer <= diff) { Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 50, true); if (!pTarget) { EnterEvadeMode(); return; } pTarget->CastSpell(pTarget, 44007, true);//cloud visual DoCast(pTarget, SPELL_ELECTRICAL_STORM, false);//storm cyclon + visual float x,y,z; pTarget->GetPosition(x,y,z); if (pTarget) { pTarget->SetUnitMovementFlags(MOVEFLAG_LEVITATING); pTarget->SendMonsterMove(x,y,me->GetPositionZ()+15,0); } Unit *Cloud = me->SummonTrigger(x, y, me->GetPositionZ()+16, 0, 15000); if (Cloud) { CloudGUID = Cloud->GetGUID(); Cloud->SetUnitMovementFlags(MOVEFLAG_LEVITATING); Cloud->StopMoving(); Cloud->SetFloatValue(OBJECT_FIELD_SCALE_X, 1.0f); Cloud->setFaction(35); Cloud->SetMaxHealth(9999999); Cloud->SetHealth(9999999); Cloud->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); } ElectricalStorm_Timer = 60000; //60 seconds(bosskillers) StormCount = 1; StormSequenceTimer = 0; } else ElectricalStorm_Timer -= diff; if (SummonEagles_Timer <= diff) { me->MonsterYell(SAY_ONSUMMON, LANG_UNIVERSAL, NULL); DoPlaySoundToSet(me, SOUND_ONSUMMON); float x, y, z; me->GetPosition(x, y, z); for (uint8 i = 0; i < 8; ++i) { Unit* bird = Unit::GetUnit(*me,BirdGUIDs[i]); if (!bird) //they despawned on die { if (Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0)) { x = pTarget->GetPositionX() + irand(-10,10); y = pTarget->GetPositionY() + irand(-10,10); z = pTarget->GetPositionZ() + urand(16,20); if (z > 95) z = 95 - urand(0,5); } Creature *pCreature = me->SummonCreature(MOB_SOARING_EAGLE, x, y, z, 0, TEMPSUMMON_CORPSE_DESPAWN, 0); if (pCreature) { pCreature->AddThreat(me->getVictim(), 1.0f); pCreature->AI()->AttackStart(me->getVictim()); BirdGUIDs[i] = pCreature->GetGUID(); } } } SummonEagles_Timer = 999999; } else SummonEagles_Timer -= diff; DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 diff) { if (!UpdateVictim()) return; if (me->HasUnitState(UNIT_STATE_CASTING)) return; events.Update(diff); while (uint32 eventId = events.ExecuteEvent()) { switch (eventId) { case EVENT_BLOODY_PREY: if (Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO)) me->CastSpell(target, SPELL_BLOODY_PREY, false); events.ScheduleEvent(EVENT_BLOODY_PREY, 10000); break; case EVENT_CLAW_RIP: if (Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO)) me->CastSpell(target, SPELL_CLAW_RIP, false); events.ScheduleEvent(EVENT_CLAW_RIP, 15000); break; case EVENT_GROWL: if (Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO)) me->CastSpell(target, SPELL_GROWL, false); events.ScheduleEvent(EVENT_GROWL, 28000); break; case EVENT_ROAR_OF_COURAGE: if (Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO)) me->CastSpell(target, SPELL_ROAR_OF_COURAGE, false); events.ScheduleEvent(EVENT_ROAR_OF_COURAGE, 70000); break; case EVENT_BLOOD_CRAZED: if (Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO)) me->CastSpell(target, SPELL_BLOOD_CRAZED, false); events.ScheduleEvent(EVENT_BLOOD_CRAZED, 31000); break; case EVENT_BLOODTHIRST: if (Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO)) me->CastSpell(target, SPELL_BLOODTHIRST, false); events.ScheduleEvent(EVENT_BLOODTHIRST, 40000); break; case EVENT_CLAW_SLASH: if (Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO)) me->CastSpell(target, SPELL_CLAW_SLASH, false); events.ScheduleEvent(EVENT_CLAW_SLASH, 25000); break; case EVENT_FRENZY: if (Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO)) me->CastSpell(target, SPELL_FRENZY, false); events.ScheduleEvent(EVENT_FRENZY, 50000); break; default: break; } } DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 uiDiff) { if (!m_creature->SelectHostileTarget() || !m_creature->getVictim()) return; //START NOT TRANSFORMED if (!m_bTransformed) { //MindBlast if (m_uiMindBlast_Timer < uiDiff) { DoCastSpellIfCan(m_creature->getVictim(),SPELL_MINDBLAST); m_uiMindBlast_Timer = urand(15000, 20000); } else m_uiMindBlast_Timer -= uiDiff; //CrusadersHammer if (m_uiCrusadersHammer_Timer < uiDiff) { DoCastSpellIfCan(m_creature->getVictim(),SPELL_CRUSADERSHAMMER); m_uiCrusadersHammer_Timer = 12000; } else m_uiCrusadersHammer_Timer -= uiDiff; //CrusaderStrike if (m_uiCrusaderStrike_Timer < uiDiff) { DoCastSpellIfCan(m_creature->getVictim(),SPELL_CRUSADERSTRIKE); m_uiCrusaderStrike_Timer = 15000; } else m_uiCrusaderStrike_Timer -= uiDiff; //HolyStrike if (m_uiHolyStrike_Timer < uiDiff) { DoCastSpellIfCan(m_creature->getVictim(),SPELL_HOLYSTRIKE); m_uiHolyStrike_Timer = 15000; } else m_uiHolyStrike_Timer -= uiDiff; //BalnazzarTransform if (m_creature->GetHealthPercent() < 40.0f) { //restore hp, mana and stun if (DoCastSpellIfCan(m_creature, SPELL_BALNAZZARTRANSFORM) == CAST_OK) { m_creature->UpdateEntry(NPC_BALNAZZAR); DoScriptText(SAY_TRANSFORM, m_creature); m_bTransformed = true; } } } else { //MindBlast if (m_uiMindBlast_Timer < uiDiff) { DoCastSpellIfCan(m_creature->getVictim(),SPELL_MINDBLAST); m_uiMindBlast_Timer = urand(15000, 20000); } else m_uiMindBlast_Timer -= uiDiff; //ShadowShock if (m_uiShadowShock_Timer < uiDiff) { DoCastSpellIfCan(m_creature->getVictim(),SPELL_SHADOWSHOCK); m_uiShadowShock_Timer = 11000; } else m_uiShadowShock_Timer -= uiDiff; //PsychicScream if (m_uiPsychicScream_Timer < uiDiff) { if (Unit* pTarget = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM,0)) DoCastSpellIfCan(pTarget,SPELL_PSYCHICSCREAM); m_uiPsychicScream_Timer = 20000; } else m_uiPsychicScream_Timer -= uiDiff; //DeepSleep if (m_uiDeepSleep_Timer < uiDiff) { if (Unit *pTarget = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM,0)) DoCastSpellIfCan(pTarget,SPELL_SLEEP); m_uiDeepSleep_Timer = 15000; } else m_uiDeepSleep_Timer -= uiDiff; //MindControl if (m_uiMindControl_Timer < uiDiff) { DoCastSpellIfCan(m_creature->getVictim(),SPELL_MINDCONTROL); m_uiMindControl_Timer = 15000; } else m_uiMindControl_Timer -= uiDiff; } DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 uiDiff) { if (!UpdateVictim()) return; if (m_bIsStriking) { if (m_uiPause_Timer <= uiDiff) { if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() != CHASE_MOTION_TYPE) if (me->getVictim()) me->GetMotionMaster()->MoveChase(me->getVictim()); m_bHasTemper = false; m_bIsStriking = false; m_uiPause_Timer = 3500; } else m_uiPause_Timer -= uiDiff; return; } // When to start shatter? After 60, 40 or 20% hp? if (!m_bHasTemper && m_uiHealthAmountModifier >= 3) { if (m_uiShatteringStomp_Timer <= uiDiff) { // Should he stomp even if he has no brittle golem to shatter? Talk(SAY_STOMP); DoCast(me, SPELL_SHATTERING_STOMP_N); Talk(EMOTE_SHATTER); m_uiShatteringStomp_Timer = 30000; m_bCanShatterGolem = true; } else m_uiShatteringStomp_Timer -= uiDiff; } // Shatter Golems 3 seconds after Shattering Stomp if (m_bCanShatterGolem) { if (m_uiShatter_Timer <= uiDiff) { ShatterGolem(); m_uiShatter_Timer = 3000; m_bCanShatterGolem = false; } else m_uiShatter_Timer -= uiDiff; } // Health check if (!m_bCanShatterGolem && me->HealthBelowPct(100 - 20 * m_uiHealthAmountModifier)) { ++m_uiHealthAmountModifier; if (me->IsNonMeleeSpellCasted(false)) me->InterruptNonMeleeSpells(false); Talk(SAY_FORGE); m_bHasTemper = true; m_uiSummonPhase = 1; } switch (m_uiSummonPhase) { case 1: // 1 - Start run to Anvil Talk(EMOTE_TO_ANVIL); me->GetMotionMaster()->MoveTargetedHome(); m_uiSummonPhase = 2; // Set Next Phase break; case 2: // 2 - Check if reached Anvil // This is handled in: void JustReachedHome() break; case 3: // 3 - Cast Temper on the Anvil if (Unit* target = GetClosestCreatureWithEntry(me, NPC_VOLKHAN_ANVIL, 1000.0f, true)) { me->SetOrientation(2.29f); DoCast(target, SPELL_TEMPER, false); DoCast(target, SPELL_TEMPER_DUMMY, false); } m_uiDelay_Timer = 1000; // Delay 2 seconds before next phase can begin m_uiSummonPhase = 4; // Set Next Phase break; case 4: // 4 - Wait for delay to expire if (m_uiDelay_Timer <= uiDiff) { if (Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO, 0)) { me->SetReactState(REACT_AGGRESSIVE); me->SetInCombatWith(target); me->GetMotionMaster()->MoveFollow(target, 0.0f, 0.0f); } m_uiSummonPhase = 5; } else m_uiDelay_Timer -= uiDiff; break; case 5: // 5 - Spawn the Golems if (Creature* creatureTarget = GetClosestCreatureWithEntry(me, NPC_VOLKHAN_ANVIL, 1000.0f, true)) for (uint8 i = 0; i < MAX_GOLEM; ++i) me->CastSpell(creatureTarget, SPELL_SUMMON_MOLTEN_GOLEM, true); m_bIsStriking = true; m_uiSummonPhase = 0; // Reset back to Phase 0 for next time break; } DoMeleeAttackIfReady(); }
void UpdateAI(const uint32 uiDiff) override { if (!m_creature->SelectHostileTarget() || !m_creature->getVictim()) return; if (m_uiAbilityCount == 2) { if (m_uiPhaseChangeTimer < uiDiff) DoPhaseSwitch(); else m_uiPhaseChangeTimer -= uiDiff; } if (m_bIsTrollPhase) { if (m_uiPunctureTimer < uiDiff) { DoCastSpellIfCan(m_creature->getVictim(), m_bIsRegularMode ? SPELL_PUNCTURE : SPELL_PUNCTURE_H); m_uiPunctureTimer = 25000; } else m_uiPunctureTimer -= uiDiff; if (m_uiStampedeTimer < uiDiff) { switch (urand(0, 2)) { case 0: DoScriptText(SAY_SUMMON_1, m_creature); break; case 1: DoScriptText(SAY_SUMMON_2, m_creature); break; case 2: DoScriptText(SAY_SUMMON_3, m_creature); break; } DoCastSpellIfCan(m_creature->getVictim(), SPELL_STAMPEDE); m_uiStampedeTimer = 15000; } else m_uiStampedeTimer -= uiDiff; if (m_uiSpecialAbilityTimer < uiDiff) { if (DoCastSpellIfCan(m_creature->getVictim(), m_bIsRegularMode ? SPELL_WHIRLING_SLASH : SPELL_WHIRLING_SLASH_H) == CAST_OK) m_uiSpecialAbilityTimer = 12000; ++m_uiAbilityCount; } else m_uiSpecialAbilityTimer -= uiDiff; } else { if (m_uiEnrageTimer < uiDiff) { DoCastSpellIfCan(m_creature, m_bIsRegularMode ? SPELL_ENRAGE : SPELL_ENRAGE_H); m_uiEnrageTimer = 15000; } else m_uiEnrageTimer -= uiDiff; if (m_uiStompTimer < uiDiff) { DoCastSpellIfCan(m_creature, m_bIsRegularMode ? SPELL_STOMP : SPELL_STOMP_H); m_uiStompTimer = 10000; } else m_uiStompTimer -= uiDiff; if (m_uiSpecialAbilityTimer < uiDiff) { Unit* pTarget = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM, 1); if (!pTarget) pTarget = m_creature->getVictim(); if (DoCastSpellIfCan(pTarget, m_bIsRegularMode ? SPELL_IMPALING_CHARGE : SPELL_IMPALING_CHARGE_H) == CAST_OK) { DoScriptText(EMOTE_IMPALED, m_creature, pTarget); m_uiSpecialAbilityTimer = 12000; ++m_uiAbilityCount; } } else m_uiSpecialAbilityTimer -= uiDiff; } DoMeleeAttackIfReady(); }