Example #1
0
        void UpdateAI(const uint32 uiDiff)
        {
            npc_escortAI::UpdateAI(uiDiff);

            if (HasEscortState(STATE_ESCORT_PAUSED))
            {
                if (m_uiWave_Timer <= uiDiff)
                {
                    switch (m_uiWave)
                    {
                        case 0:
                            DoScriptText(SAY_BREAKOUT3, me);
                            SummonAcolyte(3);
                            m_uiWave_Timer = 20000;
                            break;
                        case 1:
                            DoScriptText(SAY_BREAKOUT4, me);
                            SummonAcolyte(3);
                            m_uiWave_Timer = 20000;
                            break;
                        case 2:
                            DoScriptText(SAY_BREAKOUT5, me);
                            SummonAcolyte(4);
                            m_uiWave_Timer = 20000;
                            break;
                        case 3:
                            DoScriptText(SAY_BREAKOUT6, me);
                            me->SummonCreature(NPC_HIGH_INQUISITOR_VALROTH, 1642.329f, -6045.818f, 127.583f, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 1000);
                            m_uiWave_Timer = 1000;
                            break;
                        case 4:
                        {
                            Creature* temp = Unit::GetCreature(*me, m_uiValrothGUID);

                            if (!temp || !temp->isAlive())
                            {
                                DoScriptText(SAY_BREAKOUT8, me);
                                m_uiWave_Timer = 5000;
                            }
                            else
                            {
                                m_uiWave_Timer = 2500;
                                return;                         //return, we don't want m_uiWave to increment now
                            }
                            break;
                        }
                        case 5:
                            DoScriptText(SAY_BREAKOUT9, me);
                            me->RemoveAurasDueToSpell(SPELL_ANTI_MAGIC_ZONE);
                            // i do not know why the armor will also be removed
                            m_uiWave_Timer = 2500;
                            break;
                        case 6:
                            DoScriptText(SAY_BREAKOUT10, me);
                            SetEscortPaused(false);
                            break;
                    }

                    ++m_uiWave;
                }
                else
                    m_uiWave_Timer -= uiDiff;
            }
        }
    void UpdateAI(const uint32 diff)
    {
        if (!StartCombat)
            return;

        if (IsBanished)
        {
            // Akama is set in the threatlist so when we reset, we make sure that he is not included in our check
            if (me->getThreatManager().getThreatList().size() < 2)
            {
                EnterEvadeMode();
                return;
            }

            if (DefenderTimer <= diff)
            {
                uint32 ran = rand()%2;
                Creature* Defender = me->SummonCreature(CREATURE_DEFENDER, SpawnLocations[ran].x, SpawnLocations[ran].y, Z_SPAWN, 0, TEMPSUMMON_TIMED_OR_CORPSE_DESPAWN, 25000);
                if (Defender)
                {
                    Defender->RemoveUnitMovementFlag(MOVEFLAG_WALK_MODE);
                    bool move = true;
                    if (AkamaGUID)
                    {
                        if (Creature* Akama = Unit::GetCreature(*me, AkamaGUID))
                        {
                            float x, y, z;
                            Akama->GetPosition(x,y,z);
                            // They move towards AKama
                            Defender->GetMotionMaster()->MovePoint(0, x, y, z);
                            Defender->AI()->AttackStart(Akama);
                        } else move = false;
                    } else move = false;
                    if (!move)
                        Defender->GetMotionMaster()->MovePoint(0, AKAMA_X, AKAMA_Y, AKAMA_Z);
                }
                DefenderTimer = 15000;
            } else DefenderTimer -= diff;

            if (SummonTimer <= diff)
            {
                SummonCreature();
                SummonTimer = 35000;
            } else SummonTimer -= diff;

            if (DeathCount >= 6)
            {
                if (AkamaGUID)
                {
                    Creature* Akama = Unit::GetCreature((*me), AkamaGUID);
                    if (Akama && Akama->isAlive())
                    {
                        IsBanished = false;
                        me->GetMotionMaster()->Clear(false);
                        me->GetMotionMaster()->MoveChase(Akama);
                        Akama->GetMotionMaster()->Clear();
                        // Shade should move to Akama, not the other way around
                        Akama->GetMotionMaster()->MoveIdle();
                        me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
                        // Crazy amount of threat
                        me->AddThreat(Akama, 10000000.0f);
                        Akama->AddThreat(me, 10000000.0f);
                        me->Attack(Akama, true);
                        Akama->Attack(me, true);
                    }
                }
            }
        }
        else                                                // No longer banished, let's fight Akama now
        {
            if (ReduceHealthTimer <= diff)
            {
                if (AkamaGUID)
                {
                    Creature* Akama = Unit::GetCreature((*me), AkamaGUID);
                    if (Akama && Akama->isAlive())
                    {
                        //10 % less health every few seconds.
                        me->DealDamage(Akama, Akama->GetMaxHealth()/10, NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false);
                        ReduceHealthTimer = 12000;
                    }
                }
            } else ReduceHealthTimer -= diff;

            if (HasKilledAkama)
            {
                if (!HasKilledAkamaAndReseting)//do not let players kill Shade if Akama is dead and Shade is waiting for ResetTimer!! event would bug
                {
                    HasKilledAkamaAndReseting = true;
                    me->RemoveAllAuras();
                    me->DeleteThreatList();
                    me->CombatStop();
                    //me->SetHealth(me->GetMaxHealth());
                    me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
                    me->GetMotionMaster()->MoveTargetedHome();
                }
                if (ResetTimer <= diff)
                {
                    EnterEvadeMode();// Reset a little while after killing Akama, evade and respawn Akama
                    return;
                } else ResetTimer -= diff;
            }

            DoMeleeAttackIfReady();
        }
    }
Example #3
0
 void SetData(uint32 type, uint32 data)
 {
     switch (type)
     {
     case DATA_MAGTHERIDON_EVENT:
         m_auiEncounter[0] = data;
         if (data == NOT_STARTED)
             RespawnTimer = 10000;
         if (data != IN_PROGRESS)
            HandleGameObject(DoorGUID, true);
         break;
     case DATA_CHANNELER_EVENT:
         switch (data)
         {
         case NOT_STARTED: // Reset all channelers once one is reset.
             if (m_auiEncounter[1] != NOT_STARTED)
             {
                 m_auiEncounter[1] = NOT_STARTED;
                 for (std::set<uint64>::const_iterator i = ChannelerGUID.begin(); i != ChannelerGUID.end(); ++i)
                 {
                     if (Creature* Channeler = instance->GetCreature(*i))
                     {
                         if (Channeler->isAlive())
                             Channeler->AI()->EnterEvadeMode();
                         else
                             Channeler->Respawn();
                     }
                 }
                 CageTimer = 0;
                 HandleGameObject(DoorGUID, true);
             }
             break;
         case IN_PROGRESS: // Event start.
             if (m_auiEncounter[1] != IN_PROGRESS)
             {
                 m_auiEncounter[1] = IN_PROGRESS;
                 // Let all five channelers aggro.
                 for (std::set<uint64>::const_iterator i = ChannelerGUID.begin(); i != ChannelerGUID.end(); ++i)
                 {
                     Creature* Channeler = instance->GetCreature(*i);
                     if (Channeler && Channeler->isAlive())
                         Channeler->AI()->AttackStart(Channeler->SelectNearestTarget(999));
                 }
                 // Release Magtheridon after two minutes.
                 Creature* Magtheridon = instance->GetCreature(MagtheridonGUID);
                 if (Magtheridon && Magtheridon->isAlive())
                 {
                     Magtheridon->MonsterTextEmote(EMOTE_BONDS_WEAKEN, 0);
                     CageTimer = 120000;
                 }
                 HandleGameObject(DoorGUID, false);
             }
             break;
         case DONE: // Add buff and check if all channelers are dead.
             for (std::set<uint64>::const_iterator i = ChannelerGUID.begin(); i != ChannelerGUID.end(); ++i)
             {
                 Creature* Channeler = instance->GetCreature(*i);
                 if (Channeler && Channeler->isAlive())
                 {
                     //Channeler->CastSpell(Channeler, SPELL_SOUL_TRANSFER, true);
                     data = IN_PROGRESS;
                     break;
                 }
             }
             break;
         }
         m_auiEncounter[1] = data;
         break;
     case DATA_COLLAPSE:
         // true - collapse / false - reset
         for (std::set<uint64>::const_iterator i = ColumnGUID.begin(); i != ColumnGUID.end(); ++i)
             DoUseDoorOrButton(*i);
         break;
     default:
         break;
     }
 }
Example #4
0
        void UpdateAI(const uint32 diff)
        {
            if (EventInProgress) {
                Player* pWarrior = NULL;

                if (PlayerGUID)
                    pWarrior = Unit::GetPlayer(*me, PlayerGUID);

                if (!pWarrior)
                    return;

                if (!pWarrior->isAlive() && pWarrior->GetQuestStatus(1719) == QUEST_STATUS_INCOMPLETE) {
                    EventInProgress = false;
                    DoScriptText(SAY_TWIGGY_FLATHEAD_DOWN, me);
                    pWarrior->FailQuest(1719);

                    for (uint8 i = 0; i < 6; ++i)
                    {
                        if (AffrayChallenger[i])
                        {
                            Creature* creature = Unit::GetCreature((*me), AffrayChallenger[i]);
                            if (creature) {
                                if (creature->isAlive())
                                {
                                    creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_IN_COMBAT);
                                    creature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
                                    creature->setDeathState(JUST_DIED);
                                }
                            }
                        }
                        AffrayChallenger[i] = 0;
                        Challenger_down[i] = false;
                    }

                    if (BigWill)
                    {
                        Creature* creature = Unit::GetCreature((*me), BigWill);
                        if (creature) {
                            if (creature->isAlive()) {
                                creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_IN_COMBAT);
                                creature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
                                creature->setDeathState(JUST_DIED);
                            }
                        }
                    }
                    BigWill = 0;
                }

                if (!EventGrate && EventInProgress)
                {
                    float x, y, z;
                    pWarrior->GetPosition(x, y, z);

                    if (x >= -1684 && x <= -1674 && y >= -4334 && y <= -4324) {
                        pWarrior->AreaExploredOrEventHappens(1719);
                        DoScriptText(SAY_TWIGGY_FLATHEAD_BEGIN, me);

                        for (uint8 i = 0; i < 6; ++i)
                        {
                            Creature* creature = me->SummonCreature(NPC_AFFRAY_CHALLENGER, AffrayChallengerLoc[i][0], AffrayChallengerLoc[i][1], AffrayChallengerLoc[i][2], AffrayChallengerLoc[i][3], TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 600000);
                            if (!creature)
                                continue;
                            creature->setFaction(35);
                            creature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
                            creature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
                            creature->HandleEmoteCommand(EMOTE_ONESHOT_ROAR);
                            AffrayChallenger[i] = creature->GetGUID();
                        }
                        Wave_Timer = 5000;
                        Challenger_checker = 1000;
                        EventGrate = true;
                    }
                }
                else if (EventInProgress)
                {
                    if (Challenger_checker <= diff)
                    {
                        for (uint8 i = 0; i < 6; ++i)
                        {
                            if (AffrayChallenger[i])
                            {
                                Creature* creature = Unit::GetCreature((*me), AffrayChallenger[i]);
                                if ((!creature || (!creature->isAlive())) && !Challenger_down[i])
                                {
                                    DoScriptText(SAY_TWIGGY_FLATHEAD_DOWN, me);
                                    Challenger_down[i] = true;
                                }
                            }
                        }
                        Challenger_checker = 1000;
                    } else Challenger_checker -= diff;

                    if (Wave_Timer <= diff)
                    {
                        if (Wave < 6 && AffrayChallenger[Wave] && !EventBigWill)
                        {
                            DoScriptText(SAY_TWIGGY_FLATHEAD_FRAY, me);
                            Creature* creature = Unit::GetCreature((*me), AffrayChallenger[Wave]);
                            if (creature && (creature->isAlive()))
                            {
                                creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
                                creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
                                creature->HandleEmoteCommand(EMOTE_ONESHOT_ROAR);
                                creature->setFaction(14);
                                creature->AI()->AttackStart(pWarrior);
                                ++Wave;
                                Wave_Timer = 20000;
                            }
                        }
                        else if (Wave >= 6 && !EventBigWill) {
                            if (Creature* creature = me->SummonCreature(NPC_BIG_WILL, -1722, -4341, 6.12f, 6.26f, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 480000))
                            {
                                BigWill = creature->GetGUID();
                                //creature->GetMotionMaster()->MovePoint(0, -1693, -4343, 4.32f);
                                //creature->GetMotionMaster()->MovePoint(1, -1684, -4333, 2.78f);
                                creature->GetMotionMaster()->MovePoint(2, -1682, -4329, 2.79f);
                                creature->HandleEmoteCommand(EMOTE_STATE_READYUNARMED);
                                EventBigWill = true;
                                Wave_Timer = 1000;
                            }
                        }
                        else if (Wave >= 6 && EventBigWill && BigWill)
                        {
                            Creature* creature = Unit::GetCreature((*me), BigWill);
                            if (!creature || !creature->isAlive())
                            {
                                DoScriptText(SAY_TWIGGY_FLATHEAD_OVER, me);
                                EventInProgress = false;
                                EventBigWill = false;
                                EventGrate = false;
                                PlayerGUID = 0;
                                Wave = 0;
                            }
                        }
                    } else Wave_Timer -= diff;
                }
            }
        }
