Share Pastebin
Guest
Public paste!

boss_xt002/ulduar

By: a guest | Mar 22nd, 2010 | Syntax: None | Size: 28.29 KB | Hits: 76 | Expires: Never
Copy text to clipboard
  1. /*
  2.  * Copyright (C) 2008 - 2009 Trinity <http://www.trinitycore.org/>
  3.  *
  4.  * This program is free software; you can redistribute it and/or modify
  5.  * it under the terms of the GNU General Public License as published by
  6.  * the Free Software Foundation; either version 2 of the License, or
  7.  * (at your option) any later version.
  8.  *
  9.  * This program is distributed in the hope that it will be useful,
  10.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12.  * GNU General Public License for more details.
  13.  *
  14.  * You should have received a copy of the GNU General Public License
  15.  * along with this program; if not, write to the Free Software
  16.  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  17.  */
  18.  
  19. #include "ScriptedPch.h"
  20. #include "ulduar.h"
  21.  
  22.  
  23. enum Spells
  24. {
  25.     SPELL_TYMPANIC_TANTRUM                      = 62776,
  26.     SPELL_SEARING_LIGHT_10                      = 63018,
  27.     SPELL_SEARING_LIGHT_25                      = 65121,
  28.  
  29.  
  30.     SPELL_GRAVITY_BOMB_10                       = 63024,
  31.     SPELL_GRAVITY_BOMB_25                       = 63234,
  32.     SPELL_GRAVITY_BOMB_AURA_10                  = 63025,
  33.     SPELL_GRAVITY_BOMB_AURA_25                  = 63233,
  34.  
  35.  
  36.     SPELL_HEARTBREAK_10                         = 65737,
  37.     SPELL_HEARTBREAK_25                         = 64193,
  38.  
  39.  
  40.     SPELL_ENRAGE                                = 26662,
  41.  
  42.  
  43.     //------------------VOID ZONE--------------------
  44.     SPELL_VOID_ZONE_10                          = 64203,
  45.     SPELL_VOID_ZONE_25                          = 64235,
  46.  
  47.  
  48.     // Life Spark
  49.     SPELL_STATIC_CHARGED_10                     = 64227,
  50.     SPELL_STATIC_CHARGED_25                     = 64236,
  51.     SPELL_SHOCK                                 = 64230,
  52.  
  53.  
  54.     //----------------XT-002 HEART-------------------
  55.     SPELL_EXPOSED_HEART                         = 63849,
  56.  
  57.  
  58.     //---------------XM-024 PUMMELLER----------------
  59.     SPELL_ARCING_SMASH                          = 8374,
  60.     SPELL_TRAMPLE                               = 5568,
  61.     SPELL_UPPERCUT                              = 10966,
  62.  
  63.  
  64.     //------------------BOOMBOT-----------------------
  65.     SPELL_BOOM                                  = 62834,
  66. };
  67.  
  68.  
  69. enum Timers
  70. {
  71.     TIMER_TYMPANIC_TANTRUM_MIN                  = 32000,
  72.     TIMER_TYMPANIC_TANTRUM_MAX                  = 36000,
  73.     TIMER_SEARING_LIGHT                         = 20000,
  74.     TIMER_SPAWN_LIFE_SPARK                      = 9000,
  75.     TIMER_GRAVITY_BOMB                          = 20000,
  76.     TIMER_HEART_PHASE                           = 30000,
  77.     TIMER_ENRAGE                                = 600000,
  78.     TIMER_GRAVITY_BOMB_AURA                     = 8900,
  79.  
  80.  
  81.     TIMER_VOID_ZONE                             = 3000,
  82.  
  83.  
  84.     // Life Spark
  85.     TIMER_SHOCK                                 = 12000,
  86.  
  87.  
  88.     // Pummeller
  89.     // Timers may be off
  90.     TIMER_ARCING_SMASH                          = 27000,
  91.     TIMER_TRAMPLE                               = 22000,
  92.     TIMER_UPPERCUT                              = 17000,
  93.  
  94.  
  95.     TIMER_SPAWN_ADD                             = 12000,
  96. };
  97.  
  98.  
  99. enum Creatures
  100. {
  101.     NPC_VOID_ZONE                               = 34001,
  102.     NPC_LIFE_SPARK                              = 34004,
  103.     NPC_XT002_HEART                             = 33329,
  104.     NPC_XS013_SCRAPBOT                          = 33343,
  105.     NPC_XM024_PUMMELLER                         = 33344,
  106.     NPC_XE321_BOOMBOT                           = 33346,
  107. };
  108.  
  109.  
  110. enum Actions
  111. {
  112.     ACTION_ENTER_HARD_MODE                      = 0,
  113. };
  114.  
  115.  
  116. enum XT002Data
  117. {
  118.     DATA_TRANSFERED_HEALTH                      = 0,
  119. };
  120.  
  121.  
  122. enum Yells
  123. {
  124.     SAY_AGGRO                                   = -1603300,
  125.     SAY_HEART_OPENED                            = -1603301,
  126.     SAY_HEART_CLOSED                            = -1603302,
  127.     SAY_TYMPANIC_TANTRUM                        = -1603303,
  128.     SAY_SLAY_1                                  = -1603304,
  129.     SAY_SLAY_2                                  = -1603305,
  130.     SAY_BERSERK                                 = -1603306,
  131.     SAY_DEATH                                   = -1603307,
  132.     SAY_SUMMON                                  = -1603308,
  133. };
  134.  
  135.  
  136. //#define GRAVITY_BOMB_DMG_MIN_10                11700
  137. //#define GRAVITY_BOMB_DMG_MAX_10                12300
  138. //#define GRAVITY_BOMB_DMG_MIN_25                14625
  139. //#define GRAVITY_BOMB_DMG_MAX_25                15375
  140. //#define GRAVITY_BOMB_RADIUS                    12
  141.  
  142.  
  143. //#define VOID_ZONE_DMG_10                      5000
  144. //#define VOID_ZONE_DMG_25                      7500
  145. //#define VOID_ZONE_RADIUS                      
  146.  
  147.  
  148.  
  149.  
  150. /************************************************
  151. -----------------SPAWN LOCATIONS-----------------
  152. ************************************************/
  153. //Shared Z-level
  154. #define SPAWN_Z                                 412
  155. //Lower right
  156. #define LR_X                                    796
  157. #define LR_Y                                    -94
  158. //Lower left
  159. #define LL_X                                    796
  160. #define LL_Y                                    57
  161. //Upper right
  162. #define UR_X                                    890
  163. #define UR_Y                                    -82
  164. //Upper left
  165. #define UL_X                                    894
  166. #define UL_Y                                    62
  167.  
  168.  
  169. /*-------------------------------------------------------
  170.  *
  171.  *        XT-002 DECONSTRUCTOR
  172.  *
  173.  *///----------------------------------------------------
  174. struct boss_xt002_AI : public BossAI
  175. {
  176.     boss_xt002_AI(Creature *pCreature) : BossAI(pCreature, TYPE_XT002)
  177.     {
  178.     }
  179.  
  180.  
  181.     uint32 uiSearingLightTimer;
  182.     uint32 uiSpawnLifeSparkTimer;
  183.     uint32 uiGravityBombTimer;
  184.     uint32 uiGravityBombAuraTimer;
  185.     uint32 uiTympanicTantrumTimer;
  186.     uint32 uiHeartPhaseTimer;
  187.     uint32 uiSpawnAddTimer;
  188.     uint32 uiEnrageTimer;
  189.    
  190.     bool searing_light_active;
  191.     uint64 uiSearingLightTarget;
  192.  
  193.  
  194.     bool gravity_bomb_active;
  195.     uint64 uiGravityBombTarget;
  196.  
  197.  
  198.     uint8 phase;
  199.     uint8 heart_exposed;
  200.     bool enraged;
  201.  
  202.  
  203.     uint32 transferHealth;
  204.     bool enterHardMode;
  205.     bool hardMode;
  206.  
  207.  
  208.     void Reset()
  209.     {
  210.         m_creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE | UNIT_FLAG_DISABLE_MOVE | UNIT_FLAG_NOT_SELECTABLE);
  211.  
  212.  
  213.         //Makes XT-002 to cast a light bomb 10 seconds after aggro.
  214.         uiSearingLightTimer = TIMER_SEARING_LIGHT/2;
  215.         uiSpawnLifeSparkTimer = TIMER_SPAWN_LIFE_SPARK;
  216.         uiGravityBombTimer = TIMER_GRAVITY_BOMB;
  217.         uiGravityBombAuraTimer = TIMER_GRAVITY_BOMB_AURA;
  218.         uiHeartPhaseTimer = TIMER_HEART_PHASE;
  219.         uiSpawnAddTimer = TIMER_SPAWN_ADD;
  220.         uiEnrageTimer = TIMER_ENRAGE;
  221.  
  222.  
  223.         //Tantrum is casted a bit slower the first time.
  224.         uiTympanicTantrumTimer = urand(TIMER_TYMPANIC_TANTRUM_MIN, TIMER_TYMPANIC_TANTRUM_MAX) * 2;
  225.  
  226.  
  227.         searing_light_active = false;
  228.         gravity_bomb_active = false;
  229.         enraged = false;
  230.         hardMode = false;
  231.         enterHardMode = false;
  232.  
  233.  
  234.         phase = 1;
  235.         heart_exposed = 0;
  236.     }
  237.  
  238.  
  239.     void EnterCombat(Unit* who)
  240.     {
  241.         DoScriptText(SAY_AGGRO, m_creature);
  242.         _EnterCombat();
  243.     }
  244.  
  245.  
  246.     void DoAction(const int32 action)
  247.     {
  248.         switch (action)
  249.         {
  250.             case ACTION_ENTER_HARD_MODE:
  251.                 if (!hardMode)
  252.                 {
  253.                     hardMode = true;
  254.  
  255.  
  256.                     // Enter hard mode
  257.                     enterHardMode = true;
  258.  
  259.  
  260.                     // set max health
  261.                     m_creature->SetHealth(m_creature->GetMaxHealth());
  262.  
  263.  
  264.                     // Get his heartbreak buff
  265.                     m_creature->CastSpell(m_creature, RAID_MODE(SPELL_HEARTBREAK_10, SPELL_HEARTBREAK_25), true);
  266.                 }
  267.                 break;
  268.         }
  269.     }
  270.  
  271.  
  272.     void SetData(uint32 id, uint32 value)
  273.     {
  274.         switch(id)
  275.         {
  276.             case DATA_TRANSFERED_HEALTH:
  277.                 transferHealth = value;
  278.                 break;
  279.         }
  280.     }
  281.  
  282.  
  283.     void KilledUnit(Unit* victim)
  284.     {
  285.         DoScriptText(RAND(SAY_SLAY_1,SAY_SLAY_2), m_creature);
  286.     }
  287.  
  288.  
  289.     void JustDied(Unit *victim)
  290.     {
  291.         DoScriptText(SAY_DEATH, m_creature);
  292.         _JustDied();
  293.     }
  294.  
  295.  
  296.     void UpdateAI(const uint32 diff)
  297.     {
  298.         if (!UpdateVictim())
  299.             return;
  300.  
  301.  
  302.         if (enterHardMode)
  303.         {
  304.             SetPhaseOne();
  305.             enterHardMode = false;
  306.         }
  307.  
  308.  
  309.         // Handles spell casting. These spells only occur during phase 1 and hard mode
  310.         if (phase == 1 || hardMode)
  311.         {
  312.             if (uiSearingLightTimer <= diff)
  313.             {
  314.                 if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0))
  315.                 {
  316.                     DoCast(pTarget, RAID_MODE(SPELL_SEARING_LIGHT_10, SPELL_SEARING_LIGHT_25));
  317.                     uiSearingLightTarget = pTarget->GetGUID();
  318.                 }
  319.                 uiSpawnLifeSparkTimer = TIMER_SPAWN_LIFE_SPARK;
  320.                 if (hardMode)
  321.                     searing_light_active = true;
  322.                 uiSearingLightTimer = TIMER_SEARING_LIGHT;
  323.             } else uiSearingLightTimer -= diff;
  324.  
  325.  
  326.             if (uiGravityBombTimer <= diff)
  327.             {
  328.                 if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0))
  329.                 {
  330.                     DoCast(pTarget, RAID_MODE(SPELL_GRAVITY_BOMB_10,SPELL_GRAVITY_BOMB_25));
  331.                     uiGravityBombTarget = pTarget->GetGUID();
  332.                 }
  333.                 uiGravityBombTimer = TIMER_GRAVITY_BOMB;
  334.                 gravity_bomb_active = true;
  335.             } else uiGravityBombTimer -= diff;
  336.  
  337.  
  338.             if (uiTympanicTantrumTimer <= 0)
  339.             {
  340.                 DoScriptText(SAY_TYMPANIC_TANTRUM, m_creature);
  341.                 DoCast(SPELL_TYMPANIC_TANTRUM);
  342.                 uiTympanicTantrumTimer = urand(TIMER_TYMPANIC_TANTRUM_MIN, TIMER_TYMPANIC_TANTRUM_MAX);
  343.             } else uiTympanicTantrumTimer -= diff;
  344.         }
  345.  
  346.  
  347.         if (!hardMode)
  348.         {
  349.             if (phase == 1)
  350.             {
  351.                 if (HealthBelowPct(75) && heart_exposed == 0)
  352.                 {
  353.                     exposeHeart();
  354.                 }
  355.                 else if (HealthBelowPct(50) && heart_exposed == 1)
  356.                 {
  357.                     exposeHeart();
  358.                 }
  359.                 else if (HealthBelowPct(25) && heart_exposed == 2)
  360.                 {
  361.                     exposeHeart();
  362.                 }
  363.  
  364.  
  365.                 DoMeleeAttackIfReady();
  366.             }
  367.             else
  368.             {
  369.                 //Stop moving
  370.                 m_creature->StopMoving();
  371.  
  372.  
  373.                 //Start summoning adds
  374.                 if (uiSpawnAddTimer <= diff)
  375.                 {
  376.                     DoScriptText(SAY_SUMMON, m_creature);
  377.  
  378.  
  379.                     // Spawn Pummeller
  380.                     switch (rand() % 4)
  381.                     {
  382.                         case 0: m_creature->SummonCreature(NPC_XM024_PUMMELLER, LR_X, LR_Y, SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  383.                         case 1: m_creature->SummonCreature(NPC_XM024_PUMMELLER, LL_X, LL_Y, SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  384.                         case 2: m_creature->SummonCreature(NPC_XM024_PUMMELLER, UR_X, UR_Y, SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  385.                         case 3: m_creature->SummonCreature(NPC_XM024_PUMMELLER, UL_X, UL_Y, SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  386.                     }
  387.  
  388.  
  389.                     // Spawn 5 Bombs
  390.                     for (int8 n = 0; n < 5; n++)
  391.                     {
  392.                         //Some randomes are added so they wont spawn in a pile
  393.                         switch(rand() % 4)
  394.                         {
  395.                             case 0: m_creature->SummonCreature(NPC_XS013_SCRAPBOT, irand(LR_X - 3, LR_X + 3), irand(LR_Y - 3, LR_Y + 3), SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  396.                             case 1: m_creature->SummonCreature(NPC_XS013_SCRAPBOT, irand(LL_X - 3, LL_X + 3), irand(LL_Y - 3, LL_Y + 3), SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  397.                             case 2: m_creature->SummonCreature(NPC_XS013_SCRAPBOT, irand(UR_X - 3, UR_X + 3), irand(UR_Y - 3, UR_Y + 3), SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  398.                             case 3: m_creature->SummonCreature(NPC_XS013_SCRAPBOT, irand(UL_X - 3, UL_X + 3), irand(UL_Y - 3, UL_Y + 3), SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  399.                         }
  400.                     }
  401.            
  402.                     //Spawn 5 Scrapbots
  403.                     switch (rand() % 4)
  404.                     {
  405.                         case 0: m_creature->SummonCreature(NPC_XE321_BOOMBOT, LR_X, LR_Y, SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  406.                         case 1: m_creature->SummonCreature(NPC_XE321_BOOMBOT, LL_X, LL_Y, SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  407.                         case 2: m_creature->SummonCreature(NPC_XE321_BOOMBOT, UR_X, UR_Y, SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  408.                         case 3: m_creature->SummonCreature(NPC_XE321_BOOMBOT, UL_X, UL_Y, SPAWN_Z, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000); break;
  409.                     }
  410.  
  411.  
  412.                     uiSpawnAddTimer = TIMER_SPAWN_ADD;
  413.                 } else uiSpawnAddTimer -= diff;
  414.  
  415.  
  416.                 // Is the phase over?
  417.                 if (uiHeartPhaseTimer <= diff)
  418.                 {
  419.                     DoScriptText(SAY_HEART_CLOSED, m_creature);
  420.                     SetPhaseOne();
  421.                 }
  422.                 else
  423.                     uiHeartPhaseTimer -= diff;
  424.             }
  425.         }
  426.         else
  427.         {
  428.             // Adding life sparks when searing light debuff runs out if hard mode
  429.             if (searing_light_active)
  430.             {
  431.                 if (uiSpawnLifeSparkTimer <= diff)
  432.                 {
  433.                     if (Unit *pSearingLightTarget = m_creature->GetUnit(*m_creature, uiSearingLightTarget))
  434.                         pSearingLightTarget->SummonCreature(NPC_LIFE_SPARK, pSearingLightTarget->GetPositionX(), pSearingLightTarget->GetPositionY(), pSearingLightTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000);
  435.                     uiSpawnLifeSparkTimer = TIMER_SPAWN_LIFE_SPARK;
  436.                     searing_light_active = false;
  437.                 } else uiSpawnLifeSparkTimer -= diff;
  438.             }
  439.         }
  440.        
  441.         if (gravity_bomb_active)
  442.         {
  443.             if (uiGravityBombAuraTimer <= diff)
  444.             {
  445.                 if (Unit *pGravityBombTarget = m_creature->GetUnit(*m_creature, uiGravityBombTarget))
  446.                 {
  447.                     pGravityBombTarget->RemoveAurasDueToSpell(RAID_MODE(SPELL_GRAVITY_BOMB_10,SPELL_GRAVITY_BOMB_25));
  448.                     if (hardMode)
  449.                     {
  450.                         //Remains spawned for 3 minutes
  451.                         pGravityBombTarget->SummonCreature(NPC_VOID_ZONE, pGravityBombTarget->GetPositionX(), pGravityBombTarget->GetPositionY(), pGravityBombTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN, 180000);
  452.                     }
  453.                 }
  454.  
  455.  
  456.                 gravity_bomb_active = false;
  457.                 uiGravityBombAuraTimer = TIMER_GRAVITY_BOMB_AURA;
  458.                 //gravityBomb();
  459.             } else uiGravityBombAuraTimer -= diff;
  460.         }
  461.  
  462.  
  463.         //Enrage stuff
  464.         if (!enraged)
  465.             if (uiEnrageTimer <= diff)
  466.             {
  467.                 DoScriptText(SAY_BERSERK, m_creature);
  468.                 DoCast(m_creature, SPELL_ENRAGE);
  469.                 enraged = true;
  470.             } else uiEnrageTimer -= diff;
  471.     }
  472.  
  473.  
  474.     void exposeHeart()
  475.     {
  476.         //Make untargetable
  477.         m_creature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE | UNIT_FLAG_NOT_SELECTABLE);
  478.  
  479.  
  480.         //Summon the heart npc
  481.         m_creature->SummonCreature(NPC_XT002_HEART, m_creature->GetPositionX(), m_creature->GetPositionY(), m_creature->GetPositionZ() + 7, 0, TEMPSUMMON_TIMED_DESPAWN, TIMER_HEART_PHASE);
  482.        
  483.         // Start "end of phase 2 timer"
  484.         uiHeartPhaseTimer = TIMER_HEART_PHASE;
  485.  
  486.  
  487.         //Phase 2 has offically started
  488.         phase = 2;
  489.         heart_exposed++;
  490.  
  491.  
  492.         //Reset the add spawning timer
  493.         uiSpawnAddTimer = TIMER_SPAWN_ADD;
  494.  
  495.  
  496.         DoScriptText(SAY_HEART_OPENED, m_creature);
  497.     }
  498.  
  499.  
  500.     void SetPhaseOne()
  501.     {
  502.         uiSearingLightTimer = TIMER_SEARING_LIGHT / 2;
  503.         uiGravityBombTimer = TIMER_GRAVITY_BOMB;
  504.         uiTympanicTantrumTimer = urand(TIMER_TYMPANIC_TANTRUM_MIN, TIMER_TYMPANIC_TANTRUM_MAX);
  505.         uiSpawnAddTimer = TIMER_SPAWN_ADD;
  506.  
  507.  
  508.         if (!hardMode)
  509.             m_creature->ModifyHealth(-transferHealth);
  510.  
  511.  
  512.         m_creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE | UNIT_FLAG_NOT_SELECTABLE);
  513.         phase = 1;
  514.     }
  515.  
  516.  
  517.     // TODO: put in comment and kept for reference. The spell should be fixed properly in spell system, if necessary.
  518.     ////Have to do this the custom way since the original spell messes up player movement
  519.     //void gravityBomb()
  520.     //{
  521.     //    uint32 maxDamage = RAID_MODE(GRAVITY_BOMB_DMG_MAX_10, GRAVITY_BOMB_DMG_MAX_25);
  522.     //    uint32 minDamage = RAID_MODE(GRAVITY_BOMB_DMG_MIN_10, GRAVITY_BOMB_DMG_MIN_25);
  523.     //    uint16 range = GRAVITY_BOMB_RADIUS;
  524.     //    Map* pMap = me->GetMap();
  525.     //    if (pMap && pMap->IsDungeon())
  526.     //    {
  527.     //        Map::PlayerList const &PlayerList = pMap->GetPlayers();
  528.     //        for (Map::PlayerList::const_iterator i = PlayerList.begin(); i != PlayerList.end(); ++i)
  529.     //        {
  530.     //            //If a player is within the range of the spell
  531.     //            if (i->getSource() && i->getSource()->GetDistance2d(pGravityBombTarget) <= range)
  532.     //            {
  533.     //                //Deal damage to the victim
  534.     //                int32 damage = urand(minDamage, maxDamage);
  535.     //                i->getSource()->ModifyHealth(-damage);
  536.     //                m_creature->SendSpellNonMeleeDamageLog(i->getSource(), SPELL_GRAVITY_BOMB_AURA_10, damage, SPELL_SCHOOL_MASK_SHADOW, 0, 0, false, 0);
  537.  
  538.  
  539.     //                //Replacing the tractor beam effect
  540.     //                i->getSource()->JumpTo(pGravityBombTarget, 5);
  541.     //            }
  542.     //        }
  543.     //    }
  544.     //}
  545. };
  546.  
  547.  
  548. CreatureAI* GetAI_boss_xt002(Creature* pCreature)
  549. {
  550.     return new boss_xt002_AI(pCreature);
  551. }
  552.  
  553.  
  554. /*-------------------------------------------------------
  555.  *
  556.  *        XT-002 HEART
  557.  *
  558.  *///----------------------------------------------------
  559. struct mob_xt002_heartAI : public ScriptedAI
  560. {
  561.     mob_xt002_heartAI(Creature* pCreature) : ScriptedAI(pCreature)
  562.     {
  563.         m_pInstance = pCreature->GetInstanceData();
  564.         m_creature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_DISABLE_MOVE | UNIT_FLAG_STUNNED);
  565.         m_creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE | UNIT_FLAG_NOT_SELECTABLE);
  566.         DoCast(m_creature, SPELL_EXPOSED_HEART);
  567.     }
  568.  
  569.  
  570.     ScriptedInstance* m_pInstance;
  571.  
  572.  
  573.     void JustDied(Unit *victim)
  574.     {
  575.         if (m_pInstance)
  576.             if (Creature* pXT002 = m_creature->GetCreature(*m_creature, m_pInstance->GetData64(TYPE_XT002)))
  577.                 if (pXT002->AI())
  578.                     pXT002->AI()->DoAction(ACTION_ENTER_HARD_MODE);
  579.  
  580.  
  581.         //removes the aura
  582.         m_creature->RemoveAurasDueToSpell(SPELL_EXPOSED_HEART);
  583.     }
  584.  
  585.  
  586.     void DamageTaken(Unit *pDone, uint32 &damage)
  587.     {
  588.         if (Creature* pXT002 = m_creature->GetCreature(*m_creature, m_pInstance->GetData64(TYPE_XT002)))
  589.             if (pXT002->AI())
  590.             {
  591.                 uint32 health = m_creature->GetHealth();
  592.                 health -= damage;
  593.                 if (health < 0)
  594.                     health = 0;
  595.  
  596.  
  597.                 pXT002->AI()->SetData(DATA_TRANSFERED_HEALTH, m_creature->GetMaxHealth() - health);
  598.             }
  599.     }
  600. };
  601.  
  602.  
  603. CreatureAI* GetAI_mob_xt002_heart(Creature* pCreature)
  604. {
  605.     return new mob_xt002_heartAI(pCreature);
  606. }
  607.  
  608.  
  609. /*-------------------------------------------------------
  610.  *
  611.  *        XS-013 SCRAPBOT
  612.  *
  613.  *///----------------------------------------------------
  614. struct mob_scrapbotAI : public ScriptedAI
  615. {
  616.     mob_scrapbotAI(Creature* pCreature) : ScriptedAI(pCreature)
  617.     {
  618.         m_pInstance = m_creature->GetInstanceData();
  619.     }
  620.  
  621.  
  622.     ScriptedInstance* m_pInstance;
  623.  
  624.  
  625.     void Reset()
  626.     {
  627.         m_creature->SetReactState(REACT_PASSIVE);
  628.  
  629.  
  630.         if (Creature* pXT002 = m_creature->GetCreature(*m_creature, m_pInstance->GetData64(TYPE_XT002)))
  631.             m_creature->GetMotionMaster()->MoveChase(pXT002);
  632.     }
  633.  
  634.  
  635.     void UpdateAI(const uint32 diff)
  636.     {
  637.         if (Creature* pXT002 = m_creature->GetCreature(*m_creature, m_pInstance->GetData64(TYPE_XT002)))
  638.         {
  639.             if (m_creature->GetDistance2d(pXT002) <= 0.5)
  640.             {
  641.                 // TODO Send raid message
  642.  
  643.  
  644.                 // Increase health with 1 percent
  645.                 pXT002->ModifyHealth(pXT002->GetMaxHealth() * 0.01);
  646.  
  647.  
  648.                 // Despawns the scrapbot
  649.                 m_creature->ForcedDespawn();
  650.             }
  651.         }
  652.     }
  653. };
  654.  
  655.  
  656. CreatureAI* GetAI_mob_scrapbot(Creature* pCreature)
  657. {
  658.     return new mob_scrapbotAI(pCreature);
  659. }
  660.  
  661.  
  662. /*-------------------------------------------------------
  663.  *
  664.  *        XM-024 PUMMELLER
  665.  *
  666.  *///----------------------------------------------------
  667. struct mob_pummellerAI : public ScriptedAI
  668. {
  669.     mob_pummellerAI(Creature* pCreature) : ScriptedAI(pCreature)
  670.     {
  671.         m_pInstance = pCreature->GetInstanceData();
  672.     }
  673.  
  674.  
  675.     ScriptedInstance* m_pInstance;
  676.     int32 uiArcingSmashTimer;
  677.     int32 uiTrampleTimer;
  678.     int32 uiUppercutTimer;
  679.  
  680.  
  681.     void Reset()
  682.     {
  683.         uiArcingSmashTimer = TIMER_ARCING_SMASH;
  684.         uiTrampleTimer = TIMER_TRAMPLE;
  685.         uiUppercutTimer = TIMER_UPPERCUT;
  686.     }
  687.  
  688.  
  689.     void UpdateAI(const uint32 diff)
  690.     {
  691.         if (!UpdateVictim())
  692.             return;
  693.        
  694.         if (m_creature->IsWithinMeleeRange(m_creature->getVictim()))
  695.         {
  696.             if (uiArcingSmashTimer <= diff)
  697.             {
  698.                 DoCast(m_creature->getVictim(), SPELL_ARCING_SMASH);
  699.                 uiArcingSmashTimer = TIMER_ARCING_SMASH;
  700.             } else uiArcingSmashTimer -= diff;
  701.  
  702.  
  703.             if (uiTrampleTimer <= diff)
  704.             {
  705.                 DoCast(m_creature->getVictim(), SPELL_TRAMPLE);
  706.                 uiTrampleTimer = TIMER_TRAMPLE;
  707.             } else uiTrampleTimer -= diff;
  708.  
  709.  
  710.             if (uiUppercutTimer <= diff)
  711.             {
  712.                 DoCast(m_creature->getVictim(), SPELL_UPPERCUT);
  713.                 uiUppercutTimer = TIMER_UPPERCUT;
  714.             } else uiUppercutTimer -= diff;
  715.         }
  716.  
  717.  
  718.         DoMeleeAttackIfReady();
  719.     }
  720. };
  721.  
  722.  
  723. CreatureAI* GetAI_mob_pummeller(Creature* pCreature)
  724. {
  725.     return new mob_pummellerAI(pCreature);
  726. }
  727.  
  728.  
  729. /*-------------------------------------------------------
  730.  *
  731.  *        XE-321 BOOMBOT
  732.  *
  733.  *///----------------------------------------------------
  734. struct mob_boombotAI : public ScriptedAI
  735. {
  736.     mob_boombotAI(Creature* pCreature) : ScriptedAI(pCreature)
  737.     {
  738.         m_pInstance = pCreature->GetInstanceData();
  739.     }
  740.  
  741.  
  742.     ScriptedInstance* m_pInstance;
  743.  
  744.  
  745.     void Reset()
  746.     {
  747.         m_creature->SetReactState(REACT_PASSIVE);
  748.  
  749.  
  750.         if (Creature* pXT002 = m_creature->GetCreature(*m_creature, m_pInstance->GetData64(TYPE_XT002)))
  751.             m_creature->GetMotionMaster()->MoveChase(pXT002);
  752.     }
  753.  
  754.  
  755.     void JustDied(Unit *killer)
  756.     {
  757.         DoCast(SPELL_BOOM);
  758.     }
  759.  
  760.  
  761.     void UpdateAI(const uint32 diff)
  762.     {
  763.         if (Creature* pXT002 = m_creature->GetCreature(*m_creature, m_pInstance->GetData64(TYPE_XT002)))
  764.         {
  765.             if (m_creature->GetDistance2d(pXT002) <= 0.5)
  766.             {
  767.                 //Explosion
  768.                 DoCast(m_creature, SPELL_BOOM);
  769.  
  770.  
  771.                 //Despawns the boombot
  772.                 m_creature->ForcedDespawn();
  773.             }
  774.         }
  775.     }
  776. };
  777.  
  778.  
  779. CreatureAI* GetAI_mob_boombot(Creature* pCreature)
  780. {
  781.     return new mob_boombotAI(pCreature);
  782. }
  783.  
  784.  
  785. /*-------------------------------------------------------
  786.  *
  787.  *        VOID ZONE
  788.  *
  789.  *///----------------------------------------------------
  790. struct mob_void_zoneAI : public ScriptedAI
  791. {
  792.     mob_void_zoneAI(Creature* pCreature) : ScriptedAI(pCreature)
  793.     {
  794.         m_pInstance = pCreature->GetInstanceData();
  795.         m_creature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_DISABLE_MOVE);
  796.     }
  797.  
  798.  
  799.     ScriptedInstance* m_pInstance;
  800.     uint32 uiVoidZoneTimer;
  801.  
  802.  
  803.     void Reset()
  804.     {
  805.         uiVoidZoneTimer = TIMER_VOID_ZONE;
  806.     }
  807.  
  808.  
  809.     void UpdateAI(const uint32 diff)
  810.     {
  811.         if (uiVoidZoneTimer <= diff)
  812.         {
  813.             //voidZone();
  814.             uiVoidZoneTimer = TIMER_VOID_ZONE;
  815.         } else uiVoidZoneTimer -= diff;
  816.     }
  817.  
  818.  
  819.     // TODO: put in comment and kept for reference. The spell should be fixed properly in spell system, if necessary.
  820.     //void voidZone()
  821.     //{
  822.     //    Map* pMap = me->GetMap();
  823.     //    if (pMap && pMap->IsDungeon())
  824.     //    {
  825.     //        Map::PlayerList const &PlayerList = pMap->GetPlayers();
  826.     //        for (Map::PlayerList::const_iterator i = PlayerList.begin(); i != PlayerList.end(); ++i)
  827.     //        {
  828.     //            // If a player is within the range of the spell
  829.     //            if (i->getSource() && i->getSource()->GetDistance2d(m_creature) <= 16)
  830.     //            {
  831.     //                // Deal damage to the victim
  832.     //                int32 damage = RAID_MODE(VOID_ZONE_DMG_10, VOID_ZONE_DMG_25);
  833.     //                m_creature->DealDamage(i->getSource(), damage, NULL, SPELL_DIRECT_DAMAGE, SPELL_SCHOOL_MASK_SHADOW);
  834.     //            }
  835.     //        }
  836.     //    }
  837.     //}
  838. };
  839.  
  840.  
  841. CreatureAI* GetAI_mob_void_zone(Creature* pCreature)
  842. {
  843.     return new mob_void_zoneAI(pCreature);
  844. }
  845.  
  846.  
  847. /*-------------------------------------------------------
  848.  *
  849.  *        LIFE SPARK
  850.  *
  851.  *///----------------------------------------------------
  852. struct mob_life_sparkAI : public ScriptedAI
  853. {
  854.     mob_life_sparkAI(Creature* pCreature) : ScriptedAI(pCreature)
  855.     {
  856.         m_pInstance = pCreature->GetInstanceData();
  857.     }
  858.  
  859.  
  860.     ScriptedInstance* m_pInstance;
  861.     uint32 uiShockTimer;
  862.  
  863.  
  864.     void Reset()
  865.     {
  866.         DoCast(m_creature, RAID_MODE(SPELL_STATIC_CHARGED_10, SPELL_STATIC_CHARGED_25));
  867.         uiShockTimer = 0; // first one is immediate.
  868.     }
  869.  
  870.  
  871.     void UpdateAI(const uint32 diff)
  872.     {
  873.         if (!UpdateVictim())
  874.             return;
  875.  
  876.  
  877.         if (uiShockTimer <= diff)
  878.         {
  879.             if (m_creature->IsWithinMeleeRange(m_creature->getVictim()))
  880.             {
  881.                 DoCast(m_creature->getVictim(), SPELL_SHOCK);
  882.                 uiShockTimer = TIMER_SHOCK;
  883.             }
  884.         }
  885.         else uiShockTimer -= diff;
  886.     }
  887. };
  888.  
  889.  
  890. CreatureAI* GetAI_mob_life_spark(Creature* pCreature)
  891. {
  892.     return new mob_life_sparkAI(pCreature);
  893. }
  894.  
  895.  
  896. void AddSC_boss_xt002()
  897. {
  898.     Script *newscript;
  899.  
  900.  
  901.     newscript = new Script;
  902.     newscript->Name = "boss_xt002";
  903.     newscript->GetAI = &GetAI_boss_xt002;
  904.     newscript->RegisterSelf();
  905.  
  906.  
  907.     newscript = new Script;
  908.     newscript->Name = "mob_xt002_heart";
  909.     newscript->GetAI = &GetAI_mob_xt002_heart;
  910.     newscript->RegisterSelf();
  911.  
  912.  
  913.     newscript = new Script;
  914.     newscript->Name = "mob_scrapbot";
  915.     newscript->GetAI = &GetAI_mob_scrapbot;
  916.     newscript->RegisterSelf();
  917.  
  918.  
  919.     newscript = new Script;
  920.     newscript->Name = "mob_pummeller";
  921.     newscript->GetAI = &GetAI_mob_pummeller;
  922.     newscript->RegisterSelf();
  923.  
  924.  
  925.     newscript = new Script;
  926.     newscript->Name = "mob_boombot";
  927.     newscript->GetAI = &GetAI_mob_boombot;
  928.     newscript->RegisterSelf();
  929.  
  930.  
  931.     newscript = new Script;
  932.     newscript->Name = "mob_void_zone";
  933.     newscript->GetAI = &GetAI_mob_void_zone;
  934.     newscript->RegisterSelf();
  935.  
  936.  
  937.     newscript = new Script;
  938.     newscript->Name = "mob_life_spark";
  939.     newscript->GetAI = &GetAI_mob_life_spark;
  940.     newscript->RegisterSelf();
  941. }