Example #5
0
	/**HandleNpcSetMoveTypeCommand
	 * Set the movement type for an NPC.<br/>
	 * <br/>
	 * Valid movement types are:
	 * <ul>
	 * <li> stay - NPC wont move </li>
	 * <li> random - NPC will move randomly according to the spawndist </li>
	 * <li> way - NPC will move with given waypoints set </li>
	 * </ul>
	 * additional parameter: NODEL - so no waypoints are deleted, if you
	 *                       change the movement type
	 */
	static bool HandleNpcSetMoveTypeCommand(ChatHandler* handler,
			const char* args) {
		if (!*args)
			return false;

		// 3 arguments:
		// GUID (optional - you can also select the creature)
		// stay|random|way (determines the kind of movement)
		// NODEL (optional - tells the system NOT to delete any waypoints)
		//        this is very handy if you want to do waypoints, that are
		//        later switched on/off according to special events (like escort
		//        quests, etc)
		char* guid_str = strtok((char*) args, " ");
		char* type_str = strtok((char*) NULL, " ");
		char* dontdel_str = strtok((char*) NULL, " ");

		bool doNotDelete = false;

		if (!guid_str)
			return false;

		uint32 lowguid = 0;
		Creature* pCreature = NULL;

		if (dontdel_str) {
			//sLog->outError("DEBUG: All 3 params are set");

			// All 3 params are set
			// GUID
			// type
			// doNotDEL
			if (stricmp(dontdel_str, "NODEL") == 0) {
				//sLog->outError("DEBUG: doNotDelete = true;");
				doNotDelete = true;
			}
		} else {
			// Only 2 params - but maybe NODEL is set
			if (type_str) {
				sLog->outError("DEBUG: Only 2 params ");
				if (stricmp(type_str, "NODEL") == 0) {
					//sLog->outError("DEBUG: type_str, NODEL ");
					doNotDelete = true;
					type_str = NULL;
				}
			}
		}

		if (!type_str) // case .setmovetype $move_type (with selected creature)
		{
			type_str = guid_str;
			pCreature = handler->getSelectedCreature();
			if (!pCreature || pCreature->isPet())
				return false;
			lowguid = pCreature->GetDBTableGUIDLow();
		} else // case .setmovetype #creature_guid $move_type (with selected creature)
		{
			lowguid = atoi((char*) guid_str);

			/* impossible without entry
			 if (lowguid)
			 pCreature = ObjectAccessor::GetCreature(*handler->GetSession()->GetPlayer(),MAKE_GUID(lowguid,HIGHGUID_UNIT));
			 */

			// attempt check creature existence by DB data
			if (!pCreature) {
				CreatureData const* data = sObjectMgr->GetCreatureData(lowguid);
				if (!data) {
					handler->PSendSysMessage(LANG_COMMAND_CREATGUIDNOTFOUND,
							lowguid);
					handler->SetSentErrorMessage(true);
					return false;
				}
			} else {
				lowguid = pCreature->GetDBTableGUIDLow();
			}
		}

		// now lowguid is low guid really existed creature
		// and pCreature point (maybe) to this creature or NULL

		MovementGeneratorType move_type;

		std::string type = type_str;

		if (type == "stay")
			move_type = IDLE_MOTION_TYPE;
		else if (type == "random")
			move_type = RANDOM_MOTION_TYPE;
		else if (type == "way")
			move_type = WAYPOINT_MOTION_TYPE;
		else
			return false;

		// update movement type
		//if (doNotDelete == false)
		//    WaypointMgr.DeletePath(lowguid);

		if (pCreature) {
			// update movement type
			if (doNotDelete == false)
				pCreature->LoadPath(0);

			pCreature->SetDefaultMovementType(move_type);
			pCreature->GetMotionMaster()->Initialize();
			if (pCreature->isAlive()) // dead creature will reset movement generator at respawn
			{
				pCreature->setDeathState(JUST_DIED);
				pCreature->Respawn();
			}
			pCreature->SaveToDB();
		}
		if (doNotDelete == false) {
			handler->PSendSysMessage(LANG_MOVE_TYPE_SET, type_str);
		} else {
			handler->PSendSysMessage(LANG_MOVE_TYPE_SET_NODEL, type_str);
		}

		return true;
	}
        bool OnGossipSelect(Player* player, Creature* creature, uint32 /*sender*/, uint32 /*action*/)
        {
            player->PlayerTalkClass->ClearMenus();
            player->CLOSE_GOSSIP_MENU();
            InstanceScript* instance = creature->GetInstanceScript();
            if (!instance)
                return true;

            if (instance->GetBossState(BOSS_BEASTS) != DONE)
            {
                instance->SetData(TYPE_EVENT, 110);
                instance->SetData(TYPE_NORTHREND_BEASTS, NOT_STARTED);
                instance->SetBossState(BOSS_BEASTS, NOT_STARTED);
            }
            else if (instance->GetBossState(BOSS_JARAXXUS) != DONE)
            {
                // if Jaraxxus is spawned, but the raid wiped
                if (Creature* jaraxxus = Unit::GetCreature(*player, instance->GetData64(NPC_JARAXXUS)))
                {
                    jaraxxus->RemoveAurasDueToSpell(SPELL_JARAXXUS_CHAINS);
                    jaraxxus->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
                    jaraxxus->SetReactState(REACT_DEFENSIVE);
                    jaraxxus->SetInCombatWithZone();
                }
                else
                {
                    instance->SetData(TYPE_EVENT, 1010);
                    instance->SetBossState(BOSS_JARAXXUS, NOT_STARTED);
                }
            }
            else if (instance->GetBossState(BOSS_CRUSADERS) != DONE)
            {
                if (player->GetTeam() == ALLIANCE)
                    instance->SetData(TYPE_EVENT, 3000);
                else
                    instance->SetData(TYPE_EVENT, 3001);
                instance->SetBossState(BOSS_CRUSADERS, NOT_STARTED);
            }
            else if (instance->GetBossState(BOSS_VALKIRIES) != DONE)
            {
                instance->SetData(TYPE_EVENT, 4000);
                instance->SetBossState(BOSS_VALKIRIES, NOT_STARTED);
            }
            else if (instance->GetBossState(BOSS_LICH_KING) != DONE)
            {
                if (GameObject* floor = GameObject::GetGameObject(*player, instance->GetData64(GO_ARGENT_COLISEUM_FLOOR)))
                    floor->SetDestructibleState(GO_DESTRUCTIBLE_DAMAGED);

                creature->CastSpell(creature, SPELL_CORPSE_TELEPORT, false);
                creature->CastSpell(creature, SPELL_DESTROY_FLOOR_KNOCKUP, false);

                Creature* anubArak = Unit::GetCreature(*creature, instance->GetData64(NPC_ANUBARAK));
                if (!anubArak || !anubArak->isAlive())
                    anubArak = creature->SummonCreature(NPC_ANUBARAK, AnubarakLoc[0].GetPositionX(), AnubarakLoc[0].GetPositionY(), AnubarakLoc[0].GetPositionZ(), 3, TEMPSUMMON_CORPSE_TIMED_DESPAWN, DESPAWN_TIME);

                instance->SetBossState(BOSS_ANUBARAK, NOT_STARTED);

                if (creature->IsVisible())
                    creature->SetVisible(false);
            }
            creature->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
            return true;
        }
        void UpdateAI(const uint32 diff)
        {
            //Only if not incombat check if the event is started
            if (!me->isInCombat() && pInstance && pInstance->GetData(DATA_KARATHRESSEVENT))
            {
                Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_KARATHRESSEVENT_STARTER));

                if (pTarget)
                {
                    AttackStart(pTarget);
                    GetAdvisors();
                }
            }

            //Return since we have no target
            if (!UpdateVictim())
                return;

            //someone evaded!
            if (pInstance && !pInstance->GetData(DATA_KARATHRESSEVENT))
            {
                EnterEvadeMode();
                return;
            }

            //CataclysmicBolt_Timer
            if (CataclysmicBolt_Timer <= diff)
            {
                //select a random unit other than the main tank
                Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM, 1);

                //if there aren't other units, cast on the tank
                if (!pTarget)
                    pTarget = me->getVictim();

                if (pTarget)
                    DoCast(pTarget, SPELL_CATACLYSMIC_BOLT);
                CataclysmicBolt_Timer = 10000;
            } else CataclysmicBolt_Timer -= diff;

            //SearNova_Timer
            if (SearNova_Timer <= diff)
            {
                DoCast(me->getVictim(), SPELL_SEAR_NOVA);
                SearNova_Timer = 20000+rand()%40000;
            } else SearNova_Timer -= diff;

            //Enrage_Timer
            if (Enrage_Timer <= diff)
            {
                DoCast(me, SPELL_ENRAGE);
                Enrage_Timer = 90000;
            } else Enrage_Timer -= diff;

            //Blessing of Tides Trigger
            if (!HealthAbovePct(75) && !BlessingOfTides)
            {
                BlessingOfTides = true;
                bool continueTriggering = false;
                Creature* Advisor;
                for (uint8 i = 0; i < MAX_ADVISORS; ++i)
                    if (Advisors[i])
                    {
                        Advisor = (Unit::GetCreature(*me, Advisors[i]));
                        if (Advisor && Advisor->isAlive())
                        {
                            continueTriggering = true;
                            break;
                        }
                    }
                if (continueTriggering)
                {
                    DoCast(me, SPELL_BLESSING_OF_THE_TIDES);
                    me->MonsterYell(SAY_GAIN_BLESSING_OF_TIDES, LANG_UNIVERSAL, NULL);
                    DoPlaySoundToSet(me, SOUND_GAIN_BLESSING_OF_TIDES);
                }
            }

            DoMeleeAttackIfReady();
        }
Example #8
0
void WorldSession::DoLootRelease(ObjectGuid lguid)
{
    Player*  player = GetPlayer();
    Loot*    loot;

    player->SetLootGuid(ObjectGuid());
    player->SendLootRelease(lguid);

    player->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_LOOTING);

    if (!player->IsInWorld())
        return;

    switch (lguid.GetHigh())
    {
        case HIGHGUID_GAMEOBJECT:
        {
            GameObject* go = GetPlayer()->GetMap()->GetGameObject(lguid);

            // not check distance for GO in case owned GO (fishing bobber case, for example) or Fishing hole GO
            if (!go || ((go->GetOwnerGuid() != _player->GetObjectGuid() && go->GetGoType() != GAMEOBJECT_TYPE_FISHINGHOLE) && !go->IsWithinDistInMap(_player, INTERACTION_DISTANCE)))
                return;

            loot = &go->loot;

            if (go->GetGoType() == GAMEOBJECT_TYPE_DOOR)
            {
                // locked doors are opened with spelleffect openlock, prevent remove its as looted
                go->UseDoorOrButton();
            }
            else if (loot->isLooted() || go->GetGoType() == GAMEOBJECT_TYPE_FISHINGNODE)
            {
                // GO is mineral vein? so it is not removed after its looted
                if (go->GetGoType() == GAMEOBJECT_TYPE_CHEST)
                {
                    uint32 go_min = go->GetGOInfo()->chest.minSuccessOpens;
                    uint32 go_max = go->GetGOInfo()->chest.maxSuccessOpens;

                    // only vein pass this check
                    if (go_min != 0 && go_max > go_min)
                    {
                        float amount_rate = sWorld.getConfig(CONFIG_FLOAT_RATE_MINING_AMOUNT);
                        float min_amount = go_min * amount_rate;
                        float max_amount = go_max * amount_rate;

                        go->AddUse();
                        float uses = float(go->GetUseCount());

                        if (uses < max_amount)
                        {
                            if (uses >= min_amount)
                            {
                                float chance_rate = sWorld.getConfig(CONFIG_FLOAT_RATE_MINING_NEXT);

                                int32 ReqValue = 175;
                                LockEntry const* lockInfo = sLockStore.LookupEntry(go->GetGOInfo()->chest.lockId);
                                if (lockInfo)
                                    ReqValue = lockInfo->Skill[0];
                                float skill = float(player->GetSkillValue(SKILL_MINING)) / (ReqValue + 25);
                                double chance = pow(0.8 * chance_rate, 4 * (1 / double(max_amount)) * double(uses));
                                if (roll_chance_f(float(100.0f * chance + skill)))
                                {
                                    go->SetLootState(GO_READY);
                                }
                                else                        // not have more uses
                                    go->SetLootState(GO_JUST_DEACTIVATED);
                            }
                            else                            // 100% chance until min uses
                                go->SetLootState(GO_READY);
                        }
                        else                                // max uses already
                            go->SetLootState(GO_JUST_DEACTIVATED);
                    }
                    else                                    // not vein
                        go->SetLootState(GO_JUST_DEACTIVATED);
                }
                else if (go->GetGoType() == GAMEOBJECT_TYPE_FISHINGHOLE)
                {
                    // The fishing hole used once more
                    go->AddUse();                           // if the max usage is reached, will be despawned at next tick
                    if (go->GetUseCount() >= urand(go->GetGOInfo()->fishinghole.minSuccessOpens, go->GetGOInfo()->fishinghole.maxSuccessOpens))
                    {
                        go->SetLootState(GO_JUST_DEACTIVATED);
                    }
                    else
                        go->SetLootState(GO_READY);
                }
                else // not chest (or vein/herb/etc)
                    go->SetLootState(GO_JUST_DEACTIVATED);

                loot->clear();
            }
            else
                // not fully looted object
                go->SetLootState(GO_ACTIVATED);
            break;
        }
        case HIGHGUID_CORPSE:                               // ONLY remove insignia at BG
        {
            Corpse* corpse = _player->GetMap()->GetCorpse(lguid);
            if (!corpse || !corpse->IsWithinDistInMap(_player, INTERACTION_DISTANCE))
                return;

            loot = &corpse->loot;

            if (loot->isLooted())
            {
                loot->clear();
                corpse->RemoveFlag(CORPSE_FIELD_DYNAMIC_FLAGS, CORPSE_DYNFLAG_LOOTABLE);
            }
            break;
        }
        case HIGHGUID_ITEM:
        {
            Item* pItem = player->GetItemByGuid(lguid);
            if (!pItem)
                return;

            switch (pItem->loot.loot_type)
            {
                    // temporary loot in stacking items, clear loot state, no auto loot move
                case LOOT_PROSPECTING:
                {
                    uint32 count = pItem->GetCount();

                    // >=5 checked in spell code, but will work for cheating cases also with removing from another stacks.
                    if (count > 5)
                        count = 5;

                    // reset loot for allow repeat looting if stack > 5
                    pItem->loot.clear();
                    pItem->SetLootState(ITEM_LOOT_REMOVED);

                    player->DestroyItemCount(pItem, count, true);
                    break;
                }
                // temporary loot, auto loot move
                case LOOT_DISENCHANTING:
                {
                    if (!pItem->loot.isLooted())
                        player->AutoStoreLoot(pItem->loot); // can be lost if no space
                    pItem->loot.clear();
                    pItem->SetLootState(ITEM_LOOT_REMOVED);
                    player->DestroyItem(pItem->GetBagSlot(), pItem->GetSlot(), true);
                    break;
                }
                // normal persistence loot
                default:
                {
                    // must be destroyed only if no loot
                    if (pItem->loot.isLooted())
                    {
                        pItem->SetLootState(ITEM_LOOT_REMOVED);
                        player->DestroyItem(pItem->GetBagSlot(), pItem->GetSlot(), true);
                    }
                    break;
                }
            }
            return;                                         // item can be looted only single player
        }
        case HIGHGUID_UNIT:
        {
            Creature* pCreature = GetPlayer()->GetMap()->GetCreature(lguid);

            bool ok_loot = pCreature && pCreature->isAlive() == (player->getClass() == CLASS_ROGUE && pCreature->lootForPickPocketed);
            if (!ok_loot || !pCreature->IsWithinDistInMap(_player, INTERACTION_DISTANCE))
                return;

            loot = &pCreature->loot;

            // update next looter
            if (Group* group = pCreature->GetGroupLootRecipient())
                if (group->GetLooterGuid() == player->GetObjectGuid())
                    group->UpdateLooterGuid(pCreature);

            if (loot->isLooted() && !pCreature->isAlive())
            {
                // for example skinning after normal loot
                pCreature->PrepareBodyLootState();
                pCreature->AllLootRemovedFromCorpse();
            }
            break;
        }
        default:
        {
            sLog.outError("%s is unsupported for looting.", lguid.GetString().c_str());
            return;
        }
    }

    // Player is not looking at loot list, he doesn't need to see updates on the loot list
    loot->RemoveLooter(player->GetObjectGuid());
}
Example #9
0
void WorldSession::HandleAutostoreLootItemOpcode(WorldPacket& recv_data)
{
    DEBUG_LOG("WORLD: CMSG_AUTOSTORE_LOOT_ITEM");
    Player*  player =   GetPlayer();
    ObjectGuid lguid = player->GetLootGuid();
    Loot*    loot;
    uint8    lootSlot;
    Item* pItem = NULL;

    recv_data >> lootSlot;

    switch (lguid.GetHigh())
    {
        case HIGHGUID_GAMEOBJECT:
        {
            GameObject* go = player->GetMap()->GetGameObject(lguid);

            // not check distance for GO in case owned GO (fishing bobber case, for example) or Fishing hole GO
            if (!go || ((go->GetOwnerGuid() != _player->GetObjectGuid() && go->GetGoType() != GAMEOBJECT_TYPE_FISHINGHOLE) && !go->IsWithinDistInMap(_player, INTERACTION_DISTANCE)))
            {
                player->SendLootRelease(lguid);
                return;
            }

            loot = &go->loot;
            break;
        }
        case HIGHGUID_ITEM:
        {
            pItem = player->GetItemByGuid(lguid);

            if (!pItem || !pItem->HasGeneratedLoot())
            {
                player->SendLootRelease(lguid);
                return;
            }

            loot = &pItem->loot;
            break;
        }
        case HIGHGUID_CORPSE:
        {
            Corpse* bones = player->GetMap()->GetCorpse(lguid);
            if (!bones)
            {
                player->SendLootRelease(lguid);
                return;
            }
            loot = &bones->loot;
            break;
        }
        case HIGHGUID_UNIT:
        {
            Creature* pCreature = GetPlayer()->GetMap()->GetCreature(lguid);

            bool ok_loot = pCreature && pCreature->isAlive() == (player->getClass() == CLASS_ROGUE && pCreature->lootForPickPocketed);

            if (!ok_loot || !pCreature->IsWithinDistInMap(_player, INTERACTION_DISTANCE))
            {
                player->SendLootRelease(lguid);
                return;
            }

            loot = &pCreature->loot;
            break;
        }
        default:
        {
            sLog.outError("%s is unsupported for looting.", lguid.GetString().c_str());
            return;
        }
    }

    QuestItem* qitem = NULL;
    QuestItem* ffaitem = NULL;
    QuestItem* conditem = NULL;

    LootItem* item = loot->LootItemInSlot(lootSlot, player, &qitem, &ffaitem, &conditem);

    if (!item)
    {
        player->SendEquipError(EQUIP_ERR_ALREADY_LOOTED, NULL, NULL);
        return;
    }

    // questitems use the blocked field for other purposes
    if (!qitem && item->is_blocked)
    {
        player->SendLootRelease(lguid);
        return;
    }

    if (pItem)
        pItem->SetLootState(ITEM_LOOT_CHANGED);

    ItemPosCountVec dest;
    InventoryResult msg = player->CanStoreNewItem(NULL_BAG, NULL_SLOT, dest, item->itemid, item->count);
    if (msg == EQUIP_ERR_OK)
    {
        Item* newitem = player->StoreNewItem(dest, item->itemid, true, item->randomPropertyId);

        if (qitem)
        {
            qitem->is_looted = true;
            // freeforall is 1 if everyone's supposed to get the quest item.
            if (item->freeforall || loot->GetPlayerQuestItems().size() == 1)
                player->SendNotifyLootItemRemoved(lootSlot);
            else
                loot->NotifyQuestItemRemoved(qitem->index);
        }
        else
        {
            if (ffaitem)
            {
                // freeforall case, notify only one player of the removal
                ffaitem->is_looted = true;
                player->SendNotifyLootItemRemoved(lootSlot);
            }
            else
            {
                // not freeforall, notify everyone
                if (conditem)
                    conditem->is_looted = true;
                loot->NotifyItemRemoved(lootSlot);
            }
        }

        // if only one person is supposed to loot the item, then set it to looted
        if (!item->freeforall)
            item->is_looted = true;

        --loot->unlootedCount;

        player->SendNewItem(newitem, uint32(item->count), false, false, true);
    }
    else
        player->SendEquipError(msg, NULL, NULL, item->itemid);
}
Example #10
0
        void UpdateAI(uint32 uiDiff)
        {
            npc_escortAI::UpdateAI(uiDiff);

            if (HasEscortState(STATE_ESCORT_PAUSED))
            {
                if (waveTimer <= uiDiff)
                {
                    switch (wave)
                    {
                        case 0:
                            Talk(SAY_BREAKOUT3);
                            SummonAcolyte(3);
                            waveTimer = 20000;
                            break;
                        case 1:
                            Talk(SAY_BREAKOUT4);
                            SummonAcolyte(3);
                            waveTimer = 20000;
                            break;
                        case 2:
                            Talk(SAY_BREAKOUT5);
                            SummonAcolyte(4);
                            waveTimer = 20000;
                            break;
                        case 3:
                            Talk(SAY_BREAKOUT6);
                            me->SummonCreature(NPC_HIGH_INQUISITOR_VALROTH, 1642.329f, -6045.818f, 127.583f, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 1000);
                            waveTimer = 1000;
                            break;
                        case 4:
                        {
                            Creature* temp = Unit::GetCreature(*me, valrothGUID);

                            if (!temp || !temp->isAlive())
                            {
                                Talk(SAY_BREAKOUT8);
                                waveTimer = 5000;
                            }
                            else
                            {
                                waveTimer = 2500;
                                return;
                            }
                            break;
                        }
                        case 5:
                            Talk(SAY_BREAKOUT9);
                            me->RemoveAurasDueToSpell(SPELL_ANTI_MAGIC_ZONE);
                            me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
                            waveTimer = 2500;
                            break;
                        case 6:
                            Talk(SAY_BREAKOUT10);
                            SetEscortPaused(false);
                            break;
                    }

                    ++wave;
                }
                else
                    waveTimer -= uiDiff;
            }
        }
Example #11
0
void WorldSession::HandleLootMoneyOpcode(WorldPacket & /*recv_data*/)
{
    DEBUG_LOG("WORLD: CMSG_LOOT_MONEY");

    Player* player = GetPlayer();
    ObjectGuid guid = player->GetLootGuid();
    if (!guid)
        return;

    Loot* pLoot = NULL;
    Item* pItem = NULL;

    switch (guid.GetHigh())
    {
        case HIGHGUID_GAMEOBJECT:
        {
            GameObject* pGameObject = GetPlayer()->GetMap()->GetGameObject(guid);

            // not check distance for GO in case owned GO (fishing bobber case, for example)
            if (pGameObject && (pGameObject->GetOwnerGuid() == _player->GetObjectGuid() || pGameObject->IsWithinDistInMap(_player, INTERACTION_DISTANCE)))
                pLoot = &pGameObject->loot;

            break;
        }
        case HIGHGUID_CORPSE:                               // remove insignia ONLY in BG
        {
            Corpse* bones = _player->GetMap()->GetCorpse(guid);

            if (bones && bones->IsWithinDistInMap(_player, INTERACTION_DISTANCE))
                pLoot = &bones->loot;

            break;
        }
        case HIGHGUID_ITEM:
        {
            pItem = GetPlayer()->GetItemByGuid(guid);
            if (!pItem || !pItem->HasGeneratedLoot())
                return;

            pLoot = &pItem->loot;
            break;
        }
        case HIGHGUID_UNIT:
        {
            Creature* pCreature = GetPlayer()->GetMap()->GetCreature(guid);

            bool ok_loot = pCreature && pCreature->isAlive() == (player->getClass() == CLASS_ROGUE && pCreature->lootForPickPocketed);

            if (ok_loot && pCreature->IsWithinDistInMap(_player, INTERACTION_DISTANCE))
                pLoot = &pCreature->loot ;

            break;
        }
        default:
            return;                                         // unlootable type
    }

    if (pLoot)
    {
        pLoot->NotifyMoneyRemoved();

        if (!guid.IsItem() && player->GetGroup())           // item can be looted only single player
        {
            Group* group = player->GetGroup();

            std::vector<Player*> playersNear;
            for (GroupReference* itr = group->GetFirstMember(); itr != NULL; itr = itr->next())
            {
                Player* playerGroup = itr->getSource();
                if (!playerGroup)
                    continue;
                if (player->IsWithinDistInMap(playerGroup, sWorld.getConfig(CONFIG_FLOAT_GROUP_XP_DISTANCE), false))
                    playersNear.push_back(playerGroup);
            }

            uint32 money_per_player = uint32((pLoot->gold) / (playersNear.size()));

            for (std::vector<Player*>::const_iterator i = playersNear.begin(); i != playersNear.end(); ++i)
            {
                (*i)->ModifyMoney(money_per_player);

                WorldPacket data(SMSG_LOOT_MONEY_NOTIFY, 4);
                data << uint32(money_per_player);

                (*i)->GetSession()->SendPacket(&data);
            }
        }
        else
            player->ModifyMoney(pLoot->gold);

        pLoot->gold = 0;

        if (pItem)
            pItem->SetLootState(ITEM_LOOT_CHANGED);
    }
}
Example #12
0
        void UpdateAI(const uint32 diff)
        {
            if (!UpdateVictim())
                return;

            if (Fireball_Timer <= diff)
            {
                if (Unit* pVictim = SelectUnit(SELECT_TARGET_RANDOM,0))
                    DoCast(pVictim, DUNGEON_MODE(SPELL_FIREBALL, SPELL_FIREBALL_H), true);
                Fireball_Timer = urand(4000,7000);
            }
            else
                Fireball_Timer -= diff;

            if (flight) // phase 1 - the flight
            {
                Creature *Vazruden = Unit::GetCreature(*me,VazrudenGUID);
                if (Fly_Timer < diff || !(Vazruden && Vazruden->isAlive() && Vazruden->HealthAbovePct(20)))
                {
                    flight = false;
                    BellowingRoar_Timer = 6000;
                    ConeOfFire_Timer = 12000;
                    me->RemoveUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
                    me->AddUnitMovementFlag(MOVEMENTFLAG_WALKING);
                    me->GetMotionMaster()->Clear();
                    if (Unit* pVictim = SelectUnit(SELECT_TARGET_NEAREST,0))
                        me->AI()->AttackStart(pVictim);
                    DoStartMovement(me->getVictim());
                    DoScriptText(EMOTE, me);
                    return;
                }
                else
                    Fly_Timer -= diff;

                if (Turn_Timer <= diff)
                {
                    uint32 waypoint = (Fly_Timer/10000)%2;
                    if (!me->IsWithinDist3d(VazrudenRing[waypoint][0],VazrudenRing[waypoint][1],VazrudenRing[waypoint][2], 5))
                        me->GetMotionMaster()->MovePoint(0,VazrudenRing[waypoint][0],VazrudenRing[waypoint][1],VazrudenRing[waypoint][2]);
                    Turn_Timer = 10000;
                }
                else
                    Turn_Timer -= diff;
            }
            else // phase 2 - land fight
            {
                if (ConeOfFire_Timer <= diff)
                {
                    DoCast(me, DUNGEON_MODE(SPELL_CONE_OF_FIRE, SPELL_CONE_OF_FIRE_H));
                    ConeOfFire_Timer = 12000;
                    Fireball_Timer = 4000;
                }
                else
                    ConeOfFire_Timer -= diff;

                if (IsHeroic())
                {
                    if (BellowingRoar_Timer <= diff)
                    {
                        DoCast(me, SPELL_BELLOWING_ROAR);
                        BellowingRoar_Timer = 45000;
                    }
                    else
                        BellowingRoar_Timer -= diff;
                }

                DoMeleeAttackIfReady();
            }
        }
Example #13
0
    void UpdateAI(const uint32 diff)
    {
        if (!pInstance)
            return;

        if (MobDeath_Timer)
        {
            if (MobDeath_Timer <= diff)
            {
                MobDeath_Timer = 2500;

                if (RingBossGUID)
                {
                    Creature *boss = Unit::GetCreature(*me,RingBossGUID);
                    if (boss && !boss->isAlive() && boss->isDead())
                    {
                        RingBossGUID = 0;
                        Event_Timer = 5000;
                        MobDeath_Timer = 0;
                        return;
                    }
                    return;
                }

                for (uint8 i = 0; i < MAX_MOB_AMOUNT; ++i)
                {
                    Creature *mob = Unit::GetCreature(*me,RingMobGUID[i]);
                    if (mob && !mob->isAlive() && mob->isDead())
                    {
                        RingMobGUID[i] = 0;
                        --MobCount;

                        //seems all are gone, so set timer to continue and discontinue this
                        if (!MobCount)
                        {
                            Event_Timer = 5000;
                            MobDeath_Timer = 0;
                        }
                    }
                }
            } else MobDeath_Timer -= diff;
        }

        if (Event_Timer)
        {
            if (Event_Timer <= diff)
            {
                switch(EventPhase)
                {
                case 0:
                    DoScriptText(SCRIPT_TEXT5, me);//1
                    HandleGameObject(DATA_ARENA4, false);
                    Start(false, false);
                    CanWalk = true;
                    Event_Timer = 0;
                    break;
                case 1:
                    CanWalk = true;
                    Event_Timer = 0;
                    break;
                case 2:
                    Event_Timer = 2000;
                    break;
                case 3:
                    HandleGameObject(DATA_ARENA1, true);
                    Event_Timer = 3000;
                    break;
                case 4:
                    CanWalk = true;
                    me->SetVisibility(VISIBILITY_OFF);
                    SummonRingMob();
                    Event_Timer = 8000;
                    break;
                case 5:
                    SummonRingMob();
                    SummonRingMob();
                    Event_Timer = 8000;
                    break;
                case 6:
                    SummonRingMob();
                    Event_Timer = 0;
                    break;
                case 7:
                    me->SetVisibility(VISIBILITY_ON);
                    HandleGameObject(DATA_ARENA1, false);
                    DoScriptText(SCRIPT_TEXT6, me);//4
                    CanWalk = true;
                    Event_Timer = 0;
                    break;
                case 8:
                    HandleGameObject(DATA_ARENA2, true);
                    Event_Timer = 5000;
                    break;
                case 9:
                    me->SetVisibility(VISIBILITY_OFF);
                    SummonRingBoss();
                    Event_Timer = 0;
                    break;
                case 10:
                    //if quest, complete
                    HandleGameObject(DATA_ARENA2, false);
                    HandleGameObject(DATA_ARENA3, true);
                    HandleGameObject(DATA_ARENA4, true);
                    CanWalk = true;
                    Event_Timer = 0;
                    break;
                }
                ++EventPhase;
            } else Event_Timer -= diff;
        }

        if (CanWalk)
            npc_escortAI::UpdateAI(diff);
       }
Example #14
0
    void UpdateAI(const uint32 diff)
    {
        if (!m_creature->SelectHostileTarget() || !m_creature->getVictim())
            return;

        //Only do this if we haven't spawned nef yet
        if (SpawnedAdds < 42)
        {
            //ShadowBoltTimer
            if (ShadowBoltTimer < diff)
            {
                Unit* target = NULL;
                target = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM,0);
                if (target)
                    DoCastSpellIfCan(target,SPELL_SHADOWBOLT);

                ShadowBoltTimer = urand(3000, 10000);
            }else ShadowBoltTimer -= diff;

            //FearTimer
            if (FearTimer < diff)
            {
                Unit* target = NULL;
                target = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM,0);
                if (target)
                    DoCastSpellIfCan(target,SPELL_FEAR);

                FearTimer = urand(10000, 20000);
            }else FearTimer -= diff;

            //Add spawning mechanism
            if (AddSpawnTimer < diff)
            {
                //Spawn 2 random types of creatures at the 2 locations
                uint32 CreatureID;
                Creature* Spawned = NULL;
                Unit* target = NULL;

                //1 in 3 chance it will be a chromatic
                if (!urand(0, 2))
                    CreatureID = CREATURE_CHROMATIC_DRAKANOID;
                else CreatureID = DrakType1;

                ++SpawnedAdds;

                //Spawn creature and force it to start attacking a random target
                Spawned = m_creature->SummonCreature(CreatureID,ADD_X1,ADD_Y1,ADD_Z1,5.000f,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
                target = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM,0);
                if (target && Spawned)
                {
                    Spawned->AI()->AttackStart(target);
                    Spawned->setFaction(103);
                }

                //1 in 3 chance it will be a chromatic
                if (!urand(0, 2))
                    CreatureID = CREATURE_CHROMATIC_DRAKANOID;
                else CreatureID = DrakType2;

                ++SpawnedAdds;

                target = NULL;
                Spawned = NULL;
                Spawned = m_creature->SummonCreature(CreatureID,ADD_X2,ADD_Y2,ADD_Z2,5.000,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
                target = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM,0);
                if (target && Spawned)
                {
                    Spawned->AI()->AttackStart(target);
                    Spawned->setFaction(103);
                }

                //Begin phase 2 by spawning Nefarian and what not
                if (SpawnedAdds >= 42)
                {
                    //Teleport Victor Nefarius way out of the map
                    //MapManager::Instance().GetMap(m_creature->GetMapId(), m_creature)->CreatureRelocation(m_creature,0,0,-5000,0);

                    //Inturrupt any spell casting
                    m_creature->InterruptNonMeleeSpells(false);

                    //Root self
                    DoCastSpellIfCan(m_creature,33356);

                    //Make super invis
                    DoCastSpellIfCan(m_creature,8149);

                    //Teleport self to a hiding spot
                    m_creature->NearTeleportTo(HIDE_X, HIDE_Y, HIDE_Z, 0.0f);

                    //Spawn nef and have him attack a random target
                    Creature* Nefarian = m_creature->SummonCreature(CREATURE_NEFARIAN,NEF_X,NEF_Y,NEF_Z,0,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,120000);
                    target = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM,0);

                    if (target && Nefarian)
                    {
                        Nefarian->AI()->AttackStart(target);
                        Nefarian->setFaction(103);
                        NefarianGUID = Nefarian->GetGUID();
                    }
                    else error_log("SD2: Blackwing Lair: Unable to spawn nefarian properly.");
                }

                AddSpawnTimer = 4000;
            }else AddSpawnTimer -= diff;
        }
        else if (NefarianGUID)
        {
            if (NefCheckTime < diff)
            {
                Creature* pNefarian = m_creature->GetMap()->GetCreature(NefarianGUID);

                //If nef is dead then we die to so the players get out of combat
                //and cannot repeat the event
                if (!pNefarian || !pNefarian->isAlive())
                {
                    NefarianGUID = 0;
                    m_creature->ForcedDespawn();
                }

                NefCheckTime = 2000;
            }else NefCheckTime -= diff;
        }
    }
void instance_stratholme::OnCreatureDeath(Creature* pCreature)
{
    switch (pCreature->GetEntry())
    {
        case NPC_BARONESS_ANASTARI: SetData(TYPE_BARONESS, DONE); break;
        case NPC_MALEKI_THE_PALLID: SetData(TYPE_PALLID, DONE);   break;
        case NPC_NERUBENKAN:        SetData(TYPE_NERUB, DONE);    break;
        case NPC_RAMSTEIN:          SetData(TYPE_RAMSTEIN, DONE); break;
        case NPC_BARON:             SetData(TYPE_BARON, DONE);    break;
        case NPC_AURIUS:            SetData(TYPE_AURIUS, FAIL);   break;

        case NPC_THUZADIN_ACOLYTE:
            ThazudinAcolyteJustDied(pCreature);
            break;

        case NPC_ABOM_BILE:
        case NPC_ABOM_VENOM:
            // Start Slaughterhouse Event
            SetData(TYPE_RAMSTEIN, SPECIAL);
            break;

        case NPC_MINDLESS_UNDEAD:
            m_luiUndeadGUIDs.remove(pCreature->GetObjectGuid());
            if (m_luiUndeadGUIDs.empty())
            {
                // Let the black Guards move out of the citadel
                for (GuidList::const_iterator itr = m_luiGuardGUIDs.begin(); itr != m_luiGuardGUIDs.end(); ++itr)
                {
                    Creature* pGuard = instance->GetCreature(*itr);
                    if (pGuard && pGuard->isAlive() && !pGuard->isInCombat())
                    {
                        float fX, fY, fZ;
                        pGuard->GetRandomPoint(aStratholmeLocation[5].m_fX, aStratholmeLocation[5].m_fY, aStratholmeLocation[5].m_fZ, 10.0f, fX, fY, fZ);
                        pGuard->GetMotionMaster()->MovePoint(0, fX, fY, fZ);
                    }
                }
            }
            break;
        case NPC_BLACK_GUARD:
            m_luiGuardGUIDs.remove(pCreature->GetObjectGuid());
            if (m_luiGuardGUIDs.empty())
                SetData(TYPE_BLACK_GUARDS, DONE);

            break;

            // Timmy spawn support
        case NPC_CRIMSON_INITIATE:
        case NPC_CRIMSON_GALLANT:
        case NPC_CRIMSON_GUARDSMAN:
        case NPC_CRIMSON_CONJURER:
            if (m_suiCrimsonLowGuids.find(pCreature->GetGUIDLow()) != m_suiCrimsonLowGuids.end())
            {
                m_suiCrimsonLowGuids.erase(pCreature->GetGUIDLow());

                // If all courtyard mobs are dead then summon Timmy
                if (m_suiCrimsonLowGuids.empty())
                    pCreature->SummonCreature(NPC_TIMMY_THE_CRUEL, aTimmyLocation[0].m_fX, aTimmyLocation[0].m_fY, aTimmyLocation[0].m_fZ, aTimmyLocation[0].m_fO, TEMPSUMMON_DEAD_DESPAWN, 0);
            }
            break;
    }
}
Example #16
0
void instance_naxxramas::SetData(uint32 uiType, uint32 uiData)
{
    switch(uiType)
    {
        case TYPE_ANUB_REKHAN:
            m_auiEncounter[uiType] = uiData;
            DoUseDoorOrButton(m_uiAnubDoorGUID);
            if (uiData == DONE)
                DoUseDoorOrButton(m_uiAnubGateGUID);
            break;
        case TYPE_FAERLINA:
            DoUseDoorOrButton(m_uiFaerWebGUID);
            if (uiData == DONE)
            {
                DoUseDoorOrButton(m_uiFaerDoorGUID);
                DoUseDoorOrButton(m_uiMaexOuterGUID);
            }
            if (uiData == FAIL)
            {
                for (GUIDList::const_iterator itr = m_lFaerlinaAddGUIDs.begin(); itr != m_lFaerlinaAddGUIDs.end(); ++itr)
                {
                    Creature* pAdd = instance->GetCreature(*itr);
                    if (pAdd && !pAdd->isAlive())
                        pAdd->Respawn();
                }
            }
            m_auiEncounter[uiType] = uiData;
            break;
        case TYPE_MAEXXNA:
            m_auiEncounter[uiType] = uiData;
            DoUseDoorOrButton(m_uiMaexInnerGUID, uiData);
            if (uiData == DONE)
            {
                DoUseDoorOrButton(m_uiAracEyeRampGUID);
                DoRespawnGameObject(m_uiAracPortalGUID, 30*MINUTE);
                DoTaunt();
            }
            break;
        case TYPE_NOTH:
            m_auiEncounter[uiType] = uiData;
            DoUseDoorOrButton(m_uiNothEntryDoorGUID);
            if (uiData == DONE)
            {
                DoUseDoorOrButton(m_uiNothExitDoorGUID);
                DoUseDoorOrButton(m_uiHeigEntryDoorGUID);
            }
            break;
        case TYPE_HEIGAN:
            m_auiEncounter[uiType] = uiData;
            DoUseDoorOrButton(m_uiHeigEntryDoorGUID);
            if (uiData == DONE)
                DoUseDoorOrButton(m_uiHeigExitDoorGUID);
            break;
        case TYPE_LOATHEB:
            m_auiEncounter[uiType] = uiData;
            DoUseDoorOrButton(m_uiLoathebDoorGUID);
            if (uiData == DONE)
            {
                DoUseDoorOrButton(m_uiPlagEyeRampGUID);
                DoRespawnGameObject(m_uiPlagPortalGUID, 30*MINUTE);
                DoTaunt();
            }
            break;
        case TYPE_RAZUVIOUS:
            m_auiEncounter[uiType] = uiData;
            break;
        case TYPE_GOTHIK:
            switch(uiData)
            {
                case IN_PROGRESS:
                    DoUseDoorOrButton(m_uiGothikEntryDoorGUID);
                    DoUseDoorOrButton(m_uiGothCombatGateGUID);
                    break;
                case SPECIAL:
                    DoUseDoorOrButton(m_uiGothCombatGateGUID);
                    break;
                case FAIL:
                    if (m_auiEncounter[uiType] == IN_PROGRESS)
                        DoUseDoorOrButton(m_uiGothCombatGateGUID);

                    DoUseDoorOrButton(m_uiGothikEntryDoorGUID);
                    break;
                case DONE:
                    DoUseDoorOrButton(m_uiGothikEntryDoorGUID);
                    DoUseDoorOrButton(m_uiGothikExitDoorGUID);
                    DoUseDoorOrButton(m_uiHorsemenDoorGUID);
                    break;
            }
            m_auiEncounter[uiType] = uiData;
            break;
        case TYPE_FOUR_HORSEMEN:
            m_auiEncounter[uiType] = uiData;
            DoUseDoorOrButton(m_uiHorsemenDoorGUID);
            if (uiData == DONE)
            {
                DoUseDoorOrButton(m_uiMiliEyeRampGUID);
                DoRespawnGameObject(m_uiMiliPortalGUID, 30*MINUTE);
                DoRespawnGameObject(m_uiHorsemenChestGUID, 30*MINUTE);
                DoTaunt();
            }
            break;
        case TYPE_PATCHWERK:
            m_auiEncounter[uiType] = uiData;
            if (uiData == DONE)
                DoUseDoorOrButton(m_uiPathExitDoorGUID);
            break;
        case TYPE_GROBBULUS:
            m_auiEncounter[uiType] = uiData;
            break;
        case TYPE_GLUTH:
            m_auiEncounter[uiType] = uiData;
            if (uiData == DONE)
            {
                DoUseDoorOrButton(m_uiGlutExitDoorGUID);
                DoUseDoorOrButton(m_uiThadDoorGUID);
            }
            break;
        case TYPE_THADDIUS:
            // Only process real changes here
            if (m_auiEncounter[uiType] == uiData)
                return;

            m_auiEncounter[uiType] = uiData;
            if (uiData != SPECIAL)
                DoUseDoorOrButton(m_uiThadDoorGUID, uiData);
            if (uiData == DONE)
            {
                DoUseDoorOrButton(m_uiConsEyeRampGUID);
                DoRespawnGameObject(m_uiConsPortalGUID, 30*MINUTE);
                DoTaunt();
            }
            break;
        case TYPE_SAPPHIRON:
            m_auiEncounter[uiType] = uiData;
            if (uiData == DONE)
                DoUseDoorOrButton(m_uiKelthuzadDoorGUID);
            break;
        case TYPE_KELTHUZAD:
            m_auiEncounter[uiType] = uiData;
            DoUseDoorOrButton(m_uiKelthuzadExitDoorGUID);
            break;
    }

    if (uiData == DONE)
    {
        OUT_SAVE_INST_DATA;

        std::ostringstream saveStream;
        saveStream << m_auiEncounter[0] << " " << m_auiEncounter[1] << " " << m_auiEncounter[2] << " "
            << m_auiEncounter[3] << " " << m_auiEncounter[4] << " " << m_auiEncounter[5] << " "
            << m_auiEncounter[6] << " " << m_auiEncounter[7] << " " << m_auiEncounter[8] << " "
            << m_auiEncounter[9] << " " << m_auiEncounter[10] << " " << m_auiEncounter[11] << " "
            << m_auiEncounter[12] << " " << m_auiEncounter[13] << " " << m_auiEncounter[14] << " " << m_auiEncounter[15];

        m_strInstData = saveStream.str();

        SaveToDB();
        OUT_SAVE_INST_DATA_COMPLETE;
    }
}
void instance_stratholme::Update(uint32 uiDiff)
{
    if (m_uiBarthilasRunTimer)
    {
        if (m_uiBarthilasRunTimer <= uiDiff)
        {
            Creature* pBarthilas = GetSingleCreatureFromStorage(NPC_BARTHILAS);
            if (pBarthilas && pBarthilas->isAlive() && !pBarthilas->isInCombat())
                pBarthilas->NearTeleportTo(aStratholmeLocation[1].m_fX, aStratholmeLocation[1].m_fY, aStratholmeLocation[1].m_fZ, aStratholmeLocation[1].m_fO);

            SetData(TYPE_BARTHILAS_RUN, DONE);
            m_uiBarthilasRunTimer = 0;
        }
        else
            m_uiBarthilasRunTimer -= uiDiff;
    }

    // Timer to summon Aurius into the Slaughter House once Baron is engaged
    if (m_uiAuriusSummonTimer)
    {
        if (m_uiAuriusSummonTimer <= uiDiff)
        {
            SetData(TYPE_AURIUS, IN_PROGRESS);
            m_uiAuriusSummonTimer = 0;
        }
        else
            m_uiAuriusSummonTimer -= uiDiff;
    }

    // Check changes for Baron ultimatum timer only if Baron is not already in combat
    if (m_uiBaronRunTimer && GetData(TYPE_BARON) != IN_PROGRESS)
    {
        if (m_uiYellCounter == 0 && m_uiBaronRunTimer <= 10 * MINUTE * IN_MILLISECONDS)
        {
            DoOrSimulateScriptTextForThisInstance(SAY_ANNOUNCE_RUN_10_MIN, NPC_BARON);
            ++m_uiYellCounter;
        }
        else if (m_uiYellCounter == 1 && m_uiBaronRunTimer <= 5 * MINUTE * IN_MILLISECONDS)
        {
            DoOrSimulateScriptTextForThisInstance(SAY_ANNOUNCE_RUN_5_MIN, NPC_BARON);
            ++m_uiYellCounter;
        }
        // Used to create a delay of 10s between Baron speech and Ysida's answer
        else if (m_uiYellCounter == 2 && m_uiBaronRunTimer <= (5 * MINUTE - 10) * IN_MILLISECONDS)
        {
            DoOrSimulateScriptTextForThisInstance(YSIDA_SAY_RUN_5_MIN, NPC_YSIDA);
            ++m_uiYellCounter;
        }

        if (m_uiBaronRunTimer <= uiDiff)
        {
            if (GetData(TYPE_BARON_RUN) != FAIL)
            {
                SetData(TYPE_BARON_RUN, FAIL);

                // Open the cage and let Ysida face her doom
                if (Creature* pYsida = GetSingleCreatureFromStorage(NPC_YSIDA))
                {
                    pYsida->GetMotionMaster()->MovePoint(0, aStratholmeLocation[8].m_fX, aStratholmeLocation[8].m_fY, aStratholmeLocation[8].m_fZ, aStratholmeLocation[8].m_fO);
                    DoUseDoorOrButton(GO_YSIDA_CAGE);
                }

                DoOrSimulateScriptTextForThisInstance(SAY_ANNOUNCE_RUN_FAIL, NPC_BARON);

                m_uiBaronRunTimer = 8000;  // We reset the timer so the speech of Ysida is not said at the same time than the Baron's one
            }
            else
            {
                // Baron ultimatum failed: let the Baron kill her
                if (Creature* pYsida = GetSingleCreatureFromStorage(NPC_YSIDA))
                    if (Creature* pBaron = GetSingleCreatureFromStorage(NPC_BARON))
                        pBaron->CastSpell(pYsida, SPELL_BARON_SOUL_DRAIN, true);

                DoOrSimulateScriptTextForThisInstance(YSIDA_SAY_RUN_FAIL, NPC_YSIDA);

                m_uiBaronRunTimer = 0;  // event done for good, no more speech
                debug_log("SD2: Instance Stratholme: Baron run event reached end. Event has state %u.", GetData(TYPE_BARON_RUN));
            }
        }
        else
            m_uiBaronRunTimer -= uiDiff;
    }

    if (m_uiMindlessSummonTimer)
    {
        if (m_uiMindlessCount < 30)
        {
            if (m_uiMindlessSummonTimer <= uiDiff)
            {
                if (Creature* pBaron = GetSingleCreatureFromStorage(NPC_BARON))
                {
                    // Summon mindless skeletons and move them to random point in the center of the square
                    if (Creature* pTemp = pBaron->SummonCreature(NPC_MINDLESS_UNDEAD, aStratholmeLocation[4].m_fX, aStratholmeLocation[4].m_fY, aStratholmeLocation[4].m_fZ, aStratholmeLocation[4].m_fO, TEMPSUMMON_DEAD_DESPAWN, 0))
                    {
                        float fX, fY, fZ;
                        pBaron->GetRandomPoint(aStratholmeLocation[5].m_fX, aStratholmeLocation[5].m_fY, aStratholmeLocation[5].m_fZ, 20.0f, fX, fY, fZ);
                        pTemp->GetMotionMaster()->MovePoint(0, fX, fY, fZ);
                        m_luiUndeadGUIDs.push_back(pTemp->GetObjectGuid());
                        ++m_uiMindlessCount;
                    }
                }
                m_uiMindlessSummonTimer = 400;
            }
            else
                m_uiMindlessSummonTimer -= uiDiff;
        }
        else
            m_uiMindlessSummonTimer = 0;
    }

    if (m_uiSlaugtherSquareTimer)
    {
        if (m_uiSlaugtherSquareTimer <= uiDiff)
        {
            // Call next Abomnations
            for (GuidSet::const_iterator itr = m_sAbomnationGUID.begin(); itr != m_sAbomnationGUID.end(); ++itr)
            {
                Creature* pAbom = instance->GetCreature(*itr);
                // Skip killed and already walking Abomnations
                if (!pAbom || !pAbom->isAlive() || pAbom->GetMotionMaster()->GetCurrentMovementGeneratorType() == POINT_MOTION_TYPE)
                    continue;

                // Let Move to somewhere in the middle
                if (!pAbom->isInCombat())
                {
                    if (GameObject* pDoor = GetSingleGameObjectFromStorage(GO_PORT_SLAUGTHER))
                    {
                        float fX, fY, fZ;
                        pAbom->GetRandomPoint(pDoor->GetPositionX(), pDoor->GetPositionY(), pDoor->GetPositionZ(), 10.0f, fX, fY, fZ);
                        pAbom->GetMotionMaster()->MovePoint(0, fX, fY, fZ);
                    }
                }
                break;
            }

            // TODO - how fast are they called?
            m_uiSlaugtherSquareTimer = urand(15000, 30000);
        }
        else
            m_uiSlaugtherSquareTimer -= uiDiff;
    }
}
Example #18
0
    void UpdateAI(const uint32 diff)
    {
        if (!m_pInstance)
            return;

        if (MobDeath_Timer)
        {
            if (MobDeath_Timer <= diff)
            {
                MobDeath_Timer = 2500;

                if (RingBossGUID)
                {
                    Creature *boss = (Creature*)Unit::GetUnit(*m_creature,RingBossGUID);
                    if (boss && !boss->isAlive() && boss->isDead())
                    {
                        RingBossGUID = 0;
                        Event_Timer = 5000;
                        MobDeath_Timer = 0;
                        return;
                    }
                    return;
                }

                for(uint8 i = 0; i < MAX_MOB_AMOUNT; ++i)
                {
                    Creature *mob = (Creature*)Unit::GetUnit(*m_creature,RingMobGUID[i]);
                    if (mob && !mob->isAlive() && mob->isDead())
                    {
                        RingMobGUID[i] = 0;
                        --MobCount;

                        //seems all are gone, so set timer to continue and discontinue this
                        if (!MobCount)
                        {
                            Event_Timer = 5000;
                            MobDeath_Timer = 0;
                        }
                    }
                }
            }else MobDeath_Timer -= diff;
        }

        if (Event_Timer)
        {
            if (Event_Timer <= diff)
            {
                switch(EventPhase)
                {
                    case 0:
                        DoScriptText(-1000000, m_creature);//1
                        DoGate(DATA_ARENA4,1);
                        Start(false, false, false);
                        CanWalk = true;
                        Event_Timer = 0;
                        break;
                    case 1:
                        CanWalk = true;
                        Event_Timer = 0;
                        break;
                    case 2:
                        Event_Timer = 2000;
                        break;
                    case 3:
                        DoGate(DATA_ARENA1,GO_STATE_ACTIVE);
                        Event_Timer = 3000;
                        break;
                    case 4:
                        CanWalk = true;
                        m_creature->SetVisibility(VISIBILITY_OFF);
                        SummonRingMob();
                        Event_Timer = 8000;
                        break;
                    case 5:
                        SummonRingMob();
                        SummonRingMob();
                        Event_Timer = 8000;
                        break;
                    case 6:
                        SummonRingMob();
                        Event_Timer = 0;
                        break;
                    case 7:
                        m_creature->SetVisibility(VISIBILITY_ON);
                        DoGate(DATA_ARENA1,GO_STATE_READY);
                        DoScriptText(-1000000, m_creature);//4
                        CanWalk = true;
                        Event_Timer = 0;
                        break;
                    case 8:
                        DoGate(DATA_ARENA2,GO_STATE_ACTIVE);
                        Event_Timer = 5000;
                        break;
                    case 9:
                        m_creature->SetVisibility(VISIBILITY_OFF);
                        SummonRingBoss();
                        Event_Timer = 0;
                        break;
                    case 10:
                        //if quest, complete
                        DoGate(DATA_ARENA2,GO_STATE_READY);
                        DoGate(DATA_ARENA3,GO_STATE_ACTIVE);
                        DoGate(DATA_ARENA4,GO_STATE_ACTIVE);
                        CanWalk = true;
                        Event_Timer = 0;
                        break;
                }
                ++EventPhase;
            }else Event_Timer -= diff;
        }

        if (CanWalk)
            npc_escortAI::UpdateAI(diff);
    }
            void UpdateAI(uint32 uiDiff)
            {
                if (!_instance)
                    return;

                if (_instance->GetData(TYPE_EVENT_NPC) != NPC_LICH_KING_1)
                    return;

                _updateTimer = _instance->GetData(TYPE_EVENT_TIMER);
                if (_updateTimer <= uiDiff)
                {
                    switch (_instance->GetData(TYPE_EVENT))
                    {
                        case 5010:
                            Talk(SAY_STAGE_4_02);
                            _updateTimer = 3*IN_MILLISECONDS;
                            me->GetMotionMaster()->MovePoint(0, LichKingLoc[0]);
                            _instance->SetData(TYPE_EVENT, 5020);
                            break;
                        case 5030:
                            Talk(SAY_STAGE_4_04);
                            me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_STATE_TALK);
                            _updateTimer = 10*IN_MILLISECONDS;
                            _instance->SetData(TYPE_EVENT, 5040);
                            break;
                        case 5040:
                            me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_ONESHOT_NONE);
                            me->GetMotionMaster()->MovePoint(1, LichKingLoc[1]);
                            _updateTimer = 1*IN_MILLISECONDS;
                            _instance->SetData(TYPE_EVENT, 0);
                            break;
                        case 5050:
                            me->HandleEmoteCommand(EMOTE_ONESHOT_EXCLAMATION);
                            _updateTimer = 3*IN_MILLISECONDS;
                            _instance->SetData(TYPE_EVENT, 5060);
                            break;
                        case 5060:
                            Talk(SAY_STAGE_4_05);
                            me->HandleEmoteCommand(EMOTE_ONESHOT_KNEEL);
                            _updateTimer = 2.5*IN_MILLISECONDS;
                            _instance->SetData(TYPE_EVENT, 5070);
                            break;
                        case 5070:
                            me->CastSpell(me, 68198, false);
                            _updateTimer = 1.5*IN_MILLISECONDS;
                            _instance->SetData(TYPE_EVENT, 5080);
                            break;
                        case 5080:
                            if (GameObject* go = _instance->instance->GetGameObject(_instance->GetData64(GO_ARGENT_COLISEUM_FLOOR)))
                            {
                                go->SetDisplayId(DISPLAYID_DESTROYED_FLOOR);
                                go->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_DAMAGED | GO_FLAG_NODESPAWN);
                                go->SetGoState(GO_STATE_ACTIVE);
                            }

                            me->CastSpell(me, SPELL_CORPSE_TELEPORT, false);
                            me->CastSpell(me, SPELL_DESTROY_FLOOR_KNOCKUP, false);

                            if (_instance)
                            {
                                _instance->SetBossState(BOSS_LICH_KING, DONE);
                                Creature* temp = Unit::GetCreature(*me, _instance->GetData64(NPC_ANUBARAK));
                                if (!temp || !temp->isAlive())
                                    temp = me->SummonCreature(NPC_ANUBARAK, AnubarakLoc[0].GetPositionX(), AnubarakLoc[0].GetPositionY(), AnubarakLoc[0].GetPositionZ(), 3, TEMPSUMMON_CORPSE_TIMED_DESPAWN, DESPAWN_TIME);

                                _instance->SetData(TYPE_EVENT, 0);
                            }
                            me->DespawnOrUnsummon();
                            _updateTimer = 20*IN_MILLISECONDS;
                            break;
                        default:
                            break;
                    }
                }
                else
                    _updateTimer -= uiDiff;

                _instance->SetData(TYPE_EVENT_TIMER, _updateTimer);
            }
Example #20
0
void WorldSession::HandleAutostoreLootItemOpcode(WorldPacket & recv_data)
{
    sLog->outDebug(LOG_FILTER_NETWORKIO, "WORLD: CMSG_AUTOSTORE_LOOT_ITEM");
    Player* player = GetPlayer();
    uint64 lguid = player->GetLootGUID();
    Loot* loot = NULL;
    uint8 lootSlot = 0;

    recv_data >> lootSlot;

    if (IS_GAMEOBJECT_GUID(lguid))
    {
        GameObject *go = player->GetMap()->GetGameObject(lguid);

        // not check distance for GO in case owned GO (fishing bobber case, for example) or Fishing hole GO
        if (!go || ((go->GetOwnerGUID() != _player->GetGUID() && go->GetGoType() != GAMEOBJECT_TYPE_FISHINGHOLE) && !go->IsWithinDistInMap(_player, INTERACTION_DISTANCE)))
        {
            player->SendLootRelease(lguid);
            return;
        }

        loot = &go->loot;
    }
    else if (IS_ITEM_GUID(lguid))
    {
        Item *pItem = player->GetItemByGuid(lguid);

        if (!pItem)
        {
            player->SendLootRelease(lguid);
            return;
        }

        loot = &pItem->loot;
    }
    else if (IS_CORPSE_GUID(lguid))
    {
        Corpse *bones = ObjectAccessor::GetCorpse(*player, lguid);
        if (!bones)
        {
            player->SendLootRelease(lguid);
            return;
        }

        loot = &bones->loot;
    }
    else
    {
        Creature* pCreature = GetPlayer()->GetMap()->GetCreature(lguid);

        bool ok_loot = pCreature && pCreature->isAlive() == (player->getClass() == CLASS_ROGUE && pCreature->lootForPickPocketed);

        if (!ok_loot || !pCreature->IsWithinDistInMap(_player, INTERACTION_DISTANCE))
        {
            player->SendLootRelease(lguid);
            return;
        }

        loot = &pCreature->loot;
    }

    player->StoreLootItem(lootSlot, loot);
}
        void UpdateAI(const uint32 diff)
        {
            //Only if not incombat check if the event is started
            if (!me->isInCombat() && pInstance && pInstance->GetData(DATA_KARATHRESSEVENT))
            {
                Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_KARATHRESSEVENT_STARTER));

                if (pTarget)
                {
                    AttackStart(pTarget);
                }
            }

            //Return since we have no target
            if (!UpdateVictim())
                return;

            //someone evaded!
            if (pInstance && !pInstance->GetData(DATA_KARATHRESSEVENT))
            {
                EnterEvadeMode();
                return;
            }

            //LeechingThrow_Timer
            if (LeechingThrow_Timer <= diff)
            {
                DoCast(me->getVictim(), SPELL_LEECHING_THROW);
                LeechingThrow_Timer = 20000;
            } else LeechingThrow_Timer -= diff;

            //Multishot_Timer
            if (Multishot_Timer <= diff)
            {
                DoCast(me->getVictim(), SPELL_MULTISHOT);
                Multishot_Timer = 20000;
            } else Multishot_Timer -= diff;

            //TheBeastWithin_Timer
            if (TheBeastWithin_Timer <= diff)
            {
                DoCast(me, SPELL_THE_BEAST_WITHIN);
                Creature *Pet = Unit::GetCreature(*me, SummonedPet);
                if (Pet && Pet->isAlive())
                {
                    Pet->CastSpell(Pet, SPELL_PET_ENRAGE, true);
                }
                TheBeastWithin_Timer = 30000;
            } else TheBeastWithin_Timer -= diff;

            //Pet_Timer
            if (Pet_Timer < diff && pet == false)
            {
                pet = true;
                //uint32 spell_id;
                uint32 pet_id;
                if (!urand(0, 1))
                {
                    //spell_id = SPELL_SUMMON_FATHOM_LURKER;
                    pet_id = CREATURE_FATHOM_LURKER;
                }
                else
                {
                    //spell_id = SPELL_SUMMON_FATHOM_SPOREBAT;
                    pet_id = CREATURE_FATHOM_SPOREBAT;
                }
                //DoCast(me, spell_id, true);
                Creature *Pet = DoSpawnCreature(pet_id, 0, 0, 0, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
                Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0);
                if (Pet && pTarget)
                {
                    Pet->AI()->AttackStart(pTarget);
                    SummonedPet = Pet->GetGUID();
                }
            } else Pet_Timer -= diff;

            DoMeleeAttackIfReady();
        }
Example #22
0
void WorldSession::HandleLootMoneyOpcode(WorldPacket & /*recv_data*/)
{
    sLog->outDebug(LOG_FILTER_NETWORKIO, "WORLD: CMSG_LOOT_MONEY");

    Player* player = GetPlayer();
    uint64 guid = player->GetLootGUID();
    if (!guid)
        return;

    Loot* loot = NULL;
    bool shareMoney = true;

    switch (GUID_HIPART(guid))
    {
    case HIGHGUID_GAMEOBJECT:
    {
        GameObject* go = GetPlayer()->GetMap()->GetGameObject(guid);

        // do not check distance for GO if player is the owner of it (ex. fishing bobber)
        if (go && ((go->GetOwnerGUID() == player->GetGUID() || go->IsWithinDistInMap(player, INTERACTION_DISTANCE))))
            loot = &go->loot;

        break;
    }
    case HIGHGUID_CORPSE:                               // remove insignia ONLY in BG
    {
        Corpse* bones = ObjectAccessor::GetCorpse(*player, guid);

        if (bones && bones->IsWithinDistInMap(player, INTERACTION_DISTANCE))
        {
            loot = &bones->loot;
            shareMoney = false;
        }

        break;
    }
    case HIGHGUID_ITEM:
    {
        if (Item* item = player->GetItemByGuid(guid))
        {
            loot = &item->loot;
            shareMoney = false;
        }
        break;
    }
    case HIGHGUID_UNIT:
    case HIGHGUID_VEHICLE:
    {
        Creature* creature = player->GetMap()->GetCreature(guid);
        bool lootAllowed = creature && creature->isAlive() == (player->getClass() == CLASS_ROGUE && creature->lootForPickPocketed);
        if (lootAllowed && creature->IsWithinDistInMap(player, INTERACTION_DISTANCE))
        {
            loot = &creature->loot;
            if (creature->isAlive())
                shareMoney = false;
        }
        break;
    }
    default:
        return;                                         // unlootable type
    }

    if (loot)
    {
        loot->NotifyMoneyRemoved();
        if (shareMoney && player->GetGroup())      //item, pickpocket and players can be looted only single player
        {
            Group* group = player->GetGroup();

            std::vector<Player*> playersNear;
            for (GroupReference* itr = group->GetFirstMember(); itr != NULL; itr = itr->next())
            {
                Player* member = itr->getSource();
                if (!member)
                    continue;

                if (player->IsWithinDistInMap(member, sWorld->getFloatConfig(CONFIG_GROUP_XP_DISTANCE), false))
                    playersNear.push_back(member);
            }

            uint32 goldPerPlayer = uint32((loot->gold) / (playersNear.size()));

            for (std::vector<Player*>::const_iterator i = playersNear.begin(); i != playersNear.end(); ++i)
            {
                (*i)->ModifyMoney(goldPerPlayer);
                (*i)->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_LOOT_MONEY, goldPerPlayer);

                WorldPacket data(SMSG_LOOT_MONEY_NOTIFY, 4);
                data << uint32(goldPerPlayer);
                data << uint8(playersNear.size() > 1 ? 0 : 1);     // Controls the text displayed in chat. 0 is "Your share is..." and 1 is "You loot..."
                (*i)->GetSession()->SendPacket(&data);
            }
        }
        else
        {
            player->ModifyMoney(loot->gold);
            player->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_LOOT_MONEY, loot->gold);

            WorldPacket data(SMSG_LOOT_MONEY_NOTIFY, 4);
            data << uint32(loot->gold);
            data << uint8(1);
            SendPacket(&data);
        }

        loot->gold = 0;
    }
}
Example #23
0
	//move selected creature
	static bool HandleNpcMoveCommand(ChatHandler* handler, const char* args) {
		uint32 lowguid = 0;

		Creature* pCreature = handler->getSelectedCreature();

		if (!pCreature) {
			// number or [name] Shift-click form |color|Hcreature:creature_guid|h[name]|h|r
			char* cId = handler->extractKeyFromLink((char*) args, "Hcreature");
			if (!cId)
				return false;

			lowguid = atoi(cId);

			/* FIXME: impossible without entry
			 if (lowguid)
			 pCreature = ObjectAccessor::GetCreature(*handler->GetSession()->GetPlayer(),MAKE_GUID(lowguid,HIGHGUID_UNIT));
			 */

			// Attempting creature load from DB data
			if (!pCreature) {
				CreatureData const* data = sObjectMgr->GetCreatureData(lowguid);
				if (!data) {
					handler->PSendSysMessage(LANG_COMMAND_CREATGUIDNOTFOUND,
							lowguid);
					handler->SetSentErrorMessage(true);
					return false;
				}

				uint32 map_id = data->mapid;

				if (handler->GetSession()->GetPlayer()->GetMapId() != map_id) {
					handler->PSendSysMessage(LANG_COMMAND_CREATUREATSAMEMAP,
							lowguid);
					handler->SetSentErrorMessage(true);
					return false;
				}
			} else {
				lowguid = pCreature->GetDBTableGUIDLow();
			}
		} else {
			lowguid = pCreature->GetDBTableGUIDLow();
		}

		float x = handler->GetSession()->GetPlayer()->GetPositionX();
		float y = handler->GetSession()->GetPlayer()->GetPositionY();
		float z = handler->GetSession()->GetPlayer()->GetPositionZ();
		float o = handler->GetSession()->GetPlayer()->GetOrientation();

		if (pCreature) {
			if (CreatureData const* data = sObjectMgr->GetCreatureData(pCreature->GetDBTableGUIDLow())) {
				const_cast<CreatureData*>(data)->posX = x;
				const_cast<CreatureData*>(data)->posY = y;
				const_cast<CreatureData*>(data)->posZ = z;
				const_cast<CreatureData*>(data)->orientation = o;
			}
			pCreature->GetMap()->CreatureRelocation(pCreature, x, y, z, o);
			pCreature->GetMotionMaster()->Initialize();
			if (pCreature->isAlive()) // dead creature will reset movement generator at respawn
			{
				pCreature->setDeathState(JUST_DIED);
				pCreature->Respawn();
			}
		}

		WorldDatabase.PExecute(
				"UPDATE creature SET position_x = '%f', position_y = '%f', position_z = '%f', orientation = '%f' WHERE guid = '%u'",
				x, y, z, o, lowguid);
		handler->PSendSysMessage(LANG_COMMAND_CREATUREMOVED);
		return true;
	}
Example #24
0
    void UpdateAI(const uint32 diff)
    {
        if (!UpdateVictim())
        {
            if (UnsummonCheck < diff && m_creature->isAlive())
                m_creature->DisappearAndDie();
            else
                UnsummonCheck -= diff;
            return;
        }

        if (Fireball_Timer <= diff)
        {
            if (Unit *victim = SelectUnit(SELECT_TARGET_RANDOM,0))
                DoCast(victim, SPELL_FIREBALL,true);
            Fireball_Timer = urand(4000,7000);
        } else Fireball_Timer -= diff;

        if (flight) // phase 1 - the flight
        {
            Creature *Vazruden = Unit::GetCreature(*m_creature,VazrudenGUID);
            if (Fly_Timer < diff || !(Vazruden && Vazruden->isAlive() && (Vazruden->GetHealth()*5 > Vazruden->GetMaxHealth())))
            {
                flight = false;
                BellowingRoar_Timer = 6000;
                ConeOfFire_Timer = 12000;
                m_creature->RemoveUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
                m_creature->AddUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
                m_creature->GetMotionMaster()->Clear();
                if (Unit *victim = SelectUnit(SELECT_TARGET_NEAREST,0))
                    m_creature->AI()->AttackStart(victim);
                DoStartMovement(m_creature->getVictim());
                DoScriptText(EMOTE, m_creature);
                return;
            } else Fly_Timer -= diff;

            if (Turn_Timer <= diff)
            {
                uint32 waypoint = (Fly_Timer/10000)%2;
                if (m_creature->IsWithinDist3d(VazrudenRing[waypoint][0],VazrudenRing[waypoint][1],VazrudenRing[waypoint][2], 5))
                    m_creature->GetMotionMaster()->MovePoint(0,VazrudenRing[waypoint][0],VazrudenRing[waypoint][1],VazrudenRing[waypoint][2]);
                Turn_Timer = 10000;
            } else Turn_Timer -= diff;
        }
        else // phase 2 - land fight
        {
            if (ConeOfFire_Timer <= diff)
            {
                DoCast(m_creature, SPELL_CONE_OF_FIRE);
                ConeOfFire_Timer = 12000;
                Fireball_Timer = 4000;
            } else ConeOfFire_Timer -= diff;

            if (HeroicMode && BellowingRoar_Timer <= diff)
            {
                DoCast(m_creature, SPELL_BELLOWING_ROAR);
                BellowingRoar_Timer = 45000;
            } else BellowingRoar_Timer -= diff;

            DoMeleeAttackIfReady();
        }
    }
Example #25
0
// Function to process actions for linked NPCs
void CreatureLinkingHolder::DoCreatureLinkingEvent(CreatureLinkingEvent eventType, Creature* pSource, Unit* pEnemy /* = NULL*/)
{
    // This check will be needed in reload case
    if (!sCreatureLinkingMgr.IsLinkedEventTrigger(pSource))
        return;

    // Ignore atypic behaviour
    if (pSource->IsControlledByPlayer())
        return;

    if (eventType == LINKING_EVENT_AGGRO && !pEnemy)
        return;

    uint32 eventFlagFilter = 0;
    uint32 reverseEventFlagFilter = 0;

    switch (eventType)
    {
    case LINKING_EVENT_AGGRO:
        eventFlagFilter = EVENT_MASK_ON_AGGRO;
        reverseEventFlagFilter = FLAG_TO_AGGRO_ON_AGGRO;
        break;
    case LINKING_EVENT_EVADE:
        eventFlagFilter = EVENT_MASK_ON_EVADE;
        reverseEventFlagFilter = FLAG_TO_RESPAWN_ON_EVADE;
        break;
    case LINKING_EVENT_DIE:
        eventFlagFilter = EVENT_MASK_ON_DIE;
        reverseEventFlagFilter = 0;
        break;
    case LINKING_EVENT_RESPAWN:
        eventFlagFilter = EVENT_MASK_ON_RESPAWN;
        reverseEventFlagFilter = FLAG_FOLLOW;
        break;
    }

    // Process Slaves (by entry)
    HolderMapBounds bounds = m_holderMap.equal_range(pSource->GetEntry());
    for (HolderMap::iterator itr = bounds.first; itr != bounds.second; ++itr)
        ProcessSlaveGuidList(eventType, pSource, itr->second.linkingFlag & eventFlagFilter, itr->second.searchRange, itr->second.linkedGuids, pEnemy);

    // Process Slaves (by guid)
    bounds = m_holderGuidMap.equal_range(pSource->GetGUIDLow());
    for (HolderMap::iterator itr = bounds.first; itr != bounds.second; ++itr)
        ProcessSlaveGuidList(eventType, pSource, itr->second.linkingFlag & eventFlagFilter, itr->second.searchRange, itr->second.linkedGuids, pEnemy);

    // Process Master
    if (CreatureLinkingInfo const* pInfo = sCreatureLinkingMgr.GetLinkedTriggerInformation(pSource))
    {
        if (pInfo->linkingFlag & reverseEventFlagFilter)
        {
            Creature* pMaster = NULL;
            if (pInfo->mapId != INVALID_MAP_ID)             // entry case
            {
                BossGuidMapBounds finds = m_masterGuid.equal_range(pInfo->masterId);
                for (BossGuidMap::iterator itr = finds.first; itr != finds.second; ++itr)
                {
                    pMaster = pSource->GetMap()->GetCreature(itr->second);
                    if (pMaster && IsSlaveInRangeOfBoss(pSource, pMaster, pInfo->searchRange))
                        break;
                }
            }
            else                                            // guid case
            {
                CreatureData const* masterData = sObjectMgr.GetCreatureData(pInfo->masterDBGuid);
                CreatureInfo const* cInfo = ObjectMgr::GetCreatureTemplate(masterData->id);
                pMaster = pSource->GetMap()->GetCreature(ObjectGuid(cInfo->GetHighGuid(), cInfo->Entry, pInfo->masterDBGuid));
            }

            if (pMaster)
            {
                switch (eventType)
                {
                case LINKING_EVENT_AGGRO:
                    if (pMaster->IsControlledByPlayer())
                        return;

                    if (pMaster->isInCombat())
                        pMaster->SetInCombatWith(pEnemy);
                    else
                        pMaster->AI()->AttackStart(pEnemy);
                    break;
                case LINKING_EVENT_EVADE:
                    if (!pMaster->isAlive())
                        pMaster->Respawn();
                    break;
                case LINKING_EVENT_RESPAWN:
                    if (pMaster->isAlive())
                        SetFollowing(pSource, pMaster);
                    break;
                case LINKING_EVENT_DIE:                 // Nothing linked for this case
                    break;
                }
            }
        }
    }
}
Example #26
0
    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, NULL);
                    EnterEvadeMode();
                    return;
                }
            }
            CheckTimer = 1000;
        } else CheckTimer -= diff;

        if (ResetThreat <= diff)
        {
            for (std::list<HostileReference*>::const_iterator itr = me->getThreatManager().getThreatList().begin(); itr != me->getThreatManager().getThreatList().end(); ++itr)
            {
                if (Unit* pUnit = Unit::GetUnit(*me, (*itr)->getUnitGuid()))
                {
                    if (pUnit->GetPositionZ() > me->GetPositionZ()+5)
                    {
                        me->getThreatManager().modifyThreatPercent(pUnit,-100);
                    }
                }
            }
            ResetThreat = 1000;
        } else ResetThreat -= diff;

        if (ShadowBoltTimer <= diff)
        {
            if (!(rand()%5))DoScriptText(SAY_SATH_SPELL1, me);
            DoCast(me, SPELL_SHADOW_BOLT);
            ShadowBoltTimer = 7000+(rand()%3000);
        } else ShadowBoltTimer -= diff;

        if (AgonyCurseTimer <= diff)
        {
            Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0);
            if (!pTarget) pTarget = me->getVictim();
            DoCast(pTarget, SPELL_AGONY_CURSE);
            AgonyCurseTimer = 20000;
        } else AgonyCurseTimer -= diff;

        if (CorruptionStrikeTimer <= diff)
        {
            if (!(rand()%5))DoScriptText(SAY_SATH_SPELL2, me);
            DoCast(me->getVictim(), SPELL_CORRUPTION_STRIKE);
            CorruptionStrikeTimer = 13000;
        } else CorruptionStrikeTimer -= diff;

        DoMeleeAttackIfReady();
    }
    void UpdateAI(const uint32 diff)
    {
        if (!EventBegun)
            return;

        if ((me->GetHealth()*100 / me->GetMaxHealth()) < 15 && !HasYelledOnce)
        {
            DoScriptText(SAY_LOW_HEALTH, me);
            HasYelledOnce = true;
        }

        if (ShadeGUID && !StartCombat)
        {
            Creature* Shade = (Unit::GetCreature((*me), ShadeGUID));
            if (Shade && Shade->isAlive())
            {
                if (CAST_AI(boss_shade_of_akamaAI, Shade->AI())->IsBanished)
                {
                    if (CastSoulRetrieveTimer <= diff)
                    {
                        DoCast(Shade, SPELL_AKAMA_SOUL_CHANNEL);
                        CastSoulRetrieveTimer = 60000;
                    } else CastSoulRetrieveTimer -= diff;
                }
                else
                {
                    me->InterruptNonMeleeSpells(false);
                    StartCombat = true;
                }
            }
        }

        if (ShadeHasDied && (WayPointId == 1))
        {
            if (pInstance)
                pInstance->SetData(DATA_SHADEOFAKAMAEVENT, DONE);
            me->GetMotionMaster()->MovePoint(WayPointId, AkamaWP[1].x, AkamaWP[1].y, AkamaWP[1].z);
            ++WayPointId;
        }

        if (!ShadeHasDied && StartCombat)
        {
            if (CheckTimer <= diff)
            {
                if (ShadeGUID)
                {
                    Creature* Shade = Unit::GetCreature((*me), ShadeGUID);
                    if (Shade && !Shade->isAlive())
                    {
                        ShadeHasDied = true;
                        WayPointId = 0;
                        me->SetUnitMovementFlags(MOVEFLAG_WALK_MODE);
                        me->GetMotionMaster()->MovePoint(WayPointId, AkamaWP[0].x, AkamaWP[0].y, AkamaWP[0].z);
                    }
                    if (Shade && Shade->isAlive())
                    {
                        if (Shade->getThreatManager().getThreatList().size() < 2)
                            Shade->AI()->EnterEvadeMode();
                    }
                }
                CheckTimer = 5000;
            } else CheckTimer -= diff;
        }

        if (SummonBrokenTimer && BrokenSummonIndex < 4)
        {
            if (SummonBrokenTimer <= diff)
            {
                for (uint8 i = 0; i < 4; ++i)
                {
                    float x = BrokenCoords[BrokenSummonIndex].x + (i*5);
                    float y = BrokenCoords[BrokenSummonIndex].y + (1*5);
                    float z = BrokenCoords[BrokenSummonIndex].z;
                    float o = BrokenCoords[BrokenSummonIndex].o;
                    Creature* Broken = me->SummonCreature(CREATURE_BROKEN, x, y, z, o, TEMPSUMMON_TIMED_OR_CORPSE_DESPAWN, 360000);
                    if (Broken)
                    {
                        float wx = BrokenWP[BrokenSummonIndex].x + (i*5);
                        float wy = BrokenWP[BrokenSummonIndex].y + (i*5);
                        float wz = BrokenWP[BrokenSummonIndex].z;
                        Broken->GetMotionMaster()->MovePoint(0, wx, wy, wz);
                        Broken->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
                        BrokenList.push_back(Broken->GetGUID());
                    }
                }
                ++BrokenSummonIndex;
                SummonBrokenTimer = 1000;
            } else SummonBrokenTimer -= diff;
        }

        if (SoulRetrieveTimer)
            if (SoulRetrieveTimer <= diff)
            {
                switch (EndingTalkCount)
                {
                case 0:
                    me->HandleEmoteCommand(EMOTE_ONESHOT_ROAR);
                    ++EndingTalkCount;
                    SoulRetrieveTimer = 2000;
                    SummonBrokenTimer = 1;
                    break;
                case 1:
                    DoScriptText(SAY_FREE, me);
                    ++EndingTalkCount;
                    SoulRetrieveTimer = 25000;
                    break;
                case 2:
                    if (!BrokenList.empty())
                    {
                        bool Yelled = false;
                        for (std::list<uint64>::iterator itr = BrokenList.begin(); itr != BrokenList.end(); ++itr)
                            if (Creature* pUnit = Unit::GetCreature(*me, *itr))
                            {
                                if (!Yelled)
                                {
                                    DoScriptText(SAY_BROKEN_FREE_01, pUnit);
                                    Yelled = true;
                                }
                                pUnit->HandleEmoteCommand(EMOTE_ONESHOT_KNEEL);
                            }
                    }
                    ++EndingTalkCount;
                    SoulRetrieveTimer = 1500;
                    break;
                case 3:
                    if (!BrokenList.empty())
                    {
                        for (std::list<uint64>::iterator itr = BrokenList.begin(); itr != BrokenList.end(); ++itr)
                            if (Creature* pUnit = Unit::GetCreature(*me, *itr))
                                // This is the incorrect spell, but can't seem to find the right one.
                                pUnit->CastSpell(pUnit, 39656, true);
                    }
                    ++EndingTalkCount;
                    SoulRetrieveTimer = 5000;
                    break;
                case 4:
                    if (!BrokenList.empty())
                    {
                        for (std::list<uint64>::iterator itr = BrokenList.begin(); itr != BrokenList.end(); ++itr)
                            if (Creature* pUnit = Unit::GetCreature((*me), *itr))
                                pUnit->MonsterYell(SAY_BROKEN_FREE_02, LANG_UNIVERSAL, 0);
                    }
                    SoulRetrieveTimer = 0;
                    break;
                }
            } else SoulRetrieveTimer -= diff;

        if (!UpdateVictim())
            return;

        if (DestructivePoisonTimer <= diff)
        {
            Creature* Shade = Unit::GetCreature((*me), ShadeGUID);
            if (Shade && Shade->isAlive())
                DoCast(Shade, SPELL_DESTRUCTIVE_POISON);
            DestructivePoisonTimer = 15000;
        } else DestructivePoisonTimer -= diff;

        if (LightningBoltTimer <= diff)
        {
            DoCast(me->getVictim(), SPELL_LIGHTNING_BOLT);
            LightningBoltTimer = 10000;
        } else LightningBoltTimer -= diff;

        DoMeleeAttackIfReady();
    }
void instance_stratholme::SetData(uint32 uiType, uint32 uiData)
{
    // TODO: Remove the hard-coded indexes from array accessing
    switch (uiType)
    {
        case TYPE_BARON_RUN:
            switch (uiData)
            {
                case IN_PROGRESS:
                    if (m_auiEncounter[uiType] == IN_PROGRESS || m_auiEncounter[uiType] == FAIL)
                        break;

                    // Baron ultimatum starts: summon Ysida in the cage
                    if (Creature* pBaron = GetSingleCreatureFromStorage(NPC_BARON))
                    {
                        DoOrSimulateScriptTextForThisInstance(SAY_ANNOUNCE_RUN_START, NPC_BARON);
                        pBaron->SummonCreature(NPC_YSIDA, aStratholmeLocation[7].m_fX, aStratholmeLocation[7].m_fY, aStratholmeLocation[7].m_fZ, aStratholmeLocation[7].m_fO, TEMPSUMMON_DEAD_DESPAWN, 0);
                    }

                    m_uiBaronRunTimer = 45 * MINUTE * IN_MILLISECONDS;
                    debug_log("SD2: Instance Stratholme: Baron run in progress.");
                    break;
                case FAIL:
                    // may add code to remove aura from players, but in theory the time should be up already and removed.
                    break;
                case DONE:
                    m_uiBaronRunTimer = 0;
                    break;
            }
            m_auiEncounter[uiType] = uiData;
            break;
        case TYPE_BARONESS:
        case TYPE_NERUB:
        case TYPE_PALLID:
            m_auiEncounter[uiType] = uiData;
            if (uiData == DONE)
            {
                DoSortZiggurats();
                DoUseDoorOrButton(m_zigguratStorage[uiType - TYPE_BARONESS].m_doorGuid);
            }
            if (uiData == SPECIAL)
                StartSlaugtherSquare();
            break;
        case TYPE_RAMSTEIN:
            if (uiData == SPECIAL)
            {
                if (m_auiEncounter[uiType] != SPECIAL && m_auiEncounter[uiType] != DONE)
                {
                    m_uiSlaugtherSquareTimer = 20000;       // TODO - unknown, also possible that this is not the very correct place..
                    DoUseDoorOrButton(GO_PORT_GAUNTLET);
                }

                uint32 uiCount = m_sAbomnationGUID.size();
                for (GuidSet::iterator itr = m_sAbomnationGUID.begin(); itr != m_sAbomnationGUID.end();)
                {
                    if (Creature* pAbom = instance->GetCreature(*itr))
                    {
                        ++itr;
                        if (!pAbom->isAlive())
                            --uiCount;
                    }
                    else
                    {
                        // Remove obsolete guid from set and decrement count
                        m_sAbomnationGUID.erase(itr++);
                        --uiCount;
                    }
                }

                if (!uiCount)
                {
                    // Old Comment: a bit itchy, it should close GO_ZIGGURAT_DOOR_4 door after 10 secs, but it doesn't. skipping it for now.
                    // However looks like that this door is no more closed
                    DoUseDoorOrButton(GO_ZIGGURAT_DOOR_4);

                    // No more handlng of Abomnations
                    m_uiSlaugtherSquareTimer = 0;

                    if (Creature* pBaron = GetSingleCreatureFromStorage(NPC_BARON))
                    {
                        DoScriptText(SAY_ANNOUNCE_RAMSTEIN, pBaron);
                        if (Creature* pRamstein = pBaron->SummonCreature(NPC_RAMSTEIN, aStratholmeLocation[2].m_fX, aStratholmeLocation[2].m_fY, aStratholmeLocation[2].m_fZ, aStratholmeLocation[2].m_fO, TEMPSUMMON_DEAD_DESPAWN, 0))
                            pRamstein->GetMotionMaster()->MovePoint(0, aStratholmeLocation[3].m_fX, aStratholmeLocation[3].m_fY, aStratholmeLocation[3].m_fZ);

                        debug_log("SD2: Instance Stratholme - Slaugther event: Ramstein spawned.");
                    }
                }
                else
                    debug_log("SD2: Instance Stratholme - Slaugther event: %u Abomnation left to kill.", uiCount);
            }
            // After fail aggroing Ramstein means wipe on Ramstein, so close door again
            if (uiData == IN_PROGRESS && m_auiEncounter[uiType] == FAIL)
                DoUseDoorOrButton(GO_PORT_GAUNTLET);
            if (uiData == DONE)
            {
                // Open side gate and start summoning skeletons
                DoUseDoorOrButton(GO_PORT_SLAUGHTER_GATE);
                // use this timer as a bool just to start summoning
                m_uiMindlessSummonTimer = 500;
                m_uiMindlessCount = 0;
                m_luiUndeadGUIDs.clear();

                // Summon 5 guards
                if (Creature* pBaron = GetSingleCreatureFromStorage(NPC_BARON))
                {
                    for (uint8 i = 0; i < 5; ++i)
                    {
                        float fX, fY, fZ;
                        pBaron->GetRandomPoint(aStratholmeLocation[6].m_fX, aStratholmeLocation[6].m_fY, aStratholmeLocation[6].m_fZ, 5.0f, fX, fY, fZ);
                        if (Creature* pTemp = pBaron->SummonCreature(NPC_BLACK_GUARD, aStratholmeLocation[6].m_fX, aStratholmeLocation[6].m_fY, aStratholmeLocation[6].m_fZ, aStratholmeLocation[6].m_fO, TEMPSUMMON_DEAD_DESPAWN, 0))
                            m_luiGuardGUIDs.push_back(pTemp->GetObjectGuid());
                    }

                    debug_log("SD2: Instance Stratholme - Slaugther event: Summoned 5 guards.");
                }
            }
            // Open Door again and stop Abomnation
            if (uiData == FAIL && m_auiEncounter[uiType] != FAIL)
            {
                DoUseDoorOrButton(GO_PORT_GAUNTLET);
                m_uiSlaugtherSquareTimer = 0;

                // Let already moving Abomnations stop
                for (GuidSet::const_iterator itr = m_sAbomnationGUID.begin(); itr != m_sAbomnationGUID.end(); ++itr)
                {
                    Creature* pAbom = instance->GetCreature(*itr);
                    if (pAbom && pAbom->GetMotionMaster()->GetCurrentMovementGeneratorType() == POINT_MOTION_TYPE)
                        pAbom->GetMotionMaster()->MovementExpired();
                }
            }

            m_auiEncounter[uiType] = uiData;
            break;
        case TYPE_BARON:
            if (uiData == IN_PROGRESS)
            {
                // Close Slaughterhouse door if needed
                if (m_auiEncounter[uiType] == FAIL)
                    DoUseDoorOrButton(GO_PORT_GAUNTLET);

                // If Aurius was given the medaillon wait 5s before summoning him
                if (m_auiEncounter[TYPE_AURIUS] == SPECIAL)
                    m_uiAuriusSummonTimer = 5000;
            }
            if (uiData == DONE)
            {
                // Players successfully engaged Baron within the time-limit of his ultimatum
                //     Note: UpdateAI() prevents TYPE_BARON_RUN to be marked as FAILED if the
                //     Baron is already engaged (in progress) when the ultimatum timer expires
                if (m_auiEncounter[TYPE_BARON_RUN] == IN_PROGRESS)
                {
                    SetData(TYPE_BARON_RUN, DONE);
                    Map::PlayerList const& players = instance->GetPlayers();

                    for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr)
                    {
                        if (Player* pPlayer = itr->getSource())
                        {
                            if (pPlayer->HasAura(SPELL_BARON_ULTIMATUM))
                                pPlayer->RemoveAurasDueToSpell(SPELL_BARON_ULTIMATUM);

                            if (pPlayer->GetQuestStatus(QUEST_DEAD_MAN_PLEA) == QUEST_STATUS_INCOMPLETE)
                                pPlayer->AreaExploredOrEventHappens(QUEST_DEAD_MAN_PLEA);

                            // Argent Dawn reputation reward
                            pPlayer->CastSpell(pPlayer, SPELL_YSIDA_FREED, true);
                        }
                    }

                    // Open cage, finish rescue event
                    if (Creature* pYsida = GetSingleCreatureFromStorage(NPC_YSIDA))
                    {
                        DoScriptText(SAY_EPILOGUE, pYsida);
                        DoUseDoorOrButton(GO_YSIDA_CAGE);
                        pYsida->GetMotionMaster()->MovePoint(0, aStratholmeLocation[8].m_fX, aStratholmeLocation[8].m_fY, aStratholmeLocation[8].m_fZ, aStratholmeLocation[8].m_fO);
                    }
                }

                // If Aurius was spawned to help fight the Baron, mark that event as DONE
                if (m_auiEncounter[TYPE_AURIUS] == IN_PROGRESS)
                    SetData(TYPE_AURIUS, DONE);

                // Open Slaughterhouse door again
                DoUseDoorOrButton(GO_PORT_GAUNTLET);
            }
            if (uiData == FAIL)
                DoUseDoorOrButton(GO_PORT_GAUNTLET);

            m_auiEncounter[uiType] = uiData;
            break;
        case TYPE_BARTHILAS_RUN:
            if (uiData == IN_PROGRESS)
            {
                Creature* pBarthilas = GetSingleCreatureFromStorage(NPC_BARTHILAS);
                if (pBarthilas && pBarthilas->isAlive() && !pBarthilas->isInCombat())
                {
                    DoScriptText(SAY_WARN_BARON, pBarthilas);
                    pBarthilas->SetWalk(false);
                    pBarthilas->GetMotionMaster()->MovePoint(0, aStratholmeLocation[0].m_fX, aStratholmeLocation[0].m_fY, aStratholmeLocation[0].m_fZ);

                    m_uiBarthilasRunTimer = 8000;
                }
            }
            m_auiEncounter[uiType] = uiData;
            break;
        case TYPE_BLACK_GUARDS:
            // Prevent double action
            if (m_auiEncounter[uiType] == uiData)
                return;

            // Restart after failure, close Gauntlet
            if (uiData == IN_PROGRESS && m_auiEncounter[uiType] == FAIL)
                DoUseDoorOrButton(GO_PORT_GAUNTLET);
            // Wipe case - open gauntlet
            if (uiData == FAIL)
                DoUseDoorOrButton(GO_PORT_GAUNTLET);
            if (uiData == DONE)
            {
                if (Creature* pBaron = GetSingleCreatureFromStorage(NPC_BARON))
                    DoScriptText(SAY_UNDEAD_DEFEAT, pBaron);
                DoUseDoorOrButton(GO_ZIGGURAT_DOOR_5);
            }
            m_auiEncounter[uiType] = uiData;

            // No need to save anything here, so return
            return;
        case TYPE_POSTMASTER:
            m_auiEncounter[uiType] = uiData;
            if (uiData == IN_PROGRESS)
            {
                ++m_uiPostboxesUsed;

                // After the second post box prepare to spawn the Post Master
                if (m_uiPostboxesUsed == 2)
                    SetData(TYPE_POSTMASTER, SPECIAL);
            }
            // No need to save anything here, so return
            return;
        case TYPE_AURIUS:
            m_auiEncounter[uiType] = uiData;
            // Prevent further players to complete the quest in that instance
            // or autocomplete the follow-up quest
            // the flag will be set back if event is succeed
            if (uiData == SPECIAL)
            {
                if (Creature* pAurius = GetSingleCreatureFromStorage(NPC_AURIUS))
                    pAurius->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_QUESTGIVER);
                break;
            }
            // Baron killed and Aurius is alive: give him his NPC Flags back
            // So players can complete the quest
            // Fake his death
            if (uiData == DONE)
            {
                if (Creature* pAurius = GetSingleCreatureFromStorage(NPC_AURIUS))
                {
                    DoScriptText(SAY_AURIUS_DEATH, pAurius);
                    pAurius->StopMoving();
                    pAurius->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_QUESTGIVER);
                    pAurius->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
                    pAurius->InterruptNonMeleeSpells(true);
                    pAurius->SetHealth(1);
                    pAurius->GetMotionMaster()->MovementExpired();
                    pAurius->GetMotionMaster()->MoveIdle();
                    pAurius->RemoveAllAurasOnDeath();
                    pAurius->SetStandState(UNIT_STAND_STATE_DEAD);
                }
                break;
            }
            if (uiData == IN_PROGRESS)
            {
                // Despawn Aurius in the Chapel and spawn it in the Slaughter House to engage Baron
                if (Creature* pAurius_original = GetSingleCreatureFromStorage(NPC_AURIUS))
                    pAurius_original->ForcedDespawn();
                if (Creature* pBaron = GetSingleCreatureFromStorage(NPC_BARON))
                {
                    float fX, fY, fZ, fPosX, fPosY, fPosZ;
                    fX = pBaron->GetPositionX();
                    fY = pBaron->GetPositionY();
                    fZ = pBaron->GetPositionZ();
                    pBaron->GetRandomPoint(fX, fY, fZ, 4.0f, fPosX, fPosY, fPosZ);
                    if (Creature* pAurius = pBaron->SummonCreature(NPC_AURIUS, fPosX, fPosY, fPosZ, 0, TEMPSUMMON_DEAD_DESPAWN, 0))
                    {
                        DoScriptText(YELL_AURIUS_AGGRO, pAurius);
                        pAurius->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_QUESTGIVER);
                        pAurius->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
                        pAurius->AI()->AttackStart(pBaron);
                    }
                }
            }
            if (uiData == FAIL)
            {
                // Baron encounter failed and Aurius is spawned: kill him
                if (Creature* pAurius = GetSingleCreatureFromStorage(NPC_AURIUS))
                {
                    if (pAurius->isAlive())
                    {
                        DoScriptText(SAY_AURIUS_DEATH, pAurius);
                        pAurius->DealDamage(pAurius, pAurius->GetHealth(), nullptr, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NONE, nullptr, false);
                    }
                }
                break;
            }
    }

    if (uiData == DONE)
    {
        OUT_SAVE_INST_DATA;

        std::ostringstream saveStream;
        saveStream << m_auiEncounter[0] << " " << m_auiEncounter[1] << " " << m_auiEncounter[2] << " "
                   << m_auiEncounter[3] << " " << m_auiEncounter[4] << " " << m_auiEncounter[5] << " "
                   << m_auiEncounter[6] << " " << m_auiEncounter[7];

        m_strInstData = saveStream.str();

        SaveToDB();
        OUT_SAVE_INST_DATA_COMPLETE;
    }
}
Example #29
0
void WorldSession::DoLootRelease(uint64 lguid)
{
    Player  *player = GetPlayer();
    Loot    *loot;

    player->SetLootGUID(0);
    player->SendLootRelease(lguid);

    player->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_LOOTING);

    if (!player->IsInWorld())
        return;

    if (IS_GAMEOBJECT_GUID(lguid))
    {
        GameObject *go = GetPlayer()->GetMap()->GetGameObject(lguid);

        // not check distance for GO in case owned GO (fishing bobber case, for example) or Fishing hole GO
        if (!go || ((go->GetOwnerGUID() != _player->GetGUID() && go->GetGoType() != GAMEOBJECT_TYPE_FISHINGHOLE) && !go->IsWithinDistInMap(_player, INTERACTION_DISTANCE)))
            return;

        loot = &go->loot;

        if (go->GetGoType() == GAMEOBJECT_TYPE_DOOR)
        {
            // locked doors are opened with spelleffect openlock, prevent remove its as looted
            go->UseDoorOrButton();
        }
        else if (loot->isLooted() || go->GetGoType() == GAMEOBJECT_TYPE_FISHINGNODE)
        {
            // GO is mineral vein? so it is not removed after its looted
            if (go->GetGoType() == GAMEOBJECT_TYPE_CHEST)
            {
                uint32 go_min = go->GetGOInfo()->chest.minSuccessOpens;
                uint32 go_max = go->GetGOInfo()->chest.maxSuccessOpens;

                // only vein pass this check
                if (go_min != 0 && go_max > go_min)
                {
                    float amount_rate = sWorld->getRate(RATE_MINING_AMOUNT);
                    float min_amount = go_min*amount_rate;
                    float max_amount = go_max*amount_rate;

                    go->AddUse();
                    float uses = float(go->GetUseCount());

                    if (uses < max_amount)
                    {
                        if (uses >= min_amount)
                        {
                            float chance_rate = sWorld->getRate(RATE_MINING_NEXT);

                            int32 ReqValue = 175;
                            LockEntry const *lockInfo = sLockStore.LookupEntry(go->GetGOInfo()->chest.lockId);
                            if (lockInfo)
                                ReqValue = lockInfo->Skill[0];
                            float skill = float(player->GetSkillValue(SKILL_MINING))/(ReqValue+25);
                            double chance = pow(0.8*chance_rate, 4*(1/double(max_amount))*double(uses));
                            if (roll_chance_f((float)(100*chance+skill)))
                            {
                                go->SetLootState(GO_READY);
                            }
                            else                            // not have more uses
                                go->SetLootState(GO_JUST_DEACTIVATED);
                        }
                        else                                // 100% chance until min uses
                            go->SetLootState(GO_READY);
                    }
                    else                                    // max uses already
                        go->SetLootState(GO_JUST_DEACTIVATED);
                }
                else                                        // not vein
                    go->SetLootState(GO_JUST_DEACTIVATED);
            }
            else if (go->GetGoType() == GAMEOBJECT_TYPE_FISHINGHOLE)
            {                                               // The fishing hole used once more
                go->AddUse();                               // if the max usage is reached, will be despawned in next tick
                if (go->GetUseCount() >= urand(go->GetGOInfo()->fishinghole.minSuccessOpens, go->GetGOInfo()->fishinghole.maxSuccessOpens))
                {
                    go->SetLootState(GO_JUST_DEACTIVATED);
                }
                else
                    go->SetLootState(GO_READY);
            }
            else // not chest (or vein/herb/etc)
                go->SetLootState(GO_JUST_DEACTIVATED);

            loot->clear();
        }
        else
        {
            // not fully looted object
            go->SetLootState(GO_ACTIVATED);

            // if the round robin player release, reset it.
            if (player->GetGUID() == loot->roundRobinPlayer)
            {
                if (Group* pGroup = player->GetGroup())
                {
                    if (pGroup->GetLootMethod() != MASTER_LOOT)
                    {
                        loot->roundRobinPlayer = 0;
                    }
                }
                else
                    loot->roundRobinPlayer = 0;
            }
        }
    }
    else if (IS_CORPSE_GUID(lguid))        // ONLY remove insignia at BG
    {
        Corpse *corpse = ObjectAccessor::GetCorpse(*player, lguid);
        if (!corpse || !corpse->IsWithinDistInMap(_player, INTERACTION_DISTANCE))
            return;

        loot = &corpse->loot;

        if (loot->isLooted())
        {
            loot->clear();
            corpse->RemoveFlag(CORPSE_FIELD_DYNAMIC_FLAGS, CORPSE_DYNFLAG_LOOTABLE);
        }
    }
    else if (IS_ITEM_GUID(lguid))
    {
        Item *pItem = player->GetItemByGuid(lguid);
        if (!pItem)
            return;

        ItemPrototype const* proto = pItem->GetProto();

        // destroy only 5 items from stack in case prospecting and milling
        if (proto->Flags & (ITEM_PROTO_FLAG_PROSPECTABLE | ITEM_PROTO_FLAG_MILLABLE))
        {
            pItem->m_lootGenerated = false;
            pItem->loot.clear();

            uint32 count = pItem->GetCount();

            // >=5 checked in spell code, but will work for cheating cases also with removing from another stacks.
            if (count > 5)
                count = 5;

            player->DestroyItemCount(pItem, count, true);
        }
        else
            // FIXME: item must not be deleted in case not fully looted state. But this pre-request implement loot saving in DB at item save. Or cheating possible.
            player->DestroyItem(pItem->GetBagSlot(), pItem->GetSlot(), true);
        return;                                             // item can be looted only single player
    }
    else
    {
        Creature* pCreature = GetPlayer()->GetMap()->GetCreature(lguid);

        bool ok_loot = pCreature && pCreature->isAlive() == (player->getClass() == CLASS_ROGUE && pCreature->lootForPickPocketed);
        if (!ok_loot || !pCreature->IsWithinDistInMap(_player, INTERACTION_DISTANCE))
            return;

        loot = &pCreature->loot;
        if (loot->isLooted())
        {
            // skip pickpocketing loot for speed, skinning timer redunction is no-op in fact
            if (!pCreature->isAlive())
                pCreature->AllLootRemovedFromCorpse();

            pCreature->RemoveFlag(UNIT_DYNAMIC_FLAGS, UNIT_DYNFLAG_LOOTABLE);
            loot->clear();
        }
        else
        {
            // if the round robin player release, reset it.
            if (player->GetGUID() == loot->roundRobinPlayer)
            {
                if (Group* pGroup = player->GetGroup())
                {
                    if (pGroup->GetLootMethod() != MASTER_LOOT)
                    {
                        loot->roundRobinPlayer = 0;
                        pGroup->SendLooter(pCreature, NULL);

                        // force update of dynamic flags, otherwise other group's players still not able to loot.
                        pCreature->ForceValuesUpdateAtIndex(UNIT_DYNAMIC_FLAGS);
                    }
                }
                else
                    loot->roundRobinPlayer = 0;
            }
        }
    }

    //Player is not looking at loot list, he doesn't need to see updates on the loot list
    loot->RemoveLooter(player->GetGUID());
}
Example #30
0
void hyjalAI::UpdateAI(const uint32 uiDiff)
{
    if (!m_bIsEventInProgress)
        return;

    if (m_bIsSummoningWaves && m_pInstance)
    {
        if (m_uiWaveMoveTimer < uiDiff)
        {
            // Skip the master timer, and start next wave in 5. Clear the list, it should not be any here now.
            if (!m_pInstance->GetData(TYPE_TRASH_COUNT))
            {
                lWaveMobGUIDList.clear();
                m_uiNextWaveTimer = std::min(m_uiNextWaveTimer, (uint32)5000);
            }

            for (GuidList::const_iterator itr = lWaveMobGUIDList.begin(); itr != lWaveMobGUIDList.end(); ++itr)
            {
                if (Creature* pTemp = m_pInstance->instance->GetCreature(*itr))
                {
                    if (!pTemp->isAlive() || pTemp->getVictim())
                        continue;

                    pTemp->SetWalk(false);
                    pTemp->GetMotionMaster()->MovePoint(1, m_creature->GetPositionX(), m_creature->GetPositionY(), m_creature->GetPositionZ());
                }
            }
            m_uiWaveMoveTimer = 10000;
        }
        else
            m_uiWaveMoveTimer -= uiDiff;

        if (m_uiNextWaveTimer < uiDiff)
            SummonNextWave();
        else
            m_uiNextWaveTimer -= uiDiff;
    }

    if (m_uiCheckTimer < uiDiff)
    {
        for (uint8 i = 0; i < 2; ++i)
        {
            if (m_aBossGuid[i])
            {
                Creature* pBoss = m_creature->GetMap()->GetCreature(m_aBossGuid[i]);

                if (pBoss && !pBoss->isAlive())
                {
                    if (m_aBossGuid[i] == m_aBossGuid[0])
                    {
                        DoTalk(INCOMING);
                        m_bIsFirstBossDead = true;
                    }
                    else if (m_aBossGuid[i] == m_aBossGuid[1])
                    {
                        DoTalk(SUCCESS);
                        m_bIsSecondBossDead = true;
                    }

                    m_bIsEventInProgress = false;
                    m_uiCheckTimer = 0;

                    m_creature->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);

                    m_aBossGuid[i].Clear();

                    // Reset world state for enemies to disable it
                    m_pInstance->DoUpdateWorldState(WORLD_STATE_ENEMY, 0);

                    m_creature->SetActiveObjectState(false);
                }
            }
        }

        m_uiCheckTimer = 5000;
    }
    else
        m_uiCheckTimer -= uiDiff;

    if (!m_creature->SelectHostileTarget() || !m_creature->getVictim())
        return;

    for (uint8 i = 0; i < MAX_SPELL; ++i)
    {
        if (m_aSpells[i].m_uiSpellId)
        {
            if (m_uiSpellTimer[i] < uiDiff)
            {
                if (m_creature->IsNonMeleeSpellCasted(false))
                    m_creature->InterruptNonMeleeSpells(false);

                Unit* pTarget = NULL;

                switch (m_aSpells[i].m_pType)
                {
                    case TARGETTYPE_SELF:   pTarget = m_creature; break;
                    case TARGETTYPE_RANDOM: pTarget = m_creature->SelectAttackingTarget(ATTACKING_TARGET_RANDOM, 0); break;
                    case TARGETTYPE_VICTIM: pTarget = m_creature->getVictim(); break;
                }

                if (pTarget)
                {
                    DoCastSpellIfCan(pTarget, m_aSpells[i].m_uiSpellId);
                    m_uiSpellTimer[i] = m_aSpells[i].m_uiCooldown;
                }
            }
            else
                m_uiSpellTimer[i] -= uiDiff;
        }
    }

    DoMeleeAttackIfReady();
}