aboutsummaryrefslogtreecommitdiff
path: root/src/server/scripts/Kalimdor
diff options
context:
space:
mode:
authorTartalo <none@none>2010-06-07 00:00:11 +0200
committerTartalo <none@none>2010-06-07 00:00:11 +0200
commit910980d3c65273e1dba78ec3928d5b4e78d713bd (patch)
tree7ee28a7bd61e35d6052a5540a70d2ea2057bf77a /src/server/scripts/Kalimdor
parente548d60b4e41019f585f867a23e623a60a424b75 (diff)
More case sensitive renames
--HG-- branch : trunk rename : src/server/scripts/custom/custom_example.cpp => src/server/scripts/Custom/custom_example.cpp rename : src/server/scripts/custom/custom_gossip_codebox.cpp => src/server/scripts/Custom/custom_gossip_codebox.cpp rename : src/server/scripts/custom/npc_acherus_taxi.cpp => src/server/scripts/Custom/npc_acherus_taxi.cpp rename : src/server/scripts/custom/npc_wyrmresttempel_taxi.cpp => src/server/scripts/Custom/npc_wyrmresttempel_taxi.cpp rename : src/server/scripts/custom/on_events.cpp => src/server/scripts/Custom/on_events.cpp rename : src/server/scripts/custom/test.cpp => src/server/scripts/Custom/test.cpp rename : src/server/scripts/eastern_kingdoms/alterac_mountains.cpp => src/server/scripts/EasternKingdoms/alterac_mountains.cpp rename : src/server/scripts/eastern_kingdoms/alterac_valley/alterac_valley.cpp => src/server/scripts/EasternKingdoms/alterac_valley/alterac_valley.cpp rename : src/server/scripts/eastern_kingdoms/alterac_valley/boss_balinda.cpp => src/server/scripts/EasternKingdoms/alterac_valley/boss_balinda.cpp rename : src/server/scripts/eastern_kingdoms/alterac_valley/boss_drekthar.cpp => src/server/scripts/EasternKingdoms/alterac_valley/boss_drekthar.cpp rename : src/server/scripts/eastern_kingdoms/alterac_valley/boss_galvangar.cpp => src/server/scripts/EasternKingdoms/alterac_valley/boss_galvangar.cpp rename : src/server/scripts/eastern_kingdoms/alterac_valley/boss_vanndar.cpp => src/server/scripts/EasternKingdoms/alterac_valley/boss_vanndar.cpp rename : src/server/scripts/eastern_kingdoms/arathi_highlands.cpp => src/server/scripts/EasternKingdoms/arathi_highlands.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/blackrock_depths.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/blackrock_depths.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/blackrock_depths.h => src/server/scripts/EasternKingdoms/blackrock_depths/blackrock_depths.h rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_ambassador_flamelash.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_ambassador_flamelash.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_anubshiah.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_anubshiah.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_emperor_dagran_thaurissan.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_emperor_dagran_thaurissan.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_general_angerforge.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_general_angerforge.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_gorosh_the_dervish.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_gorosh_the_dervish.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_grizzle.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_grizzle.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_high_interrogator_gerstahn.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_high_interrogator_gerstahn.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_magmus.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_magmus.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_moira_bronzebeard.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_moira_bronzebeard.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/boss_tomb_of_seven.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/boss_tomb_of_seven.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_depths/instance_blackrock_depths.cpp => src/server/scripts/EasternKingdoms/blackrock_depths/instance_blackrock_depths.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/blackrock_spire.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/blackrock_spire.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/blackrock_spire.h => src/server/scripts/EasternKingdoms/blackrock_spire/blackrock_spire.h rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_drakkisath.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_drakkisath.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_gyth.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_gyth.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_halycon.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_halycon.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_highlord_omokk.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_highlord_omokk.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_mother_smolderweb.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_mother_smolderweb.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_overlord_wyrmthalak.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_overlord_wyrmthalak.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_pyroguard_emberseer.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_pyroguard_emberseer.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_quartermaster_zigris.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_quartermaster_zigris.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_rend_blackhand.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_rend_blackhand.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_shadow_hunter_voshgajin.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_shadow_hunter_voshgajin.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_the_beast.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_the_beast.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/boss_warmaster_voone.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/boss_warmaster_voone.cpp rename : src/server/scripts/eastern_kingdoms/blackrock_spire/instance_blackrock_spire.cpp => src/server/scripts/EasternKingdoms/blackrock_spire/instance_blackrock_spire.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/boss_broodlord_lashlayer.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/boss_broodlord_lashlayer.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/boss_chromaggus.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/boss_chromaggus.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/boss_ebonroc.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/boss_ebonroc.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/boss_firemaw.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/boss_firemaw.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/boss_flamegor.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/boss_flamegor.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/boss_nefarian.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/boss_nefarian.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/boss_razorgore.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/boss_razorgore.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/boss_vaelastrasz.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/boss_vaelastrasz.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/boss_victor_nefarius.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/boss_victor_nefarius.cpp rename : src/server/scripts/eastern_kingdoms/blackwing_lair/instance_blackwing_lair.cpp => src/server/scripts/EasternKingdoms/blackwing_lair/instance_blackwing_lair.cpp rename : src/server/scripts/eastern_kingdoms/blasted_lands.cpp => src/server/scripts/EasternKingdoms/blasted_lands.cpp rename : src/server/scripts/eastern_kingdoms/boss_kruul.cpp => src/server/scripts/EasternKingdoms/boss_kruul.cpp rename : src/server/scripts/eastern_kingdoms/burning_steppes.cpp => src/server/scripts/EasternKingdoms/burning_steppes.cpp rename : src/server/scripts/eastern_kingdoms/deadmines/boss_mr_smite.cpp => src/server/scripts/EasternKingdoms/deadmines/boss_mr_smite.cpp rename : src/server/scripts/eastern_kingdoms/deadmines/deadmines.cpp => src/server/scripts/EasternKingdoms/deadmines/deadmines.cpp rename : src/server/scripts/eastern_kingdoms/deadmines/deadmines.h => src/server/scripts/EasternKingdoms/deadmines/deadmines.h rename : src/server/scripts/eastern_kingdoms/deadmines/instance_deadmines.cpp => src/server/scripts/EasternKingdoms/deadmines/instance_deadmines.cpp rename : src/server/scripts/eastern_kingdoms/dun_morogh.cpp => src/server/scripts/EasternKingdoms/dun_morogh.cpp rename : src/server/scripts/eastern_kingdoms/duskwood.cpp => src/server/scripts/EasternKingdoms/duskwood.cpp rename : src/server/scripts/eastern_kingdoms/eastern_plaguelands.cpp => src/server/scripts/EasternKingdoms/eastern_plaguelands.cpp rename : src/server/scripts/eastern_kingdoms/elwynn_forest.cpp => src/server/scripts/EasternKingdoms/elwynn_forest.cpp rename : src/server/scripts/eastern_kingdoms/eversong_woods.cpp => src/server/scripts/EasternKingdoms/eversong_woods.cpp rename : src/server/scripts/eastern_kingdoms/ghostlands.cpp => src/server/scripts/EasternKingdoms/ghostlands.cpp rename : src/server/scripts/eastern_kingdoms/gnomeregan/gnomeregan.cpp => src/server/scripts/EasternKingdoms/gnomeregan/gnomeregan.cpp rename : src/server/scripts/eastern_kingdoms/gnomeregan/gnomeregan.h => src/server/scripts/EasternKingdoms/gnomeregan/gnomeregan.h rename : src/server/scripts/eastern_kingdoms/gnomeregan/instance_gnomeregan.cpp => src/server/scripts/EasternKingdoms/gnomeregan/instance_gnomeregan.cpp rename : src/server/scripts/eastern_kingdoms/hinterlands.cpp => src/server/scripts/EasternKingdoms/hinterlands.cpp rename : src/server/scripts/eastern_kingdoms/ironforge.cpp => src/server/scripts/EasternKingdoms/ironforge.cpp rename : src/server/scripts/eastern_kingdoms/isle_of_queldanas.cpp => src/server/scripts/EasternKingdoms/isle_of_queldanas.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/boss_curator.cpp => src/server/scripts/EasternKingdoms/karazhan/boss_curator.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/boss_maiden_of_virtue.cpp => src/server/scripts/EasternKingdoms/karazhan/boss_maiden_of_virtue.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/boss_midnight.cpp => src/server/scripts/EasternKingdoms/karazhan/boss_midnight.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/boss_moroes.cpp => src/server/scripts/EasternKingdoms/karazhan/boss_moroes.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/boss_netherspite.cpp => src/server/scripts/EasternKingdoms/karazhan/boss_netherspite.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/boss_nightbane.cpp => src/server/scripts/EasternKingdoms/karazhan/boss_nightbane.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/boss_prince_malchezaar.cpp => src/server/scripts/EasternKingdoms/karazhan/boss_prince_malchezaar.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/boss_shade_of_aran.cpp => src/server/scripts/EasternKingdoms/karazhan/boss_shade_of_aran.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/boss_terestian_illhoof.cpp => src/server/scripts/EasternKingdoms/karazhan/boss_terestian_illhoof.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/bosses_opera.cpp => src/server/scripts/EasternKingdoms/karazhan/bosses_opera.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/instance_karazhan.cpp => src/server/scripts/EasternKingdoms/karazhan/instance_karazhan.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/karazhan.cpp => src/server/scripts/EasternKingdoms/karazhan/karazhan.cpp rename : src/server/scripts/eastern_kingdoms/karazhan/karazhan.h => src/server/scripts/EasternKingdoms/karazhan/karazhan.h rename : src/server/scripts/eastern_kingdoms/loch_modan.cpp => src/server/scripts/EasternKingdoms/loch_modan.cpp rename : src/server/scripts/eastern_kingdoms/magisters_terrace/boss_felblood_kaelthas.cpp => src/server/scripts/EasternKingdoms/magisters_terrace/boss_felblood_kaelthas.cpp rename : src/server/scripts/eastern_kingdoms/magisters_terrace/boss_priestess_delrissa.cpp => src/server/scripts/EasternKingdoms/magisters_terrace/boss_priestess_delrissa.cpp rename : src/server/scripts/eastern_kingdoms/magisters_terrace/boss_selin_fireheart.cpp => src/server/scripts/EasternKingdoms/magisters_terrace/boss_selin_fireheart.cpp rename : src/server/scripts/eastern_kingdoms/magisters_terrace/boss_vexallus.cpp => src/server/scripts/EasternKingdoms/magisters_terrace/boss_vexallus.cpp rename : src/server/scripts/eastern_kingdoms/magisters_terrace/instance_magisters_terrace.cpp => src/server/scripts/EasternKingdoms/magisters_terrace/instance_magisters_terrace.cpp rename : src/server/scripts/eastern_kingdoms/magisters_terrace/magisters_terrace.cpp => src/server/scripts/EasternKingdoms/magisters_terrace/magisters_terrace.cpp rename : src/server/scripts/eastern_kingdoms/magisters_terrace/magisters_terrace.h => src/server/scripts/EasternKingdoms/magisters_terrace/magisters_terrace.h rename : src/server/scripts/eastern_kingdoms/molten_core/boss_baron_geddon.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_baron_geddon.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/boss_garr.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_garr.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/boss_gehennas.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_gehennas.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/boss_golemagg.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_golemagg.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/boss_lucifron.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_lucifron.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/boss_magmadar.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_magmadar.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/boss_majordomo_executus.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_majordomo_executus.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/boss_ragnaros.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_ragnaros.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/boss_shazzrah.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_shazzrah.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/boss_sulfuron_harbinger.cpp => src/server/scripts/EasternKingdoms/molten_core/boss_sulfuron_harbinger.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/instance_molten_core.cpp => src/server/scripts/EasternKingdoms/molten_core/instance_molten_core.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/molten_core.cpp => src/server/scripts/EasternKingdoms/molten_core/molten_core.cpp rename : src/server/scripts/eastern_kingdoms/molten_core/molten_core.h => src/server/scripts/EasternKingdoms/molten_core/molten_core.h rename : src/server/scripts/eastern_kingdoms/redridge_mountains.cpp => src/server/scripts/EasternKingdoms/redridge_mountains.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_enclave/chapter1.cpp => src/server/scripts/EasternKingdoms/scarlet_enclave/chapter1.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_enclave/chapter2.cpp => src/server/scripts/EasternKingdoms/scarlet_enclave/chapter2.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_enclave/chapter5.cpp => src/server/scripts/EasternKingdoms/scarlet_enclave/chapter5.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_enclave/the_scarlet_enclave.cpp => src/server/scripts/EasternKingdoms/scarlet_enclave/the_scarlet_enclave.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_arcanist_doan.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_arcanist_doan.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_azshir_the_sleepless.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_azshir_the_sleepless.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_bloodmage_thalnos.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_bloodmage_thalnos.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_headless_horseman.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_headless_horseman.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_herod.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_herod.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_high_inquisitor_fairbanks.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_high_inquisitor_fairbanks.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_houndmaster_loksey.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_houndmaster_loksey.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_interrogator_vishas.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_interrogator_vishas.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_mograine_and_whitemane.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_mograine_and_whitemane.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/boss_scorn.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/boss_scorn.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/instance_scarlet_monastery.cpp => src/server/scripts/EasternKingdoms/scarlet_monastery/instance_scarlet_monastery.cpp rename : src/server/scripts/eastern_kingdoms/scarlet_monastery/scarlet_monastery.h => src/server/scripts/EasternKingdoms/scarlet_monastery/scarlet_monastery.h rename : src/server/scripts/eastern_kingdoms/scholomance/boss_darkmaster_gandling.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_darkmaster_gandling.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_death_knight_darkreaver.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_death_knight_darkreaver.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_doctor_theolen_krastinov.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_doctor_theolen_krastinov.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_illucia_barov.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_illucia_barov.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_instructor_malicia.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_instructor_malicia.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_jandice_barov.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_jandice_barov.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_kormok.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_kormok.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_lord_alexei_barov.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_lord_alexei_barov.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_lorekeeper_polkelt.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_lorekeeper_polkelt.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_ras_frostwhisper.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_ras_frostwhisper.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_the_ravenian.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_the_ravenian.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/boss_vectus.cpp => src/server/scripts/EasternKingdoms/scholomance/boss_vectus.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/instance_scholomance.cpp => src/server/scripts/EasternKingdoms/scholomance/instance_scholomance.cpp rename : src/server/scripts/eastern_kingdoms/scholomance/scholomance.h => src/server/scripts/EasternKingdoms/scholomance/scholomance.h rename : src/server/scripts/eastern_kingdoms/searing_gorge.cpp => src/server/scripts/EasternKingdoms/searing_gorge.cpp rename : src/server/scripts/eastern_kingdoms/shadowfang_keep/instance_shadowfang_keep.cpp => src/server/scripts/EasternKingdoms/shadowfang_keep/instance_shadowfang_keep.cpp rename : src/server/scripts/eastern_kingdoms/shadowfang_keep/shadowfang_keep.cpp => src/server/scripts/EasternKingdoms/shadowfang_keep/shadowfang_keep.cpp rename : src/server/scripts/eastern_kingdoms/shadowfang_keep/shadowfang_keep.h => src/server/scripts/EasternKingdoms/shadowfang_keep/shadowfang_keep.h rename : src/server/scripts/eastern_kingdoms/silvermoon_city.cpp => src/server/scripts/EasternKingdoms/silvermoon_city.cpp rename : src/server/scripts/eastern_kingdoms/silverpine_forest.cpp => src/server/scripts/EasternKingdoms/silverpine_forest.cpp rename : src/server/scripts/eastern_kingdoms/stormwind_city.cpp => src/server/scripts/EasternKingdoms/stormwind_city.cpp rename : src/server/scripts/eastern_kingdoms/stranglethorn_vale.cpp => src/server/scripts/EasternKingdoms/stranglethorn_vale.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_baron_rivendare.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_baron_rivendare.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_baroness_anastari.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_baroness_anastari.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_cannon_master_willey.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_cannon_master_willey.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_dathrohan_balnazzar.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_dathrohan_balnazzar.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_magistrate_barthilas.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_magistrate_barthilas.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_maleki_the_pallid.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_maleki_the_pallid.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_nerubenkan.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_nerubenkan.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_order_of_silver_hand.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_order_of_silver_hand.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_postmaster_malown.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_postmaster_malown.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_ramstein_the_gorger.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_ramstein_the_gorger.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/boss_timmy_the_cruel.cpp => src/server/scripts/EasternKingdoms/stratholme/boss_timmy_the_cruel.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/instance_stratholme.cpp => src/server/scripts/EasternKingdoms/stratholme/instance_stratholme.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/stratholme.cpp => src/server/scripts/EasternKingdoms/stratholme/stratholme.cpp rename : src/server/scripts/eastern_kingdoms/stratholme/stratholme.h => src/server/scripts/EasternKingdoms/stratholme/stratholme.h rename : src/server/scripts/eastern_kingdoms/sunken_temple/instance_sunken_temple.cpp => src/server/scripts/EasternKingdoms/sunken_temple/instance_sunken_temple.cpp rename : src/server/scripts/eastern_kingdoms/sunken_temple/sunken_temple.cpp => src/server/scripts/EasternKingdoms/sunken_temple/sunken_temple.cpp rename : src/server/scripts/eastern_kingdoms/sunken_temple/sunken_temple.h => src/server/scripts/EasternKingdoms/sunken_temple/sunken_temple.h rename : src/server/scripts/eastern_kingdoms/sunwell_plateau/boss_brutallus.cpp => src/server/scripts/EasternKingdoms/sunwell_plateau/boss_brutallus.cpp rename : src/server/scripts/eastern_kingdoms/sunwell_plateau/boss_eredar_twins.cpp => src/server/scripts/EasternKingdoms/sunwell_plateau/boss_eredar_twins.cpp rename : src/server/scripts/eastern_kingdoms/sunwell_plateau/boss_felmyst.cpp => src/server/scripts/EasternKingdoms/sunwell_plateau/boss_felmyst.cpp rename : src/server/scripts/eastern_kingdoms/sunwell_plateau/boss_kalecgos.cpp => src/server/scripts/EasternKingdoms/sunwell_plateau/boss_kalecgos.cpp rename : src/server/scripts/eastern_kingdoms/sunwell_plateau/boss_kiljaeden.cpp => src/server/scripts/EasternKingdoms/sunwell_plateau/boss_kiljaeden.cpp rename : src/server/scripts/eastern_kingdoms/sunwell_plateau/boss_muru.cpp => src/server/scripts/EasternKingdoms/sunwell_plateau/boss_muru.cpp rename : src/server/scripts/eastern_kingdoms/sunwell_plateau/instance_sunwell_plateau.cpp => src/server/scripts/EasternKingdoms/sunwell_plateau/instance_sunwell_plateau.cpp rename : src/server/scripts/eastern_kingdoms/sunwell_plateau/sunwell_plateau.cpp => src/server/scripts/EasternKingdoms/sunwell_plateau/sunwell_plateau.cpp rename : src/server/scripts/eastern_kingdoms/sunwell_plateau/sunwell_plateau.h => src/server/scripts/EasternKingdoms/sunwell_plateau/sunwell_plateau.h rename : src/server/scripts/eastern_kingdoms/tirisfal_glades.cpp => src/server/scripts/EasternKingdoms/tirisfal_glades.cpp rename : src/server/scripts/eastern_kingdoms/uldaman/boss_archaedas.cpp => src/server/scripts/EasternKingdoms/uldaman/boss_archaedas.cpp rename : src/server/scripts/eastern_kingdoms/uldaman/boss_ironaya.cpp => src/server/scripts/EasternKingdoms/uldaman/boss_ironaya.cpp rename : src/server/scripts/eastern_kingdoms/uldaman/instance_uldaman.cpp => src/server/scripts/EasternKingdoms/uldaman/instance_uldaman.cpp rename : src/server/scripts/eastern_kingdoms/uldaman/uldaman.cpp => src/server/scripts/EasternKingdoms/uldaman/uldaman.cpp rename : src/server/scripts/eastern_kingdoms/undercity.cpp => src/server/scripts/EasternKingdoms/undercity.cpp rename : src/server/scripts/eastern_kingdoms/western_plaguelands.cpp => src/server/scripts/EasternKingdoms/western_plaguelands.cpp rename : src/server/scripts/eastern_kingdoms/westfall.cpp => src/server/scripts/EasternKingdoms/westfall.cpp rename : src/server/scripts/eastern_kingdoms/wetlands.cpp => src/server/scripts/EasternKingdoms/wetlands.cpp rename : src/server/scripts/eastern_kingdoms/zulaman/boss_akilzon.cpp => src/server/scripts/EasternKingdoms/zulaman/boss_akilzon.cpp rename : src/server/scripts/eastern_kingdoms/zulaman/boss_halazzi.cpp => src/server/scripts/EasternKingdoms/zulaman/boss_halazzi.cpp rename : src/server/scripts/eastern_kingdoms/zulaman/boss_hexlord.cpp => src/server/scripts/EasternKingdoms/zulaman/boss_hexlord.cpp rename : src/server/scripts/eastern_kingdoms/zulaman/boss_janalai.cpp => src/server/scripts/EasternKingdoms/zulaman/boss_janalai.cpp rename : src/server/scripts/eastern_kingdoms/zulaman/boss_nalorakk.cpp => src/server/scripts/EasternKingdoms/zulaman/boss_nalorakk.cpp rename : src/server/scripts/eastern_kingdoms/zulaman/boss_zuljin.cpp => src/server/scripts/EasternKingdoms/zulaman/boss_zuljin.cpp rename : src/server/scripts/eastern_kingdoms/zulaman/instance_zulaman.cpp => src/server/scripts/EasternKingdoms/zulaman/instance_zulaman.cpp rename : src/server/scripts/eastern_kingdoms/zulaman/zulaman.cpp => src/server/scripts/EasternKingdoms/zulaman/zulaman.cpp rename : src/server/scripts/eastern_kingdoms/zulaman/zulaman.h => src/server/scripts/EasternKingdoms/zulaman/zulaman.h rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_arlokk.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_arlokk.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_gahzranka.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_gahzranka.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_grilek.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_grilek.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_hakkar.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_hakkar.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_hazzarah.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_hazzarah.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_jeklik.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_jeklik.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_jindo.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_jindo.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_mandokir.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_mandokir.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_marli.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_marli.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_renataki.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_renataki.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_thekal.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_thekal.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_venoxis.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_venoxis.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/boss_wushoolay.cpp => src/server/scripts/EasternKingdoms/zulgurub/boss_wushoolay.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/instance_zulgurub.cpp => src/server/scripts/EasternKingdoms/zulgurub/instance_zulgurub.cpp rename : src/server/scripts/eastern_kingdoms/zulgurub/zulgurub.h => src/server/scripts/EasternKingdoms/zulgurub/zulgurub.h rename : src/server/scripts/examples/example_creature.cpp => src/server/scripts/Examples/example_creature.cpp rename : src/server/scripts/examples/example_escort.cpp => src/server/scripts/Examples/example_escort.cpp rename : src/server/scripts/examples/example_gossip_codebox.cpp => src/server/scripts/Examples/example_gossip_codebox.cpp rename : src/server/scripts/examples/example_misc.cpp => src/server/scripts/Examples/example_misc.cpp rename : src/server/scripts/kalimdor/ashenvale.cpp => src/server/scripts/Kalimdor/ashenvale.cpp rename : src/server/scripts/kalimdor/azshara.cpp => src/server/scripts/Kalimdor/azshara.cpp rename : src/server/scripts/kalimdor/azuremyst_isle.cpp => src/server/scripts/Kalimdor/azuremyst_isle.cpp rename : src/server/scripts/kalimdor/blackfathom_depths/blackfathom_deeps.cpp => src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.cpp rename : src/server/scripts/kalimdor/blackfathom_depths/blackfathom_deeps.h => src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.h rename : src/server/scripts/kalimdor/blackfathom_depths/boss_aku_mai.cpp => src/server/scripts/Kalimdor/blackfathom_depths/boss_aku_mai.cpp rename : src/server/scripts/kalimdor/blackfathom_depths/boss_gelihast.cpp => src/server/scripts/Kalimdor/blackfathom_depths/boss_gelihast.cpp rename : src/server/scripts/kalimdor/blackfathom_depths/boss_kelris.cpp => src/server/scripts/Kalimdor/blackfathom_depths/boss_kelris.cpp rename : src/server/scripts/kalimdor/blackfathom_depths/instance_blackfathom_deeps.cpp => src/server/scripts/Kalimdor/blackfathom_depths/instance_blackfathom_deeps.cpp rename : src/server/scripts/kalimdor/bloodmyst_isle.cpp => src/server/scripts/Kalimdor/bloodmyst_isle.cpp rename : src/server/scripts/kalimdor/boss_azuregos.cpp => src/server/scripts/Kalimdor/boss_azuregos.cpp rename : src/server/scripts/kalimdor/caverns_of_time/culling_of_stratholme/boss_epoch.cpp => src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_epoch.cpp rename : src/server/scripts/kalimdor/caverns_of_time/culling_of_stratholme/boss_infinite.cpp => src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_infinite.cpp rename : src/server/scripts/kalimdor/caverns_of_time/culling_of_stratholme/boss_mal_ganis.cpp => src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_mal_ganis.cpp rename : src/server/scripts/kalimdor/caverns_of_time/culling_of_stratholme/boss_meathook.cpp => src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_meathook.cpp rename : src/server/scripts/kalimdor/caverns_of_time/culling_of_stratholme/boss_salramm.cpp => src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_salramm.cpp rename : src/server/scripts/kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.cpp => src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.cpp rename : src/server/scripts/kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.h => src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.h rename : src/server/scripts/kalimdor/caverns_of_time/culling_of_stratholme/instance_culling_of_stratholme.cpp => src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/instance_culling_of_stratholme.cpp rename : src/server/scripts/kalimdor/caverns_of_time/dark_portal/boss_aeonus.cpp => src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_aeonus.cpp rename : src/server/scripts/kalimdor/caverns_of_time/dark_portal/boss_chrono_lord_deja.cpp => src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_chrono_lord_deja.cpp rename : src/server/scripts/kalimdor/caverns_of_time/dark_portal/boss_temporus.cpp => src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_temporus.cpp rename : src/server/scripts/kalimdor/caverns_of_time/dark_portal/dark_portal.cpp => src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.cpp rename : src/server/scripts/kalimdor/caverns_of_time/dark_portal/dark_portal.h => src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.h rename : src/server/scripts/kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp => src/server/scripts/Kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/boss_anetheron.cpp => src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_anetheron.cpp rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp => src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/boss_azgalor.cpp => src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_azgalor.cpp rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/boss_kazrogal.cpp => src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_kazrogal.cpp rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/boss_rage_winterchill.cpp => src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_rage_winterchill.cpp rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/hyjal.cpp => src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.cpp rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/hyjal.h => src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.h rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/hyjalAI.cpp => src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.cpp rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/hyjalAI.h => src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.h rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/hyjal_trash.cpp => src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.cpp rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/hyjal_trash.h => src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.h rename : src/server/scripts/kalimdor/caverns_of_time/hyjal/instance_hyjal.cpp => src/server/scripts/Kalimdor/caverns_of_time/hyjal/instance_hyjal.cpp rename : src/server/scripts/kalimdor/caverns_of_time/old_hillsbrad/boss_captain_skarloc.cpp => src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_captain_skarloc.cpp rename : src/server/scripts/kalimdor/caverns_of_time/old_hillsbrad/boss_epoch_hunter.cpp => src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_epoch_hunter.cpp rename : src/server/scripts/kalimdor/caverns_of_time/old_hillsbrad/boss_leutenant_drake.cpp => src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_leutenant_drake.cpp rename : src/server/scripts/kalimdor/caverns_of_time/old_hillsbrad/instance_old_hillsbrad.cpp => src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/instance_old_hillsbrad.cpp rename : src/server/scripts/kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.cpp => src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.cpp rename : src/server/scripts/kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.h => src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.h rename : src/server/scripts/kalimdor/darkshore.cpp => src/server/scripts/Kalimdor/darkshore.cpp rename : src/server/scripts/kalimdor/desolace.cpp => src/server/scripts/Kalimdor/desolace.cpp rename : src/server/scripts/kalimdor/durotar.cpp => src/server/scripts/Kalimdor/durotar.cpp rename : src/server/scripts/kalimdor/dustwallow_marsh.cpp => src/server/scripts/Kalimdor/dustwallow_marsh.cpp rename : src/server/scripts/kalimdor/felwood.cpp => src/server/scripts/Kalimdor/felwood.cpp rename : src/server/scripts/kalimdor/feralas.cpp => src/server/scripts/Kalimdor/feralas.cpp rename : src/server/scripts/kalimdor/maraudon/boss_celebras_the_cursed.cpp => src/server/scripts/Kalimdor/maraudon/boss_celebras_the_cursed.cpp rename : src/server/scripts/kalimdor/maraudon/boss_landslide.cpp => src/server/scripts/Kalimdor/maraudon/boss_landslide.cpp rename : src/server/scripts/kalimdor/maraudon/boss_noxxion.cpp => src/server/scripts/Kalimdor/maraudon/boss_noxxion.cpp rename : src/server/scripts/kalimdor/maraudon/boss_princess_theradras.cpp => src/server/scripts/Kalimdor/maraudon/boss_princess_theradras.cpp rename : src/server/scripts/kalimdor/moonglade.cpp => src/server/scripts/Kalimdor/moonglade.cpp rename : src/server/scripts/kalimdor/mulgore.cpp => src/server/scripts/Kalimdor/mulgore.cpp rename : src/server/scripts/kalimdor/onyxias_lair/boss_onyxia.cpp => src/server/scripts/Kalimdor/onyxias_lair/boss_onyxia.cpp rename : src/server/scripts/kalimdor/onyxias_lair/instance_onyxias_lair.cpp => src/server/scripts/Kalimdor/onyxias_lair/instance_onyxias_lair.cpp rename : src/server/scripts/kalimdor/onyxias_lair/onyxias_lair.h => src/server/scripts/Kalimdor/onyxias_lair/onyxias_lair.h rename : src/server/scripts/kalimdor/orgrimmar.cpp => src/server/scripts/Kalimdor/orgrimmar.cpp rename : src/server/scripts/kalimdor/razorfen_downs/boss_amnennar_the_coldbringer.cpp => src/server/scripts/Kalimdor/razorfen_downs/boss_amnennar_the_coldbringer.cpp rename : src/server/scripts/kalimdor/razorfen_downs/instance_razorfen_downs.cpp => src/server/scripts/Kalimdor/razorfen_downs/instance_razorfen_downs.cpp rename : src/server/scripts/kalimdor/razorfen_downs/razorfen_downs.cpp => src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.cpp rename : src/server/scripts/kalimdor/razorfen_downs/razorfen_downs.h => src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.h rename : src/server/scripts/kalimdor/razorfen_kraul/instance_razorfen_kraul.cpp => src/server/scripts/Kalimdor/razorfen_kraul/instance_razorfen_kraul.cpp rename : src/server/scripts/kalimdor/razorfen_kraul/razorfen_kraul.cpp => src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.cpp rename : src/server/scripts/kalimdor/razorfen_kraul/razorfen_kraul.h => src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.h rename : src/server/scripts/kalimdor/ruins_of_ahnqiraj/boss_ayamiss.cpp => src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ayamiss.cpp rename : src/server/scripts/kalimdor/ruins_of_ahnqiraj/boss_buru.cpp => src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_buru.cpp rename : src/server/scripts/kalimdor/ruins_of_ahnqiraj/boss_kurinnaxx.cpp => src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_kurinnaxx.cpp rename : src/server/scripts/kalimdor/ruins_of_ahnqiraj/boss_moam.cpp => src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_moam.cpp rename : src/server/scripts/kalimdor/ruins_of_ahnqiraj/boss_ossirian.cpp => src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ossirian.cpp rename : src/server/scripts/kalimdor/ruins_of_ahnqiraj/boss_rajaxx.cpp => src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_rajaxx.cpp rename : src/server/scripts/kalimdor/ruins_of_ahnqiraj/instance_ruins_of_ahnqiraj.cpp => src/server/scripts/Kalimdor/ruins_of_ahnqiraj/instance_ruins_of_ahnqiraj.cpp rename : src/server/scripts/kalimdor/ruins_of_ahnqiraj/ruins_of_ahnqiraj.h => src/server/scripts/Kalimdor/ruins_of_ahnqiraj/ruins_of_ahnqiraj.h rename : src/server/scripts/kalimdor/silithus.cpp => src/server/scripts/Kalimdor/silithus.cpp rename : src/server/scripts/kalimdor/stonetalon_mountains.cpp => src/server/scripts/Kalimdor/stonetalon_mountains.cpp rename : src/server/scripts/kalimdor/tanaris.cpp => src/server/scripts/Kalimdor/tanaris.cpp rename : src/server/scripts/kalimdor/teldrassil.cpp => src/server/scripts/Kalimdor/teldrassil.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/boss_bug_trio.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_bug_trio.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/boss_cthun.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_cthun.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/boss_fankriss.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_fankriss.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/boss_huhuran.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_huhuran.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/boss_ouro.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_ouro.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/boss_sartura.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_sartura.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/boss_skeram.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_skeram.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/boss_twinemperors.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_twinemperors.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/boss_viscidus.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_viscidus.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/instance_temple_of_ahnqiraj.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/instance_temple_of_ahnqiraj.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/mob_anubisath_sentinel.cpp => src/server/scripts/Kalimdor/temple_of_ahnqiraj/mob_anubisath_sentinel.cpp rename : src/server/scripts/kalimdor/temple_of_ahnqiraj/temple_of_ahnqiraj.h => src/server/scripts/Kalimdor/temple_of_ahnqiraj/temple_of_ahnqiraj.h rename : src/server/scripts/kalimdor/the_barrens.cpp => src/server/scripts/Kalimdor/the_barrens.cpp rename : src/server/scripts/kalimdor/thousand_needles.cpp => src/server/scripts/Kalimdor/thousand_needles.cpp rename : src/server/scripts/kalimdor/thunder_bluff.cpp => src/server/scripts/Kalimdor/thunder_bluff.cpp rename : src/server/scripts/kalimdor/ungoro_crater.cpp => src/server/scripts/Kalimdor/ungoro_crater.cpp rename : src/server/scripts/kalimdor/wailing_caverns/instance_wailing_caverns.cpp => src/server/scripts/Kalimdor/wailing_caverns/instance_wailing_caverns.cpp rename : src/server/scripts/kalimdor/wailing_caverns/wailing_caverns.cpp => src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.cpp rename : src/server/scripts/kalimdor/wailing_caverns/wailing_caverns.h => src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.h rename : src/server/scripts/kalimdor/winterspring.cpp => src/server/scripts/Kalimdor/winterspring.cpp rename : src/server/scripts/kalimdor/zulfarrak/instance_zulfarrak.cpp => src/server/scripts/Kalimdor/zulfarrak/instance_zulfarrak.cpp rename : src/server/scripts/kalimdor/zulfarrak/zulfarrak.cpp => src/server/scripts/Kalimdor/zulfarrak/zulfarrak.cpp rename : src/server/scripts/northrend/azjol_nerub/ahnkahet/ahnkahet.h => src/server/scripts/Northrend/azjol_nerub/ahnkahet/ahnkahet.h rename : src/server/scripts/northrend/azjol_nerub/ahnkahet/boss_amanitar.cpp => src/server/scripts/Northrend/azjol_nerub/ahnkahet/boss_amanitar.cpp rename : src/server/scripts/northrend/azjol_nerub/ahnkahet/boss_elder_nadox.cpp => src/server/scripts/Northrend/azjol_nerub/ahnkahet/boss_elder_nadox.cpp rename : src/server/scripts/northrend/azjol_nerub/ahnkahet/boss_herald_volazj.cpp => src/server/scripts/Northrend/azjol_nerub/ahnkahet/boss_herald_volazj.cpp rename : src/server/scripts/northrend/azjol_nerub/ahnkahet/boss_jedoga_shadowseeker.cpp => src/server/scripts/Northrend/azjol_nerub/ahnkahet/boss_jedoga_shadowseeker.cpp rename : src/server/scripts/northrend/azjol_nerub/ahnkahet/boss_prince_taldaram.cpp => src/server/scripts/Northrend/azjol_nerub/ahnkahet/boss_prince_taldaram.cpp rename : src/server/scripts/northrend/azjol_nerub/ahnkahet/instance_ahnkahet.cpp => src/server/scripts/Northrend/azjol_nerub/ahnkahet/instance_ahnkahet.cpp rename : src/server/scripts/northrend/azjol_nerub/azjol_nerub/azjol_nerub.h => src/server/scripts/Northrend/azjol_nerub/azjol_nerub/azjol_nerub.h rename : src/server/scripts/northrend/azjol_nerub/azjol_nerub/boss_anubarak.cpp => src/server/scripts/Northrend/azjol_nerub/azjol_nerub/boss_anubarak.cpp rename : src/server/scripts/northrend/azjol_nerub/azjol_nerub/boss_hadronox.cpp => src/server/scripts/Northrend/azjol_nerub/azjol_nerub/boss_hadronox.cpp rename : src/server/scripts/northrend/azjol_nerub/azjol_nerub/boss_krikthir_the_gatewatcher.cpp => src/server/scripts/Northrend/azjol_nerub/azjol_nerub/boss_krikthir_the_gatewatcher.cpp rename : src/server/scripts/northrend/azjol_nerub/azjol_nerub/instance_azjol_nerub.cpp => src/server/scripts/Northrend/azjol_nerub/azjol_nerub/instance_azjol_nerub.cpp rename : src/server/scripts/northrend/borean_tundra.cpp => src/server/scripts/Northrend/borean_tundra.cpp rename : src/server/scripts/northrend/crusaders_coliseum/trial_of_the_champion/boss_argent_challenge.cpp => src/server/scripts/Northrend/crusaders_coliseum/trial_of_the_champion/boss_argent_challenge.cpp rename : src/server/scripts/northrend/crusaders_coliseum/trial_of_the_champion/boss_black_knight.cpp => src/server/scripts/Northrend/crusaders_coliseum/trial_of_the_champion/boss_black_knight.cpp rename : src/server/scripts/northrend/crusaders_coliseum/trial_of_the_champion/boss_grand_champions.cpp => src/server/scripts/Northrend/crusaders_coliseum/trial_of_the_champion/boss_grand_champions.cpp rename : src/server/scripts/northrend/crusaders_coliseum/trial_of_the_champion/instance_trial_of_the_champion.cpp => src/server/scripts/Northrend/crusaders_coliseum/trial_of_the_champion/instance_trial_of_the_champion.cpp rename : src/server/scripts/northrend/crusaders_coliseum/trial_of_the_champion/trial_of_the_champion.cpp => src/server/scripts/Northrend/crusaders_coliseum/trial_of_the_champion/trial_of_the_champion.cpp rename : src/server/scripts/northrend/crusaders_coliseum/trial_of_the_champion/trial_of_the_champion.h => src/server/scripts/Northrend/crusaders_coliseum/trial_of_the_champion/trial_of_the_champion.h rename : src/server/scripts/northrend/crystalsong_forest.cpp => src/server/scripts/Northrend/crystalsong_forest.cpp rename : src/server/scripts/northrend/dalaran.cpp => src/server/scripts/Northrend/dalaran.cpp rename : src/server/scripts/northrend/dragonblight.cpp => src/server/scripts/Northrend/dragonblight.cpp rename : src/server/scripts/northrend/draktharon_keep/boss_dred.cpp => src/server/scripts/Northrend/draktharon_keep/boss_dred.cpp rename : src/server/scripts/northrend/draktharon_keep/boss_novos.cpp => src/server/scripts/Northrend/draktharon_keep/boss_novos.cpp rename : src/server/scripts/northrend/draktharon_keep/boss_tharon_ja.cpp => src/server/scripts/Northrend/draktharon_keep/boss_tharon_ja.cpp rename : src/server/scripts/northrend/draktharon_keep/boss_trollgore.cpp => src/server/scripts/Northrend/draktharon_keep/boss_trollgore.cpp rename : src/server/scripts/northrend/draktharon_keep/drak_tharon_keep.h => src/server/scripts/Northrend/draktharon_keep/drak_tharon_keep.h rename : src/server/scripts/northrend/draktharon_keep/instance_drak_tharon_keep.cpp => src/server/scripts/Northrend/draktharon_keep/instance_drak_tharon_keep.cpp rename : src/server/scripts/northrend/frozen_halls/forge_of_souls/boss_bronjahm.cpp => src/server/scripts/Northrend/frozen_halls/forge_of_souls/boss_bronjahm.cpp rename : src/server/scripts/northrend/frozen_halls/forge_of_souls/boss_devourer_of_souls.cpp => src/server/scripts/Northrend/frozen_halls/forge_of_souls/boss_devourer_of_souls.cpp rename : src/server/scripts/northrend/frozen_halls/forge_of_souls/forge_of_souls.cpp => src/server/scripts/Northrend/frozen_halls/forge_of_souls/forge_of_souls.cpp rename : src/server/scripts/northrend/frozen_halls/forge_of_souls/forge_of_souls.h => src/server/scripts/Northrend/frozen_halls/forge_of_souls/forge_of_souls.h rename : src/server/scripts/northrend/frozen_halls/forge_of_souls/instance_forge_of_souls.cpp => src/server/scripts/Northrend/frozen_halls/forge_of_souls/instance_forge_of_souls.cpp rename : src/server/scripts/northrend/frozen_halls/halls_of_reflection/boss_falric.cpp => src/server/scripts/Northrend/frozen_halls/halls_of_reflection/boss_falric.cpp rename : src/server/scripts/northrend/frozen_halls/halls_of_reflection/boss_marwyn.cpp => src/server/scripts/Northrend/frozen_halls/halls_of_reflection/boss_marwyn.cpp rename : src/server/scripts/northrend/frozen_halls/halls_of_reflection/halls_of_reflection.cpp => src/server/scripts/Northrend/frozen_halls/halls_of_reflection/halls_of_reflection.cpp rename : src/server/scripts/northrend/frozen_halls/halls_of_reflection/halls_of_reflection.h => src/server/scripts/Northrend/frozen_halls/halls_of_reflection/halls_of_reflection.h rename : src/server/scripts/northrend/frozen_halls/halls_of_reflection/instance_halls_of_reflection.cpp => src/server/scripts/Northrend/frozen_halls/halls_of_reflection/instance_halls_of_reflection.cpp rename : src/server/scripts/northrend/frozen_halls/pit_of_saron/boss_forgemaster_garfrost.cpp => src/server/scripts/Northrend/frozen_halls/pit_of_saron/boss_forgemaster_garfrost.cpp rename : src/server/scripts/northrend/frozen_halls/pit_of_saron/boss_krickandick.cpp => src/server/scripts/Northrend/frozen_halls/pit_of_saron/boss_krickandick.cpp rename : src/server/scripts/northrend/frozen_halls/pit_of_saron/boss_scourgelord_tyrannus.cpp => src/server/scripts/Northrend/frozen_halls/pit_of_saron/boss_scourgelord_tyrannus.cpp rename : src/server/scripts/northrend/frozen_halls/pit_of_saron/instance_pit_of_saron.cpp => src/server/scripts/Northrend/frozen_halls/pit_of_saron/instance_pit_of_saron.cpp rename : src/server/scripts/northrend/frozen_halls/pit_of_saron/pit_of_saron.cpp => src/server/scripts/Northrend/frozen_halls/pit_of_saron/pit_of_saron.cpp rename : src/server/scripts/northrend/frozen_halls/pit_of_saron/pit_of_saron.h => src/server/scripts/Northrend/frozen_halls/pit_of_saron/pit_of_saron.h rename : src/server/scripts/northrend/grizzly_hills.cpp => src/server/scripts/Northrend/grizzly_hills.cpp rename : src/server/scripts/northrend/gundrak/boss_drakkari_colossus.cpp => src/server/scripts/Northrend/gundrak/boss_drakkari_colossus.cpp rename : src/server/scripts/northrend/gundrak/boss_eck.cpp => src/server/scripts/Northrend/gundrak/boss_eck.cpp rename : src/server/scripts/northrend/gundrak/boss_gal_darah.cpp => src/server/scripts/Northrend/gundrak/boss_gal_darah.cpp rename : src/server/scripts/northrend/gundrak/boss_moorabi.cpp => src/server/scripts/Northrend/gundrak/boss_moorabi.cpp rename : src/server/scripts/northrend/gundrak/boss_slad_ran.cpp => src/server/scripts/Northrend/gundrak/boss_slad_ran.cpp rename : src/server/scripts/northrend/gundrak/gundrak.h => src/server/scripts/Northrend/gundrak/gundrak.h rename : src/server/scripts/northrend/gundrak/instance_gundrak.cpp => src/server/scripts/Northrend/gundrak/instance_gundrak.cpp rename : src/server/scripts/northrend/howling_fjord.cpp => src/server/scripts/Northrend/howling_fjord.cpp rename : src/server/scripts/northrend/icecrown.cpp => src/server/scripts/Northrend/icecrown.cpp rename : src/server/scripts/northrend/naxxramas/boss_anubrekhan.cpp => src/server/scripts/Northrend/naxxramas/boss_anubrekhan.cpp rename : src/server/scripts/northrend/naxxramas/boss_faerlina.cpp => src/server/scripts/Northrend/naxxramas/boss_faerlina.cpp rename : src/server/scripts/northrend/naxxramas/boss_four_horsemen.cpp => src/server/scripts/Northrend/naxxramas/boss_four_horsemen.cpp rename : src/server/scripts/northrend/naxxramas/boss_gluth.cpp => src/server/scripts/Northrend/naxxramas/boss_gluth.cpp rename : src/server/scripts/northrend/naxxramas/boss_gothik.cpp => src/server/scripts/Northrend/naxxramas/boss_gothik.cpp rename : src/server/scripts/northrend/naxxramas/boss_grobbulus.cpp => src/server/scripts/Northrend/naxxramas/boss_grobbulus.cpp rename : src/server/scripts/northrend/naxxramas/boss_heigan.cpp => src/server/scripts/Northrend/naxxramas/boss_heigan.cpp rename : src/server/scripts/northrend/naxxramas/boss_highlord_mograine.cpp => src/server/scripts/Northrend/naxxramas/boss_highlord_mograine.cpp rename : src/server/scripts/northrend/naxxramas/boss_kelthuzad.cpp => src/server/scripts/Northrend/naxxramas/boss_kelthuzad.cpp rename : src/server/scripts/northrend/naxxramas/boss_loatheb.cpp => src/server/scripts/Northrend/naxxramas/boss_loatheb.cpp rename : src/server/scripts/northrend/naxxramas/boss_maexxna.cpp => src/server/scripts/Northrend/naxxramas/boss_maexxna.cpp rename : src/server/scripts/northrend/naxxramas/boss_noth.cpp => src/server/scripts/Northrend/naxxramas/boss_noth.cpp rename : src/server/scripts/northrend/naxxramas/boss_patchwerk.cpp => src/server/scripts/Northrend/naxxramas/boss_patchwerk.cpp rename : src/server/scripts/northrend/naxxramas/boss_razuvious.cpp => src/server/scripts/Northrend/naxxramas/boss_razuvious.cpp rename : src/server/scripts/northrend/naxxramas/boss_sapphiron.cpp => src/server/scripts/Northrend/naxxramas/boss_sapphiron.cpp rename : src/server/scripts/northrend/naxxramas/boss_thaddius.cpp => src/server/scripts/Northrend/naxxramas/boss_thaddius.cpp rename : src/server/scripts/northrend/naxxramas/instance_naxxramas.cpp => src/server/scripts/Northrend/naxxramas/instance_naxxramas.cpp rename : src/server/scripts/northrend/naxxramas/naxxramas.h => src/server/scripts/Northrend/naxxramas/naxxramas.h rename : src/server/scripts/northrend/nexus/eye_of_eternity/boss_malygos.cpp => src/server/scripts/Northrend/nexus/eye_of_eternity/boss_malygos.cpp rename : src/server/scripts/northrend/nexus/eye_of_eternity/eye_of_eternity.h => src/server/scripts/Northrend/nexus/eye_of_eternity/eye_of_eternity.h rename : src/server/scripts/northrend/nexus/eye_of_eternity/instance_eye_of_eternity.cpp => src/server/scripts/Northrend/nexus/eye_of_eternity/instance_eye_of_eternity.cpp rename : src/server/scripts/northrend/nexus/nexus/boss_anomalus.cpp => src/server/scripts/Northrend/nexus/nexus/boss_anomalus.cpp rename : src/server/scripts/northrend/nexus/nexus/boss_keristrasza.cpp => src/server/scripts/Northrend/nexus/nexus/boss_keristrasza.cpp rename : src/server/scripts/northrend/nexus/nexus/boss_magus_telestra.cpp => src/server/scripts/Northrend/nexus/nexus/boss_magus_telestra.cpp rename : src/server/scripts/northrend/nexus/nexus/boss_ormorok.cpp => src/server/scripts/Northrend/nexus/nexus/boss_ormorok.cpp rename : src/server/scripts/northrend/nexus/nexus/commander_kolurg.cpp => src/server/scripts/Northrend/nexus/nexus/commander_kolurg.cpp rename : src/server/scripts/northrend/nexus/nexus/commander_stoutbeard.cpp => src/server/scripts/Northrend/nexus/nexus/commander_stoutbeard.cpp rename : src/server/scripts/northrend/nexus/nexus/instance_nexus.cpp => src/server/scripts/Northrend/nexus/nexus/instance_nexus.cpp rename : src/server/scripts/northrend/nexus/nexus/nexus.h => src/server/scripts/Northrend/nexus/nexus/nexus.h rename : src/server/scripts/northrend/nexus/oculus/boss_drakos.cpp => src/server/scripts/Northrend/nexus/oculus/boss_drakos.cpp rename : src/server/scripts/northrend/nexus/oculus/boss_eregos.cpp => src/server/scripts/Northrend/nexus/oculus/boss_eregos.cpp rename : src/server/scripts/northrend/nexus/oculus/boss_urom.cpp => src/server/scripts/Northrend/nexus/oculus/boss_urom.cpp rename : src/server/scripts/northrend/nexus/oculus/boss_varos.cpp => src/server/scripts/Northrend/nexus/oculus/boss_varos.cpp rename : src/server/scripts/northrend/nexus/oculus/instance_oculus.cpp => src/server/scripts/Northrend/nexus/oculus/instance_oculus.cpp rename : src/server/scripts/northrend/nexus/oculus/oculus.cpp => src/server/scripts/Northrend/nexus/oculus/oculus.cpp rename : src/server/scripts/northrend/nexus/oculus/oculus.h => src/server/scripts/Northrend/nexus/oculus/oculus.h rename : src/server/scripts/northrend/obsidian_sanctum/boss_sartharion.cpp => src/server/scripts/Northrend/obsidian_sanctum/boss_sartharion.cpp rename : src/server/scripts/northrend/obsidian_sanctum/instance_obsidian_sanctum.cpp => src/server/scripts/Northrend/obsidian_sanctum/instance_obsidian_sanctum.cpp rename : src/server/scripts/northrend/obsidian_sanctum/obsidian_sanctum.h => src/server/scripts/Northrend/obsidian_sanctum/obsidian_sanctum.h rename : src/server/scripts/northrend/sholazar_basin.cpp => src/server/scripts/Northrend/sholazar_basin.cpp rename : src/server/scripts/northrend/storm_peaks.cpp => src/server/scripts/Northrend/storm_peaks.cpp rename : src/server/scripts/northrend/ulduar/halls_of_lightning/boss_bjarngrim.cpp => src/server/scripts/Northrend/ulduar/halls_of_lightning/boss_bjarngrim.cpp rename : src/server/scripts/northrend/ulduar/halls_of_lightning/boss_ionar.cpp => src/server/scripts/Northrend/ulduar/halls_of_lightning/boss_ionar.cpp rename : src/server/scripts/northrend/ulduar/halls_of_lightning/boss_loken.cpp => src/server/scripts/Northrend/ulduar/halls_of_lightning/boss_loken.cpp rename : src/server/scripts/northrend/ulduar/halls_of_lightning/boss_volkhan.cpp => src/server/scripts/Northrend/ulduar/halls_of_lightning/boss_volkhan.cpp rename : src/server/scripts/northrend/ulduar/halls_of_lightning/halls_of_lightning.h => src/server/scripts/Northrend/ulduar/halls_of_lightning/halls_of_lightning.h rename : src/server/scripts/northrend/ulduar/halls_of_lightning/instance_halls_of_lightning.cpp => src/server/scripts/Northrend/ulduar/halls_of_lightning/instance_halls_of_lightning.cpp rename : src/server/scripts/northrend/ulduar/halls_of_stone/boss_krystallus.cpp => src/server/scripts/Northrend/ulduar/halls_of_stone/boss_krystallus.cpp rename : src/server/scripts/northrend/ulduar/halls_of_stone/boss_maiden_of_grief.cpp => src/server/scripts/Northrend/ulduar/halls_of_stone/boss_maiden_of_grief.cpp rename : src/server/scripts/northrend/ulduar/halls_of_stone/boss_sjonnir.cpp => src/server/scripts/Northrend/ulduar/halls_of_stone/boss_sjonnir.cpp rename : src/server/scripts/northrend/ulduar/halls_of_stone/halls_of_stone.cpp => src/server/scripts/Northrend/ulduar/halls_of_stone/halls_of_stone.cpp rename : src/server/scripts/northrend/ulduar/halls_of_stone/halls_of_stone.h => src/server/scripts/Northrend/ulduar/halls_of_stone/halls_of_stone.h rename : src/server/scripts/northrend/ulduar/halls_of_stone/instance_halls_of_stone.cpp => src/server/scripts/Northrend/ulduar/halls_of_stone/instance_halls_of_stone.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_algalon.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_algalon.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_assembly_of_iron.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_assembly_of_iron.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_auriaya.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_auriaya.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_flame_leviathan.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_flame_leviathan.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_freya.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_freya.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_general_vezax.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_general_vezax.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_hodir.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_hodir.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_ignis.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_ignis.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_kologarn.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_kologarn.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_mimiron.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_mimiron.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_razorscale.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_razorscale.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_thorim.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_thorim.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_xt002.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_xt002.cpp rename : src/server/scripts/northrend/ulduar/ulduar/boss_yoggsaron.cpp => src/server/scripts/Northrend/ulduar/ulduar/boss_yoggsaron.cpp rename : src/server/scripts/northrend/ulduar/ulduar/instance_ulduar.cpp => src/server/scripts/Northrend/ulduar/ulduar/instance_ulduar.cpp rename : src/server/scripts/northrend/ulduar/ulduar/ulduar.h => src/server/scripts/Northrend/ulduar/ulduar/ulduar.h rename : src/server/scripts/northrend/ulduar/ulduar/ulduar_teleporter.cpp => src/server/scripts/Northrend/ulduar/ulduar/ulduar_teleporter.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_keep/boss_ingvar_the_plunderer.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_keep/boss_ingvar_the_plunderer.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_keep/boss_keleseth.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_keep/boss_keleseth.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_keep/boss_skarvald_dalronn.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_keep/boss_skarvald_dalronn.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_keep/instance_utgarde_keep.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_keep/instance_utgarde_keep.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_keep/utgarde_keep.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_keep/utgarde_keep.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_keep/utgarde_keep.h => src/server/scripts/Northrend/utgarde_keep/utgarde_keep/utgarde_keep.h rename : src/server/scripts/northrend/utgarde_keep/utgarde_pinnacle/boss_palehoof.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_pinnacle/boss_palehoof.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_pinnacle/boss_skadi.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_pinnacle/boss_skadi.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_pinnacle/boss_svala.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_pinnacle/boss_svala.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_pinnacle/boss_ymiron.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_pinnacle/boss_ymiron.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_pinnacle/instance_pinnacle.cpp => src/server/scripts/Northrend/utgarde_keep/utgarde_pinnacle/instance_pinnacle.cpp rename : src/server/scripts/northrend/utgarde_keep/utgarde_pinnacle/utgarde_pinnacle.h => src/server/scripts/Northrend/utgarde_keep/utgarde_pinnacle/utgarde_pinnacle.h rename : src/server/scripts/northrend/vault_of_archavon/boss_archavon.cpp => src/server/scripts/Northrend/vault_of_archavon/boss_archavon.cpp rename : src/server/scripts/northrend/vault_of_archavon/boss_emalon.cpp => src/server/scripts/Northrend/vault_of_archavon/boss_emalon.cpp rename : src/server/scripts/northrend/vault_of_archavon/boss_koralon.cpp => src/server/scripts/Northrend/vault_of_archavon/boss_koralon.cpp rename : src/server/scripts/northrend/vault_of_archavon/boss_toravon.cpp => src/server/scripts/Northrend/vault_of_archavon/boss_toravon.cpp rename : src/server/scripts/northrend/vault_of_archavon/instance_vault_of_archavon.cpp => src/server/scripts/Northrend/vault_of_archavon/instance_vault_of_archavon.cpp rename : src/server/scripts/northrend/vault_of_archavon/vault_of_archavon.h => src/server/scripts/Northrend/vault_of_archavon/vault_of_archavon.h rename : src/server/scripts/northrend/violet_hold/boss_cyanigosa.cpp => src/server/scripts/Northrend/violet_hold/boss_cyanigosa.cpp rename : src/server/scripts/northrend/violet_hold/boss_erekem.cpp => src/server/scripts/Northrend/violet_hold/boss_erekem.cpp rename : src/server/scripts/northrend/violet_hold/boss_ichoron.cpp => src/server/scripts/Northrend/violet_hold/boss_ichoron.cpp rename : src/server/scripts/northrend/violet_hold/boss_lavanthor.cpp => src/server/scripts/Northrend/violet_hold/boss_lavanthor.cpp rename : src/server/scripts/northrend/violet_hold/boss_moragg.cpp => src/server/scripts/Northrend/violet_hold/boss_moragg.cpp rename : src/server/scripts/northrend/violet_hold/boss_xevozz.cpp => src/server/scripts/Northrend/violet_hold/boss_xevozz.cpp rename : src/server/scripts/northrend/violet_hold/boss_zuramat.cpp => src/server/scripts/Northrend/violet_hold/boss_zuramat.cpp rename : src/server/scripts/northrend/violet_hold/instance_violet_hold.cpp => src/server/scripts/Northrend/violet_hold/instance_violet_hold.cpp rename : src/server/scripts/northrend/violet_hold/violet_hold.cpp => src/server/scripts/Northrend/violet_hold/violet_hold.cpp rename : src/server/scripts/northrend/violet_hold/violet_hold.h => src/server/scripts/Northrend/violet_hold/violet_hold.h rename : src/server/scripts/northrend/zuldrak.cpp => src/server/scripts/Northrend/zuldrak.cpp rename : src/server/scripts/outland/auchindoun/auchenai_crypts/boss_exarch_maladaar.cpp => src/server/scripts/Outland/auchindoun/auchenai_crypts/boss_exarch_maladaar.cpp rename : src/server/scripts/outland/auchindoun/auchenai_crypts/boss_shirrak_the_dead_watcher.cpp => src/server/scripts/Outland/auchindoun/auchenai_crypts/boss_shirrak_the_dead_watcher.cpp rename : src/server/scripts/outland/auchindoun/mana_tombs/boss_nexusprince_shaffar.cpp => src/server/scripts/Outland/auchindoun/mana_tombs/boss_nexusprince_shaffar.cpp rename : src/server/scripts/outland/auchindoun/mana_tombs/boss_pandemonius.cpp => src/server/scripts/Outland/auchindoun/mana_tombs/boss_pandemonius.cpp rename : src/server/scripts/outland/auchindoun/sethekk_halls/boss_darkweaver_syth.cpp => src/server/scripts/Outland/auchindoun/sethekk_halls/boss_darkweaver_syth.cpp rename : src/server/scripts/outland/auchindoun/sethekk_halls/boss_tailonking_ikiss.cpp => src/server/scripts/Outland/auchindoun/sethekk_halls/boss_tailonking_ikiss.cpp rename : src/server/scripts/outland/auchindoun/sethekk_halls/instance_sethekk_halls.cpp => src/server/scripts/Outland/auchindoun/sethekk_halls/instance_sethekk_halls.cpp rename : src/server/scripts/outland/auchindoun/sethekk_halls/sethekk_halls.h => src/server/scripts/Outland/auchindoun/sethekk_halls/sethekk_halls.h rename : src/server/scripts/outland/auchindoun/shadow_labyrinth/boss_ambassador_hellmaw.cpp => src/server/scripts/Outland/auchindoun/shadow_labyrinth/boss_ambassador_hellmaw.cpp rename : src/server/scripts/outland/auchindoun/shadow_labyrinth/boss_blackheart_the_inciter.cpp => src/server/scripts/Outland/auchindoun/shadow_labyrinth/boss_blackheart_the_inciter.cpp rename : src/server/scripts/outland/auchindoun/shadow_labyrinth/boss_grandmaster_vorpil.cpp => src/server/scripts/Outland/auchindoun/shadow_labyrinth/boss_grandmaster_vorpil.cpp rename : src/server/scripts/outland/auchindoun/shadow_labyrinth/boss_murmur.cpp => src/server/scripts/Outland/auchindoun/shadow_labyrinth/boss_murmur.cpp rename : src/server/scripts/outland/auchindoun/shadow_labyrinth/instance_shadow_labyrinth.cpp => src/server/scripts/Outland/auchindoun/shadow_labyrinth/instance_shadow_labyrinth.cpp rename : src/server/scripts/outland/auchindoun/shadow_labyrinth/shadow_labyrinth.h => src/server/scripts/Outland/auchindoun/shadow_labyrinth/shadow_labyrinth.h rename : src/server/scripts/outland/black_temple/black_temple.cpp => src/server/scripts/Outland/black_temple/black_temple.cpp rename : src/server/scripts/outland/black_temple/black_temple.h => src/server/scripts/Outland/black_temple/black_temple.h rename : src/server/scripts/outland/black_temple/boss_bloodboil.cpp => src/server/scripts/Outland/black_temple/boss_bloodboil.cpp rename : src/server/scripts/outland/black_temple/boss_illidan.cpp => src/server/scripts/Outland/black_temple/boss_illidan.cpp rename : src/server/scripts/outland/black_temple/boss_mother_shahraz.cpp => src/server/scripts/Outland/black_temple/boss_mother_shahraz.cpp rename : src/server/scripts/outland/black_temple/boss_reliquary_of_souls.cpp => src/server/scripts/Outland/black_temple/boss_reliquary_of_souls.cpp rename : src/server/scripts/outland/black_temple/boss_shade_of_akama.cpp => src/server/scripts/Outland/black_temple/boss_shade_of_akama.cpp rename : src/server/scripts/outland/black_temple/boss_supremus.cpp => src/server/scripts/Outland/black_temple/boss_supremus.cpp rename : src/server/scripts/outland/black_temple/boss_teron_gorefiend.cpp => src/server/scripts/Outland/black_temple/boss_teron_gorefiend.cpp rename : src/server/scripts/outland/black_temple/boss_warlord_najentus.cpp => src/server/scripts/Outland/black_temple/boss_warlord_najentus.cpp rename : src/server/scripts/outland/black_temple/illidari_council.cpp => src/server/scripts/Outland/black_temple/illidari_council.cpp rename : src/server/scripts/outland/black_temple/instance_black_temple.cpp => src/server/scripts/Outland/black_temple/instance_black_temple.cpp rename : src/server/scripts/outland/blades_edge_mountains.cpp => src/server/scripts/Outland/blades_edge_mountains.cpp rename : src/server/scripts/outland/boss_doomlord_kazzak.cpp => src/server/scripts/Outland/boss_doomlord_kazzak.cpp rename : src/server/scripts/outland/boss_doomwalker.cpp => src/server/scripts/Outland/boss_doomwalker.cpp rename : src/server/scripts/outland/coilfang_resevoir/serpent_shrine/boss_fathomlord_karathress.cpp => src/server/scripts/Outland/coilfang_resevoir/serpent_shrine/boss_fathomlord_karathress.cpp rename : src/server/scripts/outland/coilfang_resevoir/serpent_shrine/boss_hydross_the_unstable.cpp => src/server/scripts/Outland/coilfang_resevoir/serpent_shrine/boss_hydross_the_unstable.cpp rename : src/server/scripts/outland/coilfang_resevoir/serpent_shrine/boss_lady_vashj.cpp => src/server/scripts/Outland/coilfang_resevoir/serpent_shrine/boss_lady_vashj.cpp rename : src/server/scripts/outland/coilfang_resevoir/serpent_shrine/boss_leotheras_the_blind.cpp => src/server/scripts/Outland/coilfang_resevoir/serpent_shrine/boss_leotheras_the_blind.cpp rename : src/server/scripts/outland/coilfang_resevoir/serpent_shrine/boss_lurker_below.cpp => src/server/scripts/Outland/coilfang_resevoir/serpent_shrine/boss_lurker_below.cpp rename : src/server/scripts/outland/coilfang_resevoir/serpent_shrine/boss_morogrim_tidewalker.cpp => src/server/scripts/Outland/coilfang_resevoir/serpent_shrine/boss_morogrim_tidewalker.cpp rename : src/server/scripts/outland/coilfang_resevoir/serpent_shrine/instance_serpent_shrine.cpp => src/server/scripts/Outland/coilfang_resevoir/serpent_shrine/instance_serpent_shrine.cpp rename : src/server/scripts/outland/coilfang_resevoir/serpent_shrine/serpent_shrine.h => src/server/scripts/Outland/coilfang_resevoir/serpent_shrine/serpent_shrine.h rename : src/server/scripts/outland/coilfang_resevoir/steam_vault/boss_hydromancer_thespia.cpp => src/server/scripts/Outland/coilfang_resevoir/steam_vault/boss_hydromancer_thespia.cpp rename : src/server/scripts/outland/coilfang_resevoir/steam_vault/boss_mekgineer_steamrigger.cpp => src/server/scripts/Outland/coilfang_resevoir/steam_vault/boss_mekgineer_steamrigger.cpp rename : src/server/scripts/outland/coilfang_resevoir/steam_vault/boss_warlord_kalithresh.cpp => src/server/scripts/Outland/coilfang_resevoir/steam_vault/boss_warlord_kalithresh.cpp rename : src/server/scripts/outland/coilfang_resevoir/steam_vault/instance_steam_vault.cpp => src/server/scripts/Outland/coilfang_resevoir/steam_vault/instance_steam_vault.cpp rename : src/server/scripts/outland/coilfang_resevoir/steam_vault/steam_vault.h => src/server/scripts/Outland/coilfang_resevoir/steam_vault/steam_vault.h rename : src/server/scripts/outland/coilfang_resevoir/underbog/boss_hungarfen.cpp => src/server/scripts/Outland/coilfang_resevoir/underbog/boss_hungarfen.cpp rename : src/server/scripts/outland/coilfang_resevoir/underbog/boss_the_black_stalker.cpp => src/server/scripts/Outland/coilfang_resevoir/underbog/boss_the_black_stalker.cpp rename : src/server/scripts/outland/gruuls_lair/boss_gruul.cpp => src/server/scripts/Outland/gruuls_lair/boss_gruul.cpp rename : src/server/scripts/outland/gruuls_lair/boss_high_king_maulgar.cpp => src/server/scripts/Outland/gruuls_lair/boss_high_king_maulgar.cpp rename : src/server/scripts/outland/gruuls_lair/gruuls_lair.h => src/server/scripts/Outland/gruuls_lair/gruuls_lair.h rename : src/server/scripts/outland/gruuls_lair/instance_gruuls_lair.cpp => src/server/scripts/Outland/gruuls_lair/instance_gruuls_lair.cpp rename : src/server/scripts/outland/hellfire_citadel/blood_furnace/blood_furnace.h => src/server/scripts/Outland/hellfire_citadel/blood_furnace/blood_furnace.h rename : src/server/scripts/outland/hellfire_citadel/blood_furnace/boss_broggok.cpp => src/server/scripts/Outland/hellfire_citadel/blood_furnace/boss_broggok.cpp rename : src/server/scripts/outland/hellfire_citadel/blood_furnace/boss_kelidan_the_breaker.cpp => src/server/scripts/Outland/hellfire_citadel/blood_furnace/boss_kelidan_the_breaker.cpp rename : src/server/scripts/outland/hellfire_citadel/blood_furnace/boss_the_maker.cpp => src/server/scripts/Outland/hellfire_citadel/blood_furnace/boss_the_maker.cpp rename : src/server/scripts/outland/hellfire_citadel/blood_furnace/instance_blood_furnace.cpp => src/server/scripts/Outland/hellfire_citadel/blood_furnace/instance_blood_furnace.cpp rename : src/server/scripts/outland/hellfire_citadel/hellfire_ramparts/boss_omor_the_unscarred.cpp => src/server/scripts/Outland/hellfire_citadel/hellfire_ramparts/boss_omor_the_unscarred.cpp rename : src/server/scripts/outland/hellfire_citadel/hellfire_ramparts/boss_vazruden_the_herald.cpp => src/server/scripts/Outland/hellfire_citadel/hellfire_ramparts/boss_vazruden_the_herald.cpp rename : src/server/scripts/outland/hellfire_citadel/hellfire_ramparts/boss_watchkeeper_gargolmar.cpp => src/server/scripts/Outland/hellfire_citadel/hellfire_ramparts/boss_watchkeeper_gargolmar.cpp rename : src/server/scripts/outland/hellfire_citadel/hellfire_ramparts/hellfire_ramparts.h => src/server/scripts/Outland/hellfire_citadel/hellfire_ramparts/hellfire_ramparts.h rename : src/server/scripts/outland/hellfire_citadel/hellfire_ramparts/instance_hellfire_ramparts.cpp => src/server/scripts/Outland/hellfire_citadel/hellfire_ramparts/instance_hellfire_ramparts.cpp rename : src/server/scripts/outland/hellfire_citadel/magtheridons_lair/boss_magtheridon.cpp => src/server/scripts/Outland/hellfire_citadel/magtheridons_lair/boss_magtheridon.cpp rename : src/server/scripts/outland/hellfire_citadel/magtheridons_lair/instance_magtheridons_lair.cpp => src/server/scripts/Outland/hellfire_citadel/magtheridons_lair/instance_magtheridons_lair.cpp rename : src/server/scripts/outland/hellfire_citadel/magtheridons_lair/magtheridons_lair.h => src/server/scripts/Outland/hellfire_citadel/magtheridons_lair/magtheridons_lair.h rename : src/server/scripts/outland/hellfire_citadel/shattered_halls/boss_nethekurse.cpp => src/server/scripts/Outland/hellfire_citadel/shattered_halls/boss_nethekurse.cpp rename : src/server/scripts/outland/hellfire_citadel/shattered_halls/boss_warbringer_omrogg.cpp => src/server/scripts/Outland/hellfire_citadel/shattered_halls/boss_warbringer_omrogg.cpp rename : src/server/scripts/outland/hellfire_citadel/shattered_halls/boss_warchief_kargath_bladefist.cpp => src/server/scripts/Outland/hellfire_citadel/shattered_halls/boss_warchief_kargath_bladefist.cpp rename : src/server/scripts/outland/hellfire_citadel/shattered_halls/instance_shattered_halls.cpp => src/server/scripts/Outland/hellfire_citadel/shattered_halls/instance_shattered_halls.cpp rename : src/server/scripts/outland/hellfire_citadel/shattered_halls/shattered_halls.h => src/server/scripts/Outland/hellfire_citadel/shattered_halls/shattered_halls.h rename : src/server/scripts/outland/hellfire_peninsula.cpp => src/server/scripts/Outland/hellfire_peninsula.cpp rename : src/server/scripts/outland/nagrand.cpp => src/server/scripts/Outland/nagrand.cpp rename : src/server/scripts/outland/netherstorm.cpp => src/server/scripts/Outland/netherstorm.cpp rename : src/server/scripts/outland/shadowmoon_valley.cpp => src/server/scripts/Outland/shadowmoon_valley.cpp rename : src/server/scripts/outland/shattrath_city.cpp => src/server/scripts/Outland/shattrath_city.cpp rename : src/server/scripts/outland/tempest_keep/arcatraz/arcatraz.cpp => src/server/scripts/Outland/tempest_keep/arcatraz/arcatraz.cpp rename : src/server/scripts/outland/tempest_keep/arcatraz/arcatraz.h => src/server/scripts/Outland/tempest_keep/arcatraz/arcatraz.h rename : src/server/scripts/outland/tempest_keep/arcatraz/boss_harbinger_skyriss.cpp => src/server/scripts/Outland/tempest_keep/arcatraz/boss_harbinger_skyriss.cpp rename : src/server/scripts/outland/tempest_keep/arcatraz/instance_arcatraz.cpp => src/server/scripts/Outland/tempest_keep/arcatraz/instance_arcatraz.cpp rename : src/server/scripts/outland/tempest_keep/botanica/boss_high_botanist_freywinn.cpp => src/server/scripts/Outland/tempest_keep/botanica/boss_high_botanist_freywinn.cpp rename : src/server/scripts/outland/tempest_keep/botanica/boss_laj.cpp => src/server/scripts/Outland/tempest_keep/botanica/boss_laj.cpp rename : src/server/scripts/outland/tempest_keep/botanica/boss_warp_splinter.cpp => src/server/scripts/Outland/tempest_keep/botanica/boss_warp_splinter.cpp rename : src/server/scripts/outland/tempest_keep/the_eye/boss_alar.cpp => src/server/scripts/Outland/tempest_keep/the_eye/boss_alar.cpp rename : src/server/scripts/outland/tempest_keep/the_eye/boss_astromancer.cpp => src/server/scripts/Outland/tempest_keep/the_eye/boss_astromancer.cpp rename : src/server/scripts/outland/tempest_keep/the_eye/boss_kaelthas.cpp => src/server/scripts/Outland/tempest_keep/the_eye/boss_kaelthas.cpp rename : src/server/scripts/outland/tempest_keep/the_eye/boss_void_reaver.cpp => src/server/scripts/Outland/tempest_keep/the_eye/boss_void_reaver.cpp rename : src/server/scripts/outland/tempest_keep/the_eye/instance_the_eye.cpp => src/server/scripts/Outland/tempest_keep/the_eye/instance_the_eye.cpp rename : src/server/scripts/outland/tempest_keep/the_eye/the_eye.cpp => src/server/scripts/Outland/tempest_keep/the_eye/the_eye.cpp rename : src/server/scripts/outland/tempest_keep/the_eye/the_eye.h => src/server/scripts/Outland/tempest_keep/the_eye/the_eye.h rename : src/server/scripts/outland/tempest_keep/the_mechanar/boss_gatewatcher_gyrokill.cpp => src/server/scripts/Outland/tempest_keep/the_mechanar/boss_gatewatcher_gyrokill.cpp rename : src/server/scripts/outland/tempest_keep/the_mechanar/boss_gatewatcher_ironhand.cpp => src/server/scripts/Outland/tempest_keep/the_mechanar/boss_gatewatcher_ironhand.cpp rename : src/server/scripts/outland/tempest_keep/the_mechanar/boss_nethermancer_sepethrea.cpp => src/server/scripts/Outland/tempest_keep/the_mechanar/boss_nethermancer_sepethrea.cpp rename : src/server/scripts/outland/tempest_keep/the_mechanar/boss_pathaleon_the_calculator.cpp => src/server/scripts/Outland/tempest_keep/the_mechanar/boss_pathaleon_the_calculator.cpp rename : src/server/scripts/outland/tempest_keep/the_mechanar/instance_mechanar.cpp => src/server/scripts/Outland/tempest_keep/the_mechanar/instance_mechanar.cpp rename : src/server/scripts/outland/tempest_keep/the_mechanar/mechanar.h => src/server/scripts/Outland/tempest_keep/the_mechanar/mechanar.h rename : src/server/scripts/outland/terokkar_forest.cpp => src/server/scripts/Outland/terokkar_forest.cpp rename : src/server/scripts/outland/zangarmarsh.cpp => src/server/scripts/Outland/zangarmarsh.cpp rename : src/server/scripts/world/areatrigger_scripts.cpp => src/server/scripts/World/areatrigger_scripts.cpp rename : src/server/scripts/world/boss_emeriss.cpp => src/server/scripts/World/boss_emeriss.cpp rename : src/server/scripts/world/boss_lethon.cpp => src/server/scripts/World/boss_lethon.cpp rename : src/server/scripts/world/boss_taerar.cpp => src/server/scripts/World/boss_taerar.cpp rename : src/server/scripts/world/boss_ysondre.cpp => src/server/scripts/World/boss_ysondre.cpp rename : src/server/scripts/world/go_scripts.cpp => src/server/scripts/World/go_scripts.cpp rename : src/server/scripts/world/guards.cpp => src/server/scripts/World/guards.cpp rename : src/server/scripts/world/item_scripts.cpp => src/server/scripts/World/item_scripts.cpp rename : src/server/scripts/world/mob_generic_creature.cpp => src/server/scripts/World/mob_generic_creature.cpp rename : src/server/scripts/world/npc_innkeeper.cpp => src/server/scripts/World/npc_innkeeper.cpp rename : src/server/scripts/world/npc_professions.cpp => src/server/scripts/World/npc_professions.cpp rename : src/server/scripts/world/npc_taxi.cpp => src/server/scripts/World/npc_taxi.cpp rename : src/server/scripts/world/npcs_special.cpp => src/server/scripts/World/npcs_special.cpp
Diffstat (limited to 'src/server/scripts/Kalimdor')
-rw-r--r--src/server/scripts/Kalimdor/ashenvale.cpp465
-rw-r--r--src/server/scripts/Kalimdor/azshara.cpp514
-rw-r--r--src/server/scripts/Kalimdor/azuremyst_isle.cpp718
-rw-r--r--src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.cpp252
-rw-r--r--src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.h53
-rw-r--r--src/server/scripts/Kalimdor/blackfathom_depths/boss_aku_mai.cpp94
-rw-r--r--src/server/scripts/Kalimdor/blackfathom_depths/boss_gelihast.cpp85
-rw-r--r--src/server/scripts/Kalimdor/blackfathom_depths/boss_kelris.cpp108
-rw-r--r--src/server/scripts/Kalimdor/blackfathom_depths/instance_blackfathom_deeps.cpp259
-rw-r--r--src/server/scripts/Kalimdor/bloodmyst_isle.cpp149
-rw-r--r--src/server/scripts/Kalimdor/boss_azuregos.cpp155
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_epoch.cpp156
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_infinite.cpp88
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_mal_ganis.cpp262
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_meathook.cpp140
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_salramm.cpp170
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.cpp1210
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.h68
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/instance_culling_of_stratholme.cpp244
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_aeonus.cpp145
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_chrono_lord_deja.cpp154
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_temporus.cpp152
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.cpp404
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.h35
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp346
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_anetheron.cpp309
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp635
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_azgalor.cpp285
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_kazrogal.cpp197
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_rage_winterchill.cpp192
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.cpp247
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.h38
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.cpp1157
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.h248
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.cpp1440
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.h35
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/hyjal/instance_hyjal.cpp324
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_captain_skarloc.cpp152
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_epoch_hunter.cpp138
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_leutenant_drake.cpp190
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/instance_old_hillsbrad.cpp238
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.cpp658
-rw-r--r--src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.h19
-rw-r--r--src/server/scripts/Kalimdor/darkshore.cpp398
-rw-r--r--src/server/scripts/Kalimdor/desolace.cpp259
-rw-r--r--src/server/scripts/Kalimdor/durotar.cpp103
-rw-r--r--src/server/scripts/Kalimdor/dustwallow_marsh.cpp425
-rw-r--r--src/server/scripts/Kalimdor/felwood.cpp90
-rw-r--r--src/server/scripts/Kalimdor/feralas.cpp206
-rw-r--r--src/server/scripts/Kalimdor/maraudon/boss_celebras_the_cursed.cpp98
-rw-r--r--src/server/scripts/Kalimdor/maraudon/boss_landslide.cpp95
-rw-r--r--src/server/scripts/Kalimdor/maraudon/boss_noxxion.cpp131
-rw-r--r--src/server/scripts/Kalimdor/maraudon/boss_princess_theradras.cpp109
-rw-r--r--src/server/scripts/Kalimdor/moonglade.cpp571
-rw-r--r--src/server/scripts/Kalimdor/mulgore.cpp316
-rw-r--r--src/server/scripts/Kalimdor/onyxias_lair/boss_onyxia.cpp500
-rw-r--r--src/server/scripts/Kalimdor/onyxias_lair/instance_onyxias_lair.cpp249
-rw-r--r--src/server/scripts/Kalimdor/onyxias_lair/onyxias_lair.h65
-rw-r--r--src/server/scripts/Kalimdor/orgrimmar.cpp286
-rw-r--r--src/server/scripts/Kalimdor/razorfen_downs/boss_amnennar_the_coldbringer.cpp130
-rw-r--r--src/server/scripts/Kalimdor/razorfen_downs/instance_razorfen_downs.cpp215
-rw-r--r--src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.cpp165
-rw-r--r--src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.h45
-rw-r--r--src/server/scripts/Kalimdor/razorfen_kraul/instance_razorfen_kraul.cpp104
-rw-r--r--src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.cpp194
-rw-r--r--src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.h21
-rw-r--r--src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ayamiss.cpp125
-rw-r--r--src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_buru.cpp72
-rw-r--r--src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_kurinnaxx.cpp143
-rw-r--r--src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_moam.cpp162
-rw-r--r--src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ossirian.cpp79
-rw-r--r--src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_rajaxx.cpp85
-rw-r--r--src/server/scripts/Kalimdor/ruins_of_ahnqiraj/instance_ruins_of_ahnqiraj.cpp213
-rw-r--r--src/server/scripts/Kalimdor/ruins_of_ahnqiraj/ruins_of_ahnqiraj.h34
-rw-r--r--src/server/scripts/Kalimdor/silithus.cpp1140
-rw-r--r--src/server/scripts/Kalimdor/stonetalon_mountains.cpp172
-rw-r--r--src/server/scripts/Kalimdor/tanaris.cpp635
-rw-r--r--src/server/scripts/Kalimdor/teldrassil.cpp114
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_bug_trio.cpp346
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_cthun.cpp1307
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_fankriss.cpp206
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_huhuran.cpp148
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_ouro.cpp140
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_sartura.cpp297
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_skeram.cpp298
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_twinemperors.cpp596
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_viscidus.cpp30
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/instance_temple_of_ahnqiraj.cpp166
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/mob_anubisath_sentinel.cpp296
-rw-r--r--src/server/scripts/Kalimdor/temple_of_ahnqiraj/temple_of_ahnqiraj.h23
-rw-r--r--src/server/scripts/Kalimdor/the_barrens.cpp701
-rw-r--r--src/server/scripts/Kalimdor/thousand_needles.cpp454
-rw-r--r--src/server/scripts/Kalimdor/thunder_bluff.cpp138
-rw-r--r--src/server/scripts/Kalimdor/ungoro_crater.cpp356
-rw-r--r--src/server/scripts/Kalimdor/wailing_caverns/instance_wailing_caverns.cpp142
-rw-r--r--src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.cpp396
-rw-r--r--src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.h24
-rw-r--r--src/server/scripts/Kalimdor/winterspring.cpp168
-rw-r--r--src/server/scripts/Kalimdor/zulfarrak/instance_zulfarrak.cpp58
-rw-r--r--src/server/scripts/Kalimdor/zulfarrak/zulfarrak.cpp280
100 files changed, 27247 insertions, 0 deletions
diff --git a/src/server/scripts/Kalimdor/ashenvale.cpp b/src/server/scripts/Kalimdor/ashenvale.cpp
new file mode 100644
index 00000000000..13e8f442048
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ashenvale.cpp
@@ -0,0 +1,465 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+/* ScriptData
+SDName: Ashenvale
+SD%Complete: 70
+SDComment: Quest support: 6544, 6482
+SDCategory: Ashenvale Forest
+EndScriptData */
+
+/* ContentData
+npc_torek
+npc_ruul_snowhoof
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+
+/*####
+# npc_torek
+####*/
+
+#define SAY_READY -1000106
+#define SAY_MOVE -1000107
+#define SAY_PREPARE -1000108
+#define SAY_WIN -1000109
+#define SAY_END -1000110
+
+#define SPELL_REND 11977
+#define SPELL_THUNDERCLAP 8078
+
+#define QUEST_TOREK_ASSULT 6544
+
+#define ENTRY_SPLINTERTREE_RAIDER 12859
+#define ENTRY_DURIEL 12860
+#define ENTRY_SILVERWING_SENTINEL 12896
+#define ENTRY_SILVERWING_WARRIOR 12897
+
+struct npc_torekAI : public npc_escortAI
+{
+ npc_torekAI(Creature *c) : npc_escortAI(c) {}
+
+ uint32 Rend_Timer;
+ uint32 Thunderclap_Timer;
+ bool Completed;
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch (i)
+ {
+ case 1:
+ DoScriptText(SAY_MOVE, me, pPlayer);
+ break;
+ case 8:
+ DoScriptText(SAY_PREPARE, me, pPlayer);
+ break;
+ case 19:
+ //TODO: verify location and creatures amount.
+ me->SummonCreature(ENTRY_DURIEL,1776.73,-2049.06,109.83,1.54,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,25000);
+ me->SummonCreature(ENTRY_SILVERWING_SENTINEL,1774.64,-2049.41,109.83,1.40,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,25000);
+ me->SummonCreature(ENTRY_SILVERWING_WARRIOR,1778.73,-2049.50,109.83,1.67,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,25000);
+ break;
+ case 20:
+ DoScriptText(SAY_WIN, me, pPlayer);
+ Completed = true;
+ if (pPlayer)
+ pPlayer->GroupEventHappens(QUEST_TOREK_ASSULT, me);
+ break;
+ case 21:
+ DoScriptText(SAY_END, me, pPlayer);
+ break;
+ }
+ }
+
+ void Reset()
+ {
+ Rend_Timer = 5000;
+ Thunderclap_Timer = 8000;
+ Completed = false;
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ }
+
+ void JustSummoned(Creature* summoned)
+ {
+ summoned->AI()->AttackStart(me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ npc_escortAI::UpdateAI(diff);
+
+ if (!UpdateVictim())
+ return;
+
+ if (Rend_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_REND);
+ Rend_Timer = 20000;
+ } else Rend_Timer -= diff;
+
+ if (Thunderclap_Timer <= diff)
+ {
+ DoCast(me, SPELL_THUNDERCLAP);
+ Thunderclap_Timer = 30000;
+ } else Thunderclap_Timer -= diff;
+ }
+};
+
+bool QuestAccept_npc_torek(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_TOREK_ASSULT)
+ {
+ //TODO: find companions, make them follow Torek, at any time (possibly done by core/database in future?)
+ DoScriptText(SAY_READY, pCreature, pPlayer);
+ pCreature->setFaction(113);
+
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_torekAI, pCreature->AI()))
+ pEscortAI->Start(true, true, pPlayer->GetGUID());
+ }
+
+ return true;
+}
+
+CreatureAI* GetAI_npc_torek(Creature* pCreature)
+{
+ return new npc_torekAI(pCreature);
+}
+
+/*####
+# npc_ruul_snowhoof
+####*/
+
+#define QUEST_FREEDOM_TO_RUUL 6482
+#define GO_CAGE 178147
+
+struct npc_ruul_snowhoofAI : public npc_escortAI
+{
+ npc_ruul_snowhoofAI(Creature *c) : npc_escortAI(c) {}
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch(i)
+ {
+ case 0: {
+ me->SetUInt32Value(UNIT_FIELD_BYTES_1, 0);
+ GameObject* Cage = me->FindNearestGameObject(GO_CAGE, 20);
+ if (Cage)
+ Cage->SetGoState(GO_STATE_ACTIVE);
+ break;}
+ case 13:
+ me->SummonCreature(3922, 3449.218018, -587.825073, 174.978867, 4.714445, TEMPSUMMON_DEAD_DESPAWN, 60000);
+ me->SummonCreature(3921, 3446.384521, -587.830872, 175.186279, 4.714445, TEMPSUMMON_DEAD_DESPAWN, 60000);
+ me->SummonCreature(3926, 3444.218994, -587.835327, 175.380600, 4.714445, TEMPSUMMON_DEAD_DESPAWN, 60000);
+ break;
+ case 19:
+ me->SummonCreature(3922, 3508.344482, -492.024261, 186.929031, 4.145029, TEMPSUMMON_DEAD_DESPAWN, 60000);
+ me->SummonCreature(3921, 3506.265625, -490.531006, 186.740128, 4.239277, TEMPSUMMON_DEAD_DESPAWN, 60000);
+ me->SummonCreature(3926, 3503.682373, -489.393799, 186.629684, 4.349232, TEMPSUMMON_DEAD_DESPAWN, 60000);
+ break;
+
+ case 21:{
+ if (pPlayer)
+ pPlayer->GroupEventHappens(QUEST_FREEDOM_TO_RUUL, me);
+
+ break; }
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void Reset()
+ {
+ GameObject* Cage = me->FindNearestGameObject(GO_CAGE, 20);
+ if (Cage)
+ Cage->SetGoState(GO_STATE_READY);
+ }
+
+ void JustSummoned(Creature* summoned)
+ {
+ summoned->AI()->AttackStart(me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ npc_escortAI::UpdateAI(diff);
+ }
+};
+
+bool QuestAccept_npc_ruul_snowhoof(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_FREEDOM_TO_RUUL)
+ {
+ pCreature->setFaction(113);
+
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_ruul_snowhoofAI, (pCreature->AI())))
+ pEscortAI->Start(true, false, pPlayer->GetGUID());
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_ruul_snowhoofAI(Creature* pCreature)
+{
+ return new npc_ruul_snowhoofAI(pCreature);
+}
+
+enum eEnums
+{
+ SAY_MUG_START1 = -1800054,
+ SAY_MUG_START2 = -1800055,
+ SAY_MUG_BRAZIER = -1800056,
+ SAY_MUG_BRAZIER_WAIT = -1800057,
+ SAY_MUG_ON_GUARD = -1800058,
+ SAY_MUG_REST = -1800059,
+ SAY_MUG_DONE = -1800060,
+ SAY_MUG_GRATITUDE = -1800061,
+ SAY_MUG_PATROL = -1800062,
+ SAY_MUG_RETURN = -1800063,
+
+ QUEST_VORSHA = 6641,
+
+ GO_NAGA_BRAZIER = 178247,
+
+ NPC_WRATH_RIDER = 3713,
+ NPC_WRATH_SORCERESS = 3717,
+ NPC_WRATH_RAZORTAIL = 3712,
+
+ NPC_WRATH_PRIESTESS = 3944,
+ NPC_WRATH_MYRMIDON = 3711,
+ NPC_WRATH_SEAWITCH = 3715,
+
+ NPC_VORSHA = 12940,
+ NPC_MUGLASH = 12717
+};
+
+static float m_afFirstNagaCoord[3][3]=
+{
+ {3603.504150, 1122.631104, 1.635}, // rider
+ {3589.293945, 1148.664063, 5.565}, // sorceress
+ {3609.925537, 1168.759521, -1.168} // razortail
+};
+
+static float m_afSecondNagaCoord[3][3]=
+{
+ {3609.925537, 1168.759521, -1.168}, // witch
+ {3645.652100, 1139.425415, 1.322}, // priest
+ {3583.602051, 1128.405762, 2.347} // myrmidon
+};
+
+static float m_fVorshaCoord[]={3633.056885, 1172.924072, -5.388};
+
+
+struct npc_muglashAI : public npc_escortAI
+{
+ npc_muglashAI(Creature* pCreature) : npc_escortAI(pCreature) { }
+
+ uint32 m_uiWaveId;
+ uint32 m_uiEventTimer;
+ bool m_bIsBrazierExtinguished;
+
+ void JustSummoned(Creature* pSummoned)
+ {
+ pSummoned->AI()->AttackStart(me);
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ switch(i)
+ {
+ case 0:
+ if (pPlayer)
+ DoScriptText(SAY_MUG_START2, me, pPlayer);
+ break;
+ case 24:
+ if (pPlayer)
+ DoScriptText(SAY_MUG_BRAZIER, me, pPlayer);
+
+ if (GameObject* pGo = GetClosestGameObjectWithEntry(me, GO_NAGA_BRAZIER, INTERACTION_DISTANCE*2))
+ {
+ pGo->RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_UNK1);
+ SetEscortPaused(true);
+ }
+ break;
+ case 25:
+ DoScriptText(SAY_MUG_GRATITUDE, me);
+
+ if (pPlayer)
+ pPlayer->GroupEventHappens(QUEST_VORSHA, me);
+ break;
+ case 26:
+ DoScriptText(SAY_MUG_PATROL, me);
+ break;
+ case 27:
+ DoScriptText(SAY_MUG_RETURN, me);
+ break;
+ }
+ }
+
+ void Aggro(Unit* /*pWho*/)
+ {
+ if (HasEscortState(STATE_ESCORT_PAUSED))
+ {
+ if (urand(0, 1))
+ DoScriptText(SAY_MUG_ON_GUARD, me);
+ return;
+ }
+ }
+
+ void Reset()
+ {
+ m_uiEventTimer = 10000;
+ m_uiWaveId = 0;
+ m_bIsBrazierExtinguished = false;
+ }
+
+ void JustDied(Unit* /*pKiller*/)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+ if (HasEscortState(STATE_ESCORT_ESCORTING))
+ {
+ if (pPlayer)
+ {
+ pPlayer->FailQuest(QUEST_VORSHA);
+ }
+ }
+ }
+
+ void DoWaveSummon()
+ {
+ switch(m_uiWaveId)
+ {
+ case 1:
+ me->SummonCreature(NPC_WRATH_RIDER, m_afFirstNagaCoord[0][0], m_afFirstNagaCoord[0][1], m_afFirstNagaCoord[0][2], 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000);
+ me->SummonCreature(NPC_WRATH_SORCERESS, m_afFirstNagaCoord[1][0], m_afFirstNagaCoord[1][1], m_afFirstNagaCoord[1][2], 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000);
+ me->SummonCreature(NPC_WRATH_RAZORTAIL, m_afFirstNagaCoord[2][0], m_afFirstNagaCoord[2][1], m_afFirstNagaCoord[2][2], 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000);
+ break;
+ case 2:
+ me->SummonCreature(NPC_WRATH_PRIESTESS, m_afSecondNagaCoord[0][0], m_afSecondNagaCoord[0][1], m_afSecondNagaCoord[0][2], 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000);
+ me->SummonCreature(NPC_WRATH_MYRMIDON, m_afSecondNagaCoord[1][0], m_afSecondNagaCoord[1][1], m_afSecondNagaCoord[1][2], 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000);
+ me->SummonCreature(NPC_WRATH_SEAWITCH, m_afSecondNagaCoord[2][0], m_afSecondNagaCoord[2][1], m_afSecondNagaCoord[2][2], 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000);
+ break;
+ case 3:
+ me->SummonCreature(NPC_VORSHA, m_fVorshaCoord[0], m_fVorshaCoord[1], m_fVorshaCoord[2], 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000);
+ break;
+ case 4:
+ SetEscortPaused(false);
+ DoScriptText(SAY_MUG_DONE, me);
+ break;
+ }
+ }
+
+ void UpdateAI(const uint32 uiDiff)
+ {
+ npc_escortAI::UpdateAI(uiDiff);
+
+ if (!me->getVictim())
+ {
+ if (HasEscortState(STATE_ESCORT_PAUSED) && m_bIsBrazierExtinguished)
+ {
+ if (m_uiEventTimer < uiDiff)
+ {
+ ++m_uiWaveId;
+ DoWaveSummon();
+ m_uiEventTimer = 10000;
+ }
+ else
+ m_uiEventTimer -= uiDiff;
+ }
+ return;
+ }
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_muglash(Creature* pCreature)
+{
+ return new npc_muglashAI(pCreature);
+}
+
+bool QuestAccept_npc_muglash(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_VORSHA)
+ {
+ if (npc_muglashAI* pEscortAI = CAST_AI(npc_muglashAI, pCreature->AI()))
+ {
+ DoScriptText(SAY_MUG_START1, pCreature);
+ pCreature->setFaction(113);
+
+ pEscortAI->Start(true, true, pPlayer->GetGUID());
+ }
+ }
+ return true;
+}
+
+
+bool GOHello_go_naga_brazier(Player* /*pPlayer*/, GameObject* pGo)
+{
+ if (Creature* pCreature = GetClosestCreatureWithEntry(pGo, NPC_MUGLASH, INTERACTION_DISTANCE*2))
+ {
+ if (npc_muglashAI* pEscortAI = CAST_AI(npc_muglashAI, pCreature->AI()))
+ {
+ DoScriptText(SAY_MUG_BRAZIER_WAIT, pCreature);
+
+ pEscortAI->m_bIsBrazierExtinguished = true;
+ return false;
+ }
+ }
+ return true;
+}
+
+void AddSC_ashenvale()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_torek";
+ newscript->GetAI = &GetAI_npc_torek;
+ newscript->pQuestAccept = &QuestAccept_npc_torek;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_ruul_snowhoof";
+ newscript->GetAI = &GetAI_npc_ruul_snowhoofAI;
+ newscript->pQuestAccept = &QuestAccept_npc_ruul_snowhoof;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_muglash";
+ newscript->GetAI = &GetAI_npc_muglash;
+ newscript->pQuestAccept = &QuestAccept_npc_muglash;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "go_naga_brazier";
+ newscript->pGOHello = &GOHello_go_naga_brazier;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/azshara.cpp b/src/server/scripts/Kalimdor/azshara.cpp
new file mode 100644
index 00000000000..937afe0ae5d
--- /dev/null
+++ b/src/server/scripts/Kalimdor/azshara.cpp
@@ -0,0 +1,514 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Azshara
+SD%Complete: 90
+SDComment: Quest support: 2744, 3141, 9364, 10994
+SDCategory: Azshara
+EndScriptData */
+
+/* ContentData
+mobs_spitelashes
+npc_loramus_thalipedes
+mob_rizzle_sprysprocket
+mob_depth_charge
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "World.h"
+#include "WorldPacket.h"
+
+/*######
+## mobs_spitelashes
+######*/
+
+struct mobs_spitelashesAI : public ScriptedAI
+{
+ mobs_spitelashesAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 morphtimer;
+ bool spellhit;
+
+ void Reset()
+ {
+ morphtimer = 0;
+ spellhit = false;
+ }
+
+ void EnterCombat(Unit * /*who*/) { }
+
+ void SpellHit(Unit *Hitter, const SpellEntry *Spellkind)
+ {
+ if (!spellhit &&
+ Hitter->GetTypeId() == TYPEID_PLAYER &&
+ CAST_PLR(Hitter)->GetQuestStatus(9364) == QUEST_STATUS_INCOMPLETE &&
+ (Spellkind->Id == 118 || Spellkind->Id == 12824 || Spellkind->Id == 12825 || Spellkind->Id == 12826))
+ {
+ spellhit=true;
+ DoCast(me, 29124); //become a sheep
+ }
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ // we mustn't remove the Creature in the same round in which we cast the summon spell, otherwise there will be no summons
+ if (spellhit && morphtimer >= 5000)
+ {
+ me->ForcedDespawn();
+ return;
+ }
+ // walk 5 seconds before summoning
+ if (spellhit && morphtimer<5000)
+ {
+ morphtimer+=diff;
+ if (morphtimer >= 5000)
+ {
+ DoCast(me, 28406); //summon copies
+ DoCast(me, 6924); //visual explosion
+ }
+ }
+ if (!UpdateVictim())
+ return;
+
+ //TODO: add abilities for the different creatures
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_mobs_spitelashes(Creature* pCreature)
+{
+ return new mobs_spitelashesAI (pCreature);
+}
+
+/*######
+## npc_loramus_thalipedes
+######*/
+
+#define GOSSIP_HELLO_LT1 "Can you help me?"
+#define GOSSIP_HELLO_LT2 "Tell me your story"
+#define GOSSIP_SELECT_LT1 "Please continue"
+#define GOSSIP_SELECT_LT2 "I do not understand"
+#define GOSSIP_SELECT_LT3 "Indeed"
+#define GOSSIP_SELECT_LT4 "I will do this with or your help, Loramus"
+#define GOSSIP_SELECT_LT5 "Yes"
+
+bool GossipHello_npc_loramus_thalipedes(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(2744) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HELLO_LT1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+
+ if (pPlayer->GetQuestStatus(3141) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HELLO_LT2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_loramus_thalipedes(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch (uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pPlayer->AreaExploredOrEventHappens(2744);
+ break;
+
+ case GOSSIP_ACTION_INFO_DEF+2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_LT1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 21);
+ pPlayer->SEND_GOSSIP_MENU(1813, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+21:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_LT2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 22);
+ pPlayer->SEND_GOSSIP_MENU(1814, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+22:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_LT3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 23);
+ pPlayer->SEND_GOSSIP_MENU(1815, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+23:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_LT4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 24);
+ pPlayer->SEND_GOSSIP_MENU(1816, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+24:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_LT5, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 25);
+ pPlayer->SEND_GOSSIP_MENU(1817, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+25:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pPlayer->AreaExploredOrEventHappens(3141);
+ break;
+ }
+ return true;
+}
+
+/*####
+# mob_rizzle_sprysprocket
+####*/
+
+#define MOB_DEPTH_CHARGE 23025
+#define SPELL_RIZZLE_BLACKJACK 39865
+#define SPELL_RIZZLE_ESCAPE 39871
+#define SPELL_RIZZLE_FROST_GRENADE 40525
+#define SPELL_DEPTH_CHARGE_TRAP 38576
+#define SPELL_PERIODIC_DEPTH_CHARGE 39912
+#define SPELL_GIVE_SOUTHFURY_MOONSTONE 39886
+
+#define SAY_RIZZLE_START -1000245
+#define SAY_RIZZLE_GRENADE -1000246
+#define SAY_RIZZLE_FINAL -1000247
+
+#define GOSSIP_GET_MOONSTONE "Hand over the Southfury moonstone and I'll let you go."
+
+//next message must be send to player when Rizzle jump into river, not implemented
+#define MSG_ESCAPE_NOTICE "Rizzle Sprysprocket takes the Southfury moonstone and escapes into the river. Follow her!"
+
+float WPs[58][4] =
+{
+//pos_x pos_y pos_z orien
+{3691.97, -3962.41, 35.9118, 3.67},
+{3675.02, -3960.49, 35.9118, 3.67},
+{3653.19, -3958.33, 33.9118, 3.59},
+{3621.12, -3958.51, 29.9118, 3.48},
+{3604.86, -3963, 29.9118, 3.48},
+{3569.94, -3970.25, 29.9118, 3.44},
+{3541.03, -3975.64, 29.9118, 3.41},
+{3510.84, -3978.71, 29.9118, 3.41},
+{3472.7, -3997.07, 29.9118, 3.35},
+{3439.15, -4014.55, 29.9118, 3.29},
+{3412.8, -4025.87, 29.9118, 3.25},
+{3384.95, -4038.04, 29.9118, 3.24},
+{3346.77, -4052.93, 29.9118, 3.22},
+{3299.56, -4071.59, 29.9118, 3.20},
+{3261.22, -4080.38, 30.9118, 3.19},
+{3220.68, -4083.09, 31.9118, 3.18},
+{3187.11, -4070.45, 33.9118, 3.16},
+{3162.78, -4062.75, 33.9118, 3.15},
+{3136.09, -4050.32, 33.9118, 3.07},
+{3119.47, -4044.51, 36.0363, 3.07},
+{3098.95, -4019.8, 33.9118, 3.07},
+{3073.07, -4011.42, 33.9118, 3.07},
+{3051.71, -3993.37, 33.9118, 3.02},
+{3027.52, -3978.6, 33.9118, 3.00},
+{3003.78, -3960.14, 33.9118, 2.98},
+{2977.99, -3941.98, 31.9118, 2.96},
+{2964.57, -3932.07, 30.9118, 2.96},
+{2947.9, -3921.31, 29.9118, 2.96},
+{2924.91, -3910.8, 29.9118, 2.94},
+{2903.04, -3896.42, 29.9118, 2.93},
+{2884.75, -3874.03, 29.9118, 2.90},
+{2868.19, -3851.48, 29.9118, 2.82},
+{2854.62, -3819.72, 29.9118, 2.80},
+{2825.53, -3790.4, 29.9118, 2.744},
+{2804.31, -3773.05, 29.9118, 2.71},
+{2769.78, -3763.57, 29.9118, 2.70},
+{2727.23, -3745.92, 30.9118, 2.69},
+{2680.12, -3737.49, 30.9118, 2.67},
+{2647.62, -3739.94, 30.9118, 2.66},
+{2616.6, -3745.75, 30.9118, 2.64},
+{2589.38, -3731.97, 30.9118, 2.61},
+{2562.94, -3722.35, 31.9118, 2.56},
+{2521.05, -3716.6, 31.9118, 2.55},
+{2485.26, -3706.67, 31.9118, 2.51},
+{2458.93, -3696.67, 31.9118, 2.51},
+{2432, -3692.03, 31.9118, 2.46},
+{2399.59, -3681.97, 31.9118, 2.45},
+{2357.75, -3666.6, 31.9118, 2.44},
+{2311.99, -3656.88, 31.9118, 2.94},
+{2263.41, -3649.55, 31.9118, 3.02},
+{2209.05, -3641.76, 31.9118, 2.99},
+{2164.83, -3637.64, 31.9118, 3.15},
+{2122.42, -3639, 31.9118, 3.21},
+{2075.73, -3643.59, 31.9118, 3.22},
+{2033.59, -3649.52, 31.9118, 3.42},
+{1985.22, -3662.99, 31.9118, 3.42},
+{1927.09, -3679.56, 33.9118, 3.42},
+{1873.57, -3695.32, 33.9118, 3.44}
+};
+
+struct mob_rizzle_sprysprocketAI : public ScriptedAI
+{
+ mob_rizzle_sprysprocketAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 spellEscape_Timer;
+ uint32 Teleport_Timer;
+ uint32 Check_Timer;
+ uint32 Grenade_Timer;
+ uint32 Must_Die_Timer;
+ uint32 CurrWP;
+
+ uint64 PlayerGUID;
+
+ bool Must_Die;
+ bool Escape;
+ bool ContinueWP;
+ bool Reached;
+
+ void Reset()
+ {
+ spellEscape_Timer = 1300;
+ Teleport_Timer = 3500;
+ Check_Timer = 10000;
+ Grenade_Timer = 30000;
+ Must_Die_Timer = 3000;
+ CurrWP = 0;
+
+ PlayerGUID = 0;
+
+ Must_Die = false;
+ Escape = false;
+ ContinueWP = false;
+ Reached = false;
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (Must_Die)
+ if (Must_Die_Timer <= diff)
+ {
+ me->ForcedDespawn();
+ return;
+ } else Must_Die_Timer -= diff;
+
+ if (!Escape)
+ {
+ if (!PlayerGUID)
+ return;
+
+ if (spellEscape_Timer <= diff)
+ {
+ DoCast(me, SPELL_RIZZLE_ESCAPE, false);
+ spellEscape_Timer = 10000;
+ } else spellEscape_Timer -= diff;
+
+ if (Teleport_Timer <= diff)
+ {
+ //temp solution - unit can't be teleported by core using spelleffect 5, only players
+ Map* pMap = me->GetMap();
+ if (pMap)
+ {
+ pMap->CreatureRelocation(me, 3706.39, -3969.15, 35.9118, 0);
+ me->AI_SendMoveToPacket(3706.39, -3969.15, 35.9118, 0, 0, 0);
+ }
+ //begin swimming and summon depth charges
+ Player* pPlayer = Unit::GetPlayer(PlayerGUID);
+ SendText(MSG_ESCAPE_NOTICE, pPlayer);
+ DoCast(me, SPELL_PERIODIC_DEPTH_CHARGE);
+ me->SetUnitMovementFlags(MOVEMENTFLAG_HOVER | MOVEMENTFLAG_SWIMMING);
+ me->SetSpeed(MOVE_RUN, 0.85f, true);
+ me->GetMotionMaster()->MovementExpired();
+ me->GetMotionMaster()->MovePoint(CurrWP, WPs[CurrWP][0], WPs[CurrWP][1], WPs[CurrWP][2]);
+ Escape = true;
+ } else Teleport_Timer -= diff;
+
+ return;
+ }
+
+ if (ContinueWP)
+ {
+ me->GetMotionMaster()->MovePoint(CurrWP, WPs[CurrWP][0], WPs[CurrWP][1], WPs[CurrWP][2]);
+ ContinueWP = false;
+ }
+
+ if (Grenade_Timer <= diff)
+ {
+ Player* pPlayer = Unit::GetPlayer(PlayerGUID);
+ if (pPlayer)
+ {
+ DoScriptText(SAY_RIZZLE_GRENADE, me, pPlayer);
+ DoCast(pPlayer, SPELL_RIZZLE_FROST_GRENADE, true);
+ }
+ Grenade_Timer = 30000;
+ } else Grenade_Timer -= diff;
+
+ if (Check_Timer <= diff)
+ {
+ Player* pPlayer = Unit::GetPlayer(PlayerGUID);
+ if (!pPlayer)
+ {
+ me->ForcedDespawn();
+ return;
+ }
+
+ if (me->IsWithinDist(pPlayer, 10) && me->GetPositionX() > pPlayer->GetPositionX() && !Reached)
+ {
+ DoScriptText(SAY_RIZZLE_FINAL, me);
+ me->SetUInt32Value(UNIT_NPC_FLAGS, 1);
+ me->setFaction(35);
+ me->GetMotionMaster()->MoveIdle();
+ me->RemoveAurasDueToSpell(SPELL_PERIODIC_DEPTH_CHARGE);
+ Reached = true;
+ }
+
+ Check_Timer = 1000;
+ } else Check_Timer -= diff;
+
+ }
+
+ void SendText(const char *text, Player* pPlayer)
+ {
+ WorldPacket data(SMSG_SERVER_MESSAGE, 0); // guess size
+ data << text;
+ if (pPlayer)
+ pPlayer->GetSession()->SendPacket(&data);
+ }
+
+ void AttackStart(Unit *who)
+ {
+ if (!who || PlayerGUID)
+ return;
+
+ if (who->GetTypeId() == TYPEID_PLAYER && CAST_PLR(who)->GetQuestStatus(10994) == QUEST_STATUS_INCOMPLETE)
+ {
+ PlayerGUID = who->GetGUID();
+ DoScriptText(SAY_RIZZLE_START, me);
+ DoCast(who, SPELL_RIZZLE_BLACKJACK, false);
+ return;
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void MovementInform(uint32 type, uint32 id)
+ {
+ if (type != POINT_MOTION_TYPE)
+ return;
+
+ if (id == 57)
+ {
+ me->ForcedDespawn();
+ return;
+ }
+
+ ++CurrWP;
+ ContinueWP = true;
+ }
+
+};
+
+bool GossipHello_mob_rizzle_sprysprocket(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->GetQuestStatus(10994) != QUEST_STATUS_INCOMPLETE)
+ return true;
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_GET_MOONSTONE, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+ pPlayer->SEND_GOSSIP_MENU(10811, pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_mob_rizzle_sprysprocket(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF + 1 && pPlayer->GetQuestStatus(10994) == QUEST_STATUS_INCOMPLETE)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pCreature->CastSpell(pPlayer, SPELL_GIVE_SOUTHFURY_MOONSTONE, true);
+ CAST_AI(mob_rizzle_sprysprocketAI, pCreature->AI())->Must_Die_Timer = 3000;
+ CAST_AI(mob_rizzle_sprysprocketAI, pCreature->AI())->Must_Die = true;
+ }
+ return true;
+}
+
+CreatureAI* GetAI_mob_rizzle_sprysprocket(Creature* pCreature)
+{
+ return new mob_rizzle_sprysprocketAI (pCreature);
+}
+
+/*####
+# mob_depth_charge
+####*/
+
+struct mob_depth_chargeAI : public ScriptedAI
+{
+ mob_depth_chargeAI(Creature *c) : ScriptedAI(c) {}
+
+ bool we_must_die;
+ uint32 must_die_timer;
+
+ void Reset()
+ {
+ me->SetUnitMovementFlags(MOVEMENTFLAG_HOVER | MOVEMENTFLAG_SWIMMING);
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ we_must_die = false;
+ must_die_timer = 1000;
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (we_must_die)
+ if (must_die_timer <= diff)
+ {
+ me->ForcedDespawn();
+ } else must_die_timer -= diff;
+ return;
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ if (!who)
+ return;
+
+ if (who->GetTypeId() == TYPEID_PLAYER && me->IsWithinDistInMap(who, 5))
+ {
+ DoCast(who, SPELL_DEPTH_CHARGE_TRAP);
+ we_must_die = true;
+ return;
+ }
+ }
+
+ void AttackStart(Unit * /*who*/)
+ {
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ }
+};
+
+CreatureAI* GetAI_mob_depth_charge(Creature* pCreature)
+{
+ return new mob_depth_chargeAI (pCreature);
+}
+
+void AddSC_azshara()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "mobs_spitelashes";
+ newscript->GetAI = &GetAI_mobs_spitelashes;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_loramus_thalipedes";
+ newscript->pGossipHello = &GossipHello_npc_loramus_thalipedes;
+ newscript->pGossipSelect = &GossipSelect_npc_loramus_thalipedes;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_rizzle_sprysprocket";
+ newscript->GetAI = &GetAI_mob_rizzle_sprysprocket;
+ newscript->pGossipHello = &GossipHello_mob_rizzle_sprysprocket;
+ newscript->pGossipSelect = &GossipSelect_mob_rizzle_sprysprocket;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_depth_charge";
+ newscript->GetAI = &GetAI_mob_depth_charge;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/azuremyst_isle.cpp b/src/server/scripts/Kalimdor/azuremyst_isle.cpp
new file mode 100644
index 00000000000..d31eaa9e84b
--- /dev/null
+++ b/src/server/scripts/Kalimdor/azuremyst_isle.cpp
@@ -0,0 +1,718 @@
+ /* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Azuremyst_Isle
+SD%Complete: 75
+SDComment: Quest support: 9283, 9537, 9582, 9554, 9531, 9303(special flight path, proper model for mount missing). Injured Draenei cosmetic only, 9582.
+SDCategory: Azuremyst Isle
+EndScriptData */
+
+/* ContentData
+npc_draenei_survivor
+npc_engineer_spark_overgrind
+npc_injured_draenei
+npc_magwin
+npc_geezle
+mob_nestlewood_owlkin
+go_ravager_cage
+npc_death_ravager
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+#include <cmath>
+
+/*######
+## npc_draenei_survivor
+######*/
+
+enum eEnums
+{
+ SAY_HEAL1 = -1000176,
+ SAY_HEAL2 = -1000177,
+ SAY_HEAL3 = -1000178,
+ SAY_HEAL4 = -1000179,
+
+ SAY_HELP1 = -1000180,
+ SAY_HELP2 = -1000181,
+ SAY_HELP3 = -1000182,
+ SAY_HELP4 = -1000183,
+
+ SPELL_IRRIDATION = 35046,
+ SPELL_STUNNED = 28630
+};
+
+struct npc_draenei_survivorAI : public ScriptedAI
+{
+ npc_draenei_survivorAI(Creature *c) : ScriptedAI(c) {}
+
+ uint64 pCaster;
+
+ uint32 SayThanksTimer;
+ uint32 RunAwayTimer;
+ uint32 SayHelpTimer;
+
+ bool CanSayHelp;
+
+ void Reset()
+ {
+ pCaster = 0;
+
+ SayThanksTimer = 0;
+ RunAwayTimer = 0;
+ SayHelpTimer = 10000;
+
+ CanSayHelp = true;
+
+ DoCast(me, SPELL_IRRIDATION, true);
+
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_PVP_ATTACKABLE);
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_IN_COMBAT);
+ me->SetHealth(int(me->GetMaxHealth()*.1));
+ me->SetStandState(UNIT_STAND_STATE_SLEEP);
+ }
+
+ void EnterCombat(Unit * /*who*/) {}
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ if (CanSayHelp && who->GetTypeId() == TYPEID_PLAYER && me->IsFriendlyTo(who) && me->IsWithinDistInMap(who, 25.0f))
+ {
+ //Random switch between 4 texts
+ DoScriptText(RAND(SAY_HELP1, SAY_HELP2, SAY_HELP3, SAY_HELP4), me, who);
+
+ SayHelpTimer = 20000;
+ CanSayHelp = false;
+ }
+ }
+
+ void SpellHit(Unit *Caster, const SpellEntry *Spell)
+ {
+ if (Spell->SpellFamilyFlags[2] & 0x080000000)
+ {
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_PVP_ATTACKABLE);
+ me->SetStandState(UNIT_STAND_STATE_STAND);
+
+ DoCast(me, SPELL_STUNNED, true);
+
+ pCaster = Caster->GetGUID();
+
+ SayThanksTimer = 5000;
+ }
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (SayThanksTimer)
+ {
+ if (SayThanksTimer <= diff)
+ {
+ me->RemoveAurasDueToSpell(SPELL_IRRIDATION);
+
+ if (Player* pPlayer = Unit::GetPlayer(pCaster))
+ {
+ DoScriptText(RAND(SAY_HEAL1, SAY_HEAL2, SAY_HEAL3, SAY_HEAL4), me, pPlayer);
+
+ pPlayer->TalkedToCreature(me->GetEntry(),me->GetGUID());
+ }
+
+ me->GetMotionMaster()->Clear();
+ me->GetMotionMaster()->MovePoint(0, -4115.053711f, -13754.831055f, 73.508949f);
+
+ RunAwayTimer = 10000;
+ SayThanksTimer = 0;
+ } else SayThanksTimer -= diff;
+
+ return;
+ }
+
+ if (RunAwayTimer)
+ {
+ if (RunAwayTimer <= diff)
+ me->ForcedDespawn();
+ else
+ RunAwayTimer -= diff;
+
+ return;
+ }
+
+ if (SayHelpTimer <= diff)
+ {
+ CanSayHelp = true;
+ SayHelpTimer = 20000;
+ } else SayHelpTimer -= diff;
+ }
+};
+CreatureAI* GetAI_npc_draenei_survivor(Creature* pCreature)
+{
+ return new npc_draenei_survivorAI (pCreature);
+}
+
+/*######
+## npc_engineer_spark_overgrind
+######*/
+
+enum eOvergrind
+{
+ SAY_TEXT = -1000184,
+ SAY_EMOTE = -1000185,
+ ATTACK_YELL = -1000186,
+
+ AREA_COVE = 3579,
+ AREA_ISLE = 3639,
+ QUEST_GNOMERCY = 9537,
+ FACTION_HOSTILE = 14,
+ SPELL_DYNAMITE = 7978
+};
+
+#define GOSSIP_FIGHT "Traitor! You will be brought to justice!"
+
+struct npc_engineer_spark_overgrindAI : public ScriptedAI
+{
+ npc_engineer_spark_overgrindAI(Creature *c) : ScriptedAI(c)
+ {
+ NormFaction = c->getFaction();
+ NpcFlags = c->GetUInt32Value(UNIT_NPC_FLAGS);
+
+ if (c->GetAreaId() == AREA_COVE || c->GetAreaId() == AREA_ISLE)
+ IsTreeEvent = true;
+ }
+
+ uint32 NormFaction;
+ uint32 NpcFlags;
+
+ uint32 Dynamite_Timer;
+ uint32 Emote_Timer;
+
+ bool IsTreeEvent;
+
+ void Reset()
+ {
+ Dynamite_Timer = 8000;
+ Emote_Timer = 120000 + rand()%30000;
+
+ me->setFaction(NormFaction);
+ me->SetUInt32Value(UNIT_NPC_FLAGS, NpcFlags);
+
+ IsTreeEvent = false;
+ }
+
+ void EnterCombat(Unit* who)
+ {
+ DoScriptText(ATTACK_YELL, me, who);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!me->isInCombat() && !IsTreeEvent)
+ {
+ if (Emote_Timer <= diff)
+ {
+ DoScriptText(SAY_TEXT, me);
+ DoScriptText(SAY_EMOTE, me);
+ Emote_Timer = 120000 + rand()%30000;
+ } else Emote_Timer -= diff;
+ }
+ else if (IsTreeEvent)
+ return;
+
+ if (!UpdateVictim())
+ return;
+
+ if (Dynamite_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_DYNAMITE);
+ Dynamite_Timer = 8000;
+ } else Dynamite_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_engineer_spark_overgrind(Creature* pCreature)
+{
+ return new npc_engineer_spark_overgrindAI (pCreature);
+}
+
+bool GossipHello_npc_engineer_spark_overgrind(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->GetQuestStatus(QUEST_GNOMERCY) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_FIGHT, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_engineer_spark_overgrind(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pCreature->setFaction(FACTION_HOSTILE);
+ CAST_AI(npc_engineer_spark_overgrindAI, pCreature->AI())->AttackStart(pPlayer);
+ }
+ return true;
+}
+
+/*######
+## npc_injured_draenei
+######*/
+
+struct npc_injured_draeneiAI : public ScriptedAI
+{
+ npc_injured_draeneiAI(Creature *c) : ScriptedAI(c) {}
+
+ void Reset()
+ {
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_IN_COMBAT);
+ me->SetHealth(int(me->GetMaxHealth()*.15));
+ switch (rand()%2)
+ {
+ case 0: me->SetStandState(UNIT_STAND_STATE_SIT); break;
+ case 1: me->SetStandState(UNIT_STAND_STATE_SLEEP); break;
+ }
+ }
+
+ void EnterCombat(Unit * /*who*/) {}
+
+ void MoveInLineOfSight(Unit * /*who*/)
+ {
+ }
+
+ void UpdateAI(const uint32 /*diff*/)
+ {
+ }
+
+};
+CreatureAI* GetAI_npc_injured_draenei(Creature* pCreature)
+{
+ return new npc_injured_draeneiAI (pCreature);
+}
+
+/*######
+## npc_magwin
+######*/
+
+enum eMagwin
+{
+ SAY_START = -1000111,
+ SAY_AGGRO = -1000112,
+ SAY_PROGRESS = -1000113,
+ SAY_END1 = -1000114,
+ SAY_END2 = -1000115,
+ EMOTE_HUG = -1000116,
+
+ QUEST_A_CRY_FOR_SAY_HELP = 9528
+};
+
+struct npc_magwinAI : public npc_escortAI
+{
+ npc_magwinAI(Creature *c) : npc_escortAI(c) {}
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch(i)
+ {
+ case 0:
+ DoScriptText(SAY_START, me, pPlayer);
+ break;
+ case 17:
+ DoScriptText(SAY_PROGRESS, me, pPlayer);
+ break;
+ case 28:
+ DoScriptText(SAY_END1, me, pPlayer);
+ break;
+ case 29:
+ DoScriptText(EMOTE_HUG, me, pPlayer);
+ DoScriptText(SAY_END2, me, pPlayer);
+ pPlayer->GroupEventHappens(QUEST_A_CRY_FOR_SAY_HELP,me);
+ break;
+ }
+ }
+
+ void EnterCombat(Unit* who)
+ {
+ DoScriptText(SAY_AGGRO, me, who);
+ }
+
+ void Reset() { }
+};
+
+bool QuestAccept_npc_magwin(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_A_CRY_FOR_SAY_HELP)
+ {
+ pCreature->setFaction(113);
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_escortAI, pCreature->AI()))
+ pEscortAI->Start(true, false, pPlayer->GetGUID());
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_magwinAI(Creature* pCreature)
+{
+ return new npc_magwinAI(pCreature);
+}
+
+/*######
+## npc_geezle
+######*/
+
+enum eGeezle
+{
+ QUEST_TREES_COMPANY = 9531,
+
+ SPELL_TREE_DISGUISE = 30298,
+
+ GEEZLE_SAY_1 = -1100259,
+ SPARK_SAY_2 = -1100260,
+ SPARK_SAY_3 = -1100261,
+ GEEZLE_SAY_4 = -1100262,
+ SPARK_SAY_5 = -1100263,
+ SPARK_SAY_6 = -1100264,
+ GEEZLE_SAY_7 = -1100265,
+
+ EMOTE_SPARK = -1100266,
+
+ MOB_SPARK = 17243,
+ GO_NAGA_FLAG = 181694
+};
+
+static float SparkPos[3] = {-5029.91, -11291.79, 8.096};
+
+struct npc_geezleAI : public ScriptedAI
+{
+ npc_geezleAI(Creature *c) : ScriptedAI(c) {}
+
+ uint64 SparkGUID;
+
+ uint32 Step;
+ uint32 SayTimer;
+
+ bool EventStarted;
+
+ void Reset()
+ {
+ SparkGUID = 0;
+ Step = 0;
+ StartEvent();
+ }
+
+ void EnterCombat(Unit* /*who*/){}
+
+ void StartEvent()
+ {
+ Step = 0;
+ EventStarted = true;
+ Creature* Spark = me->SummonCreature(MOB_SPARK, SparkPos[0], SparkPos[1], SparkPos[2], 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 1000);
+ if (Spark)
+ {
+ SparkGUID = Spark->GetGUID();
+ Spark->setActive(true);
+ Spark->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ }
+ SayTimer = 8000;
+ }
+
+ uint32 NextStep(uint32 Step)
+ {
+ Creature* Spark = Unit::GetCreature(*me, SparkGUID);
+
+ switch(Step)
+ {
+ case 0:
+ if (Spark)
+ Spark->GetMotionMaster()->MovePoint(0, -5080.70, -11253.61, 0.56);
+ me->GetMotionMaster()->MovePoint(0, -5092.26, -11252, 0.71);
+ return 9000; // NPCs are walking up to fire
+ case 1:
+ DespawnNagaFlag(true);
+ DoScriptText(EMOTE_SPARK, Spark);
+ return 1000;
+ case 2:
+ DoScriptText(GEEZLE_SAY_1, me, Spark);
+ if (Spark)
+ {
+ Spark->SetInFront(me);
+ me->SetInFront(Spark);
+ }
+ return 5000;
+ case 3: DoScriptText(SPARK_SAY_2, Spark); return 7000;
+ case 4: DoScriptText(SPARK_SAY_3, Spark); return 8000;
+ case 5: DoScriptText(GEEZLE_SAY_4, me, Spark); return 8000;
+ case 6: DoScriptText(SPARK_SAY_5, Spark); return 9000;
+ case 7: DoScriptText(SPARK_SAY_6, Spark); return 8000;
+ case 8: DoScriptText(GEEZLE_SAY_7, me, Spark); return 2000;
+ case 9:
+ me->GetMotionMaster()->MoveTargetedHome();
+ if (Spark)
+ Spark->GetMotionMaster()->MovePoint(0, SparkPos[0], SparkPos[1], SparkPos[2]);
+ CompleteQuest();
+ return 9000;
+ case 10:
+ if (Spark)
+ Spark->DisappearAndDie();
+ DespawnNagaFlag(false);
+ me->DisappearAndDie();
+ default: return 99999999;
+ }
+ }
+
+ // will complete Tree's company quest for all nearby players that are disguised as trees
+ void CompleteQuest()
+ {
+ float radius = 50.0f;
+ std::list<Player*> players;
+ Trinity::AnyPlayerInObjectRangeCheck checker(me, radius);
+ Trinity::PlayerListSearcher<Trinity::AnyPlayerInObjectRangeCheck> searcher(me, players, checker);
+ me->VisitNearbyWorldObject(radius, searcher);
+
+ for (std::list<Player*>::const_iterator itr = players.begin(); itr != players.end(); ++itr)
+ {
+ if ((*itr)->GetQuestStatus(QUEST_TREES_COMPANY) == QUEST_STATUS_INCOMPLETE
+ &&(*itr)->HasAura(SPELL_TREE_DISGUISE))
+ {
+ (*itr)->KilledMonsterCredit(MOB_SPARK,0);
+ }
+ }
+ }
+
+ void DespawnNagaFlag(bool despawn)
+ {
+ std::list<GameObject*> FlagList;
+ me->GetGameObjectListWithEntryInGrid(FlagList,GO_NAGA_FLAG, 100.0f);
+
+ if (!FlagList.empty())
+ {
+ for (std::list<GameObject*>::const_iterator itr = FlagList.begin(); itr != FlagList.end(); ++itr)
+ {
+ if (despawn)
+ {
+ (*itr)->SetLootState(GO_JUST_DEACTIVATED);
+ }
+ else
+ (*itr)->Respawn();
+ }
+ } else error_log("SD2 ERROR: FlagList is empty!");
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (SayTimer <= diff)
+ {
+ if (EventStarted)
+ {
+ SayTimer = NextStep(Step++);
+ }
+ } else SayTimer -= diff;
+ }
+};
+
+CreatureAI* GetAI_npc_geezleAI(Creature* pCreature)
+{
+ return new npc_geezleAI(pCreature);
+}
+
+/*######
+## mob_nestlewood_owlkin
+######*/
+
+enum eOwlkin
+{
+ SPELL_INOCULATE_OWLKIN = 29528,
+ ENTRY_OWLKIN = 16518,
+ ENTRY_OWLKIN_INOC = 16534
+};
+
+struct npc_nestlewood_owlkinAI : public ScriptedAI
+{
+ npc_nestlewood_owlkinAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 DespawnTimer;
+
+ void Reset()
+ {
+ DespawnTimer = 0;
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //timer gets adjusted by the triggered aura effect
+ if (DespawnTimer)
+ {
+ if (DespawnTimer <= diff)
+ {
+ //once we are able to, despawn us
+ me->ForcedDespawn();
+ return;
+ } else DespawnTimer -= diff;
+ }
+
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_nestlewood_owlkinAI(Creature* pCreature)
+{
+ return new npc_nestlewood_owlkinAI (pCreature);
+}
+
+bool EffectDummyCreature_npc_nestlewood_owlkin(Unit * /*pCaster*/, uint32 spellId, uint32 effIndex, Creature *pCreatureTarget)
+{
+ //always check spellid and effectindex
+ if (spellId == SPELL_INOCULATE_OWLKIN && effIndex == 0)
+ {
+ if (pCreatureTarget->GetEntry() != ENTRY_OWLKIN)
+ return true;
+
+ pCreatureTarget->UpdateEntry(ENTRY_OWLKIN_INOC);
+
+ //set despawn timer, since we want to remove Creature after a short time
+ CAST_AI(npc_nestlewood_owlkinAI, pCreatureTarget->AI())->DespawnTimer = 15000;
+
+ //always return true when we are handling this spell and effect
+ return true;
+ }
+ return false;
+}
+
+enum eRavegerCage
+{
+ NPC_DEATH_RAVAGER = 17556,
+
+ SPELL_REND = 13443,
+ SPELL_ENRAGING_BITE = 30736,
+
+ QUEST_STRENGTH_ONE = 9582
+};
+
+bool go_ravager_cage(Player* pPlayer, GameObject* pGo)
+{
+
+ if (pPlayer->GetQuestStatus(QUEST_STRENGTH_ONE) == QUEST_STATUS_INCOMPLETE)
+ {
+ if (Creature* ravager = pGo->FindNearestCreature(NPC_DEATH_RAVAGER, 5.0f, true))
+ {
+ ravager->RemoveFlag(UNIT_FIELD_FLAGS,UNIT_FLAG_NON_ATTACKABLE);
+ ravager->SetReactState(REACT_AGGRESSIVE);
+ ravager->AI()->AttackStart(pPlayer);
+ }
+ }
+ return true ;
+}
+
+struct npc_death_ravagerAI : public ScriptedAI
+{
+ npc_death_ravagerAI(Creature *c) : ScriptedAI(c){}
+
+ uint32 RendTimer;
+ uint32 EnragingBiteTimer;
+
+ void Reset()
+ {
+ RendTimer = 30000;
+ EnragingBiteTimer = 20000;
+
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ me->SetReactState(REACT_PASSIVE);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ if (RendTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_REND);
+ RendTimer = 30000;
+ }
+ else RendTimer -= diff;
+
+ if (EnragingBiteTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_ENRAGING_BITE);
+ EnragingBiteTimer = 15000;
+ }
+ else EnragingBiteTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_death_ravagerAI(Creature* pCreature)
+{
+ return new npc_death_ravagerAI(pCreature);
+}
+
+void AddSC_azuremyst_isle()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_draenei_survivor";
+ newscript->GetAI = &GetAI_npc_draenei_survivor;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_engineer_spark_overgrind";
+ newscript->GetAI = &GetAI_npc_engineer_spark_overgrind;
+ newscript->pGossipHello = &GossipHello_npc_engineer_spark_overgrind;
+ newscript->pGossipSelect = &GossipSelect_npc_engineer_spark_overgrind;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_injured_draenei";
+ newscript->GetAI = &GetAI_npc_injured_draenei;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_magwin";
+ newscript->GetAI = &GetAI_npc_magwinAI;
+ newscript->pQuestAccept = &QuestAccept_npc_magwin;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_geezle";
+ newscript->GetAI = &GetAI_npc_geezleAI;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_nestlewood_owlkin";
+ newscript->GetAI = &GetAI_npc_nestlewood_owlkinAI;
+ newscript->pEffectDummyCreature = &EffectDummyCreature_npc_nestlewood_owlkin;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name="npc_death_ravager";
+ newscript->GetAI = &GetAI_npc_death_ravagerAI;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name="go_ravager_cage";
+ newscript->pGOHello = &go_ravager_cage;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.cpp b/src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.cpp
new file mode 100644
index 00000000000..a3fd42a0fe7
--- /dev/null
+++ b/src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.cpp
@@ -0,0 +1,252 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#include "ScriptedPch.h"
+#include "blackfathom_deeps.h"
+#include "ScriptedEscortAI.h"
+
+enum eSpells
+{
+ SPELL_BLESSING_OF_BLACKFATHOM = 8733,
+ SPELL_RAVAGE = 8391,
+ SPELL_FROST_NOVA = 865,
+ SPELL_FROST_BOLT_VOLLEY = 8398,
+ SPELL_TELEPORT_DARNASSUS = 9268
+};
+
+#define GOSSIP_ITEM_MORRIDUNE "Please port me to Darnassus"
+
+const Position HomePosition = {-815.817,-145.299,-25.870, 0};
+
+bool GoHello_blackfathom_altar(Player *pPlayer, GameObject* /*pGo*/)
+{
+ if (!pPlayer->HasAura(SPELL_BLESSING_OF_BLACKFATHOM))
+ pPlayer->AddAura(SPELL_BLESSING_OF_BLACKFATHOM,pPlayer);
+ return true;
+}
+
+bool GoHello_blackfathom_fire(Player * /*pPlayer*/, GameObject* pGo)
+{
+ ScriptedInstance *pInstance = pGo->GetInstanceData();
+
+ if (pInstance)
+ {
+ pGo->SetGoState(GO_STATE_ACTIVE);
+ pGo->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_UNK1);
+ pInstance->SetData(DATA_FIRE, pInstance->GetData(DATA_FIRE) + 1);
+ return true;
+ }
+ return false;
+}
+
+struct npc_blackfathom_deeps_eventAI : public ScriptedAI
+{
+ npc_blackfathom_deeps_eventAI(Creature* pCreature) : ScriptedAI(pCreature)
+ {
+ if (pCreature->isSummon())
+ {
+ pCreature->SetHomePosition(HomePosition);
+ AttackPlayer();
+ }
+
+ pInstance = pCreature->GetInstanceData();
+ }
+
+ ScriptedInstance* pInstance;
+
+ uint32 uiRavageTimer;
+ uint32 uiFrostNovaTimer;
+ uint32 uiFrostBoltVolleyTimer;
+
+ bool bFlee;
+
+ void Reset()
+ {
+ bFlee = false;
+
+ uiRavageTimer = urand(5000,8000);
+ uiFrostNovaTimer = urand(9000,12000);
+ uiFrostBoltVolleyTimer = urand(2000,4000);
+ }
+
+ void AttackPlayer()
+ {
+ Map::PlayerList const &PlList = me->GetMap()->GetPlayers();
+
+ if (PlList.isEmpty())
+ return;
+
+ for (Map::PlayerList::const_iterator i = PlList.begin(); i != PlList.end(); ++i)
+ {
+ if (Player* pPlayer = i->getSource())
+ {
+ if (pPlayer->isGameMaster())
+ continue;
+
+ if (pPlayer->isAlive())
+ {
+ me->SetInCombatWith(pPlayer);
+ pPlayer->SetInCombatWith(me);
+ me->AddThreat(pPlayer, 0.0f);
+ }
+ }
+ }
+ }
+
+ void UpdateAI(const uint32 uiDiff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ switch (me->GetEntry())
+ {
+ case NPC_AKU_MAI_SNAPJAW:
+ {
+ if (uiRavageTimer <= uiDiff)
+ {
+ DoCast(me->getVictim(), SPELL_RAVAGE);
+ uiRavageTimer = urand(9000,14000);
+ } else uiRavageTimer -= uiDiff;
+ break;
+ }
+ case NPC_MURKSHALLOW_SOFTSHELL:
+ case NPC_BARBED_CRUSTACEAN:
+ {
+ if (!bFlee && HealthBelowPct(15))
+ {
+ bFlee = true;
+ me->DoFleeToGetAssistance();
+ }
+ break;
+ }
+ case NPC_AKU_MAI_SERVANT:
+ {
+ if (uiFrostBoltVolleyTimer <= uiDiff)
+ {
+ if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM,0))
+ {
+ if (pTarget)
+ DoCast(pTarget, SPELL_FROST_BOLT_VOLLEY);
+ }
+ uiFrostBoltVolleyTimer = urand(5000,8000);
+ } else uiFrostBoltVolleyTimer -= uiDiff;
+ if (uiFrostNovaTimer <= uiDiff)
+ {
+ DoCastAOE(SPELL_FROST_NOVA,false);
+ uiFrostNovaTimer = urand(25000,30000);
+ } else uiFrostNovaTimer -= uiDiff;
+ break;
+ }
+ }
+
+ DoMeleeAttackIfReady();
+ }
+
+ void JustDied(Unit* /*pKiller*/)
+ {
+ if (me->isSummon()) //we are not a normal spawn.
+ if (pInstance)
+ pInstance->SetData(DATA_EVENT, pInstance->GetData(DATA_EVENT) + 1);
+ }
+};
+
+CreatureAI* GetAI_npc_blackfathom_deeps_event(Creature* pCreature)
+{
+ return new npc_blackfathom_deeps_eventAI (pCreature);
+}
+
+enum eMorridune
+{
+ SAY_MORRIDUNE_1 = -1048003,
+ SAY_MORRIDUNE_2 = -1048004
+};
+
+struct npc_morriduneAI : public npc_escortAI
+{
+ npc_morriduneAI(Creature* pCreature) : npc_escortAI(pCreature)
+ {
+ DoScriptText(SAY_MORRIDUNE_1,pCreature);
+ me->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ Start(false,false,NULL);
+ }
+
+ void WaypointReached(uint32 uiPoint)
+ {
+ switch(uiPoint)
+ {
+ case 4:
+ SetEscortPaused(true);
+ me->SetOrientation(1.775791);
+ me->SendMovementFlagUpdate();
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ DoScriptText(SAY_MORRIDUNE_2,me);
+ break;
+ }
+ }
+};
+
+CreatureAI* GetAI_npc_morridune(Creature* pCreature)
+{
+ return new npc_morriduneAI (pCreature);
+}
+
+bool GossipHello_npc_morridune(Player* pPlayer, Creature* pCreature)
+{
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_MORRIDUNE, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_morridune(Player* pPlayer, Creature* /*pCreature*/, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch(uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->TeleportTo(1,9952.239,2284.277,1341.394,1.595);
+ pPlayer->CLOSE_GOSSIP_MENU();
+ break;
+ }
+ return true;
+}
+
+void AddSC_blackfathom_deeps()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "go_blackfathom_altar";
+ newscript->pGOHello = &GoHello_blackfathom_altar;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "go_blackfathom_fire";
+ newscript->pGOHello = &GoHello_blackfathom_fire;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_blackfathom_deeps_event";
+ newscript->GetAI = &GetAI_npc_blackfathom_deeps_event;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_morridune";
+ newscript->GetAI = &GetAI_npc_morridune;
+ newscript->pGossipHello = &GossipHello_npc_morridune;
+ newscript->pGossipSelect = &GossipSelect_npc_morridune;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.h b/src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.h
new file mode 100644
index 00000000000..e8bbab9f105
--- /dev/null
+++ b/src/server/scripts/Kalimdor/blackfathom_depths/blackfathom_deeps.h
@@ -0,0 +1,53 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software licensed under GPL version 2
+ * Please see the included DOCS/LICENSE.TXT for more information */
+
+#ifndef DEF_BFD_H
+#define DEF_BFD_H
+
+enum Data64
+{
+ DATA_SHRINE1,
+ DATA_SHRINE2,
+ DATA_SHRINE3,
+ DATA_SHRINE4,
+ DATA_TWILIGHT_LORD_KELRIS,
+ DATA_SHRINE_OF_GELIHAST,
+ DATA_ALTAR_OF_THE_DEEPS,
+ DATA_MAINDOOR,
+};
+
+enum Data
+{
+ TYPE_GELIHAST,
+ TYPE_KELRIS,
+ TYPE_SHRINE,
+ TYPE_AKU_MAI,
+ DATA_FIRE,
+ DATA_EVENT
+};
+
+enum Creatures
+{
+ NPC_TWILIGHT_LORD_KELRIS = 4832,
+ NPC_LORGUS_JETT = 12902,
+
+ NPC_AKU_MAI_SNAPJAW = 4825,
+ NPC_MURKSHALLOW_SOFTSHELL = 4977,
+ NPC_AKU_MAI_SERVANT = 4978,
+ NPC_BARBED_CRUSTACEAN = 4823,
+
+ NPC_MORRIDUNE = 6729
+};
+
+enum GameObjects
+{
+ GO_SHRINE_OF_GELIHAST = 103015,
+ GO_FIRE_OF_AKU_MAI_1 = 21118,
+ GO_FIRE_OF_AKU_MAI_2 = 21119,
+ GO_FIRE_OF_AKU_MAI_3 = 21120,
+ GO_FIRE_OF_AKU_MAI_4 = 21121,
+ GO_AKU_MAI_DOOR = 21117,
+ GO_ALTAR_OF_THE_DEEPS = 103016
+};
+#endif
diff --git a/src/server/scripts/Kalimdor/blackfathom_depths/boss_aku_mai.cpp b/src/server/scripts/Kalimdor/blackfathom_depths/boss_aku_mai.cpp
new file mode 100644
index 00000000000..a4b7a160be8
--- /dev/null
+++ b/src/server/scripts/Kalimdor/blackfathom_depths/boss_aku_mai.cpp
@@ -0,0 +1,94 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#include "ScriptedPch.h"
+#include "blackfathom_deeps.h"
+
+enum Spells
+{
+ SPELL_POISON_CLOUD = 3815,
+ SPELL_FRENZIED_RAGE = 3490
+};
+
+struct boss_aku_maiAI : public ScriptedAI
+{
+ boss_aku_maiAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ uint32 uiPoisonCloudTimer;
+ bool bIsEnraged;
+
+ ScriptedInstance *pInstance;
+
+ void Reset()
+ {
+ uiPoisonCloudTimer = urand(5000,9000);
+ bIsEnraged = false;
+ if (pInstance)
+ pInstance->SetData(TYPE_AKU_MAI, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ if (pInstance)
+ pInstance->SetData(TYPE_AKU_MAI, IN_PROGRESS);
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(TYPE_AKU_MAI, DONE);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ if (uiPoisonCloudTimer < diff)
+ {
+ DoCastVictim(SPELL_POISON_CLOUD);
+ uiPoisonCloudTimer = urand(25000,50000);
+ } else uiPoisonCloudTimer -= diff;
+
+ if (!bIsEnraged && HealthBelowPct(30))
+ {
+ DoCast(me,SPELL_FRENZIED_RAGE);
+ bIsEnraged = true;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_aku_mai(Creature* pCreature)
+{
+ return new boss_aku_maiAI (pCreature);
+}
+
+void AddSC_boss_aku_mai()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "boss_aku_mai";
+ newscript->GetAI = &GetAI_boss_aku_mai;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/blackfathom_depths/boss_gelihast.cpp b/src/server/scripts/Kalimdor/blackfathom_depths/boss_gelihast.cpp
new file mode 100644
index 00000000000..374a526f098
--- /dev/null
+++ b/src/server/scripts/Kalimdor/blackfathom_depths/boss_gelihast.cpp
@@ -0,0 +1,85 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#include "ScriptedPch.h"
+#include "blackfathom_deeps.h"
+
+enum Spells
+{
+ SPELL_NET = 6533
+};
+
+struct boss_gelihastAI : public ScriptedAI
+{
+ boss_gelihastAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ uint32 uiNetTimer;
+
+ ScriptedInstance *pInstance;
+
+ void Reset()
+ {
+ uiNetTimer = urand(2000,4000);
+ if (pInstance)
+ pInstance->SetData(TYPE_GELIHAST, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ if (pInstance)
+ pInstance->SetData(TYPE_GELIHAST, IN_PROGRESS);
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(TYPE_GELIHAST, DONE);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ if (uiNetTimer < diff)
+ {
+ DoCastVictim(SPELL_NET);
+ uiNetTimer = urand(4000,7000);
+ } else uiNetTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_gelihast(Creature* pCreature)
+{
+ return new boss_gelihastAI (pCreature);
+}
+
+void AddSC_boss_gelihast()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "boss_gelihast";
+ newscript->GetAI = &GetAI_boss_gelihast;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/blackfathom_depths/boss_kelris.cpp b/src/server/scripts/Kalimdor/blackfathom_depths/boss_kelris.cpp
new file mode 100644
index 00000000000..bd7e1014d1a
--- /dev/null
+++ b/src/server/scripts/Kalimdor/blackfathom_depths/boss_kelris.cpp
@@ -0,0 +1,108 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#include "ScriptedPch.h"
+#include "blackfathom_deeps.h"
+
+enum Spells
+{
+ SPELL_MIND_BLAST = 15587,
+ SPELL_SLEEP = 8399,
+};
+
+//Id's from ACID
+enum Yells
+{
+ SAY_AGGRO = -1048002,
+ SAY_SLEEP = -1048001,
+ SAY_DEATH = -1048000
+};
+
+struct boss_kelrisAI : public ScriptedAI
+{
+ boss_kelrisAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ uint32 uiMindBlastTimer;
+ uint32 uiSleepTimer;
+
+ ScriptedInstance *pInstance;
+
+ void Reset()
+ {
+ uiMindBlastTimer = urand(2000,5000);
+ uiSleepTimer = urand(9000,12000);
+ if (pInstance)
+ pInstance->SetData(TYPE_KELRIS, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+ if (pInstance)
+ pInstance->SetData(TYPE_KELRIS, IN_PROGRESS);
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+ if (pInstance)
+ pInstance->SetData(TYPE_KELRIS, DONE);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ if (uiMindBlastTimer < diff)
+ {
+ DoCastVictim(SPELL_MIND_BLAST);
+ uiMindBlastTimer = urand(7000,9000);
+ } else uiMindBlastTimer -= diff;
+
+ if (uiSleepTimer < diff)
+ {
+ if (Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ {
+ DoScriptText(SAY_SLEEP, me);
+ DoCast(pTarget, SPELL_SLEEP);
+ }
+ uiSleepTimer = urand(15000,20000);
+ } else uiSleepTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_kelris(Creature* pCreature)
+{
+ return new boss_kelrisAI (pCreature);
+}
+
+void AddSC_boss_kelris()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "boss_kelris";
+ newscript->GetAI = &GetAI_boss_kelris;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/blackfathom_depths/instance_blackfathom_deeps.cpp b/src/server/scripts/Kalimdor/blackfathom_depths/instance_blackfathom_deeps.cpp
new file mode 100644
index 00000000000..a485684e699
--- /dev/null
+++ b/src/server/scripts/Kalimdor/blackfathom_depths/instance_blackfathom_deeps.cpp
@@ -0,0 +1,259 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Instance_Blackfathom_Deeps
+SD%Complete: 50
+SDComment:
+SDCategory: Blackfathom Deeps
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "blackfathom_deeps.h"
+
+#define MAX_ENCOUNTER 4
+
+/* Encounter 0 = Gelihast
+ Encounter 1 = Twilight Lord Kelris
+ Encounter 2 = Shrine event
+ Encounter 3 = Aku'Mai
+ */
+
+const Position LorgusPosition[4] =
+{
+ { -458.500610, -38.343079, -33.474445 },
+ { -469.423615, -88.400513, -39.265102 },
+ { -622.354980, -10.350100, -22.777000 },
+ { -759.640564, 16.658913, -29.159529 }
+};
+
+const Position SpawnsLocation[] =
+{
+ {-775.431, -153.853, -25.871, 3.207},
+ {-775.404, -174.132, -25.871, 3.185},
+ {-862.430, -154.937, -25.871, 0.060},
+ {-862.193, -174.251, -25.871, 6.182},
+ {-863.895, -458.899, -33.891, 5.637}
+};
+
+struct instance_blackfathom_deeps : public ScriptedInstance
+{
+ instance_blackfathom_deeps(Map* pMap) : ScriptedInstance(pMap) {Initialize();};
+
+ uint64 m_uiTwilightLordKelrisGUID;
+ uint64 m_uiShrine1GUID;
+ uint64 m_uiShrine2GUID;
+ uint64 m_uiShrine3GUID;
+ uint64 m_uiShrine4GUID;
+ uint64 m_uiShrineOfGelihastGUID;
+ uint64 m_uiAltarOfTheDeepsGUID;
+ uint64 m_uiMainDoorGUID;
+
+ uint8 m_auiEncounter[MAX_ENCOUNTER];
+ uint8 m_uiCountFires;
+ uint8 uiDeathTimes;
+
+ void Initialize()
+ {
+ memset(&m_auiEncounter, 0, sizeof(m_auiEncounter));
+
+ m_uiTwilightLordKelrisGUID = 0;
+ m_uiShrine1GUID = 0;
+ m_uiShrine2GUID = 0;
+ m_uiShrine3GUID = 0;
+ m_uiShrine4GUID = 0;
+ m_uiShrineOfGelihastGUID = 0;
+ m_uiAltarOfTheDeepsGUID = 0;
+ m_uiMainDoorGUID = 0;
+ m_uiCountFires = 0;
+ uiDeathTimes = 0;
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool /*add*/)
+ {
+ switch (pCreature->GetEntry())
+ {
+ case NPC_TWILIGHT_LORD_KELRIS:
+ m_uiTwilightLordKelrisGUID = pCreature->GetGUID();
+ break;
+ case NPC_LORGUS_JETT:
+ pCreature->SetHomePosition(LorgusPosition[urand(0,3)]);
+ break;
+ }
+ }
+
+ void OnGameObjectCreate(GameObject* pGo, bool /*add*/)
+ {
+ switch(pGo->GetEntry())
+ {
+ case GO_FIRE_OF_AKU_MAI_1:
+ m_uiShrine1GUID = pGo->GetGUID();
+ break;
+ case GO_FIRE_OF_AKU_MAI_2:
+ m_uiShrine2GUID = pGo->GetGUID();
+ break;
+ case GO_FIRE_OF_AKU_MAI_3:
+ m_uiShrine3GUID = pGo->GetGUID();
+ break;
+ case GO_FIRE_OF_AKU_MAI_4:
+ m_uiShrine4GUID = pGo->GetGUID();
+ break;
+ case GO_SHRINE_OF_GELIHAST:
+ m_uiShrineOfGelihastGUID = pGo->GetGUID();
+ if (m_auiEncounter[0] != DONE)
+ pGo->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_UNK1);
+ break;
+ case GO_ALTAR_OF_THE_DEEPS:
+ m_uiAltarOfTheDeepsGUID = pGo->GetGUID();
+ if (m_auiEncounter[3] != DONE)
+ pGo->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_UNK1);
+ break;
+ case GO_AKU_MAI_DOOR:
+ if (m_auiEncounter[2] == DONE)
+ HandleGameObject(NULL,true,pGo);
+ m_uiMainDoorGUID = pGo->GetGUID();
+ break;
+ }
+ }
+
+ void SetData(uint32 uiType, uint32 uiData)
+ {
+ switch(uiType)
+ {
+ case TYPE_GELIHAST:
+ m_auiEncounter[0] = uiData;
+ if (uiData == DONE)
+ if (GameObject *pGo = instance->GetGameObject(m_uiShrineOfGelihastGUID))
+ pGo->RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_UNK1);
+ break;
+ case TYPE_AKU_MAI:
+ m_auiEncounter[3] = uiData;
+ if (uiData == DONE)
+ if (GameObject *pGo = instance->GetGameObject(m_uiAltarOfTheDeepsGUID))
+ {
+ pGo->RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_UNK1);
+ pGo->SummonCreature(NPC_MORRIDUNE,SpawnsLocation[4], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ }
+ break;
+ case DATA_FIRE:
+ m_uiCountFires = uiData;
+ switch (m_uiCountFires)
+ {
+ case 1:
+ if (GameObject* pGO = instance->GetGameObject(m_uiShrine1GUID))
+ {
+ pGO->SummonCreature(NPC_AKU_MAI_SNAPJAW, SpawnsLocation[0], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_AKU_MAI_SNAPJAW, SpawnsLocation[1], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_AKU_MAI_SNAPJAW, SpawnsLocation[2], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_AKU_MAI_SNAPJAW, SpawnsLocation[3], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ }
+ break;
+ case 2:
+ if (GameObject* pGO = instance->GetGameObject(m_uiShrine1GUID))
+ {
+ for (uint8 i = 0; i < 2; ++i)
+ {
+ pGO->SummonCreature(NPC_MURKSHALLOW_SOFTSHELL, SpawnsLocation[0], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_MURKSHALLOW_SOFTSHELL, SpawnsLocation[1], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_MURKSHALLOW_SOFTSHELL, SpawnsLocation[2], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_MURKSHALLOW_SOFTSHELL, SpawnsLocation[3], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ }
+ }
+ break;
+ case 3:
+ if (GameObject* pGO = instance->GetGameObject(m_uiShrine1GUID))
+ {
+ pGO->SummonCreature(NPC_AKU_MAI_SERVANT, SpawnsLocation[1], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_AKU_MAI_SERVANT, SpawnsLocation[2], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ }
+ break;
+ case 4:
+ if (GameObject* pGO = instance->GetGameObject(m_uiShrine1GUID))
+ {
+ pGO->SummonCreature(NPC_BARBED_CRUSTACEAN, SpawnsLocation[0], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_BARBED_CRUSTACEAN, SpawnsLocation[1], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_BARBED_CRUSTACEAN, SpawnsLocation[2], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ pGO->SummonCreature(NPC_BARBED_CRUSTACEAN, SpawnsLocation[3], TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ }
+ break;
+ }
+ break;
+ case DATA_EVENT:
+ uiDeathTimes = uiData;
+ if (uiDeathTimes == 18)
+ HandleGameObject(m_uiMainDoorGUID,true);
+ break;
+ }
+ }
+
+ uint32 GetData(uint32 uiType)
+ {
+ switch(uiType)
+ {
+ case TYPE_GELIHAST:
+ return m_auiEncounter[0];
+ case TYPE_KELRIS:
+ return m_auiEncounter[1];
+ case TYPE_SHRINE:
+ return m_auiEncounter[2];
+ case TYPE_AKU_MAI:
+ return m_auiEncounter[3];
+ case DATA_FIRE:
+ return m_uiCountFires;
+ case DATA_EVENT:
+ return uiDeathTimes;
+ }
+
+ return 0;
+ }
+
+ uint64 GetData64(uint32 uiData)
+ {
+ switch(uiData)
+ {
+ case DATA_TWILIGHT_LORD_KELRIS:
+ return m_uiTwilightLordKelrisGUID;
+ case DATA_SHRINE1:
+ return m_uiShrine1GUID;
+ case DATA_SHRINE2:
+ return m_uiShrine2GUID;
+ case DATA_SHRINE3:
+ return m_uiShrine3GUID;
+ case DATA_SHRINE4:
+ return m_uiShrine4GUID;
+ case DATA_SHRINE_OF_GELIHAST:
+ return m_uiShrineOfGelihastGUID;
+ case DATA_MAINDOOR:
+ return m_uiMainDoorGUID;
+ }
+
+ return 0;
+ }
+};
+
+InstanceData* GetInstanceData_instance_blackfathom_deeps(Map* pMap)
+{
+ return new instance_blackfathom_deeps(pMap);
+}
+
+void AddSC_instance_blackfathom_deeps()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_blackfathom_deeps";
+ newscript->GetInstanceData = &GetInstanceData_instance_blackfathom_deeps;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/bloodmyst_isle.cpp b/src/server/scripts/Kalimdor/bloodmyst_isle.cpp
new file mode 100644
index 00000000000..108d03b8976
--- /dev/null
+++ b/src/server/scripts/Kalimdor/bloodmyst_isle.cpp
@@ -0,0 +1,149 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Bloodmyst_Isle
+SD%Complete: 80
+SDComment: Quest support: 9670, 9756(gossip items text needed).
+SDCategory: Bloodmyst Isle
+EndScriptData */
+
+/* ContentData
+mob_webbed_creature
+npc_captured_sunhawk_agent
+EndContentData */
+
+#include "ScriptedPch.h"
+
+/*######
+## mob_webbed_creature
+######*/
+
+//possible creatures to be spawned
+const uint32 possibleSpawns[32] = {17322, 17661, 17496, 17522, 17340, 17352, 17333, 17524, 17654, 17348, 17339, 17345, 17359, 17353, 17336, 17550, 17330, 17701, 17321, 17680, 17325, 17320, 17683, 17342, 17715, 17334, 17341, 17338, 17337, 17346, 17344, 17327};
+
+struct mob_webbed_creatureAI : public ScriptedAI
+{
+ mob_webbed_creatureAI(Creature *c) : ScriptedAI(c) {}
+
+ void Reset()
+ {
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ }
+
+ void JustDied(Unit* Killer)
+ {
+ uint32 spawnCreatureID = 0;
+
+ switch (urand(0,2))
+ {
+ case 0:
+ spawnCreatureID = 17681;
+ if (Killer->GetTypeId() == TYPEID_PLAYER)
+ CAST_PLR(Killer)->KilledMonsterCredit(spawnCreatureID, me->GetGUID());
+ break;
+ case 1:
+ case 2:
+ spawnCreatureID = possibleSpawns[urand(0,30)];
+ break;
+ }
+
+ if (spawnCreatureID)
+ me->SummonCreature(spawnCreatureID, 0.0f, 0.0f, 0.0f, me->GetOrientation(), TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 60000);
+ }
+};
+CreatureAI* GetAI_mob_webbed_creature(Creature* pCreature)
+{
+ return new mob_webbed_creatureAI (pCreature);
+}
+
+/*######
+## npc_captured_sunhawk_agent
+######*/
+
+#define C_SUNHAWK_TRIGGER 17974
+
+#define GOSSIP_HELLO_CSA "[PH] "
+#define GOSSIP_SELECT_CSA1 "[PH] "
+#define GOSSIP_SELECT_CSA2 "[PH] "
+#define GOSSIP_SELECT_CSA3 "[PH] "
+#define GOSSIP_SELECT_CSA4 "[PH] "
+#define GOSSIP_SELECT_CSA5 "[PH] "
+
+bool GossipHello_npc_captured_sunhawk_agent(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->HasAura(31609) && pPlayer->GetQuestStatus(9756) == QUEST_STATUS_INCOMPLETE)
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HELLO_CSA, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(9136, pCreature->GetGUID());
+ }
+ else
+ pPlayer->SEND_GOSSIP_MENU(9134, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_captured_sunhawk_agent(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch (uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_CSA1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+ pPlayer->SEND_GOSSIP_MENU(9137, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_CSA2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+3);
+ pPlayer->SEND_GOSSIP_MENU(9138, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+3:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_CSA3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+4);
+ pPlayer->SEND_GOSSIP_MENU(9139, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+4:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_CSA4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+5);
+ pPlayer->SEND_GOSSIP_MENU(9140, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+5:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SELECT_CSA5, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+6);
+ pPlayer->SEND_GOSSIP_MENU(9141, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+6:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pPlayer->TalkedToCreature(C_SUNHAWK_TRIGGER, pCreature->GetGUID());
+ break;
+ }
+ return true;
+}
+
+void AddSC_bloodmyst_isle()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "mob_webbed_creature";
+ newscript->GetAI = &GetAI_mob_webbed_creature;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_captured_sunhawk_agent";
+ newscript->pGossipHello = &GossipHello_npc_captured_sunhawk_agent;
+ newscript->pGossipSelect = &GossipSelect_npc_captured_sunhawk_agent;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/boss_azuregos.cpp b/src/server/scripts/Kalimdor/boss_azuregos.cpp
new file mode 100644
index 00000000000..8aeedfa199e
--- /dev/null
+++ b/src/server/scripts/Kalimdor/boss_azuregos.cpp
@@ -0,0 +1,155 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Azuregos
+SD%Complete: 90
+SDComment: Teleport not included, spell reflect not effecting dots (Core problem)
+SDCategory: Azshara
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define SAY_TELEPORT -1000100
+
+#define SPELL_MARKOFFROST 23182
+#define SPELL_MANASTORM 21097
+#define SPELL_CHILL 21098
+#define SPELL_FROSTBREATH 21099
+#define SPELL_REFLECT 22067
+#define SPELL_CLEAVE 8255 //Perhaps not right ID
+#define SPELL_ENRAGE 23537
+
+struct boss_azuregosAI : public ScriptedAI
+{
+ boss_azuregosAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 MarkOfFrost_Timer;
+ uint32 ManaStorm_Timer;
+ uint32 Chill_Timer;
+ uint32 Breath_Timer;
+ uint32 Teleport_Timer;
+ uint32 Reflect_Timer;
+ uint32 Cleave_Timer;
+ uint32 Enrage_Timer;
+ bool Enraged;
+
+ void Reset()
+ {
+ MarkOfFrost_Timer = 35000;
+ ManaStorm_Timer = 5000 + rand()%12000;
+ Chill_Timer = 10000 + rand()%20000;
+ Breath_Timer = 2000 + rand()%6000;
+ Teleport_Timer = 30000;
+ Reflect_Timer = 15000 + rand()%15000;
+ Cleave_Timer = 7000;
+ Enrage_Timer = 0;
+ Enraged = false;
+ }
+
+ void EnterCombat(Unit * /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (Teleport_Timer <= diff)
+ {
+ DoScriptText(SAY_TELEPORT, me);
+ std::list<HostileReference*>& m_threatlist = me->getThreatManager().getThreatList();
+ std::list<HostileReference*>::const_iterator i = m_threatlist.begin();
+ for (i = m_threatlist.begin(); i!= m_threatlist.end(); ++i)
+ {
+ Unit* pUnit = Unit::GetUnit((*me), (*i)->getUnitGuid());
+ if (pUnit && (pUnit->GetTypeId() == TYPEID_PLAYER))
+ {
+ DoTeleportPlayer(pUnit, me->GetPositionX(), me->GetPositionY(), me->GetPositionZ()+3, pUnit->GetOrientation());
+ }
+ }
+
+ DoResetThreat();
+ Teleport_Timer = 30000;
+ } else Teleport_Timer -= diff;
+
+ // //MarkOfFrost_Timer
+ // if (MarkOfFrost_Timer <= diff)
+ // {
+ // DoCast(me->getVictim(), SPELL_MARKOFFROST);
+ // MarkOfFrost_Timer = 25000;
+ // } else MarkOfFrost_Timer -= diff;
+
+ //Chill_Timer
+ if (Chill_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_CHILL);
+ Chill_Timer = 13000 + rand()%12000;
+ } else Chill_Timer -= diff;
+
+ //Breath_Timer
+ if (Breath_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_FROSTBREATH);
+ Breath_Timer = 10000 + rand()%5000;
+ } else Breath_Timer -= diff;
+
+ //ManaStorm_Timer
+ if (ManaStorm_Timer <= diff)
+ {
+ if (Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0))
+ DoCast(pTarget, SPELL_MANASTORM);
+ ManaStorm_Timer = 7500 + rand()%5000;
+ } else ManaStorm_Timer -= diff;
+
+ //Reflect_Timer
+ if (Reflect_Timer <= diff)
+ {
+ DoCast(me, SPELL_REFLECT);
+ Reflect_Timer = 20000 + rand()%15000;
+ } else Reflect_Timer -= diff;
+
+ //Cleave_Timer
+ if (Cleave_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_CLEAVE);
+ Cleave_Timer = 7000;
+ } else Cleave_Timer -= diff;
+
+ //Enrage_Timer
+ if (me->GetHealth()*100 / me->GetMaxHealth() < 26 && !Enraged)
+ {
+ DoCast(me, SPELL_ENRAGE);
+ Enraged = true;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_boss_azuregos(Creature* pCreature)
+{
+ return new boss_azuregosAI (pCreature);
+}
+
+void AddSC_boss_azuregos()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_azuregos";
+ newscript->GetAI = &GetAI_boss_azuregos;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_epoch.cpp b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_epoch.cpp
new file mode 100644
index 00000000000..287d3cf8e9b
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_epoch.cpp
@@ -0,0 +1,156 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+
+/* Script Data Start
+SDName: Boss epoch
+SDAuthor: Tartalo
+SD%Complete: 80
+SDComment: TODO: Intro, consecutive attacks to a random target durin time wrap, adjust timers
+SDCategory:
+Script Data End */
+
+#include "ScriptedPch.h"
+#include "culling_of_stratholme.h"
+
+enum Spells
+{
+ SPELL_CURSE_OF_EXERTION = 52772,
+ SPELL_TIME_WARP = 52766, //Time slows down, reducing attack, casting and movement speed by 70% for 6 sec.
+ SPELL_TIME_STOP = 58848, //Stops time in a 50 yard sphere for 2 sec.
+ SPELL_WOUNDING_STRIKE = 52771, //Used only on the tank
+ H_SPELL_WOUNDING_STRIKE = 58830
+};
+
+enum Yells
+{
+ SAY_INTRO = -1595000, //"Prince Arthas Menethil, on this day, a powerful darkness has taken hold of your soul. The death you are destined to visit upon others will this day be your own."
+ SAY_AGGRO = -1595001, //"We'll see about that, young prince."
+ SAY_TIME_WARP_1 = -1595002, //"Tick tock, tick tock..."
+ SAY_TIME_WARP_2 = -1595003, //"Not quick enough!"
+ SAY_TIME_WARP_3 = -1595004, //"Let's get this over with. "
+ SAY_SLAY_1 = -1595005, //"There is no future for you."
+ SAY_SLAY_2 = -1595006, //"This is the hour of our greatest triumph!"
+ SAY_SLAY_3 = -1595007, //"You were destined to fail. "
+ SAY_DEATH = -1595008 //"*gurgles*"
+};
+
+struct boss_epochAI : public ScriptedAI
+{
+ boss_epochAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ uint8 uiStep;
+
+ uint32 uiStepTimer;
+ uint32 uiWoundingStrikeTimer;
+ uint32 uiTimeWarpTimer;
+ uint32 uiTimeStopTimer;
+ uint32 uiCurseOfExertionTimer;
+
+ ScriptedInstance* pInstance;
+
+ void Reset()
+ {
+ uiStep = 1;
+ uiStepTimer = 26000;
+ uiCurseOfExertionTimer = 9300;
+ uiTimeWarpTimer = 25300;
+ uiTimeStopTimer = 21300;
+ uiWoundingStrikeTimer = 5300;
+
+ if (pInstance)
+ pInstance->SetData(DATA_EPOCH_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+
+ if (pInstance)
+ pInstance->SetData(DATA_EPOCH_EVENT, IN_PROGRESS);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (uiCurseOfExertionTimer < diff)
+ {
+ if (Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ DoCast(pTarget, SPELL_CURSE_OF_EXERTION);
+ uiCurseOfExertionTimer = 9300;
+ } else uiCurseOfExertionTimer -= diff;
+
+ if (uiWoundingStrikeTimer < diff)
+ {
+ DoCastVictim(SPELL_WOUNDING_STRIKE);
+ uiWoundingStrikeTimer = 5300;
+ } else uiWoundingStrikeTimer -= diff;
+
+ if (uiTimeStopTimer < diff)
+ {
+ DoCastAOE(SPELL_TIME_STOP);
+ uiTimeStopTimer = 21300;
+ } else uiTimeStopTimer -= diff;
+
+ if (uiTimeWarpTimer < diff)
+ {
+ DoScriptText(RAND(SAY_TIME_WARP_1,SAY_TIME_WARP_2,SAY_TIME_WARP_3), me);
+ DoCastAOE(SPELL_TIME_WARP);
+ uiTimeWarpTimer = 25300;
+ } else uiTimeWarpTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+
+ if (pInstance)
+ pInstance->SetData(DATA_EPOCH_EVENT, DONE);
+ }
+
+ void KilledUnit(Unit * victim)
+ {
+ if (victim == me)
+ return;
+
+ DoScriptText(RAND(SAY_SLAY_1,SAY_SLAY_2,SAY_SLAY_3), me);
+ }
+};
+
+CreatureAI* GetAI_boss_epoch(Creature* pCreature)
+{
+ return new boss_epochAI (pCreature);
+}
+
+void AddSC_boss_epoch()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "boss_epoch";
+ newscript->GetAI = &GetAI_boss_epoch;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_infinite.cpp b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_infinite.cpp
new file mode 100644
index 00000000000..12cdf00f2a5
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_infinite.cpp
@@ -0,0 +1,88 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#include "ScriptedPch.h"
+#include "culling_of_stratholme.h"
+
+enum Spells
+{
+ SPELL_CORRUPTING_BLIGHT = 60588,
+ SPELL_VOID_STRIKE = 60590
+};
+
+enum Yells
+{
+ SAY_AGGRO = -1595045,
+ SAY_FAIL = -1595046,
+ SAY_DEATH = -1595047
+};
+
+
+struct boss_infinite_corruptorAI : public ScriptedAI
+{
+ boss_infinite_corruptorAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance* pInstance;
+
+ void Reset()
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_INFINITE_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_INFINITE_EVENT, IN_PROGRESS);
+ }
+
+ void AttackStart(Unit* /*who*/) {}
+ void MoveInLineOfSight(Unit* /*who*/) {}
+ void UpdateAI(const uint32 /*diff*/)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_INFINITE_EVENT, DONE);
+ }
+};
+
+CreatureAI* GetAI_boss_infinite_corruptor(Creature* pCreature)
+{
+ return new boss_infinite_corruptorAI(pCreature);
+}
+
+void AddSC_boss_infinite_corruptor()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "boss_infinite_corruptor";
+ newscript->GetAI = &GetAI_boss_infinite_corruptor;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_mal_ganis.cpp b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_mal_ganis.cpp
new file mode 100644
index 00000000000..a39f3289a5a
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_mal_ganis.cpp
@@ -0,0 +1,262 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+/* Script Data Start
+SDName: Boss mal_ganis
+SDAuthor: Tartalo
+SD%Complete: 80
+SDComment: TODO: Intro & outro
+SDCategory:
+Script Data End */
+
+/*** SQL START ***
+update creature_template set scriptname = 'boss_mal_ganis' where entry = '';
+*** SQL END ***/
+#include "ScriptedPch.h"
+#include "culling_of_stratholme.h"
+
+enum Spells
+{
+ SPELL_CARRION_SWARM = 52720, //A cresting wave of chaotic magic splashes over enemies in front of the caster, dealing 3230 to 3570 Shadow damage and 380 to 420 Shadow damage every 3 sec. for 15 sec.
+ H_SPELL_CARRION_SWARM = 58852,
+ SPELL_MIND_BLAST = 52722, //Inflicts 4163 to 4837 Shadow damage to an enemy.
+ H_SPELL_MIND_BLAST = 58850,
+ SPELL_SLEEP = 52721, //Puts an enemy to sleep for up to 10 sec. Any damage caused will awaken the target.
+ H_SPELL_SLEEP = 58849,
+ SPELL_VAMPIRIC_TOUCH = 52723 //Heals the caster for half the damage dealt by a melee attack.
+};
+
+enum Yells
+{
+ SAY_INTRO_1 = -1595009,
+ SAY_INTRO_2 = -1595010,
+ SAY_AGGRO = -1595011,
+ SAY_KILL_1 = -1595012,
+ SAY_KILL_2 = -1595013,
+ SAY_KILL_3 = -1595014,
+ SAY_SLAY_1 = -1595015,
+ SAY_SLAY_2 = -1595016,
+ SAY_SLAY_3 = -1595017,
+ SAY_SLAY_4 = -1595018,
+ SAY_SLEEP_1 = -1595019,
+ SAY_SLEEP_2 = -1595020,
+ SAY_30HEALTH = -1595021,
+ SAY_15HEALTH = -1595022,
+ SAY_ESCAPE_SPEECH_1 = -1595023,
+ SAY_ESCAPE_SPEECH_2 = -1595024,
+ SAY_OUTRO = -1595025,
+};
+
+enum CombatPhases
+{
+ COMBAT,
+ OUTRO
+};
+
+struct boss_mal_ganisAI : public ScriptedAI
+{
+ boss_mal_ganisAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ uint32 uiCarrionSwarmTimer;
+ uint32 uiMindBlastTimer;
+ uint32 uiVampiricTouchTimer;
+ uint32 uiSleepTimer;
+
+ uint8 uiOutroStep;
+ uint32 uiOutroTimer;
+
+ bool bYelled;
+ bool bYelled2;
+
+ CombatPhases Phase;
+
+ ScriptedInstance* pInstance;
+
+ void Reset()
+ {
+ bYelled = false;
+ bYelled2 = false;
+ Phase = COMBAT;
+ uiCarrionSwarmTimer = 6000;
+ uiMindBlastTimer = 11000;
+ uiVampiricTouchTimer = urand(10000,15000);
+ uiSleepTimer = urand(15000,20000);
+ uiOutroTimer = 1000;
+
+ if (pInstance)
+ pInstance->SetData(DATA_MAL_GANIS_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+ if (pInstance)
+ pInstance->SetData(DATA_MAL_GANIS_EVENT, IN_PROGRESS);
+ }
+
+ void DamageTaken(Unit *done_by, uint32 &damage)
+ {
+ if (damage >= me->GetHealth() && done_by != me)
+ damage = me->GetHealth()-1;
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ switch(Phase)
+ {
+ case COMBAT:
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (!bYelled && HealthBelowPct(30))
+ {
+ DoScriptText(SAY_30HEALTH, me);
+ bYelled = true;
+ }
+
+ if (!bYelled2 && HealthBelowPct(15))
+ {
+ DoScriptText(SAY_15HEALTH, me);
+ bYelled2 = true;
+ }
+
+ if (HealthBelowPct(1))
+ {
+ //Handle Escape Event: Don't forget to add Player::RewardPlayerAndGroupAtEvent
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE | UNIT_FLAG_NOT_SELECTABLE);
+ uiOutroStep = 1;
+ Phase = OUTRO;
+ return;
+ }
+
+ if (Creature* pArthas = me->GetCreature(*me, pInstance ? pInstance->GetData64(DATA_ARTHAS) : 0))
+ if (pArthas->isDead())
+ {
+ EnterEvadeMode();
+ me->DisappearAndDie();
+ if (pInstance)
+ pInstance->SetData(DATA_MAL_GANIS_EVENT, FAIL);
+ }
+
+ if (uiCarrionSwarmTimer < diff)
+ {
+ DoCastVictim(SPELL_CARRION_SWARM);
+ uiCarrionSwarmTimer = 7000;
+ } else uiCarrionSwarmTimer -= diff;
+
+ if (uiMindBlastTimer < diff)
+ {
+ if (Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ DoCast(pTarget, SPELL_MIND_BLAST);
+ uiMindBlastTimer = 6000;
+ } else uiMindBlastTimer -= diff;
+
+ if (uiVampiricTouchTimer < diff)
+ {
+ DoCast(me, SPELL_VAMPIRIC_TOUCH);
+ uiVampiricTouchTimer = 32000;
+ } else uiVampiricTouchTimer -= diff;
+
+ if (uiSleepTimer < diff)
+ {
+ DoScriptText(RAND(SAY_SLEEP_1,SAY_SLEEP_2), me);
+ if (Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ DoCast(pTarget, SPELL_SLEEP);
+ uiSleepTimer = urand(15000,20000);
+ } else uiSleepTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ break;
+ case OUTRO:
+ if (uiOutroTimer < diff)
+ {
+ switch(uiOutroStep)
+ {
+ case 1:
+ DoScriptText(SAY_ESCAPE_SPEECH_1, me);
+ me->GetMotionMaster()->MoveTargetedHome();
+ ++uiOutroStep;
+ uiOutroTimer = 8000;
+ break;
+ case 2:
+ me->SetUInt64Value(UNIT_FIELD_TARGET, pInstance ? pInstance->GetData64(DATA_ARTHAS) : 0);
+ me->HandleEmoteCommand(29);
+ DoScriptText(SAY_ESCAPE_SPEECH_2, me);
+ ++uiOutroStep;
+ uiOutroTimer = 9000;
+ break;
+ case 3:
+ DoScriptText(SAY_OUTRO, me);
+ ++uiOutroStep;
+ uiOutroTimer = 16000;
+ break;
+ case 4:
+ me->HandleEmoteCommand(33);
+ ++uiOutroStep;
+ uiOutroTimer = 500;
+ break;
+ case 5:
+ me->SetVisibility(VISIBILITY_OFF);
+ me->Kill(me);
+ break;
+
+ }
+ } else uiOutroTimer -= diff;
+ break;
+ }
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ if (pInstance)
+ {
+ pInstance->SetData(DATA_MAL_GANIS_EVENT, DONE);
+
+ // give achievement credit to players. criteria use spell 58630 which doesn't exist.
+ if (pInstance)
+ pInstance->DoUpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_BE_SPELL_TARGET, 58630);
+ }
+ }
+
+ void KilledUnit(Unit * victim)
+ {
+ if (victim == me)
+ return;
+
+ DoScriptText(RAND(SAY_SLAY_1,SAY_SLAY_2,SAY_SLAY_3,SAY_SLAY_4), me);
+ }
+};
+
+CreatureAI* GetAI_boss_mal_ganis(Creature* pCreature)
+{
+ return new boss_mal_ganisAI (pCreature);
+}
+
+void AddSC_boss_mal_ganis()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "boss_mal_ganis";
+ newscript->GetAI = &GetAI_boss_mal_ganis;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_meathook.cpp b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_meathook.cpp
new file mode 100644
index 00000000000..eba9733c745
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_meathook.cpp
@@ -0,0 +1,140 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+/* Script Data Start
+SDName: Boss meathook
+SDAuthor: Tartalo
+SD%Complete: 100
+SDComment: It may need timer adjustment
+SDCategory:
+Script Data End */
+
+#include "ScriptedPch.h"
+#include "culling_of_stratholme.h"
+
+enum Spells
+{
+ SPELL_CONSTRICTING_CHAINS = 52696, //Encases the targets in chains, dealing 1800 Physical damage every 1 sec. and stunning the target for 5 sec.
+ H_SPELL_CONSTRICTING_CHAINS = 58823,
+ SPELL_DISEASE_EXPULSION = 52666, //Meathook belches out a cloud of disease, dealing 1710 to 1890 Nature damage and interrupting the spell casting of nearby enemy targets for 4 sec.
+ H_SPELL_DISEASE_EXPULSION = 58824,
+ SPELL_FRENZY = 58841 //Increases the caster's Physical damage by 10% for 30 sec.
+};
+
+enum Yells
+{
+ SAY_AGGRO = -1595026,
+ SAY_SLAY_1 = -1595027,
+ SAY_SLAY_2 = -1595028,
+ SAY_SLAY_3 = -1595029,
+ SAY_SPAWN = -1595030,
+ SAY_DEATH = -1595031
+};
+
+struct boss_meathookAI : public ScriptedAI
+{
+ boss_meathookAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ if (pInstance)
+ DoScriptText(SAY_SPAWN,me);
+ }
+
+ uint32 uiChainTimer;
+ uint32 uiDiseaseTimer;
+ uint32 uiFrenzyTimer;
+
+ ScriptedInstance* pInstance;
+
+ void Reset()
+ {
+ uiChainTimer = urand(12000,17000); //seen on video 13, 17, 15, 12, 16
+ uiDiseaseTimer = urand(2000,4000); //approx 3s
+ uiFrenzyTimer = urand(21000,26000); //made it up
+
+ if (pInstance)
+ pInstance->SetData(DATA_MEATHOOK_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+
+ if (pInstance)
+ pInstance->SetData(DATA_MEATHOOK_EVENT, IN_PROGRESS);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (uiDiseaseTimer <= diff)
+ {
+ DoCastAOE(SPELL_DISEASE_EXPULSION);
+ uiDiseaseTimer = urand(1500,4000);
+ } else uiDiseaseTimer -= diff;
+
+ if (uiFrenzyTimer <= diff)
+ {
+ DoCast(me, SPELL_FRENZY);
+ uiFrenzyTimer = urand(21000,26000);
+ } else uiFrenzyTimer -= diff;
+
+ if (uiChainTimer <= diff)
+ {
+ if (Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ DoCast(pTarget, SPELL_CONSTRICTING_CHAINS); //anyone but the tank
+ uiChainTimer = urand(2000,4000);
+ } else uiChainTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+
+ if (pInstance)
+ pInstance->SetData(DATA_MEATHOOK_EVENT, DONE);
+ }
+
+ void KilledUnit(Unit * victim)
+ {
+ if (victim == me)
+ return;
+
+ DoScriptText(RAND(SAY_SLAY_1,SAY_SLAY_2,SAY_SLAY_3), me);
+ }
+};
+
+CreatureAI* GetAI_boss_meathook(Creature* pCreature)
+{
+ return new boss_meathookAI (pCreature);
+}
+
+void AddSC_boss_meathook()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "boss_meathook";
+ newscript->GetAI = &GetAI_boss_meathook;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_salramm.cpp b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_salramm.cpp
new file mode 100644
index 00000000000..da1c8098517
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/boss_salramm.cpp
@@ -0,0 +1,170 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+/* Script Data Start
+SDName: Boss salramm
+SDAuthor: Tartalo
+SD%Complete: 80
+SDComment: TODO: Intro
+SDCategory:
+Script Data End */
+
+/*** SQL START ***
+update creature_template set scriptname = 'boss_salramm' where entry = '';
+*** SQL END ***/
+#include "ScriptedPch.h"
+#include "culling_of_stratholme.h"
+
+enum Spells
+{
+ SPELL_CURSE_OF_TWISTED_FLESH = 58845,
+ SPELL_EXPLODE_GHOUL = 52480,
+ H_SPELL_EXPLODE_GHOUL = 58825,
+ SPELL_SHADOW_BOLT = 57725,
+ H_SPELL_SHADOW_BOLT = 58828,
+ SPELL_STEAL_FLESH = 52708,
+ SPELL_SUMMON_GHOULS = 52451
+};
+
+enum Yells
+{
+ SAY_AGGRO = -1595032,
+ SAY_SPAWN = -1595033,
+ SAY_SLAY_1 = -1595034,
+ SAY_SLAY_2 = -1595035,
+ SAY_SLAY_3 = -1595036,
+ SAY_DEATH = -1595037,
+ SAY_EXPLODE_GHOUL_1 = -1595038,
+ SAY_EXPLODE_GHOUL_2 = -1595039,
+ SAY_STEAL_FLESH_1 = -1595040,
+ SAY_STEAL_FLESH_2 = -1595041,
+ SAY_STEAL_FLESH_3 = -1595042,
+ SAY_SUMMON_GHOULS_1 = -1595043,
+ SAY_SUMMON_GHOULS_2 = -1595044
+};
+
+struct boss_salrammAI : public ScriptedAI
+{
+ boss_salrammAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ if (pInstance)
+ DoScriptText(SAY_SPAWN,me);
+ }
+
+ uint32 uiCurseFleshTimer;
+ uint32 uiExplodeGhoulTimer;
+ uint32 uiShadowBoltTimer;
+ uint32 uiStealFleshTimer;
+ uint32 uiSummonGhoulsTimer;
+
+ ScriptedInstance* pInstance;
+
+ void Reset()
+ {
+ uiCurseFleshTimer = 30000; //30s DBM
+ uiExplodeGhoulTimer = urand(25000,28000); //approx 6 sec after summon ghouls
+ uiShadowBoltTimer = urand(8000,12000); // approx 10s
+ uiStealFleshTimer = 12345;
+ uiSummonGhoulsTimer = urand(19000,24000); //on a video approx 24s after aggro
+
+ if (pInstance)
+ pInstance->SetData(DATA_SALRAMM_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+
+ if (pInstance)
+ pInstance->SetData(DATA_SALRAMM_EVENT, IN_PROGRESS);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Curse of twisted flesh timer
+ if (uiCurseFleshTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_CURSE_OF_TWISTED_FLESH);
+ uiCurseFleshTimer = 37000;
+ } else uiCurseFleshTimer -= diff;
+
+ //Shadow bolt timer
+ if (uiShadowBoltTimer <= diff)
+ {
+ if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0))
+ DoCast(pTarget, SPELL_SHADOW_BOLT);
+ uiShadowBoltTimer = urand(8000,12000);
+ } else uiShadowBoltTimer -= diff;
+
+ //Steal Flesh timer
+ if (uiStealFleshTimer <= diff)
+ {
+ DoScriptText(RAND(SAY_STEAL_FLESH_1,SAY_STEAL_FLESH_2,SAY_STEAL_FLESH_3), me);
+ if (Unit* random_pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0))
+ DoCast(random_pTarget, SPELL_STEAL_FLESH);
+ uiStealFleshTimer = 10000;
+ } else uiStealFleshTimer -= diff;
+
+ //Summon ghouls timer
+ if (uiSummonGhoulsTimer <= diff)
+ {
+ DoScriptText(RAND(SAY_SUMMON_GHOULS_1,SAY_SUMMON_GHOULS_2), me);
+ if (Unit* random_pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0))
+ DoCast(random_pTarget, SPELL_SUMMON_GHOULS);
+ uiSummonGhoulsTimer = 10000;
+ } else uiSummonGhoulsTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+
+ if (pInstance)
+ pInstance->SetData(DATA_SALRAMM_EVENT, DONE);
+ }
+
+ void KilledUnit(Unit * victim)
+ {
+ if (victim == me)
+ return;
+
+ DoScriptText(RAND(SAY_SLAY_1,SAY_SLAY_2,SAY_SLAY_3), me);
+ }
+};
+
+CreatureAI* GetAI_boss_salramm(Creature* pCreature)
+{
+ return new boss_salrammAI (pCreature);
+}
+
+void AddSC_boss_salramm()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "boss_salramm";
+ newscript->GetAI = &GetAI_boss_salramm;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.cpp b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.cpp
new file mode 100644
index 00000000000..faaed2eb6db
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.cpp
@@ -0,0 +1,1210 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#include "ScriptedPch.h"
+#include "culling_of_stratholme.h"
+#include "ScriptedEscortAI.h"
+
+enum Says
+{
+ //First Act - Uther and Jaina Dialog
+ SAY_PHASE101 = -1595070, //Arthas
+ SAY_PHASE102 = -1595071, //Uther
+ SAY_PHASE103 = -1595072, //Arthas
+ SAY_PHASE104 = -1595073, //Arthas
+ SAY_PHASE105 = -1595074, //Uther
+ SAY_PHASE106 = -1595075, //Arthas
+ SAY_PHASE107 = -1595076, //Uther
+ SAY_PHASE108 = -1595077, //Arthas
+ SAY_PHASE109 = -1595078, //Arthas
+ SAY_PHASE110 = -1595079, //Uther
+ SAY_PHASE111 = -1595080, //Arthas
+ SAY_PHASE112 = -1595081, //Uther
+ SAY_PHASE113 = -1595082, //Jaina
+ SAY_PHASE114 = -1595083, //Arthas
+ SAY_PHASE115 = -1595084, //Uther
+ SAY_PHASE116 = -1595085, //Arthas
+ SAY_PHASE117 = -1595086, //Jaina
+ SAY_PHASE118 = -1595087, //Arthas
+ //Second Act - City Streets
+ SAY_PHASE201 = -1595088, //Arthas
+ SAY_PHASE202 = -1595089, //Cityman
+ SAY_PHASE203 = -1595090, //Arthas
+ SAY_PHASE204 = -1595091, //Crazyman
+ SAY_PHASE205 = -1595092, //Arthas
+ SAY_PHASE206 = -1595009, //Malganis
+ SAY_PHASE207 = -1595010, //Malganis
+ SAY_PHASE208 = -1595093, //Arthas
+ SAY_PHASE209 = -1595094, //Arthas
+ SAY_PHASE210 = -1595095, //Arthas
+ //Third Act - Town Hall
+ SAY_PHASE301 = -1595096, //Arthas
+ SAY_PHASE302 = -1595097, //Drakonian
+ SAY_PHASE303 = -1595098, //Arthas
+ SAY_PHASE304 = -1595099, //Arthas
+ SAY_PHASE305 = -1595100, //Drakonian
+ SAY_PHASE306 = -1595101, //Arthas
+ SAY_PHASE307 = -1595102, //Arthas
+ SAY_PHASE308 = -1595103, //Arthas
+ SAY_PHASE309 = -1595104, //Arthas
+ SAY_PHASE310 = -1595105, //Arthas
+ SAY_PHASE311 = -1595106, //Arthas
+ SAY_PHASE312 = -1595107, //Arthas
+ SAY_PHASE313 = -1595108, //Arthas
+ SAY_PHASE314 = -1595000, //Epoch
+ SAY_PHASE315 = -1595109, //Arthas
+ //Fourth Act - Fire Corridor
+ SAY_PHASE401 = -1595110, //Arthas
+ SAY_PHASE402 = -1595111, //Arthas
+ SAY_PHASE403 = -1595112, //Arthas
+ SAY_PHASE404 = -1595113, //Arthas
+ SAY_PHASE405 = -1595114, //Arthas
+ SAY_PHASE406 = -1595115, //Arthas
+ SAY_PHASE407 = -1595116, //Arthas
+ //Fifth Act - Mal'Ganis Fight
+ SAY_PHASE501 = -1595117, //Arthas
+ SAY_PHASE502 = -1595118, //Arthas
+ SAY_PHASE503 = -1595119, //Arthas
+ SAY_PHASE504 = -1595120, //Arthas
+};
+
+enum NPCs
+{
+ NPC_INFINITE_ADVERSARY = 27742,
+ NPC_INFINITE_HUNTER = 27743,
+ NPC_INFINITE_AGENT = 27744,
+ NPC_TIME_RIFT = 28409,
+ NPC_ZOMBIE = 27737,
+ NPC_GHOUL = 28249,
+ NPC_NECROMANCER = 28200,
+ NPC_STALKER = 28199,
+ NPC_FIEND = 27734,
+ NPC_GOLEM = 28201,
+ NPC_EGHOUL = 27729,
+ NPC_CONSTRUCT = 27736,
+
+ NPC_INVIS_TARGET = 20562,
+
+ NPC_KNIGHT_ESCORT = 27745,
+ NPC_PRIEST_ESCORT = 27747,
+ NPC_CITY_MAN = 28167,
+ NPC_CITY_MAN2 = 28169,
+ NPC_CITY_MAN3 = 31126,
+ NPC_CITY_MAN4 = 31127,
+};
+
+enum Spells
+{
+ SPELL_FEAR = 39176,
+ SPELL_ARTHAS_AURA = 52442,
+ SPELL_EXORCISM_N = 52445,
+ SPELL_EXORCISM_H = 58822,
+ SPELL_HOLY_LIGHT = 52444,
+};
+
+enum GossipMenuArthas
+{
+ GOSSIP_MENU_ARTHAS_1 = 100001,
+ GOSSIP_MENU_ARTHAS_2 = 100002,
+ GOSSIP_MENU_ARTHAS_3 = 100003,
+ GOSSIP_MENU_ARTHAS_4 = 100004,
+ GOSSIP_MENU_ARTHAS_5 = 100005
+};
+
+enum
+{
+ ENCOUNTER_WAVES_NUMBER = 8,
+ ENCOUNTER_WAVES_MAX_SPAWNS = 5,
+ ENCOUNTER_DRACONIAN_NUMBER = 4,
+ ENCOUNTER_CHRONO_SPAWNS = 19
+};
+
+// Locations for necromancers and add to spawn
+float WavesLocations[ENCOUNTER_WAVES_NUMBER][ENCOUNTER_WAVES_MAX_SPAWNS][5]=
+{
+ {
+ {NPC_ZOMBIE, 2164.698975, 1255.392944, 135.040878, 0.490202},
+ {NPC_ZOMBIE, 2183.501465, 1263.079102, 134.859055, 3.169981},
+ {NPC_GHOUL, 2177.512939, 1247.313843, 135.846695, 1.696574},
+ {NPC_GHOUL, 2171.991943, 1246.615845, 135.745026, 1.696574},
+ {0, 0, 0, 0, 0}
+ },
+ {
+ {NPC_GHOUL, 2254.434326, 1163.427612, 138.055038, 2.077358},
+ {NPC_GHOUL, 2254.703613, 1158.867798, 138.212234, 2.345532},
+ {NPC_GHOUL, 2257.615723, 1162.310913, 138.091202, 2.077358},
+ {NPC_NECROMANCER, 2258.258057, 1157.250732, 138.272873, 2.387766},
+ {0, 0, 0, 0, 0}
+ },
+ {
+ {NPC_STALKER, 2348.120117, 1202.302490, 130.491104, 4.698538},
+ {NPC_GHOUL, 2352.863525, 1207.819092, 130.424271, 4.949865},
+ {NPC_GHOUL, 2343.593750, 1207.915039, 130.781311, 4.321547},
+ {NPC_NECROMANCER, 2348.257324, 1212.202515, 130.670135, 4.450352},
+ {0, 0, 0, 0, 0}
+ },
+ {
+ {NPC_STALKER, 2139.825195, 1356.277100, 132.199615, 5.820131},
+ {NPC_GHOUL, 2137.073486, 1362.464844, 132.271637, 5.820131},
+ {NPC_GHOUL, 2134.075684, 1354.148071, 131.885864, 5.820131},
+ {NPC_NECROMANCER, 2133.302246, 1358.907837, 132.037689, 5.820131},
+ {0, 0, 0, 0, 0}
+ },
+ {
+ {NPC_NECROMANCER, 2264.013428, 1174.055908, 138.093094, 2.860481},
+ {NPC_GHOUL, 2264.207764, 1170.892700, 138.034973, 2.860481},
+ {NPC_GHOUL, 2266.948975, 1176.898926, 137.976929, 2.860481},
+ {NPC_STALKER, 2269.215576, 1170.109253, 137.742691, 2.860481},
+ {NPC_FIEND, 2273.106689, 1176.101074, 137.880508, 2.860481}
+ },
+ {
+ {NPC_GOLEM, 2349.701660, 1188.436646, 130.428864, 3.908642},
+ {NPC_GHOUL, 2349.909180, 1194.582642, 130.417816, 3.577001},
+ {NPC_EGHOUL, 2354.662598, 1185.692017, 130.552032, 3.577001},
+ {NPC_EGHOUL, 2354.716797, 1191.614380, 130.539810, 3.577001},
+ {0, 0, 0, 0, 0}
+ },
+ {
+ {NPC_CONSTRUCT, 2145.212891, 1355.288086, 132.288773, 6.004838},
+ {NPC_NECROMANCER, 2137.078613, 1357.612671, 132.173340, 6.004838},
+ {NPC_EGHOUL, 2139.402100, 1352.541626, 132.127518, 5.812850},
+ {NPC_EGHOUL, 2142.408447, 1360.760620, 132.321564, 5.812850},
+ {0, 0, 0, 0, 0}
+ },
+ {
+ {NPC_GHOUL, 2172.686279, 1259.618164, 134.391754, 1.865499},
+ {NPC_FIEND, 2177.649170, 1256.061157, 135.096512, 1.849572},
+ {NPC_CONSTRUCT, 2170.782959, 1253.594849, 134.973022, 1.849572},
+ {NPC_NECROMANCER, 2175.595703, 1249.041992, 135.603531, 1.849572},
+ {0, 0, 0, 0, 0}
+ }
+};
+
+// Locations for rifts to spawn and draconians to go
+float RiftAndSpawnsLocations[ENCOUNTER_CHRONO_SPAWNS][5]=
+{
+ {NPC_TIME_RIFT, 2431.790039, 1190.670044, 148.076004, 0.187923},
+ {NPC_INFINITE_ADVERSARY, 2433.857910, 1185.612061, 148.075974, 4.566168},
+ {NPC_INFINITE_ADVERSARY, 2437.577881, 1188.241089, 148.075974, 0.196999},
+ {NPC_INFINITE_AGENT, 2437.165527, 1192.294922, 148.075974, 0.169247},
+ {NPC_INFINITE_HUNTER, 2434.989990, 1197.679565, 148.075974, 0.715971},
+ {NPC_TIME_RIFT, 2403.954834, 1178.815430, 148.075943, 4.966126},
+ {NPC_INFINITE_AGENT, 2403.676758, 1171.495850, 148.075607, 4.902797},
+ {NPC_INFINITE_HUNTER, 2407.691162, 1172.162720, 148.075607, 4.963010},
+ {NPC_TIME_RIFT, 2414.217041, 1133.446167, 148.076050, 1.706972},
+ {NPC_INFINITE_ADVERSARY, 2416.024658, 1139.456177, 148.076431, 1.752129},
+ {NPC_INFINITE_HUNTER, 2410.866699, 1139.680542, 148.076431, 1.752129},
+ {NPC_TIME_RIFT, 2433.081543, 1099.869751, 148.076157, 1.809509},
+ {NPC_INFINITE_ADVERSARY, 2426.947998, 1107.471680, 148.076019, 1.877580},
+ {NPC_INFINITE_HUNTER, 2432.944580, 1108.896362, 148.208160, 2.199241},
+ {NPC_TIME_RIFT, 2444.077637, 1114.366089, 148.076157, 3.049565},
+ {NPC_INFINITE_ADVERSARY, 2438.190674, 1118.368164, 148.076172, 3.139232},
+ {NPC_INFINITE_AGENT, 2435.861328, 1113.402954, 148.169327, 2.390271},
+ {NPC_TIME_RIFT, 2463.131592, 1115.391724, 152.473129, 3.409651},
+ {NPC_EPOCH, 2451.809326, 1112.901245, 149.220459, 3.363617}
+};
+
+struct npc_arthasAI : public npc_escortAI
+{
+ npc_arthasAI(Creature *pCreature) : npc_escortAI(pCreature)
+ {
+ pInstance = pCreature->GetInstanceData();
+ Reset();
+ }
+
+ ScriptedInstance* pInstance;
+
+ bool bStepping;
+ uint32 uiStep;
+ uint32 uiPhaseTimer;
+ uint32 uiGossipStep;
+ uint32 uiPlayerFaction;
+ uint32 uiBossEvent;
+ uint32 uiWave;
+
+ uint64 uiUtherGUID;
+ uint64 uiJainaGUID;
+ uint64 uiCitymenGUID[2];
+ uint64 uiWaveGUID[ENCOUNTER_WAVES_MAX_SPAWNS];
+ uint64 uiInfiniteDraconianGUID[ENCOUNTER_DRACONIAN_NUMBER];
+ uint64 uiStalkerGUID;
+
+ uint64 uiBossGUID; //uiMeathookGUID || uiSalrammGUID
+ uint64 uiEpochGUID;
+ uint64 uiMalganisGUID;
+ uint64 uiInfiniteGUID;
+
+ uint32 uiExorcismTimer;
+
+ void Reset()
+ {
+ uiUtherGUID = 0;
+ uiJainaGUID = 0;
+
+ for (uint8 i = 0; i < 2; ++i)
+ uiCitymenGUID[i] = 0;
+
+ for (uint8 i = 0; i < ENCOUNTER_WAVES_MAX_SPAWNS; ++i)
+ uiWaveGUID[i] = 0;
+
+ for (uint8 i = 0; i < ENCOUNTER_DRACONIAN_NUMBER; ++i)
+ uiInfiniteDraconianGUID[i] = 0;
+
+ uiStalkerGUID = 0;
+ uiBossGUID = 0;
+ uiEpochGUID = 0;
+ uiMalganisGUID = 0;
+ uiInfiniteGUID = 0;
+
+ if (pInstance) {
+ pInstance->SetData(DATA_ARTHAS_EVENT, NOT_STARTED);
+ switch(pInstance->GetData(DATA_ARTHAS_EVENT))
+ {
+ case NOT_STARTED:
+ bStepping = true;
+ uiStep = 0;
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ uiBossEvent = DATA_MEATHOOK_EVENT;
+ uiGossipStep = 0;
+ break;
+ }
+ uiPhaseTimer = 1000;
+ uiExorcismTimer = 7300;
+ uiWave = 0;
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ DoCast(me, SPELL_ARTHAS_AURA);
+ }
+
+ void JustDied(Unit * /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_ARTHAS_EVENT, FAIL);
+ }
+
+ void SpawnTimeRift(uint32 timeRiftID, uint64* guidVector)
+ {
+ me->SummonCreature((uint32)RiftAndSpawnsLocations[timeRiftID][0],RiftAndSpawnsLocations[timeRiftID][1],RiftAndSpawnsLocations[timeRiftID][2],RiftAndSpawnsLocations[timeRiftID][3],RiftAndSpawnsLocations[timeRiftID][4],TEMPSUMMON_TIMED_DESPAWN,11000);
+
+ for (uint32 i = timeRiftID+1; i < ENCOUNTER_CHRONO_SPAWNS; ++i)
+ {
+ if ((uint32)RiftAndSpawnsLocations[i][0] == NPC_TIME_RIFT) break;
+ if (Creature* pTemp = me->SummonCreature((uint32)RiftAndSpawnsLocations[i][0],RiftAndSpawnsLocations[timeRiftID][1],RiftAndSpawnsLocations[timeRiftID][2],RiftAndSpawnsLocations[timeRiftID][3],RiftAndSpawnsLocations[timeRiftID][4],TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,900000))
+ {
+ guidVector[i-timeRiftID-1] = pTemp->GetGUID();
+ pTemp->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE | UNIT_FLAG_UNK_9);
+ pTemp->SetReactState(REACT_PASSIVE);
+ pTemp->GetMotionMaster()->MovePoint(0, RiftAndSpawnsLocations[i][1],RiftAndSpawnsLocations[i][2],RiftAndSpawnsLocations[i][3]);
+ if ((uint32)RiftAndSpawnsLocations[i][0] == NPC_EPOCH)
+ uiEpochGUID = pTemp->GetGUID();
+ }
+ }
+ }
+
+ void SpawnWaveGroup(uint32 waveID, uint64* guidVector)
+ {
+ for (uint32 i = 0; i < ENCOUNTER_WAVES_MAX_SPAWNS; ++i)
+ {
+ if ((uint32)WavesLocations[waveID][i][0] == 0) break;
+ if (Creature* pTemp = me->SummonCreature((uint32)WavesLocations[waveID][i][0],WavesLocations[waveID][i][1],WavesLocations[waveID][i][2],WavesLocations[waveID][i][3],WavesLocations[waveID][i][4],TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,900000))
+ {
+ guidVector[i] = pTemp->GetGUID();
+ }
+ }
+ }
+
+ void SetHoldState(bool bOnHold)
+ {
+ SetEscortPaused(bOnHold);
+ }
+
+ void JumpToNextStep(uint32 uiTimer)
+ {
+ uiPhaseTimer = uiTimer;
+ ++uiStep;
+ }
+
+ void WaypointReached(uint32 uiPointId)
+ {
+ switch(uiPointId)
+ {
+ case 0:
+ case 1:
+ case 3:
+ case 9:
+ case 10:
+ case 11:
+ case 22:
+ case 23:
+ case 26:
+ case 55:
+ case 56:
+ SetHoldState(true);
+ bStepping = true;
+ break;
+ case 7:
+ if (Unit* pCityman0 = me->SummonCreature(NPC_CITY_MAN,2091.977f,1275.021f,140.757f,0.558f,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,60000))
+ uiCitymenGUID[0] = pCityman0->GetGUID();
+ if (Unit* pCityman1 = me->SummonCreature(NPC_CITY_MAN2,2093.514f,1275.842f,140.408f,3.801f,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,60000))
+ uiCitymenGUID[1] = pCityman1->GetGUID();
+ break;
+ case 8:
+ uiGossipStep = 1;
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ SetHoldState(true);
+ break;
+ case 12:
+ SetRun(true);
+ DoScriptText(SAY_PHASE210, me);
+ if (Unit* pDisguised0 = me->SummonCreature(NPC_CITY_MAN3,2398.14f,1207.81f,134.04f,5.155249f,TEMPSUMMON_DEAD_DESPAWN,180000))
+ {
+ uiInfiniteDraconianGUID[0] = pDisguised0->GetGUID();
+ if (Unit* pDisguised1 = me->SummonCreature(NPC_CITY_MAN4,2403.22f,1205.54f,134.04f,3.311264f,TEMPSUMMON_DEAD_DESPAWN,180000))
+ {
+ uiInfiniteDraconianGUID[1] = pDisguised1->GetGUID();
+
+ if (Unit* pDisguised2 = me->SummonCreature(NPC_CITY_MAN,2400.82f,1201.69f,134.01f,1.534082f,TEMPSUMMON_DEAD_DESPAWN,180000))
+ {
+ uiInfiniteDraconianGUID[2] = pDisguised2->GetGUID();
+ pDisguised0->SetUInt64Value(UNIT_FIELD_TARGET, uiInfiniteDraconianGUID[1]);
+ pDisguised1->SetUInt64Value(UNIT_FIELD_TARGET, uiInfiniteDraconianGUID[0]);
+ pDisguised2->SetUInt64Value(UNIT_FIELD_TARGET, uiInfiniteDraconianGUID[1]);
+ }
+ }
+ }
+ break;
+ case 20:
+ uiGossipStep = 2;
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ SetRun(false);
+ SetHoldState(true);
+ break;
+ case 21:
+ DoScriptText(SAY_PHASE301, me);
+ break;
+ case 25:
+ SetRun(false);
+ SpawnTimeRift(0,&uiInfiniteDraconianGUID[0]);
+ DoScriptText(SAY_PHASE307,me);
+ break;
+ case 29:
+ SetRun(false);
+ SpawnTimeRift(5,&uiInfiniteDraconianGUID[0]);
+ SpawnTimeRift(8,&uiInfiniteDraconianGUID[2]);
+ DoScriptText(SAY_PHASE309,me);
+ SetHoldState(true);
+ bStepping = true;
+ break;
+ case 31:
+ SetRun(false);
+ SpawnTimeRift(11,&uiInfiniteDraconianGUID[0]);
+ SpawnTimeRift(14,&uiInfiniteDraconianGUID[2]);
+ DoScriptText(SAY_PHASE311,me);
+ SetHoldState(true);
+ bStepping = true;
+ break;
+ case 32:
+ DoScriptText(SAY_PHASE401,me);
+ break;
+ case 34:
+ DoScriptText(SAY_PHASE402,me);
+ break;
+ case 35:
+ DoScriptText(SAY_PHASE403,me);
+ break;
+ case 36:
+ if (pInstance)
+ {
+ GameObject* pGate = pInstance->instance->GetGameObject(pInstance->GetData64(DATA_SHKAF_GATE));
+ pGate->SetGoState(GO_STATE_ACTIVE);
+ }
+ break;
+ case 45:
+ SetRun(true);
+ SetDespawnAtFar(false);
+ uiGossipStep = 4;
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ SetHoldState(true);
+ break;
+ case 47:
+ SetRun(false);
+ DoScriptText(SAY_PHASE405,me);
+ break;
+ case 48:
+ SetRun(true);
+ DoScriptText(SAY_PHASE406,me);
+ break;
+ case 53:
+ DoScriptText(SAY_PHASE407,me);
+ break;
+ case 54:
+ uiGossipStep = 5;
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ SetHoldState(true);
+ break;
+ }
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ npc_escortAI::UpdateAI(diff);
+
+ DoMeleeAttackIfReady();
+
+ if (bStepping)
+ {
+ if (uiPhaseTimer <= diff)
+ {
+ switch(uiStep)
+ {
+ //After reset
+ case 0:
+ if (Unit* pJaina = GetClosestCreatureWithEntry(me, NPC_JAINA, 50.0f))
+ uiJainaGUID = pJaina->GetGUID();
+ else if (Unit* pJaina = me->SummonCreature(NPC_JAINA,1895.48f,1292.66f,143.706f,0.023475f,TEMPSUMMON_DEAD_DESPAWN,180000))
+ uiJainaGUID = pJaina->GetGUID();
+ bStepping = false;
+ JumpToNextStep(0);
+ break;
+ //After waypoint 0
+ case 1:
+ me->RemoveUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
+ if (Unit* pUther = me->SummonCreature(NPC_UTHER,1794.357f,1272.183f,140.558f,1.37f,TEMPSUMMON_DEAD_DESPAWN,180000))
+ {
+ uiUtherGUID = pUther->GetGUID();
+ pUther->RemoveUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
+ pUther->GetMotionMaster()->MovePoint(0, 1897.018f, 1287.487f, 143.481f);
+ pUther->SetUInt64Value(UNIT_FIELD_TARGET, me->GetGUID());
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiUtherGUID);
+ }
+ JumpToNextStep(17000);
+ break;
+ case 2:
+ DoScriptText(SAY_PHASE101, me);
+ JumpToNextStep(2000);
+ break;
+ case 3:
+ if (Creature* pUther = Unit::GetCreature(*me, uiUtherGUID))
+ {
+ DoScriptText(SAY_PHASE102, pUther);
+ }
+ JumpToNextStep(8000);
+ break;
+ case 4:
+ SetEscortPaused(false);
+ bStepping = false;
+ SetRun(false);
+ DoScriptText(SAY_PHASE103, me);
+ JumpToNextStep(0);
+ break;
+ //After waypoint 1
+ case 5:
+ if (Creature* pJaina = Unit::GetCreature(*me, uiJainaGUID))
+ pJaina->SetUInt64Value(UNIT_FIELD_TARGET, me->GetGUID());
+ DoScriptText(SAY_PHASE104, me);
+ JumpToNextStep(10000);
+ break;
+ case 6:
+ if (Creature* pUther = Unit::GetCreature(*me, uiUtherGUID))
+ DoScriptText(SAY_PHASE105, pUther);
+ JumpToNextStep(1000);
+ break;
+ case 7:
+ DoScriptText(SAY_PHASE106, me);
+ JumpToNextStep(4000);
+ break;
+ case 8:
+ if (Creature* pUther = Unit::GetCreature(*me, uiUtherGUID))
+ DoScriptText(SAY_PHASE107, pUther);
+ JumpToNextStep(6000);
+ break;
+ case 9:
+ DoScriptText(SAY_PHASE108, me);
+ JumpToNextStep(4000);
+ break;
+ case 10:
+ if (Creature* pUther = Unit::GetCreature(*me, uiUtherGUID))
+ DoScriptText(SAY_PHASE109, pUther);
+ JumpToNextStep(8000);
+ break;
+ case 11:
+ DoScriptText(SAY_PHASE110, me);
+ JumpToNextStep(4000);
+ break;
+ case 12:
+ if (Creature* pUther = Unit::GetCreature(*me, uiUtherGUID))
+ DoScriptText(SAY_PHASE111, pUther);
+ JumpToNextStep(4000);
+ break;
+ case 13:
+ DoScriptText(SAY_PHASE112, me);
+ JumpToNextStep(11000);
+ break;
+ case 14:
+ if (Creature* pJaina = Unit::GetCreature(*me, uiJainaGUID))
+ DoScriptText(SAY_PHASE113, pJaina);
+ JumpToNextStep(3000);
+ break;
+ case 15:
+ DoScriptText(SAY_PHASE114, me);
+ JumpToNextStep(9000);
+ break;
+ case 16:
+ if (Creature* pUther = Unit::GetCreature(*me, uiUtherGUID))
+ DoScriptText(SAY_PHASE115, pUther);
+ JumpToNextStep(4000);
+ break;
+ case 17:
+ if (Creature* pUther = Unit::GetCreature(*me, uiUtherGUID))
+ {
+ pUther->AddUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
+ pUther->GetMotionMaster()->MovePoint(0, 1794.357f,1272.183f,140.558f);
+ }
+ JumpToNextStep(1000);
+ break;
+ case 18:
+ if (Creature* pJaina = Unit::GetCreature(*me, uiJainaGUID))
+ {
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiJainaGUID);
+ pJaina->AddUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
+ pJaina->GetMotionMaster()->MovePoint(0, 1794.357f,1272.183f,140.558f);
+ }
+ JumpToNextStep(1000);
+ break;
+ case 19:
+ DoScriptText(SAY_PHASE116, me);
+ JumpToNextStep(1000);
+ break;
+ case 20:
+ if (Creature* pJaina = Unit::GetCreature(*me, uiJainaGUID))
+ DoScriptText(SAY_PHASE117, pJaina);
+ JumpToNextStep(3000);
+ break;
+ case 21:
+ SetEscortPaused(false);
+ bStepping = false;
+ me->SetUInt64Value(UNIT_FIELD_TARGET, 0);
+ JumpToNextStep(0);
+ break;
+ //After waypoint 3
+ case 22:
+ DoScriptText(SAY_PHASE118, me);
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiJainaGUID);
+ JumpToNextStep(10000);
+ break;
+ case 23:
+ SetEscortPaused(false);
+ bStepping = false;
+ SetRun(true);
+
+ if (Creature* pJaina = Unit::GetCreature(*me, uiJainaGUID))
+ pJaina->DisappearAndDie();
+
+ if (Creature* pUther = Unit::GetCreature(*me, uiUtherGUID))
+ pUther->DisappearAndDie();
+
+ me->SetUInt64Value(UNIT_FIELD_TARGET, 0);
+ JumpToNextStep(0);
+ break;
+ //After Gossip 1 (waypoint 8)
+ case 24:
+ if (Unit* pStalker = me->SummonCreature(NPC_INVIS_TARGET,2026.469f,1287.088f,143.596f,1.37f,TEMPSUMMON_TIMED_DESPAWN,14000))
+ {
+ uiStalkerGUID = pStalker->GetGUID();
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiStalkerGUID);
+ }
+ JumpToNextStep(1000);
+ break;
+ case 25:
+ DoScriptText(SAY_PHASE201, me);
+ JumpToNextStep(12000);
+ break;
+ case 26:
+ SetEscortPaused(false);
+ bStepping = false;
+ SetRun(false);
+ me->SetUInt64Value(UNIT_FIELD_TARGET, 0);
+ JumpToNextStep(0);
+ break;
+ //After waypoint 9
+ case 27:
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiCitymenGUID[0]);
+ if (Creature* pCityman = Unit::GetCreature(*me, uiCitymenGUID[0]))
+ {
+ pCityman->SetUInt64Value(UNIT_FIELD_TARGET, me->GetGUID());
+ pCityman->AddUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
+ pCityman->GetMotionMaster()->MovePoint(0, 2088.625f,1279.191f,140.743f);
+ }
+ JumpToNextStep(2000);
+ break;
+ case 28:
+ if (Creature* pCityman = Unit::GetCreature(*me, uiCitymenGUID[0]))
+ DoScriptText(SAY_PHASE202, pCityman);
+ JumpToNextStep(4000);
+ break;
+ case 29:
+ SetEscortPaused(false);
+ bStepping = false;
+ DoScriptText(SAY_PHASE203, me);
+ JumpToNextStep(0);
+ break;
+ //After waypoint 10
+ case 30:
+ me->HandleEmoteCommand(37);
+ JumpToNextStep(1000);
+ break;
+ case 31:
+ SetEscortPaused(false);
+ bStepping = false;
+ if (Creature* pCityman1 = Unit::GetCreature(*me, uiCitymenGUID[1]))
+ {
+ DoScriptText(SAY_PHASE204, pCityman1);
+ pCityman1->SetUInt64Value(UNIT_FIELD_TARGET, me->GetGUID());
+ if (Creature* pCityman0 = Unit::GetCreature(*me, uiCitymenGUID[0]))
+ pCityman0->Kill(pCityman0);
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiCitymenGUID[1]);
+ }
+ JumpToNextStep(0);
+ break;
+ //After waypoint 11
+ case 32:
+ me->HandleEmoteCommand(37);
+ JumpToNextStep(1000);
+ break;
+ case 33:
+ if (Creature* pCityman1 = Unit::GetCreature(*me, uiCitymenGUID[1]))
+ pCityman1->Kill(pCityman1);
+ JumpToNextStep(1000);
+ break;
+ case 34:
+ if (Unit* pStalker = me->SummonCreature(NPC_INVIS_TARGET,2081.447f,1287.770f,141.3241f,1.37f,TEMPSUMMON_TIMED_DESPAWN,10000))
+ {
+ uiStalkerGUID = pStalker->GetGUID();
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiStalkerGUID);
+ }
+ DoScriptText(SAY_PHASE205, me);
+ JumpToNextStep(3000);
+ break;
+ case 35:
+ if (Unit* pStalkerM = me->SummonCreature(NPC_INVIS_TARGET,2117.349f,1288.624f,136.271f,1.37f,TEMPSUMMON_TIMED_DESPAWN,60000))
+ {
+ uiStalkerGUID = pStalkerM->GetGUID();
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiStalkerGUID);
+ }
+ JumpToNextStep(1000);
+ break;
+ case 36:
+ if (Creature* pMalganis = me->SummonCreature(NPC_MAL_GANIS,2117.349f,1288.624f,136.271f,1.37f,TEMPSUMMON_TIMED_DESPAWN,60000))
+ {
+ if (Creature* pStalkerM = Unit::GetCreature(*me, uiStalkerGUID))
+ pMalganis->CastSpell(pStalkerM,63793,false);
+
+ uiMalganisGUID = pMalganis->GetGUID();
+ DoScriptText(SAY_PHASE206, pMalganis);
+ pMalganis->SetUInt64Value(UNIT_FIELD_TARGET, me->GetGUID());
+ pMalganis->SetReactState(REACT_PASSIVE);
+ }
+ JumpToNextStep(11000);
+ break;
+ case 37:
+ if (Creature* pMalganis = Unit::GetCreature(*me, uiMalganisGUID))
+ {
+ if (Creature* pZombie = GetClosestCreatureWithEntry(pMalganis, NPC_CITY_MAN, 100.0f))
+ pZombie->UpdateEntry(NPC_ZOMBIE, 0);
+ else if (Creature* pZombie = GetClosestCreatureWithEntry(pMalganis, NPC_CITY_MAN2, 100.0f))
+ pZombie->UpdateEntry(NPC_ZOMBIE, 0);
+ else //There's no one else to transform
+ uiStep++;
+ }
+ else
+ uiStep++;
+ uiPhaseTimer = 500;
+ break;
+ case 38:
+ if (Creature* pMalganis = Unit::GetCreature(*me, uiMalganisGUID))
+ DoScriptText(SAY_PHASE207, pMalganis);
+ JumpToNextStep(17000);
+ break;
+ case 39:
+ if (Creature* pMalganis = Unit::GetCreature(*me, uiMalganisGUID))
+ pMalganis->SetVisibility(VISIBILITY_OFF);
+ DoScriptText(SAY_PHASE208, me);
+ JumpToNextStep(7000);
+ break;
+ case 40:
+ if (Unit* pStalker = me->SummonCreature(NPC_INVIS_TARGET,2081.447f,1287.770f,141.3241f,1.37f,TEMPSUMMON_TIMED_DESPAWN,10000))
+ {
+ uiStalkerGUID = pStalker->GetGUID();
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiStalkerGUID);
+ }
+ DoScriptText(SAY_PHASE209, me);
+
+ uiBossEvent = DATA_MEATHOOK_EVENT;
+ if (pInstance)
+ pInstance->SetData(DATA_ARTHAS_EVENT, IN_PROGRESS);
+
+ me->SetReactState(REACT_DEFENSIVE);
+ SetDespawnAtFar(false);
+ JumpToNextStep(5000);
+ break;
+ case 41: //Summon wave group
+ case 43:
+ case 45:
+ case 47:
+ case 51:
+ case 53:
+ case 55:
+ case 57:
+ if (pInstance->GetData(uiBossEvent) != DONE)
+ {
+ SpawnWaveGroup(uiWave, uiWaveGUID);
+ uiWave++;
+ }
+ JumpToNextStep(500);
+ break;
+ case 42: //Wait group to die
+ case 44:
+ case 46:
+ case 48:
+ case 52:
+ case 54:
+ case 56:
+ case 58:
+ if (pInstance->GetData(uiBossEvent) != DONE)
+ {
+ uint32 mobCounter = 0;
+ uint32 deadCounter = 0;
+ for (uint8 i = 0; i < ENCOUNTER_WAVES_MAX_SPAWNS; ++i)
+ {
+ if (uiWaveGUID[i] == 0)
+ break;
+ ++mobCounter;
+ Unit* pTemp = Unit::GetCreature(*me, uiWaveGUID[i]);
+ if (!pTemp || pTemp->isDead())
+ ++deadCounter;
+ }
+
+ if (mobCounter <= deadCounter) //If group is dead
+ JumpToNextStep(1000);
+ else
+ uiPhaseTimer = 1000;
+ }
+ else
+ JumpToNextStep(500);
+ break;
+ case 49: //Summon Boss
+ case 59:
+ if (pInstance->GetData(uiBossEvent) != DONE)
+ {
+ uint32 uiBossID = 0;
+ if (uiBossEvent == DATA_MEATHOOK_EVENT)
+ uiBossID = NPC_MEATHOOK;
+ else if (uiBossEvent == DATA_SALRAMM_EVENT)
+ uiBossID = NPC_SALRAMM;
+
+ if (Unit* pBoss = me->SummonCreature(uiBossID,2232.19f,1331.933f,126.662f,3.15f,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,900000))
+ {
+ uiBossGUID = pBoss->GetGUID();
+ pBoss->AddUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
+ pBoss->GetMotionMaster()->MovePoint(0, 2194.110f,1332.00f,130.00f);
+ }
+ }
+ JumpToNextStep(30000);
+ break;
+ case 50: //Wait Boss death
+ case 60:
+ if (pInstance)
+ {
+ if (pInstance->GetData(uiBossEvent) == DONE)
+ {
+ JumpToNextStep(1000);
+ if (uiBossEvent == DATA_MEATHOOK_EVENT)
+ uiBossEvent = DATA_SALRAMM_EVENT;
+ else if (uiBossEvent == DATA_SALRAMM_EVENT)
+ {
+ SetHoldState(false);
+ bStepping = false;
+ uiBossEvent = DATA_EPOCH_EVENT;
+ }
+ }
+ else if (pInstance->GetData(uiBossEvent) == FAIL)
+ npc_escortAI::EnterEvadeMode();
+ else
+ uiPhaseTimer = 10000;
+ }
+ break;
+ //After Gossip 2 (waypoint 22)
+ case 61:
+ me->SetReactState(REACT_AGGRESSIVE);
+ if (Creature* pDisguised0 = Unit::GetCreature(*me, uiInfiniteDraconianGUID[0]))
+ pDisguised0->SetUInt64Value(UNIT_FIELD_TARGET, me->GetGUID());
+ if (Creature* pDisguised1 = Unit::GetCreature(*me, uiInfiniteDraconianGUID[1]))
+ pDisguised1->SetUInt64Value(UNIT_FIELD_TARGET, me->GetGUID());
+ if (Creature* pDisguised2 = Unit::GetCreature(*me, uiInfiniteDraconianGUID[2]))
+ pDisguised2->SetUInt64Value(UNIT_FIELD_TARGET, me->GetGUID());
+ JumpToNextStep(1000);
+ break;
+ case 62:
+ if (Creature* pDisguised0 = Unit::GetCreature(*me, uiInfiniteDraconianGUID[0]))
+ DoScriptText(SAY_PHASE302, pDisguised0);
+ JumpToNextStep(7000);
+ break;
+ case 63:
+ DoScriptText(SAY_PHASE303, me);
+ SetHoldState(false);
+ bStepping = false;
+ JumpToNextStep(0);
+ break;
+ //After waypoint 23
+ case 64:
+ me->HandleEmoteCommand(54);
+ JumpToNextStep(1000);
+ break;
+ case 65:
+ if (Creature* pDisguised0 = Unit::GetCreature(*me, uiInfiniteDraconianGUID[0]))
+ pDisguised0->HandleEmoteCommand(11);
+ JumpToNextStep(1000);
+ break;
+ case 66:
+ DoScriptText(SAY_PHASE304,me);
+ JumpToNextStep(2000);
+ break;
+ case 67:
+ if (Creature* pDisguised0 = Unit::GetCreature(*me, uiInfiniteDraconianGUID[0]))
+ DoScriptText(SAY_PHASE305,pDisguised0);
+ JumpToNextStep(1000);
+ break;
+ case 68:
+ if (Creature* pDisguised2 = Unit::GetCreature(*me, uiInfiniteDraconianGUID[2]))
+ {
+ pDisguised2->UpdateEntry(NPC_INFINITE_HUNTER, 0);
+ //Make them unattackable
+ pDisguised2->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE | UNIT_FLAG_UNK_9);
+ pDisguised2->SetReactState(REACT_PASSIVE);
+ }
+ JumpToNextStep(2000);
+ break;
+ case 69:
+ if (Creature* pDisguised1 = Unit::GetCreature(*me, uiInfiniteDraconianGUID[1]))
+ {
+ pDisguised1->UpdateEntry(NPC_INFINITE_AGENT, 0);
+ //Make them unattackable
+ pDisguised1->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE | UNIT_FLAG_UNK_9);
+ pDisguised1->SetReactState(REACT_PASSIVE);
+ }
+ JumpToNextStep(2000);
+ break;
+ case 70:
+ if (Creature* pDisguised0 = Unit::GetCreature(*me, uiInfiniteDraconianGUID[0]))
+ {
+ pDisguised0->UpdateEntry(NPC_INFINITE_ADVERSARY, 0);
+ //Make them unattackable
+ pDisguised0->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE | UNIT_FLAG_UNK_9);
+ pDisguised0->SetReactState(REACT_PASSIVE);
+ }
+ JumpToNextStep(2000);
+ break;
+ case 71:
+ //After waypoint 26,29,31
+ case 73:
+ case 75:
+ case 77:
+ //Make cratures attackable
+ for (uint32 i = 0; i< ENCOUNTER_DRACONIAN_NUMBER; ++i)
+ if (Creature* pTemp = Unit::GetCreature(*me, uiInfiniteDraconianGUID[i]))
+ {
+ pTemp->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE | UNIT_FLAG_UNK_9);
+ pTemp->SetReactState(REACT_AGGRESSIVE);
+ }
+ JumpToNextStep(5000);
+ break;
+ case 72:
+ case 74:
+ case 76:
+ if (me->isInCombat())
+ uiPhaseTimer = 1000;
+ else
+ {
+ if (uiStep == 72) DoScriptText(SAY_PHASE308,me);
+ if (uiStep == 74) DoScriptText(SAY_PHASE308,me);
+ if (uiStep == 76) DoScriptText(SAY_PHASE310,me);
+ SetHoldState(false);
+ bStepping = false;
+ SetRun(true);
+ JumpToNextStep(2000);
+ }
+ break;
+ case 78:
+ if (me->isInCombat())
+ uiPhaseTimer = 1000;
+ else
+ {
+ DoScriptText(SAY_PHASE312,me);
+ JumpToNextStep(5000);
+ }
+ break;
+ case 79:
+ DoScriptText(SAY_PHASE313,me);
+ JumpToNextStep(1000);
+ break;
+ case 80:
+ if (pInstance)
+ if (pInstance->GetData(DATA_EPOCH_EVENT) != DONE)
+ {
+ SpawnTimeRift(17,&uiEpochGUID);
+ if (Creature* pEpoch = Unit::GetCreature(*me, uiEpochGUID))
+ DoScriptText(SAY_PHASE314,pEpoch);
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiEpochGUID);
+ }
+ JumpToNextStep(18000);
+ break;
+ case 81:
+ if (pInstance)
+ if (pInstance->GetData(DATA_EPOCH_EVENT) != DONE)
+ DoScriptText(SAY_PHASE315, me);
+ JumpToNextStep(6000);
+ break;
+ case 82:
+ if (pInstance)
+ if (pInstance->GetData(DATA_EPOCH_EVENT) != DONE)
+ {
+ if (Creature* pEpoch = Unit::GetCreature(*me, uiEpochGUID))
+ {
+ //Make Epoch attackable
+ pEpoch->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE | UNIT_FLAG_UNK_9);
+ pEpoch->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ pEpoch->SetReactState(REACT_AGGRESSIVE);
+ }
+
+ }
+ JumpToNextStep(1000);
+ break;
+ case 83:
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_EPOCH_EVENT) == DONE)
+ {
+ uiGossipStep = 3;
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ bStepping = false;
+ uiBossEvent = DATA_MAL_GANIS_EVENT;
+ JumpToNextStep(15000);
+ }
+ else if (pInstance->GetData(DATA_EPOCH_EVENT) == FAIL)
+ npc_escortAI::EnterEvadeMode();
+ else
+ uiPhaseTimer = 10000;
+ }
+ break;
+ //After Gossip 4
+ case 84:
+ DoScriptText(SAY_PHASE404,me);
+ SetHoldState(false);
+ bStepping = false;
+ break;
+ //After Gossip 5
+ case 85:
+ DoScriptText(SAY_PHASE501, me);
+ if (Creature* pMalganis = me->SummonCreature(NPC_MAL_GANIS,2296.665f,1502.362f,128.362f,4.961f,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,900000))
+ {
+ uiMalganisGUID = pMalganis->GetGUID();
+ pMalganis->SetReactState(REACT_PASSIVE);
+ }
+ if (pInstance)
+ {
+ GameObject* pGate = pInstance->instance->GetGameObject(pInstance->GetData64(DATA_MAL_GANIS_GATE_1));
+ pGate->SetGoState(GO_STATE_ACTIVE);
+ }
+ SetHoldState(false);
+ bStepping = false;
+ JumpToNextStep(0);
+ break;
+ //After waypoint 55
+ case 86:
+ DoScriptText(SAY_PHASE502, me);
+ JumpToNextStep(6000);
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiMalganisGUID);
+ break;
+ case 87:
+ if (Creature* pMalganis = Unit::GetCreature(*me, uiMalganisGUID))
+ {
+ pMalganis->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE | UNIT_FLAG_UNK_6 | UNIT_FLAG_UNK_9 | UNIT_FLAG_UNK_15);
+ pMalganis->SetReactState(REACT_AGGRESSIVE);
+ }
+ JumpToNextStep(1000);
+ break;
+ case 88:
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_MAL_GANIS_EVENT) == DONE)
+ {
+ SetHoldState(false);
+ JumpToNextStep(1000);
+ }
+ else if (pInstance->GetData(DATA_MAL_GANIS_EVENT) == FAIL)
+ npc_escortAI::EnterEvadeMode();
+ else
+ uiPhaseTimer = 10000;
+ }
+ break;
+ //After waypoint 56
+ case 89:
+ SetRun(true);
+ me->SetUInt64Value(UNIT_FIELD_TARGET, uiMalganisGUID);
+ DoScriptText(SAY_PHASE503, me);
+ JumpToNextStep(7000);
+ break;
+ case 90:
+ if (pInstance)
+ {
+ pInstance->SetData(DATA_ARTHAS_EVENT, DONE); //Rewards: Achiev & Chest ;D
+ me->SetUInt64Value(UNIT_FIELD_TARGET, pInstance->GetData64(DATA_MAL_GANIS_GATE_2)); //Look behind
+ }
+ DoScriptText(SAY_PHASE504, me);
+ bStepping = false;
+ break;
+ }
+ } else uiPhaseTimer -= diff;
+ }
+
+ //Battling skills
+ if (!me->getVictim())
+ return;
+
+ if (uiExorcismTimer < diff)
+ {
+ if (Unit* target = SelectUnit(SELECT_TARGET_RANDOM,0))
+ DoCast(target, SPELL_EXORCISM_N);
+ uiExorcismTimer = 7300;
+ } else uiExorcismTimer -= diff;
+
+ if (HealthBelowPct(40))
+ DoCast(me, SPELL_HOLY_LIGHT);
+ }
+};
+
+CreatureAI* GetAI_npc_arthas(Creature* pCreature)
+{
+ return new npc_arthasAI(pCreature);
+}
+
+#define GOSSIP_ITEM_ARTHAS_0 "I'm ready to start Culling of Stratholme."
+#define GOSSIP_ITEM_ARTHAS_1 "Yes, my Prince. We're ready."
+#define GOSSIP_ITEM_ARTHAS_2 "We're only doing what is best for Loarderon your Highness."
+#define GOSSIP_ITEM_ARTHAS_3 "I'm ready."
+#define GOSSIP_ITEM_ARTHAS_4 "For Lordaeron!"
+#define GOSSIP_ITEM_ARTHAS_5 "I'm ready to battle the dreadlord, sire."
+
+bool GossipHello_npc_arthas(Player* pPlayer, Creature* pCreature)
+{
+ npc_arthasAI* pAI = CAST_AI(npc_arthasAI,pCreature->AI());
+
+ if (pAI && pAI->bStepping == false)
+ {
+ switch (pAI->uiGossipStep)
+ {
+ case 0: //This one is a workaround since the very beggining of the script is wrong.
+ if (pPlayer->GetQuestStatus(13149) != QUEST_STATUS_COMPLETE)
+ return false;
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_ARTHAS_0, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+ pPlayer->SEND_GOSSIP_MENU(907, pCreature->GetGUID());
+ break;
+ case 1:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_ARTHAS_1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_MENU_ARTHAS_1, pCreature->GetGUID());
+ break;
+ case 2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_ARTHAS_2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_MENU_ARTHAS_2, pCreature->GetGUID());
+ break;
+ case 3:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_ARTHAS_3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+3);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_MENU_ARTHAS_3, pCreature->GetGUID());
+ break;
+ case 4:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_ARTHAS_4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+4);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_MENU_ARTHAS_4, pCreature->GetGUID());
+ break;
+ case 5:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_ARTHAS_5, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+5);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_MENU_ARTHAS_5, pCreature->GetGUID());
+ break;
+ default:
+ return false;
+ }
+ }
+ return true;
+}
+
+
+bool GossipSelect_npc_arthas(Player *pPlayer, Creature *pCreature, uint32 /*sender*/, uint32 action)
+{
+ npc_arthasAI* pAI = CAST_AI(npc_arthasAI,pCreature->AI());
+
+ if (!pAI)
+ return false;
+
+ switch (action)
+ {
+ case GOSSIP_ACTION_INFO_DEF:
+ pAI->Start(true,true,pPlayer->GetGUID(),0,false,false);
+ pAI->SetDespawnAtEnd(false);
+ pAI->bStepping = false;
+ pAI->uiStep = 1;
+ break;
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pAI->bStepping = true;
+ pAI->uiStep = 24;
+ break;
+ case GOSSIP_ACTION_INFO_DEF+2:
+ pAI->SetHoldState(false);
+ pAI->bStepping = false;
+ pAI->uiStep = 61;
+ break;
+ case GOSSIP_ACTION_INFO_DEF+3:
+ pAI->SetHoldState(false);
+ break;
+ case GOSSIP_ACTION_INFO_DEF+4:
+ pAI->bStepping = true;
+ pAI->uiStep = 84;
+ break;
+ case GOSSIP_ACTION_INFO_DEF+5:
+ pAI->bStepping = true;
+ pAI->uiStep = 85;
+ break;
+ }
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pAI->SetDespawnAtFar(true);
+ pCreature->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ return true;
+}
+
+void AddSC_culling_of_stratholme()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_arthas";
+ newscript->GetAI = &GetAI_npc_arthas;
+ newscript->pGossipHello = &GossipHello_npc_arthas;
+ newscript->pGossipSelect = &GossipSelect_npc_arthas;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.h b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.h
new file mode 100644
index 00000000000..4278ad46500
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/culling_of_stratholme.h
@@ -0,0 +1,68 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#ifndef DEF_CULLING_OF_STRATHOLME_H
+#define DEF_CULLING_OF_STRATHOLME_H
+
+enum Data
+{
+ DATA_MEATHOOK_EVENT,
+ DATA_SALRAMM_EVENT,
+ DATA_EPOCH_EVENT,
+ DATA_MAL_GANIS_EVENT,
+ DATA_INFINITE_EVENT,
+ DATA_ARTHAS_EVENT
+};
+
+enum Data64
+{
+ DATA_ARTHAS,
+ DATA_MEATHOOK,
+ DATA_SALRAMM,
+ DATA_EPOCH,
+ DATA_MAL_GANIS,
+ DATA_INFINITE,
+ DATA_SHKAF_GATE,
+ DATA_MAL_GANIS_GATE_1,
+ DATA_MAL_GANIS_GATE_2,
+ DATA_EXIT_GATE,
+ DATA_MAL_GANIS_CHEST
+};
+
+enum Creatures
+{
+ NPC_MEATHOOK = 26529,
+ NPC_SALRAMM = 26530,
+ NPC_EPOCH = 26532,
+ NPC_MAL_GANIS = 26533,
+ NPC_INFINITE = 32273,
+ NPC_ARTHAS = 26499,
+ NPC_JAINA = 26497,
+ NPC_UTHER = 26528
+};
+
+enum GameObjects
+{
+ GO_SHKAF_GATE = 188686,
+ GO_MALGANIS_GATE_1 = 187711,
+ GO_MALGANIS_GATE_2 = 187723,
+ GO_EXIT_GATE = 191788,
+ GO_MALGANIS_CHEST_N = 190663,
+ GO_MALGANIS_CHEST_H = 193597
+};
+#endif
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/instance_culling_of_stratholme.cpp b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/instance_culling_of_stratholme.cpp
new file mode 100644
index 00000000000..73742a1e748
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/culling_of_stratholme/instance_culling_of_stratholme.cpp
@@ -0,0 +1,244 @@
+/*
+* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+*
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#include "ScriptedPch.h"
+#include "culling_of_stratholme.h"
+
+#define MAX_ENCOUNTER 5
+
+/* Culling of Stratholme encounters:
+0 - Meathook
+1 - Salramm the Fleshcrafter
+2 - Chrono-Lord Epoch
+3 - Mal'Ganis
+4 - Infinite Corruptor (Heroic only)
+*/
+
+struct instance_culling_of_stratholme : public ScriptedInstance
+{
+ instance_culling_of_stratholme(Map* pMap) : ScriptedInstance(pMap) {Initialize();};
+
+ uint64 uiArthas;
+ uint64 uiMeathook;
+ uint64 uiSalramm;
+ uint64 uiEpoch;
+ uint64 uiMalGanis;
+ uint64 uiInfinite;
+
+ uint64 uiShkafGate;
+ uint64 uiMalGanisGate1;
+ uint64 uiMalGanisGate2;
+ uint64 uiExitGate;
+ uint64 uiMalGanisChest;
+
+ uint32 m_auiEncounter[MAX_ENCOUNTER];
+ std::string str_data;
+
+ bool IsEncounterInProgress() const
+ {
+ for (uint8 i = 0; i < MAX_ENCOUNTER; ++i)
+ if (m_auiEncounter[i] == IN_PROGRESS) return true;
+
+ return false;
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool /*add*/)
+ {
+ switch(pCreature->GetEntry())
+ {
+ case NPC_ARTHAS:
+ uiArthas = pCreature->GetGUID();
+ break;
+ case NPC_MEATHOOK:
+ uiMeathook = pCreature->GetGUID();
+ break;
+ case NPC_SALRAMM:
+ uiSalramm = pCreature->GetGUID();
+ break;
+ case NPC_EPOCH:
+ uiEpoch = pCreature->GetGUID();
+ break;
+ case NPC_MAL_GANIS:
+ uiMalGanis = pCreature->GetGUID();
+ break;
+ case NPC_INFINITE:
+ uiInfinite = pCreature->GetGUID();
+ break;
+ }
+ }
+
+ void OnGameObjectCreate(GameObject* pGo, bool /*add*/)
+ {
+ switch(pGo->GetEntry())
+ {
+ case GO_SHKAF_GATE:
+ uiShkafGate = pGo->GetGUID();
+ break;
+ case GO_MALGANIS_GATE_1:
+ uiMalGanisGate1 = pGo->GetGUID();
+ break;
+ case GO_MALGANIS_GATE_2:
+ uiMalGanisGate2 = pGo->GetGUID();
+ break;
+ case GO_EXIT_GATE:
+ uiExitGate = pGo->GetGUID();
+ if (m_auiEncounter[3] == DONE)
+ HandleGameObject(uiExitGate,true);
+ break;
+ case GO_MALGANIS_CHEST_N:
+ case GO_MALGANIS_CHEST_H:
+ uiMalGanisChest = pGo->GetGUID();
+ if (m_auiEncounter[3] == DONE)
+ pGo->RemoveFlag(GAMEOBJECT_FLAGS,GO_FLAG_INTERACT_COND);
+ break;
+ }
+ }
+
+ void SetData(uint32 type, uint32 data)
+ {
+ switch(type)
+ {
+ case DATA_MEATHOOK_EVENT:
+ m_auiEncounter[0] = data;
+ break;
+ case DATA_SALRAMM_EVENT:
+ m_auiEncounter[1] = data;
+ break;
+ case DATA_EPOCH_EVENT:
+ m_auiEncounter[2] = data;
+ break;
+ case DATA_MAL_GANIS_EVENT:
+ m_auiEncounter[3] = data;
+
+ switch(m_auiEncounter[3])
+ {
+ case NOT_STARTED:
+ HandleGameObject(uiMalGanisGate2,true);
+ break;
+ case IN_PROGRESS:
+ HandleGameObject(uiMalGanisGate2,false);
+ break;
+ case DONE:
+ HandleGameObject(uiExitGate, true);
+ if (GameObject *pGo = instance->GetGameObject(uiMalGanisChest))
+ pGo->RemoveFlag(GAMEOBJECT_FLAGS,GO_FLAG_INTERACT_COND);
+ break;
+ }
+ break;
+ case DATA_INFINITE_EVENT:
+ m_auiEncounter[4] = data;
+ break;
+ }
+
+ if (data == DONE)
+ SaveToDB();
+ }
+
+ uint32 GetData(uint32 type)
+ {
+ switch(type)
+ {
+ case DATA_MEATHOOK_EVENT: return m_auiEncounter[0];
+ case DATA_SALRAMM_EVENT: return m_auiEncounter[1];
+ case DATA_EPOCH_EVENT: return m_auiEncounter[2];
+ case DATA_MAL_GANIS_EVENT: return m_auiEncounter[3];
+ case DATA_INFINITE_EVENT: return m_auiEncounter[4];
+ }
+ return 0;
+ }
+
+ uint64 GetData64(uint32 identifier)
+ {
+ switch(identifier)
+ {
+ case DATA_ARTHAS: return uiArthas;
+ case DATA_MEATHOOK: return uiMeathook;
+ case DATA_SALRAMM: return uiSalramm;
+ case DATA_EPOCH: return uiEpoch;
+ case DATA_MAL_GANIS: return uiMalGanis;
+ case DATA_INFINITE: return uiInfinite;
+ case DATA_SHKAF_GATE: return uiShkafGate;
+ case DATA_MAL_GANIS_GATE_1: return uiMalGanisGate1;
+ case DATA_MAL_GANIS_GATE_2: return uiMalGanisGate2;
+ case DATA_EXIT_GATE: return uiExitGate;
+ case DATA_MAL_GANIS_CHEST: return uiMalGanisChest;
+ }
+ return 0;
+ }
+
+ std::string GetSaveData()
+ {
+ OUT_SAVE_INST_DATA;
+
+ std::ostringstream saveStream;
+ saveStream << "C S " << m_auiEncounter[0] << " " << m_auiEncounter[1] << " "
+ << m_auiEncounter[2] << " " << m_auiEncounter[3] << " " << m_auiEncounter[4];
+
+ str_data = saveStream.str();
+
+ OUT_SAVE_INST_DATA_COMPLETE;
+ return str_data;
+ }
+
+ void Load(const char* in)
+ {
+ if (!in)
+ {
+ OUT_LOAD_INST_DATA_FAIL;
+ return;
+ }
+
+ OUT_LOAD_INST_DATA(in);
+
+ char dataHead1, dataHead2;
+ uint16 data0, data1, data2, data3, data4;
+
+ std::istringstream loadStream(in);
+ loadStream >> dataHead1 >> dataHead2 >> data0 >> data1 >> data2 >> data3 >> data4;
+
+ if (dataHead1 == 'C' && dataHead2 == 'S')
+ {
+ m_auiEncounter[0] = data0;
+ m_auiEncounter[1] = data1;
+ m_auiEncounter[2] = data2;
+ m_auiEncounter[3] = data3;
+ m_auiEncounter[4] = data4;
+
+ for (uint8 i = 0; i < MAX_ENCOUNTER; ++i)
+ if (m_auiEncounter[i] == IN_PROGRESS)
+ m_auiEncounter[i] = NOT_STARTED;
+
+ } else OUT_LOAD_INST_DATA_FAIL;
+
+ OUT_LOAD_INST_DATA_COMPLETE;
+ }
+};
+
+InstanceData* GetInstanceData_instance_culling_of_stratholme(Map* pMap)
+{
+ return new instance_culling_of_stratholme(pMap);
+}
+
+void AddSC_instance_culling_of_stratholme()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_culling_of_stratholme";
+ newscript->GetInstanceData = &GetInstanceData_instance_culling_of_stratholme;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_aeonus.cpp b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_aeonus.cpp
new file mode 100644
index 00000000000..49cf7cd4433
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_aeonus.cpp
@@ -0,0 +1,145 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Aeonus
+SD%Complete: 80
+SDComment: Some spells not implemented
+SDCategory: Caverns of Time, The Dark Portal
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "dark_portal.h"
+
+enum eEnums
+{
+ SAY_ENTER = -1269012,
+ SAY_AGGRO = -1269013,
+ SAY_BANISH = -1269014,
+ SAY_SLAY1 = -1269015,
+ SAY_SLAY2 = -1269016,
+ SAY_DEATH = -1269017,
+ EMOTE_FRENZY = -1269018,
+
+ SPELL_CLEAVE = 40504,
+ SPELL_TIME_STOP = 31422,
+ SPELL_ENRAGE = 37605,
+ SPELL_SAND_BREATH = 31473,
+ H_SPELL_SAND_BREATH = 39049
+};
+
+struct boss_aeonusAI : public ScriptedAI
+{
+ boss_aeonusAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 SandBreath_Timer;
+ uint32 TimeStop_Timer;
+ uint32 Frenzy_Timer;
+
+ void Reset()
+ {
+ SandBreath_Timer = 15000+rand()%15000;
+ TimeStop_Timer = 10000+rand()%5000;
+ Frenzy_Timer = 30000+rand()%15000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ //Despawn Time Keeper
+ if (who->GetTypeId() == TYPEID_UNIT && who->GetEntry() == C_TIME_KEEPER)
+ {
+ if (me->IsWithinDistInMap(who,20.0f))
+ {
+ DoScriptText(SAY_BANISH, me);
+ me->DealDamage(who, who->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false);
+ }
+ }
+
+ ScriptedAI::MoveInLineOfSight(who);
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+
+ if (pInstance)
+ {
+ pInstance->SetData(TYPE_RIFT,DONE);
+ pInstance->SetData(TYPE_MEDIVH,DONE);//FIXME: later should be removed
+ }
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ DoScriptText(RAND(SAY_SLAY1,SAY_SLAY2), me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Sand Breath
+ if (SandBreath_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_SAND_BREATH);
+ SandBreath_Timer = 15000+rand()%10000;
+ } else SandBreath_Timer -= diff;
+
+ //Time Stop
+ if (TimeStop_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_TIME_STOP);
+ TimeStop_Timer = 20000+rand()%15000;
+ } else TimeStop_Timer -= diff;
+
+ //Frenzy
+ if (Frenzy_Timer <= diff)
+ {
+ DoScriptText(EMOTE_FRENZY, me);
+ DoCast(me, SPELL_ENRAGE);
+ Frenzy_Timer = 20000+rand()%15000;
+ } else Frenzy_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_aeonus(Creature* pCreature)
+{
+ return new boss_aeonusAI (pCreature);
+}
+
+void AddSC_boss_aeonus()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_aeonus";
+ newscript->GetAI = &GetAI_boss_aeonus;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_chrono_lord_deja.cpp b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_chrono_lord_deja.cpp
new file mode 100644
index 00000000000..1f2b4a80612
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_chrono_lord_deja.cpp
@@ -0,0 +1,154 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Chrono_Lord_Deja
+SD%Complete: 65
+SDComment: All abilities not implemented
+SDCategory: Caverns of Time, The Dark Portal
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "dark_portal.h"
+
+enum eEnums
+{
+ SAY_ENTER = -1269006,
+ SAY_AGGRO = -1269007,
+ SAY_BANISH = -1269008,
+ SAY_SLAY1 = -1269009,
+ SAY_SLAY2 = -1269010,
+ SAY_DEATH = -1269011,
+
+ SPELL_ARCANE_BLAST = 31457,
+ H_SPELL_ARCANE_BLAST = 38538,
+ SPELL_ARCANE_DISCHARGE = 31472,
+ H_SPELL_ARCANE_DISCHARGE = 38539,
+ SPELL_TIME_LAPSE = 31467,
+ SPELL_ATTRACTION = 38540 //Not Implemented (Heroic mode)
+};
+
+struct boss_chrono_lord_dejaAI : public ScriptedAI
+{
+ boss_chrono_lord_dejaAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 ArcaneBlast_Timer;
+ uint32 TimeLapse_Timer;
+ uint32 Attraction_Timer;
+ uint32 ArcaneDischarge_Timer;
+
+ void Reset()
+ {
+ ArcaneBlast_Timer = 18000+rand()%5000;
+ TimeLapse_Timer = 10000+rand()%5000;
+ ArcaneDischarge_Timer = 20000+rand()%10000;
+ Attraction_Timer = 25000+rand()%10000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ //Despawn Time Keeper
+ if (who->GetTypeId() == TYPEID_UNIT && who->GetEntry() == C_TIME_KEEPER)
+ {
+ if (me->IsWithinDistInMap(who,20.0f))
+ {
+ DoScriptText(SAY_BANISH, me);
+ me->DealDamage(who, who->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false);
+ }
+ }
+
+ ScriptedAI::MoveInLineOfSight(who);
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ DoScriptText(RAND(SAY_SLAY1,SAY_SLAY2), me);
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+
+ if (pInstance)
+ pInstance->SetData(TYPE_RIFT,SPECIAL);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Arcane Blast
+ if (ArcaneBlast_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_ARCANE_BLAST);
+ ArcaneBlast_Timer = 15000+rand()%10000;
+ } else ArcaneBlast_Timer -= diff;
+
+ //Arcane Discharge
+ if (ArcaneDischarge_Timer <= diff)
+ {
+ Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0);
+ DoCast(pTarget, SPELL_ARCANE_DISCHARGE);
+ ArcaneDischarge_Timer = 20000+rand()%10000;
+ } else ArcaneDischarge_Timer -= diff;
+
+ //Time Lapse
+ if (TimeLapse_Timer <= diff)
+ {
+ DoScriptText(SAY_BANISH, me);
+ DoCast(me, SPELL_TIME_LAPSE);
+ TimeLapse_Timer = 15000+rand()%10000;
+ } else TimeLapse_Timer -= diff;
+
+ if (IsHeroic())
+ {
+ if (Attraction_Timer <= diff)
+ {
+ DoCast(me, SPELL_ATTRACTION);
+ Attraction_Timer = 25000+rand()%10000;
+ } else Attraction_Timer -= diff;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_chrono_lord_deja(Creature* pCreature)
+{
+ return new boss_chrono_lord_dejaAI (pCreature);
+}
+
+void AddSC_boss_chrono_lord_deja()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_chrono_lord_deja";
+ newscript->GetAI = &GetAI_boss_chrono_lord_deja;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_temporus.cpp b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_temporus.cpp
new file mode 100644
index 00000000000..04b4b020ead
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/boss_temporus.cpp
@@ -0,0 +1,152 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Temporus
+SD%Complete: 75
+SDComment: More abilities need to be implemented
+SDCategory: Caverns of Time, The Dark Portal
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "dark_portal.h"
+
+enum eEnums
+{
+ SAY_ENTER = -1269000,
+ SAY_AGGRO = -1269001,
+ SAY_BANISH = -1269002,
+ SAY_SLAY1 = -1269003,
+ SAY_SLAY2 = -1269004,
+ SAY_DEATH = -1269005,
+
+ SPELL_HASTE = 31458,
+ SPELL_MORTAL_WOUND = 31464,
+ SPELL_WING_BUFFET = 31475,
+ H_SPELL_WING_BUFFET = 38593,
+ SPELL_REFLECT = 38592 //Not Implemented (Heroic mod)
+};
+
+struct boss_temporusAI : public ScriptedAI
+{
+ boss_temporusAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 Haste_Timer;
+ uint32 SpellReflection_Timer;
+ uint32 MortalWound_Timer;
+ uint32 WingBuffet_Timer;
+
+ void Reset()
+ {
+ Haste_Timer = 15000+rand()%8000;
+ SpellReflection_Timer = 30000;
+ MortalWound_Timer = 8000;
+ WingBuffet_Timer = 25000+rand()%10000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ DoScriptText(RAND(SAY_SLAY1,SAY_SLAY2), me);
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+
+ if (pInstance)
+ pInstance->SetData(TYPE_RIFT,SPECIAL);
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ //Despawn Time Keeper
+ if (who->GetTypeId() == TYPEID_UNIT && who->GetEntry() == C_TIME_KEEPER)
+ {
+ if (me->IsWithinDistInMap(who,20.0f))
+ {
+ DoScriptText(SAY_BANISH, me);
+
+ me->DealDamage(who, who->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false);
+ }
+ }
+
+ ScriptedAI::MoveInLineOfSight(who);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Attack Haste
+ if (Haste_Timer <= diff)
+ {
+ DoCast(me, SPELL_HASTE);
+ Haste_Timer = 20000+rand()%5000;
+ } else Haste_Timer -= diff;
+
+ //MortalWound_Timer
+ if (MortalWound_Timer <= diff)
+ {
+ DoCast(me, SPELL_MORTAL_WOUND);
+ MortalWound_Timer = 10000+rand()%10000;
+ } else MortalWound_Timer -= diff;
+
+ //Wing ruffet
+ if (WingBuffet_Timer <= diff)
+ {
+ DoCast(me, SPELL_WING_BUFFET);
+ WingBuffet_Timer = 20000+rand()%10000;
+ } else WingBuffet_Timer -= diff;
+
+ if (IsHeroic())
+ {
+ if (SpellReflection_Timer <= diff)
+ {
+ DoCast(me, SPELL_REFLECT);
+ SpellReflection_Timer = 25000+rand()%10000;
+ } else SpellReflection_Timer -= diff;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_temporus(Creature* pCreature)
+{
+ return new boss_temporusAI (pCreature);
+}
+
+void AddSC_boss_temporus()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_temporus";
+ newscript->GetAI = &GetAI_boss_temporus;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.cpp b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.cpp
new file mode 100644
index 00000000000..b0432a9b57c
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.cpp
@@ -0,0 +1,404 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+/* ScriptData
+SDName: Dark_Portal
+SD%Complete: 30
+SDComment: Misc NPC's and mobs for instance. Most here far from complete.
+SDCategory: Caverns of Time, The Dark Portal
+EndScriptData */
+
+/* ContentData
+npc_medivh_bm
+npc_time_rift
+npc_saat
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "dark_portal.h"
+
+#define SAY_ENTER -1269020 //where does this belong?
+#define SAY_INTRO -1269021
+#define SAY_WEAK75 -1269022
+#define SAY_WEAK50 -1269023
+#define SAY_WEAK25 -1269024
+#define SAY_DEATH -1269025
+#define SAY_WIN -1269026
+#define SAY_ORCS_ENTER -1269027
+#define SAY_ORCS_ANSWER -1269028
+
+#define SPELL_CHANNEL 31556
+#define SPELL_PORTAL_RUNE 32570 //aura(portal on ground effect)
+
+#define SPELL_BLACK_CRYSTAL 32563 //aura
+#define SPELL_PORTAL_CRYSTAL 32564 //summon
+
+#define SPELL_BANISH_PURPLE 32566 //aura
+#define SPELL_BANISH_GREEN 32567 //aura
+
+#define SPELL_CORRUPT 31326
+#define SPELL_CORRUPT_AEONUS 37853
+
+#define C_COUNCIL_ENFORCER 17023
+
+struct npc_medivh_bmAI : public ScriptedAI
+{
+ npc_medivh_bmAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 SpellCorrupt_Timer;
+ uint32 Check_Timer;
+
+ bool Life75;
+ bool Life50;
+ bool Life25;
+
+ void Reset()
+ {
+ SpellCorrupt_Timer = 0;
+
+ if (!pInstance)
+ return;
+
+ if (pInstance->GetData(TYPE_MEDIVH) == IN_PROGRESS)
+ DoCast(me, SPELL_CHANNEL, true);
+ else if (me->HasAura(SPELL_CHANNEL))
+ me->RemoveAura(SPELL_CHANNEL);
+
+ DoCast(me, SPELL_PORTAL_RUNE, true);
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ if (!pInstance)
+ return;
+
+ if (who->GetTypeId() == TYPEID_PLAYER && me->IsWithinDistInMap(who, 10.0f))
+ {
+ if (pInstance->GetData(TYPE_MEDIVH) == IN_PROGRESS || pInstance->GetData(TYPE_MEDIVH) == DONE)
+ return;
+
+ DoScriptText(SAY_INTRO, me);
+ pInstance->SetData(TYPE_MEDIVH,IN_PROGRESS);
+ DoCast(me, SPELL_CHANNEL, false);
+ Check_Timer = 5000;
+ }
+ else if (who->GetTypeId() == TYPEID_UNIT && me->IsWithinDistInMap(who, 15.0f))
+ {
+ if (pInstance->GetData(TYPE_MEDIVH) != IN_PROGRESS)
+ return;
+
+ uint32 entry = who->GetEntry();
+ if (entry == C_ASSAS || entry == C_WHELP || entry == C_CHRON || entry == C_EXECU || entry == C_VANQU)
+ {
+ who->StopMoving();
+ who->CastSpell(me,SPELL_CORRUPT,false);
+ }
+ else if (entry == C_AEONUS)
+ {
+ who->StopMoving();
+ who->CastSpell(me,SPELL_CORRUPT_AEONUS,false);
+ }
+ }
+ }
+
+ void AttackStart(Unit * /*who*/)
+ {
+ //if (pInstance && pInstance->GetData(TYPE_MEDIVH) == IN_PROGRESS)
+ //return;
+
+ //ScriptedAI::AttackStart(who);
+ }
+
+ void EnterCombat(Unit * /*who*/) {}
+
+ void SpellHit(Unit* /*caster*/, const SpellEntry* spell)
+ {
+ if (SpellCorrupt_Timer)
+ return;
+
+ if (spell->Id == SPELL_CORRUPT_AEONUS)
+ SpellCorrupt_Timer = 1000;
+
+ if (spell->Id == SPELL_CORRUPT)
+ SpellCorrupt_Timer = 3000;
+ }
+
+ void JustDied(Unit* Killer)
+ {
+ if (Killer->GetEntry() == me->GetEntry())
+ return;
+
+ DoScriptText(SAY_DEATH, me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!pInstance)
+ return;
+
+ if (SpellCorrupt_Timer)
+ {
+ if (SpellCorrupt_Timer <= diff)
+ {
+ pInstance->SetData(TYPE_MEDIVH,SPECIAL);
+
+ if (me->HasAura(SPELL_CORRUPT_AEONUS))
+ SpellCorrupt_Timer = 1000;
+ else if (me->HasAura(SPELL_CORRUPT))
+ SpellCorrupt_Timer = 3000;
+ else
+ SpellCorrupt_Timer = 0;
+ } else SpellCorrupt_Timer -= diff;
+ }
+
+ if (Check_Timer)
+ {
+ if (Check_Timer <= diff)
+ {
+ uint32 pct = pInstance->GetData(DATA_SHIELD);
+
+ Check_Timer = 5000;
+
+ if (Life25 && pct <= 25)
+ {
+ DoScriptText(SAY_WEAK25, me);
+ Life25 = false;
+ }
+ else if (Life50 && pct <= 50)
+ {
+ DoScriptText(SAY_WEAK50, me);
+ Life50 = false;
+ }
+ else if (Life75 && pct <= 75)
+ {
+ DoScriptText(SAY_WEAK75, me);
+ Life75 = false;
+ }
+
+ //if we reach this it means event was running but at some point reset.
+ if (pInstance->GetData(TYPE_MEDIVH) == NOT_STARTED)
+ {
+ me->DealDamage(me, me->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false);
+ me->RemoveCorpse();
+ me->Respawn();
+ return;
+ }
+
+ if (pInstance->GetData(TYPE_RIFT) == DONE)
+ {
+ DoScriptText(SAY_WIN, me);
+ Check_Timer = 0;
+
+ if (me->HasAura(SPELL_CHANNEL))
+ me->RemoveAura(SPELL_CHANNEL);
+
+ //TODO: start the post-event here
+ pInstance->SetData(TYPE_MEDIVH,DONE);
+ }
+ } else Check_Timer -= diff;
+ }
+
+ //if (!UpdateVictim())
+ //return;
+
+ //DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_medivh_bm(Creature* pCreature)
+{
+ return new npc_medivh_bmAI (pCreature);
+}
+
+struct Wave
+{
+ uint32 PortalMob[4]; //spawns for portal waves (in order)
+};
+
+static Wave PortalWaves[]=
+{
+ {C_ASSAS, C_WHELP, C_CHRON, 0},
+ {C_EXECU, C_CHRON, C_WHELP, C_ASSAS},
+ {C_EXECU, C_VANQU, C_CHRON, C_ASSAS}
+};
+
+struct npc_time_riftAI : public ScriptedAI
+{
+ npc_time_riftAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 TimeRiftWave_Timer;
+ uint8 mRiftWaveCount;
+ uint8 mPortalCount;
+ uint8 mWaveId;
+
+ void Reset()
+ {
+
+ TimeRiftWave_Timer = 15000;
+ mRiftWaveCount = 0;
+
+ if (!pInstance)
+ return;
+
+ mPortalCount = pInstance->GetData(DATA_PORTAL_COUNT);
+
+ if (mPortalCount < 6)
+ mWaveId = 0;
+ else if (mPortalCount > 12)
+ mWaveId = 2;
+ else mWaveId = 1;
+
+ }
+ void EnterCombat(Unit * /*who*/) {}
+
+ void DoSummonAtRift(uint32 creature_entry)
+ {
+ if (!creature_entry)
+ return;
+
+ if (pInstance && pInstance->GetData(TYPE_MEDIVH) != IN_PROGRESS)
+ {
+ me->InterruptNonMeleeSpells(true);
+ me->RemoveAllAuras();
+ return;
+ }
+
+ Position pos;
+ me->GetRandomNearPosition(pos, 10.0f);
+
+ //normalize Z-level if we can, if rift is not at ground level.
+ pos.m_positionZ = std::max(me->GetMap()->GetHeight(pos.m_positionX, pos.m_positionY, MAX_HEIGHT), me->GetMap()->GetWaterLevel(pos.m_positionX, pos.m_positionY));
+
+ if (Unit *Summon = DoSummon(creature_entry, pos, 30000, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT))
+ if (Unit *temp = Unit::GetUnit(*me, pInstance ? pInstance->GetData64(DATA_MEDIVH) : 0))
+ Summon->AddThreat(temp,0.0f);
+ }
+
+ void DoSelectSummon()
+ {
+ uint32 entry = 0;
+
+ if ((mRiftWaveCount > 2 && mWaveId < 1) || mRiftWaveCount > 3)
+ mRiftWaveCount = 0;
+
+ entry = PortalWaves[mWaveId].PortalMob[mRiftWaveCount];
+ debug_log("TSCR: npc_time_rift: summoning wave Creature (Wave %u, Entry %u).",mRiftWaveCount,entry);
+
+ ++mRiftWaveCount;
+
+ if (entry == C_WHELP)
+ {
+ for (uint8 i = 0; i < 3; ++i)
+ DoSummonAtRift(entry);
+ } else DoSummonAtRift(entry);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!pInstance)
+ return;
+
+ if (TimeRiftWave_Timer <= diff)
+ {
+ DoSelectSummon();
+ TimeRiftWave_Timer = 15000;
+ } else TimeRiftWave_Timer -= diff;
+
+ if (me->IsNonMeleeSpellCasted(false))
+ return;
+
+ debug_log("TSCR: npc_time_rift: not casting anylonger, i need to die.");
+ me->setDeathState(JUST_DIED);
+
+ if (pInstance->GetData(TYPE_RIFT) == IN_PROGRESS)
+ pInstance->SetData(TYPE_RIFT,SPECIAL);
+ }
+};
+
+CreatureAI* GetAI_npc_time_rift(Creature* pCreature)
+{
+ return new npc_time_riftAI (pCreature);
+}
+
+#define SAY_SAAT_WELCOME -1269019
+
+#define GOSSIP_ITEM_OBTAIN "[PH] Obtain Chrono-Beacon"
+#define SPELL_CHRONO_BEACON 34975
+#define ITEM_CHRONO_BEACON 24289
+
+bool GossipHello_npc_saat(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(QUEST_OPENING_PORTAL) == QUEST_STATUS_INCOMPLETE && !pPlayer->HasItemCount(ITEM_CHRONO_BEACON,1))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT,GOSSIP_ITEM_OBTAIN,GOSSIP_SENDER_MAIN,GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(10000, pCreature->GetGUID());
+ return true;
+ }
+ else if (pPlayer->GetQuestRewardStatus(QUEST_OPENING_PORTAL) && !pPlayer->HasItemCount(ITEM_CHRONO_BEACON,1))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT,GOSSIP_ITEM_OBTAIN,GOSSIP_SENDER_MAIN,GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(10001, pCreature->GetGUID());
+ return true;
+ }
+
+ pPlayer->SEND_GOSSIP_MENU(10002, pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_saat(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pCreature->CastSpell(pPlayer,SPELL_CHRONO_BEACON,false);
+ }
+ return true;
+}
+
+void AddSC_dark_portal()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_medivh_bm";
+ newscript->GetAI = &GetAI_npc_medivh_bm;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_time_rift";
+ newscript->GetAI = &GetAI_npc_time_rift;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_saat";
+ newscript->pGossipHello = &GossipHello_npc_saat;
+ newscript->pGossipSelect = &GossipSelect_npc_saat;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.h b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.h
new file mode 100644
index 00000000000..7bfd8c917d7
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/dark_portal.h
@@ -0,0 +1,35 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+* This program is free software licensed under GPL version 2
+* Please see the included DOCS/LICENSE.TXT for more information */
+
+#ifndef DEF_DARKPORTAL_H
+#define DEF_DARKPORTAL_H
+
+#define TYPE_MEDIVH 1
+#define TYPE_RIFT 2
+
+#define DATA_MEDIVH 10
+#define DATA_PORTAL_COUNT 11
+#define DATA_SHIELD 12
+
+#define WORLD_STATE_BM 2541
+#define WORLD_STATE_BM_SHIELD 2540
+#define WORLD_STATE_BM_RIFT 2784
+
+#define QUEST_OPENING_PORTAL 10297
+#define QUEST_MASTER_TOUCH 9836
+
+#define C_TIME_KEEPER 17918
+#define C_RKEEP 21104
+#define C_RLORD 17839
+#define C_DEJA 17879
+#define C_TEMPO 17880
+#define C_AEONUS 17881
+#define C_ASSAS 17835
+#define C_WHELP 21818
+#define C_CHRON 17892
+#define C_EXECU 18994
+#define C_VANQU 18995
+
+#endif
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp
new file mode 100644
index 00000000000..d1280230808
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/dark_portal/instance_dark_portal.cpp
@@ -0,0 +1,346 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+/* ScriptData
+SDName: Instance_Dark_Portal
+SD%Complete: 50
+SDComment: Quest support: 9836, 10297. Currently in progress.
+SDCategory: Caverns of Time, The Dark Portal
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "dark_portal.h"
+
+#define MAX_ENCOUNTER 2
+
+#define C_MEDIVH 15608
+#define C_TIME_RIFT 17838
+
+#define SPELL_RIFT_CHANNEL 31387
+
+#define RIFT_BOSS 1
+
+inline uint32 RandRiftBoss() { return ((rand()%2) ? C_RKEEP : C_RLORD); }
+
+float PortalLocation[4][4]=
+{
+ {-2041.06, 7042.08, 29.99, 1.30},
+ {-1968.18, 7042.11, 21.93, 2.12},
+ {-1885.82, 7107.36, 22.32, 3.07},
+ {-1928.11, 7175.95, 22.11, 3.44}
+};
+
+struct Wave
+{
+ uint32 PortalBoss; //protector of current portal
+ uint32 NextPortalTime; //time to next portal, or 0 if portal boss need to be killed
+};
+
+static Wave RiftWaves[]=
+{
+ {RIFT_BOSS, 0},
+ {C_DEJA, 0},
+ {RIFT_BOSS, 120000},
+ {C_TEMPO, 140000},
+ {RIFT_BOSS, 120000},
+ {C_AEONUS, 0}
+};
+
+struct instance_dark_portal : public ScriptedInstance
+{
+ instance_dark_portal(Map* pMap) : ScriptedInstance(pMap) {Initialize();};
+
+ uint32 m_auiEncounter[MAX_ENCOUNTER];
+
+ uint32 mRiftPortalCount;
+ uint32 mShieldPercent;
+ uint8 mRiftWaveCount;
+ uint8 mRiftWaveId;
+
+ uint32 NextPortal_Timer;
+
+ uint64 MedivhGUID;
+ uint8 CurrentRiftId;
+
+ void Initialize()
+ {
+ MedivhGUID = 0;
+ Clear();
+ }
+
+ void Clear()
+ {
+ memset(&m_auiEncounter, 0, sizeof(m_auiEncounter));
+
+ mRiftPortalCount = 0;
+ mShieldPercent = 100;
+ mRiftWaveCount = 0;
+ mRiftWaveId = 0;
+
+ CurrentRiftId = 0;
+
+ NextPortal_Timer = 0;
+ }
+
+ void InitWorldState(bool Enable = true)
+ {
+ DoUpdateWorldState(WORLD_STATE_BM,Enable ? 1 : 0);
+ DoUpdateWorldState(WORLD_STATE_BM_SHIELD, 100);
+ DoUpdateWorldState(WORLD_STATE_BM_RIFT, 0);
+ }
+
+ bool IsEncounterInProgress()
+ {
+ if (GetData(TYPE_MEDIVH) == IN_PROGRESS)
+ return true;
+
+ return false;
+ }
+
+ void OnPlayerEnter(Player* pPlayer)
+ {
+ if (GetData(TYPE_MEDIVH) == IN_PROGRESS)
+ return;
+
+ pPlayer->SendUpdateWorldState(WORLD_STATE_BM,0);
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool /*add*/)
+ {
+ if (pCreature->GetEntry() == C_MEDIVH)
+ MedivhGUID = pCreature->GetGUID();
+ }
+
+ //what other conditions to check?
+ bool CanProgressEvent()
+ {
+ if (instance->GetPlayers().isEmpty())
+ return false;
+
+ return true;
+ }
+
+ uint8 GetRiftWaveId()
+ {
+ switch(mRiftPortalCount)
+ {
+ case 6:
+ mRiftWaveId = 2;
+ return 1;
+ case 12:
+ mRiftWaveId = 4;
+ return 3;
+ case 18:
+ return 5;
+ default:
+ return mRiftWaveId;
+ }
+ }
+
+ void SetData(uint32 type, uint32 data)
+ {
+ switch(type)
+ {
+ case TYPE_MEDIVH:
+ if (data == SPECIAL && m_auiEncounter[0] == IN_PROGRESS)
+ {
+ --mShieldPercent;
+
+ DoUpdateWorldState(WORLD_STATE_BM_SHIELD, mShieldPercent);
+
+ if (!mShieldPercent)
+ {
+ if (Creature* pMedivh = instance->GetCreature(MedivhGUID))
+ {
+ if (pMedivh->isAlive())
+ {
+ pMedivh->DealDamage(pMedivh, pMedivh->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false);
+ m_auiEncounter[0] = FAIL;
+ m_auiEncounter[1] = NOT_STARTED;
+ }
+ }
+ }
+ }
+ else
+ {
+ if (data == IN_PROGRESS)
+ {
+ debug_log("TSCR: Instance Dark Portal: Starting event.");
+ InitWorldState();
+ m_auiEncounter[1] = IN_PROGRESS;
+ NextPortal_Timer = 15000;
+ }
+
+ if (data == DONE)
+ {
+ //this may be completed further out in the post-event
+ debug_log("TSCR: Instance Dark Portal: Event completed.");
+ Map::PlayerList const& players = instance->GetPlayers();
+
+ if (!players.isEmpty())
+ {
+ for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr)
+ {
+ if (Player* pPlayer = itr->getSource())
+ {
+ if (pPlayer->GetQuestStatus(QUEST_OPENING_PORTAL) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->AreaExploredOrEventHappens(QUEST_OPENING_PORTAL);
+
+ if (pPlayer->GetQuestStatus(QUEST_MASTER_TOUCH) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->AreaExploredOrEventHappens(QUEST_MASTER_TOUCH);
+ }
+ }
+ }
+ }
+
+ m_auiEncounter[0] = data;
+ }
+ break;
+ case TYPE_RIFT:
+ if (data == SPECIAL)
+ {
+ if (mRiftPortalCount < 7)
+ NextPortal_Timer = 5000;
+ }
+ else
+ m_auiEncounter[1] = data;
+ break;
+ }
+ }
+
+ uint32 GetData(uint32 type)
+ {
+ switch(type)
+ {
+ case TYPE_MEDIVH:
+ return m_auiEncounter[0];
+ case TYPE_RIFT:
+ return m_auiEncounter[1];
+ case DATA_PORTAL_COUNT:
+ return mRiftPortalCount;
+ case DATA_SHIELD:
+ return mShieldPercent;
+ }
+ return 0;
+ }
+
+ uint64 GetData64(uint32 data)
+ {
+ if (data == DATA_MEDIVH)
+ return MedivhGUID;
+
+ return 0;
+ }
+
+ Creature* SummonedPortalBoss(Creature* me)
+ {
+ uint32 entry = RiftWaves[GetRiftWaveId()].PortalBoss;
+
+ if (entry == RIFT_BOSS)
+ entry = RandRiftBoss();
+
+ debug_log("TSCR: Instance Dark Portal: Summoning rift boss entry %u.",entry);
+
+ Position pos;
+ me->GetRandomNearPosition(pos, 10.0f);
+
+ //normalize Z-level if we can, if rift is not at ground level.
+ pos.m_positionZ = std::max(me->GetMap()->GetHeight(pos.m_positionX, pos.m_positionY, MAX_HEIGHT), me->GetMap()->GetWaterLevel(pos.m_positionX, pos.m_positionY));
+
+ if (Creature *summon = me->SummonCreature(entry, pos, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 600000))
+ return summon;
+
+ debug_log("TSCR: Instance Dark Portal: What just happened there? No boss, no loot, no fun...");
+ return NULL;
+ }
+
+ void DoSpawnPortal()
+ {
+ if (Creature* pMedivh = instance->GetCreature(MedivhGUID))
+ {
+ uint8 tmp = urand(0,2);
+
+ if (tmp >= CurrentRiftId)
+ ++tmp;
+
+ debug_log("TSCR: Instance Dark Portal: Creating Time Rift at locationId %i (old locationId was %u).",tmp,CurrentRiftId);
+
+ CurrentRiftId = tmp;
+
+ Creature *pTemp = pMedivh->SummonCreature(C_TIME_RIFT,
+ PortalLocation[tmp][0],PortalLocation[tmp][1],PortalLocation[tmp][2],PortalLocation[tmp][3],
+ TEMPSUMMON_CORPSE_DESPAWN,0);
+ if (pTemp)
+ {
+ pTemp->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ pTemp->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+
+ if (Creature *pBoss = SummonedPortalBoss(pTemp))
+ {
+ if (pBoss->GetEntry() == C_AEONUS)
+ pBoss->AddThreat(pMedivh,0.0f);
+ else
+ {
+ pBoss->AddThreat(pTemp,0.0f);
+ pTemp->CastSpell(pBoss,SPELL_RIFT_CHANNEL,false);
+ }
+ }
+ }
+ }
+ }
+
+ void Update(uint32 diff)
+ {
+ if (m_auiEncounter[1] != IN_PROGRESS)
+ return;
+
+ //add delay timer?
+ if (!CanProgressEvent())
+ {
+ Clear();
+ return;
+ }
+
+ if (NextPortal_Timer)
+ {
+ if (NextPortal_Timer <= diff)
+ {
+ ++mRiftPortalCount;
+
+ DoUpdateWorldState(WORLD_STATE_BM_RIFT, mRiftPortalCount);
+
+ DoSpawnPortal();
+ NextPortal_Timer = RiftWaves[GetRiftWaveId()].NextPortalTime;
+ } else NextPortal_Timer -= diff;
+ }
+ }
+};
+
+InstanceData* GetInstanceData_instance_dark_portal(Map* pMap)
+{
+ return new instance_dark_portal(pMap);
+}
+
+void AddSC_instance_dark_portal()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "instance_dark_portal";
+ newscript->GetInstanceData = &GetInstanceData_instance_dark_portal;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_anetheron.cpp b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_anetheron.cpp
new file mode 100644
index 00000000000..14ce4a59b37
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_anetheron.cpp
@@ -0,0 +1,309 @@
+
+#include "ScriptedPch.h"
+#include "hyjal.h"
+#include "hyjal_trash.h"
+
+#define SPELL_CARRION_SWARM 31306
+#define SPELL_SLEEP 31298
+#define SPELL_VAMPIRIC_AURA 38196
+#define SPELL_INFERNO 31299
+
+#define SAY_ONDEATH "The clock... is still... ticking."
+#define SOUND_ONDEATH 10982
+
+#define SAY_ONSLAY1 "Your hopes are lost!"
+#define SAY_ONSLAY2 "Scream for me!"
+#define SAY_ONSLAY3 "Pity, no time for a slow death!"
+#define SOUND_ONSLAY1 10981
+#define SOUND_ONSLAY2 11038
+#define SOUND_ONSLAY3 11039
+
+#define SAY_SWARM1 "The swarm is eager to feed!"
+#define SAY_SWARM2 "Pestilence upon you!"
+#define SOUND_SWARM1 10979
+#define SOUND_SWARM2 11037
+
+#define SAY_SLEEP1 "You look tired..."
+#define SAY_SLEEP2 "Sweet dreams..."
+#define SOUND_SLEEP1 10978
+#define SOUND_SLEEP2 11545
+
+#define SAY_INFERNO1 "Let fire rain from above!"
+#define SAY_INFERNO2 "Earth and sky shall burn!"
+#define SOUND_INFERNO1 10980
+#define SOUND_INFERNO2 11036
+
+#define SAY_ONAGGRO "You are defenders of a doomed world! Flee here, and perhaps you will prolong your pathetic lives!"
+#define SOUND_ONAGGRO 10977
+
+struct boss_anetheronAI : public hyjal_trashAI
+{
+ boss_anetheronAI(Creature *c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ SpellEntry *TempSpell = GET_SPELL(SPELL_SLEEP);
+ if (TempSpell && TempSpell->EffectImplicitTargetA[0] != 1)
+ {
+ TempSpell->EffectImplicitTargetA[0] = 1;
+ TempSpell->EffectImplicitTargetB[0] = 0;
+ }
+ }
+
+ uint32 SwarmTimer;
+ uint32 SleepTimer;
+ uint32 AuraTimer;
+ uint32 InfernoTimer;
+ bool pGo;
+ uint32 pos;
+
+ void Reset()
+ {
+ damageTaken = 0;
+ SwarmTimer = 45000;
+ SleepTimer = 60000;
+ AuraTimer = 5000;
+ InfernoTimer = 45000;
+
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_ANETHERONEVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_ANETHERONEVENT, IN_PROGRESS);
+ DoPlaySoundToSet(me, SOUND_ONAGGRO);
+ me->MonsterYell(SAY_ONAGGRO, LANG_UNIVERSAL, 0);
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ switch (urand(0,2))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_ONSLAY1);
+ me->MonsterYell(SAY_ONSLAY1, LANG_UNIVERSAL, 0);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_ONSLAY2);
+ me->MonsterYell(SAY_ONSLAY2, LANG_UNIVERSAL, 0);
+ break;
+ case 2:
+ DoPlaySoundToSet(me, SOUND_ONSLAY3);
+ me->MonsterYell(SAY_ONSLAY3, LANG_UNIVERSAL, 0);
+ break;
+ }
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance)
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_JAINAPROUDMOORE));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+
+ void JustDied(Unit *victim)
+ {
+ hyjal_trashAI::JustDied(victim);
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_ANETHERONEVENT, DONE);
+ DoPlaySoundToSet(me, SOUND_ONDEATH);
+ me->MonsterYell(SAY_ONDEATH, LANG_UNIVERSAL, 0);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (IsEvent)
+ {
+ //Must update npc_escortAI
+ npc_escortAI::UpdateAI(diff);
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ AddWaypoint(0, 4896.08, -1576.35, 1333.65);
+ AddWaypoint(1, 4898.68, -1615.02, 1329.48);
+ AddWaypoint(2, 4907.12, -1667.08, 1321.00);
+ AddWaypoint(3, 4963.18, -1699.35, 1340.51);
+ AddWaypoint(4, 4989.16, -1716.67, 1335.74);
+ AddWaypoint(5, 5026.27, -1736.89, 1323.02);
+ AddWaypoint(6, 5037.77, -1770.56, 1324.36);
+ AddWaypoint(7, 5067.23, -1789.95, 1321.17);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (SwarmTimer <= diff)
+ {
+ if (Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ DoCast(pTarget, SPELL_CARRION_SWARM);
+
+ SwarmTimer = urand(45000,60000);
+ switch (urand(0,1))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_SWARM1);
+ me->MonsterYell(SAY_SWARM1, LANG_UNIVERSAL, 0);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_SWARM2);
+ me->MonsterYell(SAY_SWARM2, LANG_UNIVERSAL, 0);
+ break;
+ }
+ } else SwarmTimer -= diff;
+
+ if (SleepTimer <= diff)
+ {
+ for (uint8 i = 0; i < 3; ++i)
+ {
+ if (Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ pTarget->CastSpell(pTarget,SPELL_SLEEP,true);
+ }
+ SleepTimer = 60000;
+ switch (urand(0,1))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_SLEEP1);
+ me->MonsterYell(SAY_SLEEP1, LANG_UNIVERSAL, 0);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_SLEEP2);
+ me->MonsterYell(SAY_SLEEP2, LANG_UNIVERSAL, 0);
+ break;
+ }
+ } else SleepTimer -= diff;
+ if (AuraTimer <= diff)
+ {
+ DoCast(me, SPELL_VAMPIRIC_AURA, true);
+ AuraTimer = urand(10000,20000);
+ } else AuraTimer -= diff;
+ if (InfernoTimer <= diff)
+ {
+ DoCast(SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true), SPELL_INFERNO);
+ InfernoTimer = 45000;
+ switch (urand(0,1))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_INFERNO1);
+ me->MonsterYell(SAY_INFERNO1, LANG_UNIVERSAL, 0);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_INFERNO2);
+ me->MonsterYell(SAY_INFERNO2, LANG_UNIVERSAL, 0);
+ break;
+ }
+ } else InfernoTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_anetheron(Creature* pCreature)
+{
+ return new boss_anetheronAI (pCreature);
+}
+
+#define SPELL_IMMOLATION 31303
+#define SPELL_INFERNO_EFFECT 31302
+
+struct mob_towering_infernalAI : public ScriptedAI
+{
+ mob_towering_infernalAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ if (pInstance)
+ AnetheronGUID = pInstance->GetData64(DATA_ANETHERON);
+ }
+
+ uint32 ImmolationTimer;
+ uint32 CheckTimer;
+ uint64 AnetheronGUID;
+ ScriptedInstance* pInstance;
+
+ void Reset()
+ {
+ DoCast(me, SPELL_INFERNO_EFFECT);
+ ImmolationTimer = 5000;
+ CheckTimer = 5000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ if (me->IsWithinDist(who, 50) && !me->isInCombat() && me->IsHostileTo(who))
+ AttackStart(who);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (CheckTimer <= diff)
+ {
+ if (AnetheronGUID)
+ {
+ Creature* boss = Unit::GetCreature((*me),AnetheronGUID);
+ if (!boss || (boss && boss->isDead()))
+ {
+ me->setDeathState(JUST_DIED);
+ me->RemoveCorpse();
+ return;
+ }
+ }
+ CheckTimer = 5000;
+ } else CheckTimer -= diff;
+
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (ImmolationTimer <= diff)
+ {
+ DoCast(me, SPELL_IMMOLATION);
+ ImmolationTimer = 5000;
+ } else ImmolationTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_mob_towering_infernal(Creature* pCreature)
+{
+ return new mob_towering_infernalAI (pCreature);
+}
+
+void AddSC_boss_anetheron()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_anetheron";
+ newscript->GetAI = &GetAI_boss_anetheron;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_towering_infernal";
+ newscript->GetAI = &GetAI_mob_towering_infernal;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp
new file mode 100644
index 00000000000..8e1fa378e07
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_archimonde.cpp
@@ -0,0 +1,635 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Archimonde
+SD%Complete: 85
+SDComment: Doomfires not completely offlike due to core limitations for random moving. Tyrande and second phase not fully implemented.
+SDCategory: Caverns of Time, Mount Hyjal
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "hyjal.h"
+#include "SpellAuras.h"
+#include "hyjal_trash.h"
+
+//text id -1534018 are the text used when previous events complete. Not part of this script.
+#define SAY_AGGRO -1534019
+#define SAY_DOOMFIRE1 -1534020
+#define SAY_DOOMFIRE2 -1534021
+#define SAY_AIR_BURST1 -1534022
+#define SAY_AIR_BURST2 -1534023
+#define SAY_SLAY1 -1534024
+#define SAY_SLAY2 -1534025
+#define SAY_SLAY3 -1534026
+#define SAY_ENRAGE -1534027
+#define SAY_DEATH -1534028
+#define SAY_SOUL_CHARGE1 -1534029
+#define SAY_SOUL_CHARGE2 -1534030
+
+#define SPELL_DENOUEMENT_WISP 32124
+#define SPELL_ANCIENT_SPARK 39349
+#define SPELL_PROTECTION_OF_ELUNE 38528
+
+#define SPELL_DRAIN_WORLD_TREE 39140
+#define SPELL_DRAIN_WORLD_TREE_2 39141
+
+#define SPELL_FINGER_OF_DEATH 31984
+#define SPELL_HAND_OF_DEATH 35354
+#define SPELL_AIR_BURST 32014
+#define SPELL_GRIP_OF_THE_LEGION 31972
+#define SPELL_DOOMFIRE_STRIKE 31903 //summons two creatures
+#define SPELL_DOOMFIRE_SPAWN 32074
+#define SPELL_DOOMFIRE 31945
+#define SPELL_SOUL_CHARGE_YELLOW 32045
+#define SPELL_SOUL_CHARGE_GREEN 32051
+#define SPELL_SOUL_CHARGE_RED 32052
+#define SPELL_UNLEASH_SOUL_YELLOW 32054
+#define SPELL_UNLEASH_SOUL_GREEN 32057
+#define SPELL_UNLEASH_SOUL_RED 32053
+#define SPELL_FEAR 31970
+
+#define CREATURE_ARCHIMONDE 17968
+#define CREATURE_DOOMFIRE 18095
+#define CREATURE_DOOMFIRE_SPIRIT 18104
+#define CREATURE_ANCIENT_WISP 17946
+#define CREATURE_CHANNEL_TARGET 22418
+
+#define NORDRASSIL_X 5503.713
+#define NORDRASSIL_Y -3523.436
+#define NORDRASSIL_Z 1608.781
+
+struct mob_ancient_wispAI : public ScriptedAI
+{
+ mob_ancient_wispAI(Creature* c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ ArchimondeGUID = 0;
+ }
+
+ ScriptedInstance* pInstance;
+ uint64 ArchimondeGUID;
+ uint32 CheckTimer;
+
+ void Reset()
+ {
+ CheckTimer = 1000;
+
+ if (pInstance)
+ ArchimondeGUID = pInstance->GetData64(DATA_ARCHIMONDE);
+
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void DamageTaken(Unit* /*done_by*/, uint32 &damage) { damage = 0; }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (CheckTimer <= diff)
+ {
+ if (Unit* Archimonde = Unit::GetUnit((*me), ArchimondeGUID))
+ {
+ if ((((Archimonde->GetHealth()*100) / Archimonde->GetMaxHealth()) < 2) || !Archimonde->isAlive())
+ DoCast(me, SPELL_DENOUEMENT_WISP);
+ else
+ DoCast(Archimonde, SPELL_ANCIENT_SPARK);
+ }
+ CheckTimer = 1000;
+ } else CheckTimer -= diff;
+ }
+};
+
+/* This script is merely a placeholder for the Doomfire that triggers Doomfire spell. It will
+ MoveChase the Doomfire Spirit always, until despawn (AttackStart is called upon it's spawn) */
+struct mob_doomfireAI : public ScriptedAI
+{
+ mob_doomfireAI(Creature* c) : ScriptedAI(c) {}
+
+ void Reset() { }
+
+ void MoveInLineOfSight(Unit* /*who*/) {}
+ void EnterCombat(Unit* /*who*/) {}
+ void DamageTaken(Unit * /*done_by*/, uint32 &damage) { damage = 0; }
+};
+
+/* This is the script for the Doomfire Spirit Mob. This mob simply follow players or
+ travels in random directions if pTarget cannot be found. */
+struct mob_doomfire_targettingAI : public ScriptedAI
+{
+ mob_doomfire_targettingAI(Creature* c) : ScriptedAI(c) {}
+
+ uint64 TargetGUID;
+ uint32 ChangeTargetTimer;
+
+ void Reset()
+ {
+ TargetGUID = 0;
+ ChangeTargetTimer = 5000;
+ }
+
+ void MoveInLineOfSight(Unit* who)
+ {
+ //will update once TargetGUID is 0. In case noone actually moves(not likely) and this is 0
+ //when UpdateAI needs it, it will be forced to select randomPoint
+ if (!TargetGUID && who->GetTypeId() == TYPEID_PLAYER)
+ TargetGUID = who->GetGUID();
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void DamageTaken(Unit * /*done_by*/, uint32 &damage) { damage = 0; }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (ChangeTargetTimer <= diff)
+ {
+ if (Unit *temp = Unit::GetUnit(*me,TargetGUID))
+ {
+ me->GetMotionMaster()->MoveFollow(temp,0.0f,0.0f);
+ TargetGUID = 0;
+ }
+ else
+ {
+ Position pos;
+ me->GetRandomNearPosition(pos, 40);
+ me->GetMotionMaster()->MovePoint(0, pos.m_positionX, pos.m_positionY, pos.m_positionZ);
+ }
+
+ ChangeTargetTimer = 5000;
+ } else ChangeTargetTimer -= diff;
+ }
+};
+
+/* Finally, Archimonde's script. His script isn't extremely complex, most are simply spells on timers.
+ The only complicated aspect of the battle is Finger of Death and Doomfire, with Doomfire being the
+ hardest bit to code. Finger of Death is simply a distance check - if no one is in melee range, then
+ select a random pTarget and cast the spell on them. However, if someone IS in melee range, and this
+ is NOT the main tank (creature's victim), then we aggro that player and they become the new victim.
+ For Doomfire, we summon a mob (Doomfire Spirit) for the Doomfire mob to follow. It's spirit will
+ randomly select it's pTarget to follow and then we create the random movement making it unpredictable. */
+
+struct boss_archimondeAI : public hyjal_trashAI
+{
+ boss_archimondeAI(Creature *c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance* pInstance;
+
+ uint64 DoomfireSpiritGUID;
+ uint64 WorldTreeGUID;
+
+ uint32 DrainNordrassilTimer;
+ uint32 FearTimer;
+ uint32 AirBurstTimer;
+ uint32 GripOfTheLegionTimer;
+ uint32 DoomfireTimer;
+ uint32 SoulChargeTimer;
+ uint32 SoulChargeCount;
+ uint32 MeleeRangeCheckTimer;
+ uint32 HandOfDeathTimer;
+ uint32 SummonWispTimer;
+ uint32 WispCount;
+ uint32 EnrageTimer;
+ uint32 CheckDistanceTimer;
+
+ bool Enraged;
+ bool BelowTenPercent;
+ bool HasProtected;
+ bool IsChanneling;
+
+ void Reset()
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_ARCHIMONDEEVENT, NOT_STARTED);
+
+ DoomfireSpiritGUID = 0;
+ damageTaken = 0;
+ WorldTreeGUID = 0;
+
+ DrainNordrassilTimer = 0;
+ FearTimer = 42000;
+ AirBurstTimer = 30000;
+ GripOfTheLegionTimer = urand(5000,25000);
+ DoomfireTimer = 20000;
+ SoulChargeTimer = urand(2000,30000);
+ SoulChargeCount = 0;
+ MeleeRangeCheckTimer = 15000;
+ HandOfDeathTimer = 2000;
+ WispCount = 0; // When ~30 wisps are summoned, Archimonde dies
+ EnrageTimer = 600000; // 10 minutes
+ CheckDistanceTimer = 30000; // This checks if he's too close to the World Tree (75 yards from a point on the tree), if true then he will enrage
+ SummonWispTimer = 0;
+
+ Enraged = false;
+ BelowTenPercent = false;
+ HasProtected = false;
+ IsChanneling = false;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ me->InterruptSpell(CURRENT_CHANNELED_SPELL);
+ DoScriptText(SAY_AGGRO, me);
+ DoZoneInCombat();
+
+ if (pInstance)
+ pInstance->SetData(DATA_ARCHIMONDEEVENT, IN_PROGRESS);
+ }
+
+ void KilledUnit(Unit * victim)
+ {
+ DoScriptText(RAND(SAY_SLAY1,SAY_SLAY2,SAY_SLAY3), me);
+
+ if (victim && (victim->GetTypeId() == TYPEID_PLAYER))
+ GainSoulCharge(CAST_PLR(victim));
+ }
+
+ void GainSoulCharge(Player* victim)
+ {
+ switch(victim->getClass())
+ {
+ case CLASS_PRIEST:
+ case CLASS_PALADIN:
+ case CLASS_WARLOCK:
+ victim->CastSpell(me, SPELL_SOUL_CHARGE_RED, true);
+ break;
+ case CLASS_MAGE:
+ case CLASS_ROGUE:
+ case CLASS_WARRIOR:
+ victim->CastSpell(me, SPELL_SOUL_CHARGE_YELLOW, true);
+ break;
+ case CLASS_DRUID:
+ case CLASS_SHAMAN:
+ case CLASS_HUNTER:
+ victim->CastSpell(me, SPELL_SOUL_CHARGE_GREEN, true);
+ break;
+ }
+
+ SoulChargeTimer = urand(2000,30000);
+ ++SoulChargeCount;
+ }
+
+ void JustDied(Unit *victim)
+ {
+ hyjal_trashAI::JustDied(victim);
+ DoScriptText(SAY_DEATH, me);
+
+ if (pInstance)
+ pInstance->SetData(DATA_ARCHIMONDEEVENT, DONE);
+ }
+
+ bool CanUseFingerOfDeath()
+ {
+ // First we check if our current victim is in melee range or not.
+ Unit* victim = me->getVictim();
+ if (victim && me->IsWithinDistInMap(victim, me->GetAttackDistance(victim)))
+ return false;
+
+ std::list<HostileReference*>& m_threatlist = me->getThreatManager().getThreatList();
+ if (m_threatlist.empty())
+ return false;
+
+ std::list<Unit*> targets;
+ std::list<HostileReference*>::const_iterator itr = m_threatlist.begin();
+ for (; itr != m_threatlist.end(); ++itr)
+ {
+ Unit* pUnit = Unit::GetUnit((*me), (*itr)->getUnitGuid());
+ if (pUnit && pUnit->isAlive())
+ targets.push_back(pUnit);
+ }
+
+ if (targets.empty())
+ return false;
+
+ targets.sort(Trinity::ObjectDistanceOrderPred(me));
+ Unit *pTarget = targets.front();
+ if (pTarget)
+ {
+ if (!me->IsWithinDistInMap(pTarget, me->GetAttackDistance(pTarget)))
+ return true; // Cast Finger of Death
+ else // This target is closest, he is our new tank
+ me->AddThreat(pTarget, me->getThreatManager().getThreat(me->getVictim()));
+ }
+
+ return false;
+ }
+
+ void JustSummoned(Creature *summoned)
+ {
+ if (summoned->GetEntry() == CREATURE_ANCIENT_WISP)
+ summoned->AI()->AttackStart(me);
+ else
+ {
+ summoned->setFaction(me->getFaction());
+ summoned->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ summoned->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ }
+
+ if (summoned->GetEntry() == CREATURE_DOOMFIRE_SPIRIT)
+ {
+ DoomfireSpiritGUID = summoned->GetGUID();
+ }
+
+ if (summoned->GetEntry() == CREATURE_DOOMFIRE)
+ {
+ summoned->CastSpell(summoned,SPELL_DOOMFIRE_SPAWN,false);
+ summoned->CastSpell(summoned,SPELL_DOOMFIRE,true,0,0,me->GetGUID());
+
+ if (Unit *DoomfireSpirit = Unit::GetUnit(*me, DoomfireSpiritGUID))
+ {
+ summoned->GetMotionMaster()->MoveFollow(DoomfireSpirit,0.0f,0.0f);
+ DoomfireSpiritGUID = 0;
+ }
+ }
+ }
+
+ //this is code doing close to what the summoning spell would do (spell 31903)
+ void SummonDoomfire(Unit *pTarget)
+ {
+ me->SummonCreature(CREATURE_DOOMFIRE_SPIRIT,
+ pTarget->GetPositionX()+15.0,pTarget->GetPositionY()+15.0,pTarget->GetPositionZ(),0,
+ TEMPSUMMON_TIMED_DESPAWN, 27000);
+
+ me->SummonCreature(CREATURE_DOOMFIRE,
+ pTarget->GetPositionX()-15.0,pTarget->GetPositionY()-15.0,pTarget->GetPositionZ(),0,
+ TEMPSUMMON_TIMED_DESPAWN, 27000);
+ }
+
+ void UnleashSoulCharge()
+ {
+ me->InterruptNonMeleeSpells(false);
+
+ bool HasCast = false;
+ uint32 chargeSpell = 0;
+ uint32 unleashSpell = 0;
+
+ switch (urand(0,2))
+ {
+ case 0:
+ chargeSpell = SPELL_SOUL_CHARGE_RED;
+ unleashSpell = SPELL_UNLEASH_SOUL_RED;
+ break;
+ case 1:
+ chargeSpell = SPELL_SOUL_CHARGE_YELLOW;
+ unleashSpell = SPELL_UNLEASH_SOUL_YELLOW;
+ break;
+ case 2:
+ chargeSpell = SPELL_SOUL_CHARGE_GREEN;
+ unleashSpell = SPELL_UNLEASH_SOUL_GREEN;
+ break;
+ }
+
+ if (me->HasAura(chargeSpell))
+ {
+ me->RemoveAuraFromStack(chargeSpell);
+ DoCast(me->getVictim(), unleashSpell);
+ HasCast = true;
+ SoulChargeCount--;
+ }
+
+ if (HasCast)
+ SoulChargeTimer = urand(2000,30000);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!me->isInCombat())
+ {
+ if (pInstance)
+ {
+ // Do not let the raid skip straight to Archimonde. Visible and hostile ONLY if Azagalor is finished.
+ if ((pInstance->GetData(DATA_AZGALOREVENT) < DONE) && ((me->GetVisibility() != VISIBILITY_OFF) || (me->getFaction() != 35)))
+ {
+ me->SetVisibility(VISIBILITY_OFF);
+ me->setFaction(35);
+ }
+ else if ((pInstance->GetData(DATA_AZGALOREVENT) >= DONE) && ((me->GetVisibility() != VISIBILITY_ON) || (me->getFaction() == 35)))
+ {
+ me->setFaction(1720);
+ me->SetVisibility(VISIBILITY_ON);
+ }
+ }
+
+ if (DrainNordrassilTimer <= diff)
+ {
+ if (!IsChanneling)
+ {
+ Creature *temp = me->SummonCreature(CREATURE_CHANNEL_TARGET, NORDRASSIL_X, NORDRASSIL_Y, NORDRASSIL_Z, 0, TEMPSUMMON_TIMED_DESPAWN, 1200000);
+
+ if (temp)
+ WorldTreeGUID = temp->GetGUID();
+
+ if (Unit *Nordrassil = Unit::GetUnit(*me, WorldTreeGUID))
+ {
+ Nordrassil->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ Nordrassil->SetDisplayId(11686);
+ DoCast(Nordrassil, SPELL_DRAIN_WORLD_TREE);
+ IsChanneling = true;
+ }
+ }
+
+ if (Unit *Nordrassil = Unit::GetUnit(*me, WorldTreeGUID))
+ {
+ Nordrassil->CastSpell(me, SPELL_DRAIN_WORLD_TREE_2, true);
+ DrainNordrassilTimer = 1000;
+ }
+ } else DrainNordrassilTimer -= diff;
+ }
+
+ if (!UpdateVictim())
+ return;
+
+ if (((me->GetHealth()*100 / me->GetMaxHealth()) < 10) && !BelowTenPercent && !Enraged)
+ BelowTenPercent = true;
+
+ if (!Enraged)
+ {
+ if (EnrageTimer <= diff)
+ {
+ if ((me->GetHealth()*100 / me->GetMaxHealth()) > 10)
+ {
+ me->GetMotionMaster()->Clear(false);
+ me->GetMotionMaster()->MoveIdle();
+ Enraged = true;
+ DoScriptText(SAY_ENRAGE, me);
+ }
+ } else EnrageTimer -= diff;
+
+ if (CheckDistanceTimer <= diff)
+ {
+ // To simplify the check, we simply summon a Creature in the location and then check how far we are from the creature
+ Creature* Check = me->SummonCreature(CREATURE_CHANNEL_TARGET, NORDRASSIL_X, NORDRASSIL_Y, NORDRASSIL_Z, 0, TEMPSUMMON_TIMED_DESPAWN, 2000);
+ if (Check)
+ {
+ Check->SetVisibility(VISIBILITY_OFF);
+
+ if (me->IsWithinDistInMap(Check, 75))
+ {
+ me->GetMotionMaster()->Clear(false);
+ me->GetMotionMaster()->MoveIdle();
+ Enraged = true;
+ DoScriptText(SAY_ENRAGE, me);
+ }
+ }
+ CheckDistanceTimer = 5000;
+ } else CheckDistanceTimer -= diff;
+ }
+
+ if (BelowTenPercent)
+ {
+ if (!HasProtected)
+ {
+ me->GetMotionMaster()->Clear(false);
+ me->GetMotionMaster()->MoveIdle();
+
+ //all members of raid must get this buff
+ DoCast(me->getVictim(), SPELL_PROTECTION_OF_ELUNE);
+ HasProtected = true;
+ Enraged = true;
+ }
+
+ if (SummonWispTimer <= diff)
+ {
+ DoSpawnCreature(CREATURE_ANCIENT_WISP, rand()%40, rand()%40, 0, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ SummonWispTimer = 1500;
+ ++WispCount;
+ } else SummonWispTimer -= diff;
+
+ if (WispCount >= 30)
+ me->DealDamage(me, me->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false);
+ }
+
+ if (Enraged)
+ {
+ if (HandOfDeathTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_HAND_OF_DEATH);
+ HandOfDeathTimer = 2000;
+ } else HandOfDeathTimer -= diff;
+ return; // Don't do anything after this point.
+ }
+
+ if (SoulChargeCount)
+ {
+ if (SoulChargeTimer <= diff)
+ UnleashSoulCharge();
+ else SoulChargeTimer -= diff;
+ }
+
+ if (GripOfTheLegionTimer <= diff)
+ {
+ DoCast(SelectUnit(SELECT_TARGET_RANDOM, 0), SPELL_GRIP_OF_THE_LEGION);
+ GripOfTheLegionTimer = urand(5000,25000);
+ } else GripOfTheLegionTimer -= diff;
+
+ if (AirBurstTimer <= diff)
+ {
+ if (urand(0,1))
+ DoScriptText(SAY_AIR_BURST1, me);
+ else
+ DoScriptText(SAY_AIR_BURST2, me);
+
+ DoCast(SelectUnit(SELECT_TARGET_RANDOM, 1), SPELL_AIR_BURST);//not on tank
+ AirBurstTimer = urand(25000,40000);
+ } else AirBurstTimer -= diff;
+
+ if (FearTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_FEAR);
+ FearTimer = 42000;
+ } else FearTimer -= diff;
+
+ if (DoomfireTimer <= diff)
+ {
+ if (urand(0,1))
+ DoScriptText(SAY_DOOMFIRE1, me);
+ else
+ DoScriptText(SAY_DOOMFIRE2, me);
+
+ Unit *temp = SelectUnit(SELECT_TARGET_RANDOM, 1);
+ if (!temp)
+ temp = me->getVictim();
+
+ //replace with spell cast 31903 once implicitTarget 73 implemented
+ SummonDoomfire(temp);
+
+ //supposedly three doomfire can be up at the same time
+ DoomfireTimer = 20000;
+ } else DoomfireTimer -= diff;
+
+ if (MeleeRangeCheckTimer <= diff)
+ {
+ if (CanUseFingerOfDeath())
+ {
+ DoCast(SelectUnit(SELECT_TARGET_RANDOM, 0), SPELL_FINGER_OF_DEATH);
+ MeleeRangeCheckTimer = 1000;
+ }
+
+ MeleeRangeCheckTimer = 5000;
+ } else MeleeRangeCheckTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+ void WaypointReached(uint32 /*i*/){}
+};
+
+CreatureAI* GetAI_boss_archimonde(Creature* pCreature)
+{
+ return new boss_archimondeAI (pCreature);
+}
+
+CreatureAI* GetAI_mob_doomfire(Creature* pCreature)
+{
+ return new mob_doomfireAI(pCreature);
+}
+
+CreatureAI* GetAI_mob_doomfire_targetting(Creature* pCreature)
+{
+ return new mob_doomfire_targettingAI(pCreature);
+}
+
+CreatureAI* GetAI_mob_ancient_wisp(Creature* pCreature)
+{
+ return new mob_ancient_wispAI(pCreature);
+}
+
+void AddSC_boss_archimonde()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_archimonde";
+ newscript->GetAI = &GetAI_boss_archimonde;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_doomfire";
+ newscript->GetAI = &GetAI_mob_doomfire;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_doomfire_targetting";
+ newscript->GetAI = &GetAI_mob_doomfire_targetting;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_ancient_wisp";
+ newscript->GetAI = &GetAI_mob_ancient_wisp;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_azgalor.cpp b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_azgalor.cpp
new file mode 100644
index 00000000000..69e37f7f740
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_azgalor.cpp
@@ -0,0 +1,285 @@
+
+#include "ScriptedPch.h"
+#include "hyjal.h"
+#include "hyjal_trash.h"
+
+#define SPELL_RAIN_OF_FIRE 31340
+#define SPELL_DOOM 31347
+#define SPELL_HOWL_OF_AZGALOR 31344
+#define SPELL_CLEAVE 31345
+#define SPELL_BERSERK 26662
+
+#define SAY_ONDEATH "Your time is almost... up"
+#define SOUND_ONDEATH 11002
+
+#define SAY_ONSLAY1 "Reesh, hokta!"
+#define SAY_ONSLAY2 "Don't fight it"
+#define SAY_ONSLAY3 "No one is going to save you"
+#define SOUND_ONSLAY1 11001
+#define SOUND_ONSLAY2 11048
+#define SOUND_ONSLAY3 11047
+
+#define SAY_DOOM1 "Just a taste... of what awaits you"
+#define SAY_DOOM2 "Suffer you despicable insect!"
+#define SOUND_DOOM1 11046
+#define SOUND_DOOM2 11000
+
+#define SAY_ONAGGRO "Abandon all hope! The legion has returned to finish what was begun so many years ago. This time there will be no escape!"
+#define SOUND_ONAGGRO 10999
+
+struct boss_azgalorAI : public hyjal_trashAI
+{
+ boss_azgalorAI(Creature *c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ SpellEntry *TempSpell = GET_SPELL(SPELL_HOWL_OF_AZGALOR);
+ if (TempSpell)
+ TempSpell->EffectRadiusIndex[0] = 12;//100yards instead of 50000?!
+ }
+
+ uint32 RainTimer;
+ uint32 DoomTimer;
+ uint32 HowlTimer;
+ uint32 CleaveTimer;
+ uint32 EnrageTimer;
+ bool enraged;
+
+ bool pGo;
+ uint32 pos;
+
+ void Reset()
+ {
+ damageTaken = 0;
+ RainTimer = 20000;
+ DoomTimer = 50000;
+ HowlTimer = 30000;
+ CleaveTimer = 10000;
+ EnrageTimer = 600000;
+ enraged = false;
+
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_AZGALOREVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_AZGALOREVENT, IN_PROGRESS);
+ DoPlaySoundToSet(me, SOUND_ONAGGRO);
+ me->MonsterYell(SAY_ONAGGRO, LANG_UNIVERSAL, NULL);
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ switch (urand(0,2))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_ONSLAY1);
+ me->MonsterYell(SAY_ONSLAY1, LANG_UNIVERSAL, NULL);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_ONSLAY2);
+ me->MonsterYell(SAY_ONSLAY2, LANG_UNIVERSAL, NULL);
+ break;
+ case 2:
+ DoPlaySoundToSet(me, SOUND_ONSLAY3);
+ me->MonsterYell(SAY_ONSLAY3, LANG_UNIVERSAL, NULL);
+ break;
+ }
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance)
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+
+ void JustDied(Unit *victim)
+ {
+ hyjal_trashAI::JustDied(victim);
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_AZGALOREVENT, DONE);
+ DoPlaySoundToSet(me, SOUND_ONDEATH);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (IsEvent)
+ {
+ //Must update npc_escortAI
+ npc_escortAI::UpdateAI(diff);
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ AddWaypoint(0, 5492.91, -2404.61, 1462.63);
+ AddWaypoint(1, 5531.76, -2460.87, 1469.55);
+ AddWaypoint(2, 5554.58, -2514.66, 1476.12);
+ AddWaypoint(3, 5554.16, -2567.23, 1479.90);
+ AddWaypoint(4, 5540.67, -2625.99, 1480.89);
+ AddWaypoint(5, 5508.16, -2659.2, 1480.15);
+ AddWaypoint(6, 5489.62, -2704.05, 1482.18);
+ AddWaypoint(7, 5457.04, -2726.26, 1485.10);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (RainTimer <= diff)
+ {
+ DoCast(SelectTarget(SELECT_TARGET_RANDOM,0,30,true), SPELL_RAIN_OF_FIRE);
+ RainTimer = 20000+rand()%15000;
+ } else RainTimer -= diff;
+
+ if (DoomTimer <= diff)
+ {
+ DoCast(SelectTarget(SELECT_TARGET_RANDOM,1,100,true), SPELL_DOOM);//never on tank
+ DoomTimer = 45000+rand()%5000;
+ } else DoomTimer -= diff;
+
+ if (HowlTimer <= diff)
+ {
+ DoCast(me, SPELL_HOWL_OF_AZGALOR);
+ HowlTimer = 30000;
+ } else HowlTimer -= diff;
+
+ if (CleaveTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_CLEAVE);
+ CleaveTimer = 10000+rand()%5000;
+ } else CleaveTimer -= diff;
+
+ if (EnrageTimer < diff && !enraged)
+ {
+ me->InterruptNonMeleeSpells(false);
+ DoCast(me, SPELL_BERSERK, true);
+ enraged = true;
+ EnrageTimer = 600000;
+ } else EnrageTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_azgalor(Creature* pCreature)
+{
+ return new boss_azgalorAI (pCreature);
+}
+
+#define SPELL_THRASH 12787
+#define SPELL_CRIPPLE 31406
+#define SPELL_WARSTOMP 31408
+
+struct mob_lesser_doomguardAI : public hyjal_trashAI
+{
+ mob_lesser_doomguardAI(Creature *c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ if (pInstance)
+ AzgalorGUID = pInstance->GetData64(DATA_AZGALOR);
+ }
+
+ uint32 CrippleTimer;
+ uint32 WarstompTimer;
+ uint32 CheckTimer;
+ uint64 AzgalorGUID;
+ ScriptedInstance* pInstance;
+
+ void Reset()
+ {
+ CrippleTimer = 50000;
+ WarstompTimer = 10000;
+ DoCast(me, SPELL_THRASH);
+ CheckTimer = 5000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ }
+
+ void WaypointReached(uint32 /*i*/)
+ {
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ if (me->IsWithinDist(who, 50) && !me->isInCombat() && me->IsHostileTo(who))
+ AttackStart(who);
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (CheckTimer <= diff)
+ {
+ if (AzgalorGUID)
+ {
+ Creature* boss = Unit::GetCreature((*me),AzgalorGUID);
+ if (!boss || (boss && boss->isDead()))
+ {
+ me->setDeathState(JUST_DIED);
+ me->RemoveCorpse();
+ return;
+ }
+ }
+ CheckTimer = 5000;
+ } else CheckTimer -= diff;
+
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (WarstompTimer <= diff)
+ {
+ DoCast(me, SPELL_WARSTOMP);
+ WarstompTimer = 10000+rand()%5000;
+ } else WarstompTimer -= diff;
+
+ if (CrippleTimer <= diff)
+ {
+ DoCast(SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true), SPELL_CRIPPLE);
+ CrippleTimer = 25000+rand()%5000;
+ } else CrippleTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_mob_lesser_doomguard(Creature* pCreature)
+{
+ return new mob_lesser_doomguardAI (pCreature);
+}
+
+void AddSC_boss_azgalor()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_azgalor";
+ newscript->GetAI = &GetAI_boss_azgalor;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_lesser_doomguard";
+ newscript->GetAI = &GetAI_mob_lesser_doomguard;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_kazrogal.cpp b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_kazrogal.cpp
new file mode 100644
index 00000000000..b52d22842e3
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_kazrogal.cpp
@@ -0,0 +1,197 @@
+
+#include "ScriptedPch.h"
+#include "hyjal.h"
+#include "hyjal_trash.h"
+
+#define SPELL_CLEAVE 31436
+#define SPELL_WARSTOMP 31480
+#define SPELL_MARK 31447
+
+#define SOUND_ONDEATH 11018
+
+#define SAY_ONSLAY1 "Shaza-Kiel!"
+#define SAY_ONSLAY2 "You... are nothing!"
+#define SAY_ONSLAY3 "Miserable nuisance!"
+#define SOUND_ONSLAY1 11017
+#define SOUND_ONSLAY2 11053
+#define SOUND_ONSLAY3 11054
+
+#define SAY_MARK1 "Your death will be a painful one."
+#define SAY_MARK2 "You... are marked."
+#define SOUND_MARK1 11016
+#define SOUND_MARK2 11052
+
+#define SAY_ONAGGRO "Cry for mercy! Your meaningless lives will soon be forfeit."
+#define SOUND_ONAGGRO 11015
+
+struct boss_kazrogalAI : public hyjal_trashAI
+{
+ boss_kazrogalAI(Creature *c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ SpellEntry *TempSpell = GET_SPELL(SPELL_MARK);
+ if (TempSpell && TempSpell->EffectImplicitTargetA[0] != 1)
+ {
+ TempSpell->EffectImplicitTargetA[0] = 1;
+ TempSpell->EffectImplicitTargetB[0] = 0;
+ }
+ }
+
+ uint32 CleaveTimer;
+ uint32 WarStompTimer;
+ uint32 MarkTimer;
+ uint32 MarkTimerBase;
+ bool pGo;
+ uint32 pos;
+
+ void Reset()
+ {
+ damageTaken = 0;
+ CleaveTimer = 5000;
+ WarStompTimer = 15000;
+ MarkTimer = 45000;
+ MarkTimerBase = 45000;
+
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_KAZROGALEVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_KAZROGALEVENT, IN_PROGRESS);
+ DoPlaySoundToSet(me, SOUND_ONAGGRO);
+ me->MonsterYell(SAY_ONAGGRO, LANG_UNIVERSAL, NULL);
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ switch (urand(0,2))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_ONSLAY1);
+ me->MonsterYell(SAY_ONSLAY1, LANG_UNIVERSAL, NULL);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_ONSLAY2);
+ me->MonsterYell(SAY_ONSLAY2, LANG_UNIVERSAL, NULL);
+ break;
+ case 2:
+ DoPlaySoundToSet(me, SOUND_ONSLAY3);
+ me->MonsterYell(SAY_ONSLAY3, LANG_UNIVERSAL, NULL);
+ break;
+ }
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance)
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+
+ void JustDied(Unit *victim)
+ {
+ hyjal_trashAI::JustDied(victim);
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_KAZROGALEVENT, DONE);
+ DoPlaySoundToSet(me, SOUND_ONDEATH);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (IsEvent)
+ {
+ //Must update npc_escortAI
+ npc_escortAI::UpdateAI(diff);
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ AddWaypoint(0, 5492.91, -2404.61, 1462.63);
+ AddWaypoint(1, 5531.76, -2460.87, 1469.55);
+ AddWaypoint(2, 5554.58, -2514.66, 1476.12);
+ AddWaypoint(3, 5554.16, -2567.23, 1479.90);
+ AddWaypoint(4, 5540.67, -2625.99, 1480.89);
+ AddWaypoint(5, 5508.16, -2659.2, 1480.15);
+ AddWaypoint(6, 5489.62, -2704.05, 1482.18);
+ AddWaypoint(7, 5457.04, -2726.26, 1485.10);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (CleaveTimer <= diff)
+ {
+ DoCast(me, SPELL_CLEAVE);
+ CleaveTimer = 6000+rand()%15000;
+ } else CleaveTimer -= diff;
+
+ if (WarStompTimer <= diff)
+ {
+ DoCast(me, SPELL_WARSTOMP);
+ WarStompTimer = 60000;
+ } else WarStompTimer -= diff;
+
+ if (me->HasAura(SPELL_MARK))
+ me->RemoveAurasDueToSpell(SPELL_MARK);
+ if (MarkTimer <= diff)
+ {
+ //cast dummy, useful for bos addons
+ me->CastCustomSpell(me, SPELL_MARK, NULL, NULL, NULL, false, NULL, NULL, me->GetGUID());
+
+ std::list<HostileReference *> t_list = me->getThreatManager().getThreatList();
+ for (std::list<HostileReference *>::const_iterator itr = t_list.begin(); itr!= t_list.end(); ++itr)
+ {
+ Unit *pTarget = Unit::GetUnit(*me, (*itr)->getUnitGuid());
+ if (pTarget && pTarget->GetTypeId() == TYPEID_PLAYER && pTarget->getPowerType() == POWER_MANA)
+ {
+ pTarget->CastSpell(pTarget, SPELL_MARK,true);//only cast on mana users
+ }
+ }
+ MarkTimerBase -= 5000;
+ if (MarkTimerBase < 5500)
+ MarkTimerBase = 5500;
+ MarkTimer = MarkTimerBase;
+ switch (urand(0,2))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_MARK1);
+ me->MonsterYell(SAY_MARK1, LANG_UNIVERSAL, NULL);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_MARK2);
+ me->MonsterYell(SAY_MARK2, LANG_UNIVERSAL, NULL);
+ break;
+ }
+ } else MarkTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_kazrogal(Creature* pCreature)
+{
+ return new boss_kazrogalAI (pCreature);
+}
+
+void AddSC_boss_kazrogal()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_kazrogal";
+ newscript->GetAI = &GetAI_boss_kazrogal;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_rage_winterchill.cpp b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_rage_winterchill.cpp
new file mode 100644
index 00000000000..7465b997117
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/boss_rage_winterchill.cpp
@@ -0,0 +1,192 @@
+
+#include "ScriptedPch.h"
+#include "hyjal.h"
+#include "hyjal_trash.h"
+
+#define SPELL_FROST_ARMOR 31256
+#define SPELL_DEATH_AND_DECAY 31258
+
+#define SPELL_FROST_NOVA 31250
+#define SPELL_ICEBOLT 31249
+
+#define SAY_ONDEATH "You have won this battle, but not... the... war"
+#define SOUND_ONDEATH 11026
+
+#define SAY_ONSLAY1 "All life must perish!"
+#define SAY_ONSLAY2 "Victory to the Legion!"
+#define SOUND_ONSLAY1 11025
+#define SOUND_ONSLAY2 11057
+
+#define SAY_DECAY1 "Crumble and rot!"
+#define SAY_DECAY2 "Ashes to ashes, dust to dust"
+#define SOUND_DECAY1 11023
+#define SOUND_DECAY2 11055
+
+#define SAY_NOVA1 "Succumb to the icy chill... of death!"
+#define SAY_NOVA2 "It will be much colder in your grave"
+#define SOUND_NOVA1 11024
+#define SOUND_NOVA2 11058
+
+#define SAY_ONAGGRO "The Legion's final conquest has begun! Once again the subjugation of this world is within our grasp. Let none survive!"
+#define SOUND_ONAGGRO 11022
+
+struct boss_rage_winterchillAI : public hyjal_trashAI
+{
+ boss_rage_winterchillAI(Creature *c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ }
+
+ uint32 FrostArmorTimer;
+ uint32 DecayTimer;
+ uint32 NovaTimer;
+ uint32 IceboltTimer;
+ bool pGo;
+ uint32 pos;
+
+ void Reset()
+ {
+ damageTaken = 0;
+ FrostArmorTimer = 37000;
+ DecayTimer = 45000;
+ NovaTimer = 15000;
+ IceboltTimer = 10000;
+
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_RAGEWINTERCHILLEVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_RAGEWINTERCHILLEVENT, IN_PROGRESS);
+ DoPlaySoundToSet(me, SOUND_ONAGGRO);
+ me->MonsterYell(SAY_ONAGGRO, LANG_UNIVERSAL, 0);
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ switch (urand(0,1))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_ONSLAY1);
+ me->MonsterYell(SAY_ONSLAY1, LANG_UNIVERSAL, NULL);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_ONSLAY2);
+ me->MonsterYell(SAY_ONSLAY2, LANG_UNIVERSAL, NULL);
+ break;
+ }
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance)
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_JAINAPROUDMOORE));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0f);
+ }
+ }
+
+ void JustDied(Unit *victim)
+ {
+ hyjal_trashAI::JustDied(victim);
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_RAGEWINTERCHILLEVENT, DONE);
+ DoPlaySoundToSet(me, SOUND_ONDEATH);
+ me->MonsterYell(SAY_ONDEATH, LANG_UNIVERSAL, NULL);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (IsEvent)
+ {
+ //Must update npc_escortAI
+ npc_escortAI::UpdateAI(diff);
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ AddWaypoint(0, 4896.08, -1576.35, 1333.65);
+ AddWaypoint(1, 4898.68, -1615.02, 1329.48);
+ AddWaypoint(2, 4907.12, -1667.08, 1321.00);
+ AddWaypoint(3, 4963.18, -1699.35, 1340.51);
+ AddWaypoint(4, 4989.16, -1716.67, 1335.74);
+ AddWaypoint(5, 5026.27, -1736.89, 1323.02);
+ AddWaypoint(6, 5037.77, -1770.56, 1324.36);
+ AddWaypoint(7, 5067.23, -1789.95, 1321.17);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (FrostArmorTimer <= diff)
+ {
+ DoCast(me, SPELL_FROST_ARMOR);
+ FrostArmorTimer = 40000+rand()%20000;
+ } else FrostArmorTimer -= diff;
+ if (DecayTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_DEATH_AND_DECAY);
+ DecayTimer = 60000+rand()%20000;
+ switch (urand(0,1))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_DECAY1);
+ me->MonsterYell(SAY_DECAY1, LANG_UNIVERSAL, NULL);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_DECAY2);
+ me->MonsterYell(SAY_DECAY2, LANG_UNIVERSAL, NULL);
+ break;
+ }
+ } else DecayTimer -= diff;
+ if (NovaTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_FROST_NOVA);
+ NovaTimer = 30000+rand()%15000;
+ switch (urand(0,1))
+ {
+ case 0:
+ DoPlaySoundToSet(me, SOUND_NOVA1);
+ me->MonsterYell(SAY_NOVA1, LANG_UNIVERSAL, NULL);
+ break;
+ case 1:
+ DoPlaySoundToSet(me, SOUND_NOVA2);
+ me->MonsterYell(SAY_NOVA2, LANG_UNIVERSAL, NULL);
+ break;
+ }
+ } else NovaTimer -= diff;
+ if (IceboltTimer <= diff)
+ {
+ DoCast(SelectTarget(SELECT_TARGET_RANDOM,0,40,true), SPELL_ICEBOLT);
+ IceboltTimer = 11000+rand()%20000;
+ } else IceboltTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_rage_winterchill(Creature* pCreature)
+{
+ return new boss_rage_winterchillAI (pCreature);
+}
+
+void AddSC_boss_rage_winterchill()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_rage_winterchill";
+ newscript->GetAI = &GetAI_boss_rage_winterchill;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.cpp b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.cpp
new file mode 100644
index 00000000000..16a050939cc
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.cpp
@@ -0,0 +1,247 @@
+ /* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Hyjal
+SD%Complete: 80
+SDComment: gossip text id's unknown
+SDCategory: Caverns of Time, Mount Hyjal
+EndScriptData */
+
+/* ContentData
+npc_jaina_proudmoore
+npc_thrall
+npc_tyrande_whisperwind
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "hyjalAI.h"
+
+#define GOSSIP_ITEM_BEGIN_ALLY "My companions and I are with you, Lady Proudmoore."
+#define GOSSIP_ITEM_ANETHERON "We are ready for whatever Archimonde might send our way, Lady Proudmoore."
+
+#define GOSSIP_ITEM_BEGIN_HORDE "I am with you, Thrall."
+#define GOSSIP_ITEM_AZGALOR "We have nothing to fear."
+
+#define GOSSIP_ITEM_RETREAT "We can't keep this up. Let's retreat!"
+
+#define GOSSIP_ITEM_TYRANDE "Aid us in defending Nordrassil"
+#define ITEM_TEAR_OF_GODDESS 24494
+
+#define GOSSIP_ITEM_GM1 "[GM] Toggle Debug Timers"
+
+CreatureAI* GetAI_npc_jaina_proudmoore(Creature* pCreature)
+{
+ hyjalAI* ai = new hyjalAI(pCreature);
+
+ ai->Reset();
+ ai->EnterEvadeMode();
+
+ ai->Spell[0].SpellId = SPELL_BLIZZARD;
+ ai->Spell[0].Cooldown = 15000 + rand()%20000;
+ ai->Spell[0].TargetType = TARGETTYPE_RANDOM;
+
+ ai->Spell[1].SpellId = SPELL_PYROBLAST;
+ ai->Spell[1].Cooldown = 5500 + rand()%4000;
+ ai->Spell[1].TargetType = TARGETTYPE_RANDOM;
+
+ ai->Spell[2].SpellId = SPELL_SUMMON_ELEMENTALS;
+ ai->Spell[2].Cooldown = 15000 + rand()%30000;
+ ai->Spell[2].TargetType = TARGETTYPE_SELF;
+
+ return ai;
+}
+
+bool GossipHello_npc_jaina_proudmoore(Player* pPlayer, Creature* pCreature)
+{
+ hyjalAI* ai = CAST_AI(hyjalAI, pCreature->AI());
+ if (ai->EventBegun)
+ return false;
+
+ uint32 RageEncounter = ai->GetInstanceData(DATA_RAGEWINTERCHILLEVENT);
+ uint32 AnetheronEncounter = ai->GetInstanceData(DATA_ANETHERONEVENT);
+ if (RageEncounter == NOT_STARTED)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_BEGIN_ALLY, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+ else if (RageEncounter == DONE && AnetheronEncounter == NOT_STARTED)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_ANETHERON, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
+ else if (RageEncounter == DONE && AnetheronEncounter == DONE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_RETREAT, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 3);
+
+ if (pPlayer->isGameMaster())
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_TRAINER, GOSSIP_ITEM_GM1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+
+ pPlayer->SEND_GOSSIP_MENU(907, pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_jaina_proudmoore(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ hyjalAI* ai = CAST_AI(hyjalAI, pCreature->AI());
+ switch(uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF + 1:
+ ai->StartEvent(pPlayer);
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 2:
+ ai->FirstBossDead = true;
+ ai->WaveCount = 9;
+ ai->StartEvent(pPlayer);
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 3:
+ ai->Retreat();
+ break;
+ case GOSSIP_ACTION_INFO_DEF:
+ ai->Debug = !ai->Debug;
+ debug_log("TSCR: HyjalAI - Debug mode has been toggled");
+ break;
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_thrall(Creature* pCreature)
+{
+ hyjalAI* ai = new hyjalAI(pCreature);
+
+ ai->Reset();
+ ai->EnterEvadeMode();
+
+ ai->Spell[0].SpellId = SPELL_CHAIN_LIGHTNING;
+ ai->Spell[0].Cooldown = 3000 + rand()%5000;
+ ai->Spell[0].TargetType = TARGETTYPE_VICTIM;
+
+ ai->Spell[1].SpellId = SPELL_SUMMON_DIRE_WOLF;
+ ai->Spell[1].Cooldown = 6000 + rand()%35000;
+ ai->Spell[1].TargetType = TARGETTYPE_RANDOM;
+
+ return ai;
+}
+
+bool GossipHello_npc_thrall(Player* pPlayer, Creature* pCreature)
+{
+ hyjalAI* ai = CAST_AI(hyjalAI, pCreature->AI());
+ if (ai->EventBegun)
+ return false;
+
+ uint32 AnetheronEvent = ai->GetInstanceData(DATA_ANETHERONEVENT);
+ // Only let them start the Horde phases if Anetheron is dead.
+ if (AnetheronEvent == DONE && ai->GetInstanceData(DATA_ALLIANCE_RETREAT))
+ {
+ uint32 KazrogalEvent = ai->GetInstanceData(DATA_KAZROGALEVENT);
+ uint32 AzgalorEvent = ai->GetInstanceData(DATA_AZGALOREVENT);
+ if (KazrogalEvent == NOT_STARTED)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_BEGIN_HORDE, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+ else if (KazrogalEvent == DONE && AzgalorEvent == NOT_STARTED)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_AZGALOR, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
+ else if (AzgalorEvent == DONE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_RETREAT, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 3);
+ }
+
+ if (pPlayer->isGameMaster())
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_TRAINER, GOSSIP_ITEM_GM1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+
+ pPlayer->SEND_GOSSIP_MENU(907, pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_thrall(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ hyjalAI* ai = CAST_AI(hyjalAI, pCreature->AI());
+ ai->DeSpawnVeins();//despawn the alliance veins
+ switch(uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF + 1:
+ ai->StartEvent(pPlayer);
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 2:
+ ai->FirstBossDead = true;
+ ai->WaveCount = 9;
+ ai->StartEvent(pPlayer);
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 3:
+ ai->Retreat();
+ break;
+ case GOSSIP_ACTION_INFO_DEF:
+ ai->Debug = !ai->Debug;
+ debug_log("TSCR: HyjalAI - Debug mode has been toggled");
+ break;
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_tyrande_whisperwind(Creature* pCreature)
+{
+ hyjalAI* ai = new hyjalAI(pCreature);
+ ai->Reset();
+ ai->EnterEvadeMode();
+ return ai;
+}
+
+bool GossipHello_npc_tyrande_whisperwind(Player* pPlayer, Creature* pCreature)
+{
+ hyjalAI* ai = CAST_AI(hyjalAI, pCreature->AI());
+ uint32 AzgalorEvent = ai->GetInstanceData(DATA_AZGALOREVENT);
+
+ // Only let them get item if Azgalor is dead.
+ if (AzgalorEvent == DONE && !pPlayer->HasItemCount(ITEM_TEAR_OF_GODDESS,1))
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_TYRANDE, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+ pPlayer->SEND_GOSSIP_MENU(907, pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_tyrande_whisperwind(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF)
+ {
+ ItemPosCountVec dest;
+ uint8 msg = pPlayer->CanStoreNewItem(NULL_BAG, NULL_SLOT, dest, ITEM_TEAR_OF_GODDESS, 1);
+ if (msg == EQUIP_ERR_OK)
+ {
+ Item* item = pPlayer->StoreNewItem(dest, ITEM_TEAR_OF_GODDESS, true);
+ if (item && pPlayer)
+ pPlayer->SendNewItem(item,1,true,false,true);
+ }
+ pPlayer->SEND_GOSSIP_MENU(907, pCreature->GetGUID());
+ CAST_AI(hyjalAI, pCreature->AI());
+ }
+ return true;
+}
+
+void AddSC_hyjal()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_jaina_proudmoore";
+ newscript->GetAI = &GetAI_npc_jaina_proudmoore;
+ newscript->pGossipHello = &GossipHello_npc_jaina_proudmoore;
+ newscript->pGossipSelect = &GossipSelect_npc_jaina_proudmoore;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_thrall";
+ newscript->GetAI = &GetAI_npc_thrall;
+ newscript->pGossipHello = &GossipHello_npc_thrall;
+ newscript->pGossipSelect = &GossipSelect_npc_thrall;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_tyrande_whisperwind";
+ newscript->pGossipHello = &GossipHello_npc_tyrande_whisperwind;
+ newscript->pGossipSelect = &GossipSelect_npc_tyrande_whisperwind;
+ newscript->GetAI = &GetAI_npc_tyrande_whisperwind;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.h b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.h
new file mode 100644
index 00000000000..bfc9a54dfd9
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal.h
@@ -0,0 +1,38 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software licensed under GPL version 2
+ * Please see the included DOCS/LICENSE.TXT for more information */
+
+#ifndef DEF_HYJAL_H
+#define DEF_HYJAL_H
+
+#define ERROR_INST_DATA "TSCR: Instance data not set properly for Mount Hyjal. Encounters will be buggy."
+
+enum eTypes
+{
+ WORLD_STATE_WAVES = 2842,
+ WORLD_STATE_ENEMY = 2453,
+ WORLD_STATE_ENEMYCOUNT = 2454,
+
+ DATA_ANETHERON = 1,
+ DATA_ANETHERONEVENT = 2,
+ DATA_ARCHIMONDE = 3,
+ DATA_ARCHIMONDEEVENT = 4,
+ DATA_AZGALOR = 5,
+ DATA_AZGALOREVENT = 6,
+ DATA_JAINAPROUDMOORE = 7,
+ DATA_KAZROGAL = 8,
+ DATA_KAZROGALEVENT = 9,
+ DATA_RAGEWINTERCHILL = 10,
+ DATA_RAGEWINTERCHILLEVENT = 11,
+ DATA_THRALL = 12,
+ DATA_TYRANDEWHISPERWIND = 13,
+ DATA_TRASH = 14,
+ DATA_RESET_TRASH_COUNT = 15,
+ DATA_ALLIANCE_RETREAT = 16,
+ DATA_HORDE_RETREAT = 17,
+ DATA_RAIDDAMAGE = 18,
+ DATA_RESET_RAIDDAMAGE = 19,
+ TYPE_RETREAT = 20
+};
+#endif
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.cpp b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.cpp
new file mode 100644
index 00000000000..3c12b54f3f4
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.cpp
@@ -0,0 +1,1157 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: HyjalAI
+SD%Complete: 90
+SDComment:
+SDCategory: Caverns of Time, Mount Hyjal
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "hyjalAI.h"
+#include "hyjal_trash.h"
+#include "MapManager.h"
+#include "Language.h"
+#include "Chat.h"
+#include "Object.h"
+
+#define SPAWN_GARG_GATE 0
+#define SPAWN_WYRM_GATE 1
+#define SPAWN_NEAR_TOWER 2
+
+#define YELL_HURRY "Hurry, we don't have much time"
+
+// Locations for summoning gargoyls and frost wyrms in special cases
+float SpawnPointSpecial[3][3]=
+{
+ {5497.08, -2493.23, 1535.72}, //spawn point for the gargoyles near the horde gate
+ {5624.53, -2548.12, 1551.54}, //spawn point for the frost wyrm near the horde gate
+ {5604.41, -2811.98, 1547.77} //spawn point for the gargoyles and wyrms near the horde tower
+};
+
+// Locations for summoning waves in Alliance base
+float AllianceBase[4][3]=
+{
+ {4928.48, -1526.38, 1326.83},
+ {4923.54, -1514.29, 1327.98},
+ {4928.41, -1510.35, 1327.99},
+ {4938.35, -1521.00, 1326.69}
+};
+
+float JainaDummySpawn[2][4]=
+{
+ {5497.01, -2719.03, 1483.08, 2.90426},
+ {5484.98, -2721.69, 1483.39, 6.00656}
+};
+
+// Locations for summoning waves in Horde base
+float HordeBase[4][3]=
+{
+ {5458.01, -2340.27, 1459.60},
+ {5466.01, -2334.69, 1460.06},
+ {5468.45, -2355.13, 1459.99},
+ {5479.06, -2344.16, 1461.74}
+};
+
+// Lady Jaina's waypoints when retreathing
+float JainaWPs[2][3]=
+{
+ {5078.56, -1789.79, 1320.73},//next to the small stairs
+ {5037.38, -1778.39, 1322.61},//center of alliance base
+};
+
+float InfernalPos[8][3]=//spawn points for the infernals in the horde base
+{
+ {5453.59, -2764.52, 1493.50},
+ {5478.4, -2781.77, 1497.52},
+ {5506.09, -2780.53, 1496.32},
+ {5532.1, -2763.42, 1492.37},
+ {5544.16, -2733.99, 1487.14},
+ {5536.19, -2708.18, 1480.01},
+ {5510.16, -2691.75, 1479.66},
+ {5482.39, -2689.19, 1481.09}
+};
+
+float InfernalSPWP[26][4]=//spawn points for the infernals in the horde base used in the cleaning wave
+{
+ {5490.96, -2718.72, 1482.96, 0.49773},
+ {5449.51, -2723.32, 1485.69, 2.69685},
+ {5520.83, -2624.68, 1483.82, 1.20459},
+ {5558.28, -2629.26, 1485.76, 0.37992},
+ {5567.97, -2758.69, 1494.10, 5.04125},
+ {5384.90, -2793.47, 1503.90, 5.55412},
+ {5495.33, -2814.06, 1501.56, 1.12055},
+ {5472.63, -2929.39, 1538.31, 1.95777},
+ {5334.72, -2952.29, 1534.34, 0.50869},
+ {5398.36, -2872.46, 1512.38, 0.76787},
+ {5514.39, -2768.63, 1492.30, 1.55721},
+ {5598.91, -2703.75, 1495.64, 2.56644},
+ {5467.80, -2655.93, 1482.27, 0.85819},
+ {5399.83, -2985.24, 1545.04, 5.92559},
+ {5232.13, -2967.05, 1553.09, 5.41351},
+ {5272.02, -3082.52, 1567.09, 3.40681},
+ {5343.26, -3120.71, 1582.92, 3.16727},
+ {5371.26, -3175.24, 1587.41, 6.10466},
+ {5434.67, -3177.91, 1579.25, 2.77850},
+ {5237.39, -3149.25, 1593.59, 0.83855},
+ {5202.15, -3016.64, 1566.28, 3.31256},
+ {5302.54, -2914.37, 1528.53, 3.37146},
+ {5439.04, -2834.81, 1508.80, 2.14231},
+ {5421.33, -2771.04, 1494.28, 6.06223},
+ {5549.76, -2692.93, 1482.68, 2.19414},
+ {5459.78, -2755.71, 1490.68, 1.05139}
+};
+
+float VeinPos[14][8]=//spawn points of the ancient gem veins
+{
+ {5184.84, -1982.59, 1382.66, 2.58079, 0, 0, 0.960944, 0.276742}, //alliance
+ {5107.66, -2071.16, 1368.37, 2.65148, 0, 0, 0.970124, 0.242611}, //alliance
+ {5040.53, -2227.65, 1403.17, 3.35049, 0, 0, 0.99455, -0.104257}, //alliance
+ {5187.59, -2453.12, 1455.51, 5.87943, 0, 0, 0.20051, -0.979692}, //alliance
+ {5429.43, -2340.65, 1465.38, 4.7681, 0, 0, 0.687138, -0.726527}, //alliance
+ {5463.99, -2315.95, 1470.29, 1.52045, 0, 0, 0.689084, 0.724682}, //alliance
+ {5624.65, -2495.09, 1510.11, 0.0124869, 0, 0, 0.00624342, 0.999981}, //alliance
+ {5285.41, -3348.32, 1663.01, 1.57152, 0, 0, 0.707362, 0.706852}, //horde
+ {5417.69, -3372.52, 1656.31, 0.361993, 0, 0, 0.18001, 0.983665}, //horde
+ {5315.34, -3238.32, 1622.88, 3.03627, 0, 0, 0.998614, 0.0526347}, //horde
+ {5303.4, -3096.44, 1596.41, 1.72073, 0, 0, 0.758081, 0.65216}, //horde
+ {5265.13, -3177.27, 1616.22, 0.813604, 0, 0, 0.395674, 0.918391}, //horde
+ {5374.3, -3420.59, 1653.43, 1.45762, 0, 0, 0.665981, 0.745969}, //horde
+ {5441.54, -3321.59, 1651.55, 0.258306, 0, 0, 0.128794, 0.991671} //horde
+};
+
+float AllianceOverrunGargPos[5][4]=//gargoyle spawn points in the alliance overrun
+{
+ {5279.94, -2049.68, 1311.38, 0},//garg1
+ {5289.15, -2219.06, 1291.12, 0},//garg2
+ {5202.07, -2136.10, 1305.07, 2.8},//garg3
+ {5071.52, -2425.63, 1454.48, 5.54},//garg4
+ {5120.65, -2467.92, 1463.93, 2.54}//garg5
+};
+
+float AllianceFirePos[92][8]=//spawn points for the fire visuals (GO) in the alliance base
+{
+ {5039.9, -1796.84, 1323.88, 2.59222, 0, 0, 0.962511, 0.271243},
+ {5087.2, -1795.2, 1320.68, 1.03946, 0, 0, 0.496644, 0.867954},
+ {5112.68, -1806.66, 1359.93, 1.37799, 0, 0, 0.63576, 0.771887},
+ {5095.61, -1793.27, 1359.78, 0.580806, 0, 0, 0.286338, 0.958129},
+ {5090.43, -1784.45, 1360.44, 0.796784, 0, 0, 0.387937, 0.921686},
+ {5139.25, -1783.11, 1359.39, 3.30849, 0, 0, 0.99652, -0.0833509},
+ {5112.16, -1763.72, 1361.35, 5.10312, 0, 0, 0.556388, -0.830922},
+ {4981.18, -1793.98, 1335.7, 3.23072, 0, 0, 0.999007, -0.0445498},
+ {4996.57, -1766.75, 1341.62, 3.5331, 0, 0, 0.980902, -0.194505},
+ {4983.74, -1769.25, 1345.75, 3.79228, 0, 0, 0.947541, -0.319635},
+ {4996.01, -1774.43, 1330.71, 3.07364, 0, 0, 0.999423, 0.0339693},
+ {5094.2, -1726.13, 1330.55, 1.56175, 0, 0, 0.703901, 0.710298},
+ {5079.82, -1721.24, 1336.26, 1.18868, 0, 0, 0.559964, 0.828517},
+ {5077.68, -1717.15, 1327.78, 0.0145145, 0, 0, 0.00725717, 0.999974},
+ {5122.27, -1738.22, 1341.67, 0.835256, 0, 0, 0.405593, 0.914054},
+ {5131.88, -1741.15, 1335.25, 2.15472, 0, 0, 0.880712, 0.473653},
+ {5196.93, -1772.99, 1345.2, 0.128397, 0, 0, 0.0641544, 0.99794},
+ {5225.33, -1756.06, 1344.17, 3.04223, 0, 0, 0.998766, 0.0496599},
+ {5224.84, -1767.05, 1360.06, 3.19538, 0, 0, 0.999638, -0.0268922},
+ {5202.05, -1763.47, 1361.68, 2.59455, 0, 0, 0.962826, 0.270122},
+ {5194.74, -1766.66, 1356.94, 0.0734191, 0, 0, 0.0367013, 0.999326},
+ {5159.67, -1832.97, 1344.5, 5.17457, 0, 0, 0.526356, -0.850264},
+ {5096.17, -1858.73, 1332.46, 5.30021, 0, 0, 0.471939, -0.881631},
+ {5110.7, -1856.59, 1342.84, 5.97564, 0, 0, 0.153167, -0.9882},
+ {5109.76, -1855.3, 1332.38, 4.89572, 0, 0, 0.639411, -0.768865},
+ {5068.95, -1837.37, 1328.81, 2.61569, 0, 0, 0.965628, 0.25993},
+ {5064.4, -1824.77, 1329.02, 2.16409, 0, 0, 0.88292, 0.469524},
+ {5059.89, -1848.79, 1329.59, 0.0709955, 0, 0, 0.0354903, 0.99937},
+ {5014.37, -1851.39, 1322.56, 4.66949, 0, 0, 0.722111, -0.691777},
+ {5025.1, -1848.27, 1323.39, 4.44565, 0, 0, 0.794854, -0.606801},
+ {4942.63, -1890.13, 1326.59, 3.28719, 0, 0, 0.997351, -0.0727343},
+ {4937.95, -1888.71, 1352.41, 3.41678, 0, 0, 0.990549, -0.13716},
+ {4922.48, -1881.92, 1352.41, 5.03077, 0, 0, 0.586075, -0.810257},
+ {4915.35, -1894.32, 1351.24, 6.22457, 0, 0, 0.0293048, -0.999571},
+ {4922.71, -1904.84, 1352.56, 1.37866, 0, 0, 0.63602, 0.771672},
+ {4932.89, -1905.49, 1352.56, 1.89702, 0, 0, 0.812549, 0.582893},
+ {5011.83, -1861.05, 1345.86, 4.43777, 0, 0, 0.797239, -0.603664},
+ {5011.83, -1861.05, 1363.26, 4.748, 0, 0, 0.694406, -0.719583},
+ {5021.46, -1858.35, 1342.17, 4.86188, 0, 0, 0.652329, -0.757936},
+ {4995.02, -1698.3, 1370.38, 6.15779, 0, 0, 0.0626579, -0.998035},
+ {5119.85, -1728.9, 1336.04, 5.87112, 0, 0, 0.204579, -0.97885},
+ {5214.75, -1751.02, 1342.5, 5.08965, 0, 0, 0.561972, -0.827156},
+ {5075.04, -1822.43, 1328.87, 3.99951, 0, 0, 0.9094, -0.415924},
+ {5057.09, -1823.32, 1350.35, 3.88169, 0, 0, 0.93231, -0.361659},
+ {4984.6, -1816.99, 1329.21, 3.05308, 0, 0, 0.999021, 0.0442417},
+ {4983.35, -1811.55, 1356.82, 3.33975, 0, 0, 0.995096, -0.098917},
+ {4984.11, -1825.73, 1350.76, 2.26375, 0, 0, 0.905211, 0.424962},
+ {4968.47, -1786.46, 1354.09, 3.07663, 0, 0, 0.999473, 0.0324733},
+ {5061.82, -1751.16, 1339.07, 5.94727, 0, 0, 0.167171, -0.985928},
+ {5063.75, -1763, 1351.91, 0.759707, 0, 0, 0.370784, 0.928719},
+ {5078.65, -1708.26, 1353.9, 1.27022, 0, 0, 0.593264, 0.805008},
+ {4983.19, -1755.96, 1331.13, 4.28221, 0, 0, 0.841733, -0.539894},
+ {4972.76, -1755.3, 1332.5, 4.21938, 0, 0, 0.858276, -0.513188},
+ {4961.65, -1760.82, 1351.69, 3.56515, 0, 0, 0.977659, -0.210198},
+ {5086.45, -1779.83, 1321.62, 6.23157, 0, 0, 0.0258051, -0.999667},
+ {5063.15, -1756.74, 1328.56, 0.886926, 0, 0, 0.42907, 0.903271},
+ {5042.45, -1800.61, 1323.88, 2.50093, 0, 0, 0.949131, 0.31488},
+ {5084.74, -1725.35, 1327.89, 1.65034, 0, 0, 0.734663, 0.678432},
+ {4993.25, -1758.1, 1331.07, 3.49995, 0, 0, 0.98399, -0.178223},
+ {5078.53, -1867.85, 1348.91, 5.85612, 0, 0, 0.211913, -0.977288},
+ {5080.74, -1869.73, 1333.18, 6.18206, 0, 0, 0.0505424, -0.998722},
+ {5089.55, -1894.13, 1356.08, 1.52072, 0, 0, 0.689181, 0.724589},
+ {5113.24, -1899.49, 1363.77, 1.50108, 0, 0, 0.682034, 0.731321},
+ {4984.18, -1907.69, 1325.62, 3.82193, 0, 0, 0.942698, -0.333646},
+ {5094.14, -2432.08, 1429.38, 4.70083, 0, 0, 0.711182, -0.703007},
+ {5329.89, -2113.30, 1281.06, 5.60560, 0, 0, 0.332347, -0.943157},
+ {5170.87, -2148.13, 1278.32, 1.63540, 0, 0, 0.729573, 0.683903 },
+ {5132.94, -1960.25, 1367.8, 3.69787, 0, 0, 0.961568, -0.274566},
+ {5280.82, -2351.55, 1431.57, 4.46913, 0, 0, 0.787677, -0.616088},
+ {5176.78, -2121.43, 1295.27, 3.24153, 0, 0, 0.998752, -0.04995},
+ {5332.75, -2101.41, 1296.37, 5.50350, 0, 0, 0.380043, -0.924969},
+ {5265.70, -2050.27, 1287.57, 0.50051, 0, 0, 0.247655, 0.968848 },
+ {5194.21, -2129.89, 1274.04, 3.08053, 0, 0, 0.999534, 0.0305272},
+ {5225.81, -1985.50, 1364.15, 0.37247, 0, 0, 0.185163, 0.982708 },
+ {5339.46, -2204.47, 1280.45, 0.99921, 0, 0, 0.479081, 0.877771 },
+ {5269.63, -2020.57, 1299.62, 3.00201, 0, 0, 0.997566, 0.0697332},
+ {5111.54, -2445.70, 1435.31, 2.70983, 0, 0, 0.976788, 0.214207 },
+ {5111.24, -1901.14, 1355.33, 1.61028, 0, 0, 0.720929, 0.693009 },
+ {5310.42, -2207.82, 1277.46, 0.50441, 0, 0, 0.249544, 0.968363 },
+ {5150.81, -2042.13, 1394.3, 2.21031, 0, 0, 0.893534, 0.448995 },
+ {5224.84, -2376.61, 1366.33, 5.0621, 0, 0, 0.573311, -0.819338},
+ {5105.41, -2454.86, 1446.16, 4.64584, 0, 0, 0.730239, -0.683191},
+ {5309.65, -2188.28, 1266.84, 5.56631, 0, 0, 0.350811, -0.936446},
+ {5281.46, -2047.82, 1287.67, 2.44909, 0, 0, 0.940652, 0.339373 },
+ {5325.45, -2189.41, 1309.6, 6.23783, 0, 0, 0.0226771, -0.999743},
+ {5190.96, -2142.54, 1293.03, 6.25668, 0, 0, 0.0132544, -0.999912},
+ {5089.99, -2467.49, 1441.8, 0.77381, 0, 0, 0.377326, 0.92608 },
+ {5195.08, -2129.01, 1285.36, 3.55727, 0, 0, 0.978480, -0.206344},
+ {5353.76, -2116.28, 1299.27, 6.17894, 0, 0, 0.0521006, -0.998642},
+ {5271.14, -2037.38, 1299.24, 4.07879, 0, 0, 0.892201, -0.451638},
+ {5332.5 , -2181.28, 1279.95, 4.6906, 0, 0, 0.714768, -0.699362},
+ {5108.2 , -2429.84, 1427.73, 4.5194, 0, 0, 0.771943, -0.635691}
+};
+
+float HordeFirePos[65][8]=//spawn points for the fire visuals (GO) in the horde base
+{
+ {5524.11, -2612.73, 1483.38, 1.96198, 0, 0, 0.831047, 0.556202},
+ {5514.42, -2617.19, 1505.77, 1.82453, 0, 0, 0.790892, 0.611956},
+ {5510.21, -2624.77, 1485.34, 1.71065, 0, 0, 0.754783, 0.655974},
+ {5570.72, -2619.04, 1487.62, 0.728898, 0, 0, 0.356435, 0.93432},
+ {5570.29, -2639.37, 1487.31, 1.49308, 0, 0, 0.679104, 0.734042},
+ {5583.56, -2637.2, 1503.78, 1.46559, 0, 0, 0.668951, 0.743307},
+ {5571.53, -2626.81, 1510.99, 0.362107, 0, 0, 0.180066, 0.983654},
+ {5545.97, -2659.62, 1489.64, 5.07055, 0, 0, 0.569845, -0.821752},
+ {5557.44, -2675.91, 1482.58, 1.70118, 0, 0, 0.751671, 0.659539},
+ {5594.98, -2742.31, 1495.51, 4.5993, 0, 0, 0.74594, -0.666013},
+ {5599.65, -2755.6, 1505.05, 1.66896, 0, 0, 0.740947, 0.671564},
+ {5565.95, -2774.75, 1499.48, 6.22425, 0, 0, 0.0294611, -0.999566},
+ {5567.1, -2769.7, 1511.17, 5.99257, 0, 0, 0.144799, -0.989461},
+ {5572.84, -2774.16, 1527.06, 0.836428, 0, 0, 0.406129, 0.913816},
+ {5538.32, -2805.94, 1498.87, 4.30082, 0, 0, 0.836674, -0.547701},
+ {5515.66, -2801.74, 1503.53, 5.57316, 0, 0, 0.347602, -0.937642},
+ {5516.76, -2827.14, 1501.15, 0.35026, 0, 0, 0.174236, 0.984704},
+ {5536.13, -2813.51, 1537.21, 4.51681, 0, 0, 0.772765, -0.634692},
+ {5525.05, -2825.16, 1538.53, 0.489275, 0, 0, 0.242205, 0.970225},
+ {5534.42, -2815.45, 1562.84, 4.62834, 0, 0, 0.736191, -0.676774},
+ {5519.64, -2831.12, 1526.46, 0.611008, 0, 0, 0.300774, 0.953696},
+ {5551.04, -2827.55, 1523.5, 3.35206, 0, 0, 0.994468, -0.10504},
+ {5469.22, -2802.87, 1503.5, 4.99509, 0, 0, 0.600436, -0.799673},
+ {5427.8, -2737.26, 1487.12, 1.78673, 0, 0, 0.779186, 0.626793},
+ {5454.1, -2709.1, 1485.92, 3.03552, 0, 0, 0.998594, 0.0530137},
+ {5436.3, -2718.2, 1506.02, 2.7567, 0, 0, 0.981539, 0.191261},
+ {5412.6, -2740.55, 1510.79, 2.98446, 0, 0, 0.996915, 0.0784832},
+ {5406.12, -2752.48, 1521.01, 2.05769, 0, 0, 0.856705, 0.515807},
+ {5445.24, -2676.35, 1521.89, 2.91378, 0, 0, 0.99352, 0.113661},
+ {5481.4, -2665.08, 1482.23, 4.30001, 0, 0, 0.836895, -0.547363},
+ {5443.51, -2675.44, 1487.12, 2.90986, 0, 0, 0.993295, 0.115606},
+ {5391.72, -2647.3, 1528.9, 3.76987, 0, 0, 0.951063, -0.308997},
+ {5421.09, -2734.12, 1521.01, 2.70567, 0, 0, 0.97634, 0.216242},
+ {5405.39, -2710.33, 1533.77, 2.51324, 0, 0, 0.951052, 0.309032},
+ {5423.96, -2703.76, 1516.34, 2.79206, 0, 0, 0.984767, 0.173879},
+ {5444.75, -2735.23, 1486.37, 2.22657, 0, 0, 0.897155, 0.441715},
+ {5570.98, -2747.91, 1495.7, 5.14433, 0, 0, 0.53915, -0.84221},
+ {5567.79, -2673.9, 1484.66, 2.72529, 0, 0, 0.978415, 0.20665},
+ {5600.71, -2696.8, 1500.42, 0.443704, 0, 0, 0.220036, 0.975492},
+ {5600.7, -2693.04, 1515.2, 5.16003, 0, 0, 0.532522, -0.846416},
+ {5627.56, -2839.66, 1510.53, 5.41527, 0, 0, 0.420463, -0.907309},
+ {5622.02, -2868.71, 1516.22, 2.25482, 0, 0, 0.903303, 0.429002},
+ {5586.61, -2878.97, 1510.34, 4.55604, 0, 0, 0.76017, -0.649724},
+ {5583.78, -2843.71, 1509.54, 5.35715, 0, 0, 0.44665, -0.894709},
+ {5580.95, -2811.3, 1513.3, 3.57587, 0, 0, 0.976518, -0.215434},
+ {5542.52, -2869.31, 1523.13, 5.23304, 0, 0, 0.501275, -0.865288},
+ {5557.35, -2866.36, 1518.76, 4.48299, 0, 0, 0.783388, -0.621533},
+ {5380.91, -2849.36, 1512.81, 3.90962, 0, 0, 0.927168, -0.374646},
+ {5395.76, -2881.41, 1521.11, 4.28426, 0, 0, 0.84118, -0.540755},
+ {5374.87, -2859.63, 1528.98, 3.30252, 0, 0, 0.996765, -0.0803745},
+ {5356.07, -2854.66, 1520.34, 5.83933, 0, 0, 0.220108, -0.975475},
+ {5363.01, -2975.72, 1539.02, 4.13738, 0, 0, 0.87859, -0.477576},
+ {5336.85, -2980.74, 1561.24, 5.11126, 0, 0, 0.553001, -0.83318},
+ {5335.23, -2974.62, 1540.05, 5.04451, 0, 0, 0.580496, -0.814263},
+ {5422.37, -2998.87, 1549.98, 4.51831, 0, 0, 0.772288, -0.635272},
+ {5405.54, -3014.6, 1562.16, 5.86761, 0, 0, 0.206298, -0.978489},
+ {5427.96, -3019.4, 1561.58, 3.53498, 0, 0, 0.980718, -0.19543},
+ {5348.12, -2977.84, 1582.47, 3.94025, 0, 0, 0.921323, -0.388799},
+ {5331.12, -2993.71, 1576.14, 0.0642734, 0, 0, 0.0321311, 0.999484},
+ {5321.63, -2986.55, 1552.2, 5.29503, 0, 0, 0.474219, -0.880407},
+ {5292.1, -2914.36, 1529.52, 2.9742, 0, 0, 0.996499, 0.083601},
+ {5281.77, -2926.5, 1530.62, 1.67829, 0, 0, 0.744071, 0.6681},
+ {5287.19, -2909.94, 1543.49, 3.31192, 0, 0, 0.996376, -0.0850591},
+ {5534.15, -2679.35, 1483.61, 0.428685, 0, 0, 0.212705, 0.977116},
+ {5545.43, -2647.82, 1483.05, 5.38848, 0, 0, 0.432578, -0.901596}
+};
+
+hyjalAI::hyjalAI(Creature *c) : npc_escortAI(c), Summons(me)
+{
+ pInstance = c->GetInstanceData();
+ VeinsSpawned[0] = false;
+ VeinsSpawned[1] = false;
+ for (uint8 i=0; i<14; ++i)
+ VeinGUID[i] = 0;
+ InfernalCount = 0;
+ TeleportTimer = 1000;
+ Overrun = false;
+ Teleported = false;
+ WaitForTeleport = false;
+ OverrunCounter = 0;
+ OverrunCounter2 = 0;
+ InfernalPoint = 0;
+ RespawnTimer = 10000;
+ DoRespawn = false;
+ DoHide = false;
+ MassTeleportTimer = 0;
+ DoMassTeleport = false;
+}
+
+void hyjalAI::JustSummoned(Creature *summoned)
+{
+ Summons.Summon(summoned);
+}
+
+void hyjalAI::SummonedCreatureDespawn(Creature* summoned)
+{
+ Summons.Despawn(summoned);
+}
+
+void hyjalAI::Reset()
+{
+ IsDummy = false;
+ me->setActive(true);
+ // GUIDs
+ PlayerGUID = 0;
+ BossGUID[0] = 0;
+ BossGUID[1] = 0;
+
+ // Timers
+ NextWaveTimer = 10000;
+ CheckTimer = 0;
+ RetreatTimer = 1000;
+
+ // Misc
+ WaveCount = 0;
+ EnemyCount = 0;
+
+ // Set faction properly based on Creature entry
+ switch(me->GetEntry())
+ {
+ case JAINA:
+ Faction = 0;
+ DoCast(me, SPELL_BRILLIANCE_AURA, true);
+ break;
+
+ case THRALL:
+ Faction = 1;
+ break;
+
+ case TYRANDE:
+ Faction = 2;
+ break;
+ }
+
+ //Bools
+ EventBegun = false;
+ FirstBossDead = false;
+ SecondBossDead = false;
+ Summon = false;
+ bRetreat = false;
+ Debug = false;
+
+ //Flags
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+
+ //Initialize spells
+ memset(Spell, 0, sizeof(Spell));
+
+ //Reset Instance Data for trash count
+ if (pInstance)
+ {
+ if ((!pInstance->GetData(DATA_ALLIANCE_RETREAT) && me->GetEntry() == JAINA) || (pInstance->GetData(DATA_ALLIANCE_RETREAT) && me->GetEntry() == THRALL))
+ {
+ //Reset World States
+ pInstance->DoUpdateWorldState(WORLD_STATE_WAVES, 0);
+ pInstance->DoUpdateWorldState(WORLD_STATE_ENEMY, 0);
+ pInstance->DoUpdateWorldState(WORLD_STATE_ENEMYCOUNT, 0);
+ pInstance->SetData(DATA_RESET_TRASH_COUNT, 0);
+ }
+ } else error_log(ERROR_INST_DATA);
+
+ //Visibility
+ DoHide = true;
+}
+
+void hyjalAI::EnterEvadeMode()
+{
+ if (me->GetEntry() != JAINA)
+ me->RemoveAllAuras();
+ me->DeleteThreatList();
+ me->CombatStop(true);
+ me->LoadCreaturesAddon();
+
+ if (me->isAlive())
+ me->GetMotionMaster()->MoveTargetedHome();
+
+ me->SetLootRecipient(NULL);
+}
+
+void hyjalAI::EnterCombat(Unit * /*who*/)
+{
+ if (IsDummy)return;
+ for (uint8 i = 0; i < 3; ++i)
+ if (Spell[i].Cooldown)
+ SpellTimer[i] = Spell[i].Cooldown;
+
+ Talk(ATTACKED);
+}
+
+void hyjalAI::MoveInLineOfSight(Unit *who)
+{
+ if (IsDummy)
+ return;
+
+ npc_escortAI::MoveInLineOfSight(who);
+}
+
+void hyjalAI::SummonCreature(uint32 entry, float Base[4][3])
+{
+ uint32 random = rand()%4;
+ float SpawnLoc[3];
+
+ for (uint8 i = 0; i < 3; ++i)
+ {
+ SpawnLoc[i] = Base[random][i];
+ }
+ Creature* pCreature = NULL;
+ switch(entry)
+ {
+ case 17906: //GARGOYLE
+
+ if (!FirstBossDead && (WaveCount == 1 || WaveCount == 3))
+ {//summon at tower
+ pCreature = me->SummonCreature(entry, SpawnPointSpecial[SPAWN_NEAR_TOWER][0]+irand(-20,20), SpawnPointSpecial[SPAWN_NEAR_TOWER][1]+irand(-20,20), SpawnPointSpecial[SPAWN_NEAR_TOWER][2]+irand(-10,10), 0, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 120000);
+ if (pCreature)
+ CAST_AI(hyjal_trashAI, pCreature->AI())->useFlyPath = true;
+ }else{//summon at gate
+ pCreature = me->SummonCreature(entry, SpawnPointSpecial[SPAWN_GARG_GATE][0]+irand(-10,10), SpawnPointSpecial[SPAWN_GARG_GATE][1]+irand(-10,10), SpawnPointSpecial[SPAWN_GARG_GATE][2]+irand(-10,10), 0, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 120000);
+ }
+ break;
+ case 17907: //FROST_WYRM ,
+ if (FirstBossDead && WaveCount == 1) //summon at gate
+ pCreature = me->SummonCreature(entry, SpawnPointSpecial[SPAWN_WYRM_GATE][0],SpawnPointSpecial[SPAWN_WYRM_GATE][1],SpawnPointSpecial[SPAWN_WYRM_GATE][2], 0, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 120000);
+ else
+ {
+ pCreature = me->SummonCreature(entry, SpawnPointSpecial[SPAWN_NEAR_TOWER][0], SpawnPointSpecial[SPAWN_NEAR_TOWER][1],SpawnPointSpecial[SPAWN_NEAR_TOWER][2], 0, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 120000);
+ if (pCreature)
+ CAST_AI(hyjal_trashAI, pCreature->AI())->useFlyPath = true;
+ }
+ break;
+ case 17908: //GIANT_INFERNAL
+ ++InfernalCount;
+ if (InfernalCount > 7)
+ InfernalCount = 0;
+ pCreature = me->SummonCreature(entry, InfernalPos[InfernalCount][0], InfernalPos[InfernalCount][1], InfernalPos[InfernalCount][2], 0, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 120000);
+ break;
+ default:
+ pCreature = me->SummonCreature(entry, SpawnLoc[0], SpawnLoc[1], SpawnLoc[2], 0, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 120000);
+ break;
+
+ }
+
+ if (pCreature)
+ {
+ // Increment Enemy Count to be used in World States and instance script
+ ++EnemyCount;
+
+ pCreature->RemoveUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
+ pCreature->setActive(true);
+ switch(entry)
+ {
+ case NECROMANCER:
+ case ABOMINATION:
+ case GHOUL:
+ case BANSHEE:
+ case CRYPT_FIEND:
+ case GARGOYLE:
+ case FROST_WYRM:
+ case GIANT_INFERNAL:
+ case FEL_STALKER:
+ case RAGE_WINTERCHILL:
+ case ANETHERON:
+ case KAZROGAL:
+ case AZGALOR:
+ CAST_AI(hyjal_trashAI, pCreature->AI())->IsEvent = true;
+ break;
+ }
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_RAIDDAMAGE) < MINRAIDDAMAGE)
+ pCreature->SetDisableReputationGain(true);//no repu for solo farming
+ }
+ // Check if Creature is a boss.
+ if (pCreature->isWorldBoss())
+ {
+ if (!FirstBossDead) BossGUID[0] = pCreature->GetGUID();
+ else BossGUID[1] = pCreature->GetGUID();
+ CheckTimer = 5000;
+ }
+ }
+}
+
+void hyjalAI::SummonNextWave(Wave wave[18], uint32 Count, float Base[4][3])
+{
+ // 1 in 4 chance we give a rally yell. Not sure if the chance is offilike.
+ if (rand()%4 == 0)
+ Talk(RALLY);
+
+ if (!pInstance)
+ {
+ error_log(ERROR_INST_DATA);
+ return;
+ }
+ InfernalCount = 0;//reset infernal count every new wave
+
+ EnemyCount = pInstance->GetData(DATA_TRASH);
+ for (uint8 i = 0; i < 18; ++i)
+ {
+ if (wave[Count].Mob[i])
+ SummonCreature(wave[Count].Mob[i], Base);
+ }
+
+ if (!wave[Count].IsBoss)
+ {
+ uint32 stateValue = Count+1;
+ if (FirstBossDead)
+ stateValue -= 9; // Subtract 9 from it to give the proper wave number if we are greater than 8
+
+ // Set world state to our current wave number
+ pInstance->DoUpdateWorldState(WORLD_STATE_WAVES, stateValue); // Set world state to our current wave number
+ // Enable world state
+ pInstance->DoUpdateWorldState(WORLD_STATE_ENEMY, 1); // Enable world state
+
+ pInstance->SetData(DATA_TRASH, EnemyCount); // Send data for instance script to update count
+
+ if (!Debug)
+ NextWaveTimer = wave[Count].WaveTimer;
+ else
+ {
+ NextWaveTimer = 15000;
+ debug_log("TSCR: HyjalAI: debug mode is enabled. Next Wave in 15 seconds");
+ }
+ }
+ else
+ {
+ // Set world state for waves to 0 to disable it.
+ pInstance->DoUpdateWorldState(WORLD_STATE_WAVES, 0);
+ pInstance->DoUpdateWorldState(WORLD_STATE_ENEMY, 1);
+
+ // Set World State for enemies invading to 1.
+ pInstance->DoUpdateWorldState(WORLD_STATE_ENEMYCOUNT, 1);
+
+ Summon = false;
+ }
+ CheckTimer = 5000;
+}
+
+void hyjalAI::StartEvent(Player* pPlayer)
+{
+ if (!pPlayer || IsDummy || !pInstance)
+ return;
+
+ Talk(BEGIN);
+
+ EventBegun = true;
+ Summon = true;
+
+ NextWaveTimer = 15000;
+ CheckTimer = 5000;
+ PlayerGUID = pPlayer->GetGUID();
+
+ me->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+
+ pInstance->DoUpdateWorldState(WORLD_STATE_WAVES, 0);
+ pInstance->DoUpdateWorldState(WORLD_STATE_ENEMY, 0);
+ pInstance->DoUpdateWorldState(WORLD_STATE_ENEMYCOUNT, 0);
+
+ DeSpawnVeins();
+}
+
+uint32 hyjalAI::GetInstanceData(uint32 Event)
+{
+ if (pInstance)
+ return pInstance->GetData(Event);
+ else error_log(ERROR_INST_DATA);
+
+ return 0;
+}
+
+void hyjalAI::Talk(uint32 id)
+{
+ std::list<uint8> index;
+ for (uint8 i = 0; i < 9; ++i)
+ {
+ if (Faction == 0) // Alliance
+ {
+ if (JainaQuotes[i].id == id)
+ index.push_back(i);
+ }
+ else if (Faction == 1) // Horde
+ {
+ if (ThrallQuotes[i].id == id)
+ index.push_back(i);
+ }
+ }
+
+ if (index.empty())
+ return; // No quotes found, no use to continue
+
+ uint8 ind = *(index.begin()) + rand()%index.size();
+
+ int32 YellId = 0;
+ if (Faction == 0) // Alliance
+ {
+ YellId = JainaQuotes[ind].textid;
+ }
+ else if (Faction == 1) // Horde
+ {
+ YellId = ThrallQuotes[ind].textid;
+ }
+
+ if (YellId)
+ DoScriptText(YellId, me);
+}
+
+void hyjalAI::Retreat()
+{
+ if (pInstance)
+ {
+ pInstance->SetData(TYPE_RETREAT,SPECIAL);
+
+ if (Faction == 0)
+ {
+ pInstance->SetData(DATA_ALLIANCE_RETREAT, 1);
+ AddWaypoint(0,JainaWPs[0][0],JainaWPs[0][1],JainaWPs[0][2]);
+ AddWaypoint(1,JainaWPs[1][0],JainaWPs[1][1],JainaWPs[1][2]);
+ Start(false, false);
+ SetDespawnAtEnd(false);//move to center of alliance base
+ }
+ if (Faction == 1)
+ {
+ pInstance->SetData(DATA_HORDE_RETREAT, 1);
+ Creature* JainaDummy = me->SummonCreature(JAINA,JainaDummySpawn[0][0],JainaDummySpawn[0][1],JainaDummySpawn[0][2],JainaDummySpawn[0][3],TEMPSUMMON_TIMED_DESPAWN,60000);
+ if (JainaDummy)
+ {
+ JainaDummy->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ CAST_AI(hyjalAI, JainaDummy->AI())->IsDummy = true;
+ DummyGuid = JainaDummy->GetGUID();
+ }
+ AddWaypoint(0,JainaDummySpawn[1][0],JainaDummySpawn[1][1],JainaDummySpawn[1][2]);
+ Start(false, false);
+ SetDespawnAtEnd(false);//move to center of alliance base
+ }
+ }
+ SpawnVeins();
+ Overrun = true;
+ me->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);//cant talk after overrun event started
+}
+
+void hyjalAI::SpawnVeins()
+{
+ if (Faction == 0)
+ {
+ if (VeinsSpawned[0])//prevent any buggers
+ return;
+ for (uint8 i = 0; i<7; ++i)
+ {
+ GameObject* gem = me->SummonGameObject(ANCIENT_VEIN,VeinPos[i][0],VeinPos[i][1],VeinPos[i][2],VeinPos[i][3],VeinPos[i][4],VeinPos[i][5],VeinPos[i][6],VeinPos[i][7],0);
+ if (gem)
+ VeinGUID[i]=gem->GetGUID();
+ }
+ VeinsSpawned[0] = true;
+ }else{
+ if (VeinsSpawned[1])
+ return;
+ for (uint8 i = 7; i<14; ++i)
+ {
+ GameObject* gem = me->SummonGameObject(ANCIENT_VEIN,VeinPos[i][0],VeinPos[i][1],VeinPos[i][2],VeinPos[i][3],VeinPos[i][4],VeinPos[i][5],VeinPos[i][6],VeinPos[i][7],0);
+ if (gem)
+ VeinGUID[i]=gem->GetGUID();
+ }
+ VeinsSpawned[1] = true;
+ }
+}
+
+void hyjalAI::DeSpawnVeins()
+{
+ if (!pInstance)
+ return;
+ if (Faction == 1)
+ {
+ Creature* pUnit=Unit::GetCreature((*me),pInstance->GetData64(DATA_JAINAPROUDMOORE));
+ if (!pUnit)return;
+ hyjalAI* ai = CAST_AI(hyjalAI, pUnit->AI());
+ if (!ai)return;
+ for (uint8 i = 0; i<7; ++i)
+ {
+ if (GameObject* gem = pInstance->instance->GetGameObject(pInstance->GetData64(ai->VeinGUID[i])))
+ gem->Delete();
+ }
+ } else if (Faction)
+ {
+ Creature* pUnit=Unit::GetCreature((*me),pInstance->GetData64(DATA_THRALL));
+ if (!pUnit)return;
+ hyjalAI* ai = CAST_AI(hyjalAI, pUnit->AI());
+ if (!ai)return;
+ for (uint8 i = 7; i<14; ++i)
+ {
+ if (GameObject* gem = pInstance->instance->GetGameObject(pInstance->GetData64(ai->VeinGUID[i])))
+ gem->Delete();
+ }
+ }
+}
+
+void hyjalAI::UpdateAI(const uint32 diff)
+{
+ if (IsDummy)
+ {
+ if (MassTeleportTimer < diff && DoMassTeleport)
+ {
+ DoCast(me, SPELL_MASS_TELEPORT, false);
+ DoMassTeleport = false;
+ } else MassTeleportTimer -= diff;
+ return;
+ }
+ if (DoHide)
+ {
+ DoHide = false;
+ switch(me->GetEntry())
+ {
+ case JAINA:
+ if (pInstance && pInstance->GetData(DATA_ALLIANCE_RETREAT))
+ {
+ me->SetVisibility(VISIBILITY_OFF);
+ HideNearPos(me->GetPositionX(), me->GetPositionY());
+ HideNearPos(5037.76, -1889.71);
+ for (uint8 i = 0; i < 92; ++i)//summon fires
+ me->SummonGameObject(FLAMEOBJECT,AllianceFirePos[i][0],AllianceFirePos[i][1],AllianceFirePos[i][2],AllianceFirePos[i][3],AllianceFirePos[i][4],AllianceFirePos[i][5],AllianceFirePos[i][6],AllianceFirePos[i][7],0);
+
+ }
+ else me->SetVisibility(VISIBILITY_ON);
+ break;
+ case THRALL: //thrall
+ if (pInstance && pInstance->GetData(DATA_HORDE_RETREAT))
+ {
+ me->SetVisibility(VISIBILITY_OFF);
+ HideNearPos(me->GetPositionX(), me->GetPositionY());
+ HideNearPos(5563, -2763.19);
+ HideNearPos(5542.2, -2629.36);
+ for (uint8 i = 0; i < 65; ++i)//summon fires
+ me->SummonGameObject(FLAMEOBJECT,HordeFirePos[i][0],HordeFirePos[i][1],HordeFirePos[i][2],HordeFirePos[i][3],HordeFirePos[i][4],HordeFirePos[i][5],HordeFirePos[i][6],HordeFirePos[i][7],0);
+
+ }
+ else me->SetVisibility(VISIBILITY_ON);
+ break;
+ }
+ }
+ if (DoRespawn)
+ {
+ if (RespawnTimer <= diff)
+ {
+ DoRespawn = false;
+ RespawnNearPos(me->GetPositionX(), me->GetPositionY());
+ if (Faction == 0)
+ {
+ RespawnNearPos(5037.76, -1889.71);
+ } else if (Faction == 1)
+ {
+ RespawnNearPos(5563, -2763.19);
+ RespawnNearPos(5542.2, -2629.36);
+ }
+ me->SetVisibility(VISIBILITY_ON);
+ }else{
+ RespawnTimer -= diff;
+ me->SetVisibility(VISIBILITY_OFF);
+ }
+ return;
+ }
+ if (Overrun)
+ DoOverrun(Faction, diff);
+ if (bRetreat)
+ {
+ if (RetreatTimer <= diff)
+ {
+ IsDummy = true;
+ bRetreat = false;
+ HideNearPos(me->GetPositionX(), me->GetPositionY());
+ switch(me->GetEntry())
+ {
+ case JAINA://jaina
+ HideNearPos(5037.76, -1889.71);
+ break;
+ case THRALL://thrall
+ HideNearPos(5563, -2763.19);
+ HideNearPos(5542.2, -2629.36);
+ HideNearPos(5603.75, -2853.12);
+ break;
+ }
+ me->SetVisibility(VISIBILITY_OFF);
+ } else RetreatTimer -= diff;
+ }
+
+ if (!EventBegun)
+ return;
+
+ if (Summon)
+ {
+ if (pInstance && EnemyCount)
+ {
+ EnemyCount = pInstance->GetData(DATA_TRASH);
+ if (!EnemyCount)
+ NextWaveTimer = 5000;
+ }
+
+ if (NextWaveTimer <= diff)
+ {
+ if (Faction == 0)
+ SummonNextWave(AllianceWaves, WaveCount, AllianceBase);
+ else if (Faction == 1)
+ SummonNextWave(HordeWaves, WaveCount, HordeBase);
+ ++WaveCount;
+ } else NextWaveTimer -= diff;
+ }
+
+ if (CheckTimer <= diff)
+ {
+ for (uint8 i = 0; i < 2; ++i)
+ {
+ if (BossGUID[i])
+ {
+ Unit* pUnit = Unit::GetUnit((*me), BossGUID[i]);
+ if (pUnit && (!pUnit->isAlive()))
+ {
+ if (BossGUID[i] == BossGUID[0])
+ {
+ Talk(INCOMING);
+ FirstBossDead = true;
+ }
+ else if (BossGUID[i] == BossGUID[1])
+ {
+ Talk(SUCCESS);
+ SecondBossDead = true;
+ }
+ EventBegun = false;
+ CheckTimer = 0;
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ BossGUID[i] = 0;
+ if (pInstance)
+ pInstance->DoUpdateWorldState(WORLD_STATE_ENEMY, 0); // Reset world state for enemies to disable it
+ }
+ }
+ }
+ CheckTimer = 5000;
+ } else CheckTimer -= diff;
+
+ if (!UpdateVictim())
+ return;
+
+ for (uint8 i = 0; i < 3; ++i)
+ {
+ if (Spell[i].SpellId)
+ {
+ if (SpellTimer[i] <= diff)
+ {
+ if (me->IsNonMeleeSpellCasted(false))
+ me->InterruptNonMeleeSpells(false);
+
+ Unit *pTarget = NULL;
+
+ switch(Spell[i].TargetType)
+ {
+ case TARGETTYPE_SELF: pTarget = me; break;
+ case TARGETTYPE_RANDOM: pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0); break;
+ case TARGETTYPE_VICTIM: pTarget = me->getVictim(); break;
+ }
+
+ if (pTarget && pTarget->isAlive())
+ {
+ DoCast(pTarget, Spell[i].SpellId);
+ SpellTimer[i] = Spell[i].Cooldown;
+ }
+ } else SpellTimer[i] -= diff;
+ }
+ }
+
+ DoMeleeAttackIfReady();
+}
+void hyjalAI::JustDied(Unit* /*killer*/)
+{
+ if (IsDummy)return;
+ me->Respawn();
+ me->SetVisibility(VISIBILITY_OFF);
+ DoRespawn = true;
+ RespawnTimer = 120000;
+ Talk(DEATH);
+ Summons.DespawnAll();//despawn all wave's summons
+ if (pInstance)
+ {//reset encounter if boss is despawned (ex: thrall is killed, boss despawns, event stucks at inprogress)
+ if (pInstance->GetData(DATA_RAGEWINTERCHILLEVENT) == IN_PROGRESS)
+ pInstance->SetData(DATA_RAGEWINTERCHILLEVENT, NOT_STARTED);
+ if (pInstance->GetData(DATA_ANETHERONEVENT) == IN_PROGRESS)
+ pInstance->SetData(DATA_ANETHERONEVENT, NOT_STARTED);
+ if (pInstance->GetData(DATA_KAZROGALEVENT) == IN_PROGRESS)
+ pInstance->SetData(DATA_KAZROGALEVENT, NOT_STARTED);
+ if (pInstance->GetData(DATA_AZGALOREVENT) == IN_PROGRESS)
+ pInstance->SetData(DATA_AZGALOREVENT, NOT_STARTED);
+ pInstance->SetData(DATA_RESET_RAIDDAMAGE, NULL);//reset damage on die
+ }
+}
+void hyjalAI::HideNearPos(float x, float y)
+{
+ CellPair pair(Trinity::ComputeCellPair(x, y));
+ Cell cell(pair);
+ cell.data.Part.reserved = ALL_DISTRICT;
+ cell.SetNoCreate();
+
+ // First get all creatures.
+ std::list<Creature*> creatures;
+ Trinity::AllFriendlyCreaturesInGrid creature_check(me);
+ Trinity::CreatureListSearcher<Trinity::AllFriendlyCreaturesInGrid> creature_searcher(me, creatures, creature_check);
+ TypeContainerVisitor
+ <Trinity::CreatureListSearcher<Trinity::AllFriendlyCreaturesInGrid>,
+ GridTypeMapContainer> creature_visitor(creature_searcher);
+
+ // Get Creatures
+ cell.Visit(pair, creature_visitor, *(me->GetMap()));
+
+ if (!creatures.empty())
+ {
+ for (std::list<Creature*>::const_iterator itr = creatures.begin(); itr != creatures.end(); ++itr)
+ {
+ (*itr)->SetVisibility(VISIBILITY_OFF);
+ (*itr)->setFaction(35);//make them friendly so mobs won't attack them
+ }
+ }
+}
+void hyjalAI::RespawnNearPos(float x, float y)
+{
+ CellPair p(Trinity::ComputeCellPair(x, y));
+ Cell cell(p);
+ cell.data.Part.reserved = ALL_DISTRICT;
+ cell.SetNoCreate();
+
+ Trinity::RespawnDo u_do;
+ Trinity::WorldObjectWorker<Trinity::RespawnDo> worker(me, u_do);
+ TypeContainerVisitor<Trinity::WorldObjectWorker<Trinity::RespawnDo>, GridTypeMapContainer > obj_worker(worker);
+ cell.Visit(p, obj_worker, *me->GetMap());
+}
+void hyjalAI::WaypointReached(uint32 i)
+{
+ if (i == 1 || (i == 0 && me->GetEntry() == THRALL))
+ {
+ me->MonsterYell(YELL_HURRY,0,0);
+ WaitForTeleport = true;
+ TeleportTimer = 20000;
+ if (me->GetEntry() == JAINA)
+ DoCast(me, SPELL_MASS_TELEPORT, false);
+ if (me->GetEntry() == THRALL && DummyGuid)
+ {
+ Unit* Dummy = Unit::GetUnit((*me),DummyGuid);
+ if (Dummy)
+ {
+ CAST_AI(hyjalAI, CAST_CRE(Dummy)->AI())->DoMassTeleport = true;
+ CAST_AI(hyjalAI, CAST_CRE(Dummy)->AI())->MassTeleportTimer = 20000;
+ Dummy->CastSpell(me, SPELL_MASS_TELEPORT, false);
+ }
+ }
+ //do some talking
+ //all alive guards walk near here
+ CellPair pair(Trinity::ComputeCellPair(me->GetPositionX(), me->GetPositionY()));
+ Cell cell(pair);
+ cell.data.Part.reserved = ALL_DISTRICT;
+ cell.SetNoCreate();
+
+ // First get all creatures.
+ std::list<Creature*> creatures;
+ Trinity::AllFriendlyCreaturesInGrid creature_check(me);
+ Trinity::CreatureListSearcher<Trinity::AllFriendlyCreaturesInGrid> creature_searcher(me, creatures, creature_check);
+ TypeContainerVisitor
+ <Trinity::CreatureListSearcher<Trinity::AllFriendlyCreaturesInGrid>,
+ GridTypeMapContainer> creature_visitor(creature_searcher);
+
+ cell.Visit(pair, creature_visitor, *(me->GetMap()));
+
+ if (!creatures.empty())
+ {
+ for (std::list<Creature*>::const_iterator itr = creatures.begin(); itr != creatures.end(); ++itr)
+ {
+ if ((*itr) && (*itr)->isAlive() && (*itr) != me && (*itr)->GetEntry() != JAINA)
+ {
+ if (!(*itr)->IsWithinDist(me, 60))
+ (*itr)->RemoveUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
+ float x, y, z;
+ (*itr)->SetDefaultMovementType(IDLE_MOTION_TYPE);
+ (*itr)->GetMotionMaster()->Initialize();
+ float range = 10;
+ if (me->GetEntry() == THRALL)range = 20;
+ me->GetNearPoint(me, x, y, z, range, 0, me->GetAngle((*itr)));
+ (*itr)->GetMotionMaster()->MovePoint(0, x+irand(-5,5), y+irand(-5,5), me->GetPositionZ());
+ }
+ }
+ }
+ }
+}
+void hyjalAI::DoOverrun(uint32 faction, const uint32 diff)
+{
+ npc_escortAI::UpdateAI(diff);
+ if (WaitForTeleport)
+ {
+ if (TeleportTimer <= diff)
+ {
+ CellPair pair(Trinity::ComputeCellPair(me->GetPositionX(), me->GetPositionY()));
+ Cell cell(pair);
+ cell.data.Part.reserved = ALL_DISTRICT;
+ cell.SetNoCreate();
+
+ std::list<Creature*> creatures;
+ Trinity::AllFriendlyCreaturesInGrid creature_check(me);
+ Trinity::CreatureListSearcher<Trinity::AllFriendlyCreaturesInGrid> creature_searcher(me, creatures, creature_check);
+ TypeContainerVisitor
+ <Trinity::CreatureListSearcher<Trinity::AllFriendlyCreaturesInGrid>,
+ GridTypeMapContainer> creature_visitor(creature_searcher);
+
+ cell.Visit(pair, creature_visitor, *(me->GetMap()));
+
+ if (!creatures.empty())
+ {
+ for (std::list<Creature*>::const_iterator itr = creatures.begin(); itr != creatures.end(); ++itr)
+ {
+ if ((*itr) && (*itr)->isAlive())
+ {
+ (*itr)->CastSpell(*itr, SPELL_TELEPORT_VISUAL, true);
+ (*itr)->setFaction(35);//make them friendly so mobs won't attack them
+ (*itr)->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ }
+ }
+ DoCast(me, SPELL_TELEPORT_VISUAL);
+ bRetreat = true;
+ RetreatTimer = 1000;
+ }
+
+ WaitForTeleport = false;
+ Teleported = true;
+ }TeleportTimer -= diff;
+ }
+ if (!Teleported)
+ return;
+ Overrun = false;//execute once
+ switch(faction)
+ {
+ case 0://alliance
+ for (uint8 i = 0; i < 92; ++i)//summon fires
+ me->SummonGameObject(FLAMEOBJECT,AllianceFirePos[i][0],AllianceFirePos[i][1],AllianceFirePos[i][2],AllianceFirePos[i][3],AllianceFirePos[i][4],AllianceFirePos[i][5],AllianceFirePos[i][6],AllianceFirePos[i][7],0);
+
+ for (uint8 i = 0; i < 25; ++i)//summon 25 ghouls
+ {
+ uint8 r = rand()%4;
+ Creature* pUnit = me->SummonCreature(GHOUL, AllianceBase[r][0]+irand(-15,15), AllianceBase[r][1]+irand(-15,15), AllianceBase[r][2], 0, TEMPSUMMON_MANUAL_DESPAWN, 2*60*1000);
+ if (pUnit)
+ {
+ CAST_AI(hyjal_trashAI, pUnit->AI())->faction = Faction;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->IsOverrun = true;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->OverrunType = i;
+ pUnit->setActive(true);
+ }
+ }
+ for (uint8 i = 0; i < 3; ++i)//summon 3 abominations
+ {
+ uint8 r = rand()%4;
+ Creature* pUnit = me->SummonCreature(ABOMINATION, AllianceBase[r][0]+irand(-15,15), AllianceBase[r][1]+irand(-15,15), AllianceBase[r][2], 0, TEMPSUMMON_MANUAL_DESPAWN, 2*60*1000);
+ if (pUnit)
+ {
+ CAST_AI(hyjal_trashAI, pUnit->AI())->faction = Faction;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->IsOverrun = true;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->OverrunType = i;
+ pUnit->setActive(true);
+ }
+ }
+ for (uint8 i = 0; i < 5; ++i)//summon 5 gargoyles
+ {
+ Creature* pUnit = me->SummonCreature(GARGOYLE, AllianceOverrunGargPos[i][0], AllianceOverrunGargPos[i][1], AllianceOverrunGargPos[i][2], AllianceOverrunGargPos[i][3], TEMPSUMMON_MANUAL_DESPAWN, 2*60*1000);
+ if (pUnit)
+ {
+ pUnit->SetHomePosition(AllianceOverrunGargPos[i][0], AllianceOverrunGargPos[i][1], AllianceOverrunGargPos[i][2], AllianceOverrunGargPos[i][3]);
+ CAST_AI(hyjal_trashAI, pUnit->AI())->faction = Faction;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->IsOverrun = true;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->OverrunType = i;
+ pUnit->setActive(true);
+ }
+ }
+ break;
+ case 1://horde
+ for (uint8 i = 0; i < 65; ++i)//summon fires
+ me->SummonGameObject(FLAMEOBJECT,HordeFirePos[i][0],HordeFirePos[i][1],HordeFirePos[i][2],HordeFirePos[i][3],HordeFirePos[i][4],HordeFirePos[i][5],HordeFirePos[i][6],HordeFirePos[i][7],0);
+
+ for (uint8 i = 0; i < 26; ++i)//summon infernals
+ {
+ Creature* pUnit = me->SummonCreature(GIANT_INFERNAL, InfernalSPWP[i][0], InfernalSPWP[i][1], InfernalSPWP[i][2], InfernalSPWP[i][3], TEMPSUMMON_MANUAL_DESPAWN, 2*60*1000);
+ if (pUnit)
+ {
+ pUnit->SetHomePosition(InfernalSPWP[i][0], InfernalSPWP[i][1], InfernalSPWP[i][2], InfernalSPWP[i][3]);
+ CAST_AI(hyjal_trashAI, pUnit->AI())->faction = Faction;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->IsOverrun = true;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->OverrunType = i;
+ pUnit->setActive(true);
+ }
+ }
+ for (uint8 i = 0; i < 25; ++i)//summon 25 ghouls
+ {
+ uint8 r = rand()%4;
+ Creature* pUnit = me->SummonCreature(GHOUL, HordeBase[r][0]+irand(-15,15), HordeBase[r][1]+irand(-15,15), HordeBase[r][2], 0, TEMPSUMMON_MANUAL_DESPAWN, 2*60*1000);
+ if (pUnit)
+ {
+ CAST_AI(hyjal_trashAI, pUnit->AI())->faction = Faction;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->IsOverrun = true;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->OverrunType = i;
+ pUnit->setActive(true);
+ }
+ }
+ for (uint8 i = 0; i < 5; ++i)//summon 5 abominations
+ {
+ uint8 r = rand()%4;
+ Creature* pUnit = me->SummonCreature(ABOMINATION, HordeBase[r][0]+irand(-15,15), HordeBase[r][1]+irand(-15,15), HordeBase[r][2], 0, TEMPSUMMON_MANUAL_DESPAWN, 2*60*1000);
+ if (pUnit)
+ {
+ CAST_AI(hyjal_trashAI, pUnit->AI())->faction = Faction;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->IsOverrun = true;
+ CAST_AI(hyjal_trashAI, pUnit->AI())->OverrunType = i;
+ pUnit->setActive(true);
+ }
+ }
+ break;
+ }
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.h b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.h
new file mode 100644
index 00000000000..5c75465b7b4
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjalAI.h
@@ -0,0 +1,248 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software licensed under GPL version 2
+ * Please see the included DOCS/LICENSE.TXT for more information */
+
+#ifndef SC_HYJALAI_H
+#define SC_HYJALAI_H
+
+#include "hyjal.h"
+#include "ScriptedEscortAI.h"
+
+// Trash Mobs summoned in waves
+#define NECROMANCER 17899//done
+#define ABOMINATION 17898//done
+#define GHOUL 17895//done
+#define BANSHEE 17905//done
+#define CRYPT_FIEND 17897//done
+#define GARGOYLE 17906//done
+#define FROST_WYRM 17907//done
+#define GIANT_INFERNAL 17908//done
+#define FEL_STALKER 17916//done
+
+#define JAINA 17772
+#define THRALL 17852
+#define TYRANDE 17948
+
+#define ANCIENT_VEIN 185557
+#define FLAMEOBJECT 182592
+
+// Bosses summoned after every 8 waves
+#define RAGE_WINTERCHILL 17767
+#define ANETHERON 17808
+#define KAZROGAL 17888
+#define AZGALOR 17842
+#define ARCHIMONDE 17968
+
+#define SPELL_TELEPORT_VISUAL 41232
+#define SPELL_MASS_TELEPORT 16807
+
+//Spells for Jaina
+#define SPELL_BRILLIANCE_AURA 31260 // The database must handle this spell via creature_addon(it should, but is removed in evade..)
+#define SPELL_BLIZZARD 31266
+#define SPELL_PYROBLAST 31263
+#define SPELL_SUMMON_ELEMENTALS 31264
+
+//Thrall spells
+#define SPELL_CHAIN_LIGHTNING 31330
+#define SPELL_SUMMON_DIRE_WOLF 31331
+
+struct Wave
+{
+ uint32 Mob[18]; // Stores Creature Entries to be summoned in Waves
+ uint32 WaveTimer; // The timer before the next wave is summoned
+ bool IsBoss; // Simply used to inform the wave summoner that the next wave contains a boss to halt all waves after that
+};
+
+static Wave AllianceWaves[]= // Waves that will be summoned in the Alliance Base
+{ // Rage Winterchill Wave 1-8
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, 0, 0, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, CRYPT_FIEND, CRYPT_FIEND, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, ABOMINATION, ABOMINATION, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 180000, false},
+ // All 8 Waves are summoned, summon Rage Winterchill, next few waves are for Anetheron
+ {RAGE_WINTERCHILL, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, true},
+ // Anetheron Wave 1-8
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, 0, 0, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 0, 0, 120000, false},
+ {NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, BANSHEE, BANSHEE, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, NECROMANCER, NECROMANCER, BANSHEE, BANSHEE, BANSHEE, BANSHEE, 0, 0, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, ABOMINATION, ABOMINATION, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 0, 0, 120000, false},
+ {CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, BANSHEE, BANSHEE, BANSHEE, BANSHEE, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, GHOUL, GHOUL, 0, 0, 0, 0, 120000, false},
+ {GHOUL, GHOUL, GHOUL, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, BANSHEE, BANSHEE, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 180000, false},
+ // All 8 Waves are summoned, summon Anatheron
+ {ANETHERON, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, true}
+};
+
+static Wave HordeWaves[]= // Waves that are summoned in the Horde base
+{ // Kaz'Rogal Wave 1-8
+ {GHOUL, GHOUL, GHOUL, GHOUL, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, BANSHEE, BANSHEE, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 0, 0, 180000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, 0, 0, 0, 0, 180000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 180000, false},
+ {CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 180000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 180000, false},
+ {GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, FROST_WYRM, 0, 0, 0, 0, 0, 0, 0, 0, 0, 180000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, FROST_WYRM, 0, 0, 0, 0, 0, 0, 0, 180000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, CRYPT_FIEND, CRYPT_FIEND, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, BANSHEE, BANSHEE, NECROMANCER, NECROMANCER, 0, 0, 240000, false},
+ // All 8 Waves are summoned, summon Kaz'Rogal, next few waves are for Azgalor
+ {KAZROGAL, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, true},
+ // Azgalor Wave 1-8
+ {ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 0, 0, 180000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, FROST_WYRM, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, GARGOYLE, 0, 0, 0, 0, 180000, false},
+ {GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GHOUL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, 0, 0, 0, 0, 180000, false},
+ {GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, FEL_STALKER, FEL_STALKER, FEL_STALKER, FEL_STALKER, FEL_STALKER, FEL_STALKER, 0, 0, 0, 0, 180000, false},
+ {FEL_STALKER, FEL_STALKER, FEL_STALKER, FEL_STALKER, FEL_STALKER, FEL_STALKER, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, 0, 0, 0, 0, 180000, false},
+ {NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, NECROMANCER, BANSHEE, BANSHEE, BANSHEE, BANSHEE, BANSHEE, BANSHEE, 0, 0, 0, 0, 0, 0, 180000, false},
+ {GHOUL, GHOUL, CRYPT_FIEND, CRYPT_FIEND, FEL_STALKER, FEL_STALKER, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, GIANT_INFERNAL, 0, 0, 0, 0, 180000, false},
+ {CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, CRYPT_FIEND, FEL_STALKER, FEL_STALKER, ABOMINATION, ABOMINATION, ABOMINATION, ABOMINATION, BANSHEE, BANSHEE, BANSHEE, BANSHEE, NECROMANCER, NECROMANCER, 0, 0, 240000, false},
+ // All 8 Waves are summoned, summon Azgalor
+ {AZGALOR, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, true}
+};
+
+enum TargetType // Used in the spell cast system for the AI
+{
+ TARGETTYPE_SELF = 0,
+ TARGETTYPE_RANDOM = 1,
+ TARGETTYPE_VICTIM = 2,
+};
+
+struct Yells
+{
+ uint32 id; // Used to determine the type of yell (attack, rally, etc)
+ int32 textid; // The text id to be yelled
+};
+
+enum YellId
+{
+ ATTACKED = 0, // Used when attacked and set in combat
+ BEGIN = 1, // Used when the event is begun
+ INCOMING = 2, // Used to warn the raid that another wave phase is coming
+ RALLY = 3, // Used to rally the raid and warn that the next wave has been summoned
+ FAILURE = 4, // Used when raid has failed (unsure where to place)
+ SUCCESS = 5, // Used when the raid has sucessfully defeated a wave phase
+ DEATH = 6, // Used on death
+};
+
+static Yells JainaQuotes[]=
+{
+ {ATTACKED, -1534000},
+ {ATTACKED, -1534001},
+ {INCOMING, -1534002},
+ {BEGIN, -1534003},
+ {RALLY, -1534004},
+ {RALLY, -1534005},
+ {FAILURE, -1534006},
+ {SUCCESS, -1534007},
+ {DEATH, -1534008},
+};
+
+static Yells ThrallQuotes[]=
+{
+ {ATTACKED, -1534009},
+ {ATTACKED, -1534010},
+ {INCOMING, -1534011},
+ {BEGIN, -1534012},
+ {RALLY, -1534013},
+ {RALLY, -1534014},
+ {FAILURE, -1534015},
+ {SUCCESS, -1534016},
+ {DEATH, -1534017},
+};
+
+struct hyjalAI : public npc_escortAI
+{
+ hyjalAI(Creature *c);
+
+ void Reset(); // Generically used to reset our variables. Do *not* call in EnterEvadeMode as this may make problems if the raid is still in combat
+
+ void EnterEvadeMode(); // Send creature back to spawn location and evade.
+
+ void EnterCombat(Unit * /*who*/); // Used to reset cooldowns for our spells and to inform the raid that we're under attack
+
+ void UpdateAI(const uint32 diff); // Called to summon waves, check for boss deaths and to cast our spells.
+
+ void JustDied(Unit* /*killer*/); // Called on death, informs the raid that they have failed.
+
+ void SetFaction(uint32 _faction) // Set the faction to either Alliance or Horde in Hyjal
+ {
+ Faction = _faction;
+ }
+
+ void Retreat(); // "Teleport" (teleport visual + set invisible) all friendly creatures away from the base.
+
+ void SpawnVeins();
+ void DeSpawnVeins();
+ void JustSummoned(Creature *summoned);
+ void SummonedCreatureDespawn(Creature* summoned);
+ void HideNearPos(float x, float y);
+ void RespawnNearPos(float x, float y);
+ void WaypointReached(uint32 i);
+ void DoOverrun(uint32 faction, const uint32 diff);
+ void MoveInLineOfSight(Unit *who);
+
+ void SummonCreature(uint32 entry, float Base[4][3]); // Summons a creature for that wave in that base
+
+ // Summons the next wave, calls SummonCreature
+ void SummonNextWave(Wave wave[18], uint32 Count, float Base[4][3]);
+
+ void StartEvent(Player* player); // Begins the event by gossip click
+
+ uint32 GetInstanceData(uint32 Event); // Gets instance data for this instance, used to check if raid has gotten past a certain point and can access the next phase
+
+ void Talk(uint32 id); // Searches for the appropriate yell and sound and uses it to inform the raid of various things
+
+ public:
+ ScriptedInstance* pInstance;
+
+ uint64 PlayerGUID;
+ uint64 BossGUID[2];
+ uint64 VeinGUID[14];
+
+ uint32 NextWaveTimer;
+ uint32 WaveCount;
+ uint32 CheckTimer;
+ uint32 Faction;
+ uint32 EnemyCount;
+ uint32 RetreatTimer;
+
+ bool EventBegun;
+ bool FirstBossDead;
+ bool SecondBossDead;
+ bool Summon;
+ bool bRetreat;
+ bool Debug;
+ bool VeinsSpawned[2];
+ uint8 InfernalCount;
+ SummonList Summons;
+ bool Overrun;
+ bool Teleported;
+ bool WaitForTeleport;
+ uint32 TeleportTimer;
+ uint32 OverrunCounter;
+ uint32 OverrunCounter2;
+ uint32 InfernalPoint;
+ uint32 RespawnTimer;
+ bool DoRespawn;
+ bool DoHide;
+ bool IsDummy;
+ uint32 MassTeleportTimer;
+ bool DoMassTeleport;
+ uint64 DummyGuid;
+
+ struct Spell
+ {
+ uint32 SpellId;
+ uint32 Cooldown;
+ uint32 TargetType;
+ }Spell[3];
+
+ private:
+ uint32 SpellTimer[3];
+ //std::list<uint64> CreatureList;
+};
+#endif
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.cpp b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.cpp
new file mode 100644
index 00000000000..c4cf9ede397
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.cpp
@@ -0,0 +1,1440 @@
+
+#include "ScriptedPch.h"
+#include "hyjal.h"
+#include "hyjal_trash.h"
+#include "hyjalAI.h"
+
+#define SPELL_METEOR 33814 //infernal visual
+#define SPELL_IMMOLATION 37059
+#define SPELL_FLAME_BUFFET 31724
+#define NPC_TRIGGER 21987 //World Trigger (Tiny)
+#define MODEL_INVIS 11686 //invisible model
+
+float HordeWPs[8][3]=//basic waypoints from spawn to leader
+{
+ {5492.91, -2404.61, 1462.63},
+ {5531.76, -2460.87, 1469.55},
+ {5554.58, -2514.66, 1476.12},
+ {5554.16, -2567.23, 1479.90},
+ {5540.67, -2625.99, 1480.89},
+ {5508.16, -2659.20, 1480.15},//random rush starts from here
+ {5489.62, -2704.05, 1482.18},
+ {5457.04, -2726.26, 1485.10}
+};
+float AllianceWPs[8][3]=//basic waypoints from spawn to leader
+{
+ {4896.08, -1576.35, 1333.65},
+ {4898.68, -1615.02, 1329.48},
+ {4907.12, -1667.08, 1321.00},
+ {4963.18, -1699.35, 1340.51},
+ {4989.16, -1716.67, 1335.74},//first WP in the base, after the gate
+ {5026.27, -1736.89, 1323.02},
+ {5037.77, -1770.56, 1324.36},
+ {5067.23, -1789.95, 1321.17}
+};
+
+float FrostWyrmWPs[3][3]=//waypoints for the frost wyrms in horde base
+{
+ {5580.82, -2628.83, 1528.28},
+ {5550.90, -2667.16, 1505.45},
+ {5459.64, -2725.91, 1484.83}
+};
+
+float GargoyleWPs[3][3]=//waypoints for the gargoyles in horde base
+{
+ {5533.66, -2634.32, 1495.33},
+ {5517.88, -2712.05, 1490.54},
+ {5459.64, -2725.91, 1484.83}
+};
+
+float FlyPathWPs[3][3]=//waypoints for the gargoyls and frost wyrms in horde base in wave 1/3
+{
+ {5531.96, -2772.83, 1516.68},
+ {5498.32, -2734.84, 1497.01},
+ {5456.67, -2725.48, 1493.08}
+};
+
+float AllianceOverrunWP[55][3]=//waypoints in the alliance base used in the end in the cleaning wave
+{
+ {4976.37,-1708.02,1339.43},//0spawn
+ {4994.83,-1725.52,1333.25},//1 start
+ {4982.92,-1753.7,1330.69},//2 end
+ {4996.75,-1721.47,1332.95},//3 start
+ {5015.74,-1755.05,1322.49},//4
+ {4998.68,-1773.44,1329.59},//5
+ {4994.83,-1725.52,1333.25},//6 start
+ {5022.8,-1735.46,1323.53},//7
+ {5052.15,-1729.02,1320.88},//8
+ {5082.43,-1726.29,1327.87},//9
+ {4994.83,-1725.52,1333.25},//10 start
+ {5018.92,-1751.14,1322.19},//11
+ {5040.09,-1792.09,1322.1},//12
+ {4994.83,-1725.52,1333.25},//13 start
+ {5023.47,-1748.1,1322.51},//14
+ {5013.43,-1842.39,1322.07},//15
+ {4994.83,-1725.52,1333.25},//16 start
+ {5020.8,-1756.86,1322.2},//17
+ {5019.53,-1824.6,1321.96},//18
+ {5043.42,-1853.75,1324.52},//19
+ {5053.02,-1864.13,1330.36},//20
+ {5062.49,-1852.47,1330.49},//21
+ {5015.27, -1738.77, 1324.83},//35//start 22
+ {5027.97, -1775.25, 1321.87},//34 23
+ {5015.94, -1821.24, 1321.86},//33 24
+ {4983.25, -1857.4, 1320.48},//32 25
+ {4981.51, -1883.7, 1322.34},//31 26
+ {5002.33, -1893.98, 1325.88},//30 27
+ {5049.32, -1886.54, 1331.69},//29 28
+ {5089.68, -1846.88, 1328.99},//28 29
+ {5127.90, -1825.14, 1335.58},//27 30
+ {5163.27, -1789.08, 1337.04},//26 31
+ {5138.97, -1755.88, 1334.57},//25 32
+ {5096.63, -1742.22, 1329.61},//24 33
+ {5065.81, -1729.43, 1325.66},//23 34
+ {5049.32, -1726.31, 1320.64},//22 start
+ {5081.07, -1902.10, 1346.36},//36 abo start
+ {5107.65, -1912.03, 1356.49},//37
+ {5132.83, -1927.07, 1362.42},//38
+ {5147.78, -1954.41, 1365.98},//39
+ {5164.96, -1966.48, 1367.04},//40
+ {5189.04, -1961.06, 1367.90},//41
+ {5212.27, -1975.30, 1365.58},//42
+ {5221.82, -1994.18, 1364.97},//43 end1
+ {5202.23, -1994.94, 1367.59},//44 end2
+ {5279.94, -2049.68, 1311.38},//45 garg1
+ {5289.15, -2219.06, 1291.12},//46 garg2
+ {5202.07, -2136.10, 1305.07},//47 garg3
+ {5071.52, -2425.63, 1454.48},//48 garg4
+ {5120.65, -2467.92, 1463.93},//49 garg5
+ {5283.04, -2043.26, 1300.11},//50 garg target1
+ {5313.22, -2207.60, 1290.06},//51 garg target2
+ {5180.41, -2121.87, 1292.62},//52 garg target3
+ {5088.68, -2432.04, 1441.73},//53 garg target4
+ {5111.26, -2454.73, 1449.63}//54 garg target5
+
+};
+
+float HordeOverrunWP[21][3]=//waypoints in the horde base used in the end in the cleaning wave
+{
+ {5490.72,-2702.94,1482.14},//0 start
+ {5469.77,-2741.34,1486.95},
+ {5439.47,-2771.02,1494.59},
+ {5408.85,-2811.92,1505.68},
+ {5423.87,-2857.80,1515.55},
+ {5428.19,-2898.15,1524.61},
+ {5394.59,-2930.05,1528.23},
+ {5351.11,-2935.80,1532.24},
+ {5312.37,-2959.06,1536.21},
+ {5264.93,-2989.80,1545.70},
+ {5256.63,-3056.16,1559.24},
+ {5267.32,-3119.55,1575.36},
+ {5305.61,-3139.88,1586.38},
+ {5330.56,-3135.37,1588.58},
+ {5365.87,-3139.78,1583.96},
+ {5389.39,-3163.57,1582.57},//15 end
+ {5500.86,-2669.89,1481.04},//16 start
+ {5472.08,-2715.14,1483.55},
+ {5450.11,-2721.47,1485.61},
+ {5433.25,-2712.93,1493.02},//19 end 1
+ {5429.91,-2718.44,1493.42}//20 end 2
+};
+
+hyjal_trashAI::hyjal_trashAI(Creature *c) : npc_escortAI(c)
+{
+ pInstance = c->GetInstanceData();
+ IsEvent = false;
+ Delay = 0;
+ LastOverronPos = 0;
+ IsOverrun = false;
+ OverrunType = 0;
+ SetupOverrun = false;
+ faction = 0;
+ useFlyPath = false;
+ damageTaken = 0;
+ Reset();
+}
+
+void hyjal_trashAI::DamageTaken(Unit *done_by, uint32 &damage)
+{
+ if (done_by->GetTypeId() == TYPEID_PLAYER || (done_by->GetTypeId() == TYPEID_UNIT && CAST_CRE(done_by)->isPet()))
+ {
+ damageTaken += damage;
+ if (pInstance)
+ pInstance->SetData(DATA_RAIDDAMAGE,damage);//store raid's damage
+ }
+}
+
+void hyjal_trashAI::UpdateAI(const uint32 /*diff*/)
+{
+ if (IsOverrun && !SetupOverrun)
+ {
+ SetupOverrun = true;
+ if (faction == 0)
+ {
+ if (me->GetEntry() == GARGOYLE)
+ {
+ DummyTarget[0] = AllianceOverrunWP[50+OverrunType][0]; //+OverrunType 0 - 4
+ DummyTarget[1] = AllianceOverrunWP[50+OverrunType][1];
+ DummyTarget[2] = AllianceOverrunWP[50+OverrunType][2];
+ }
+ if (me->GetEntry() == ABOMINATION)
+ {
+ for (uint8 i = 0; i < 4; ++i)
+ AddWaypoint(i, AllianceWPs[i][0]+irand(-3,3), AllianceWPs[i][1]+irand(-3,3), AllianceWPs[i][2]);
+ switch(OverrunType)
+ {
+ case 0:
+ AddWaypoint(4, AllianceOverrunWP[22][0]+irand(-3,3), AllianceOverrunWP[22][1]+irand(-3,3), AllianceOverrunWP[22][2]);
+ AddWaypoint(5, AllianceOverrunWP[23][0]+irand(-3,3), AllianceOverrunWP[23][1]+irand(-3,3), AllianceOverrunWP[23][2]);
+ AddWaypoint(6, AllianceOverrunWP[24][0]+irand(-3,3), AllianceOverrunWP[24][1]+irand(-3,3), AllianceOverrunWP[24][2]);
+ AddWaypoint(7, AllianceOverrunWP[25][0]+irand(-3,3), AllianceOverrunWP[25][1]+irand(-3,3), AllianceOverrunWP[25][2]);
+ AddWaypoint(8, AllianceOverrunWP[26][0]+irand(-3,3), AllianceOverrunWP[26][1]+irand(-3,3), AllianceOverrunWP[26][2]);
+ AddWaypoint(9, AllianceOverrunWP[27][0]+irand(-3,3), AllianceOverrunWP[27][1]+irand(-3,3), AllianceOverrunWP[27][2]);
+ AddWaypoint(10, AllianceOverrunWP[28][0]+irand(-3,3), AllianceOverrunWP[28][1]+irand(-3,3), AllianceOverrunWP[28][2]);
+
+ AddWaypoint(11, AllianceOverrunWP[36][0]+irand(-3,3), AllianceOverrunWP[36][1]+irand(-3,3), AllianceOverrunWP[36][2]);
+ AddWaypoint(12, AllianceOverrunWP[37][0]+irand(-3,3), AllianceOverrunWP[37][1]+irand(-3,3), AllianceOverrunWP[37][2]);
+ AddWaypoint(13, AllianceOverrunWP[38][0]+irand(-3,3), AllianceOverrunWP[38][1]+irand(-3,3), AllianceOverrunWP[38][2]);
+ AddWaypoint(14, AllianceOverrunWP[39][0]+irand(-3,3), AllianceOverrunWP[39][1]+irand(-3,3), AllianceOverrunWP[39][2]);
+ AddWaypoint(15, AllianceOverrunWP[40][0]+irand(-3,3), AllianceOverrunWP[40][1]+irand(-3,3), AllianceOverrunWP[40][2]);
+ AddWaypoint(16, AllianceOverrunWP[41][0]+irand(-3,3), AllianceOverrunWP[41][1]+irand(-3,3), AllianceOverrunWP[41][2]);
+ AddWaypoint(17, AllianceOverrunWP[42][0]+irand(-3,3), AllianceOverrunWP[42][1]+irand(-3,3), AllianceOverrunWP[42][2]);
+ AddWaypoint(18, AllianceOverrunWP[43][0]+irand(-3,3), AllianceOverrunWP[43][1]+irand(-3,3), AllianceOverrunWP[43][2]);
+ me->SetHomePosition(AllianceOverrunWP[43][0]+irand(-3,3), AllianceOverrunWP[43][1]+irand(-3,3), AllianceOverrunWP[43][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 18;
+ Start(true, true);
+ break;
+ case 1:
+ AddWaypoint(4, AllianceOverrunWP[22][0]+irand(-3,3), AllianceOverrunWP[22][1]+irand(-3,3), AllianceOverrunWP[22][2]);
+ AddWaypoint(5, AllianceOverrunWP[23][0]+irand(-3,3), AllianceOverrunWP[23][1]+irand(-3,3), AllianceOverrunWP[23][2]);
+ AddWaypoint(6, AllianceOverrunWP[24][0]+irand(-3,3), AllianceOverrunWP[24][1]+irand(-3,3), AllianceOverrunWP[24][2]);
+ AddWaypoint(7, AllianceOverrunWP[25][0]+irand(-3,3), AllianceOverrunWP[25][1]+irand(-3,3), AllianceOverrunWP[25][2]);
+ AddWaypoint(8, AllianceOverrunWP[26][0]+irand(-3,3), AllianceOverrunWP[26][1]+irand(-3,3), AllianceOverrunWP[26][2]);
+ AddWaypoint(9, AllianceOverrunWP[27][0]+irand(-3,3), AllianceOverrunWP[27][1]+irand(-3,3), AllianceOverrunWP[27][2]);
+ AddWaypoint(10, AllianceOverrunWP[28][0]+irand(-3,3), AllianceOverrunWP[28][1]+irand(-3,3), AllianceOverrunWP[28][2]);
+
+ AddWaypoint(11, AllianceOverrunWP[36][0]+irand(-3,3), AllianceOverrunWP[36][1]+irand(-3,3), AllianceOverrunWP[36][2]);
+ AddWaypoint(12, AllianceOverrunWP[37][0]+irand(-3,3), AllianceOverrunWP[37][1]+irand(-3,3), AllianceOverrunWP[37][2]);
+ AddWaypoint(13, AllianceOverrunWP[38][0]+irand(-3,3), AllianceOverrunWP[38][1]+irand(-3,3), AllianceOverrunWP[38][2]);
+ AddWaypoint(14, AllianceOverrunWP[39][0]+irand(-3,3), AllianceOverrunWP[39][1]+irand(-3,3), AllianceOverrunWP[39][2]);
+ AddWaypoint(15, AllianceOverrunWP[40][0]+irand(-3,3), AllianceOverrunWP[40][1]+irand(-3,3), AllianceOverrunWP[40][2]);
+ AddWaypoint(16, AllianceOverrunWP[41][0]+irand(-3,3), AllianceOverrunWP[41][1]+irand(-3,3), AllianceOverrunWP[41][2]);
+ AddWaypoint(17, AllianceOverrunWP[42][0]+irand(-3,3), AllianceOverrunWP[42][1]+irand(-3,3), AllianceOverrunWP[42][2]);
+ AddWaypoint(18, AllianceOverrunWP[44][0]+irand(-3,3), AllianceOverrunWP[44][1]+irand(-3,3), AllianceOverrunWP[44][2]);
+ me->SetHomePosition(AllianceOverrunWP[44][0]+irand(-3,3), AllianceOverrunWP[44][1]+irand(-3,3), AllianceOverrunWP[44][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 18;
+ Start(true, true);
+ break;
+ default:
+ for (uint8 i = 22; i < 36; ++i)
+ AddWaypoint(i-18, AllianceOverrunWP[i][0]+irand(-3,3), AllianceOverrunWP[i][1]+irand(-3,3), AllianceOverrunWP[i][2]);
+
+ SetDespawnAtEnd(true);
+ LastOverronPos = 17;
+ Start(true, true);
+ break;
+ }
+ }
+ if (me->GetEntry() == GHOUL)
+ {
+ for (uint8 i = 0; i < 4; ++i)
+ AddWaypoint(i, AllianceWPs[i][0]+irand(-3,3), AllianceWPs[i][1]+irand(-3,3), AllianceWPs[i][2]);
+ switch(OverrunType)
+ {
+ case 0:
+ AddWaypoint(4, AllianceOverrunWP[1][0]+irand(-3,3), AllianceOverrunWP[1][1]+irand(-3,3), AllianceOverrunWP[1][2]);
+ AddWaypoint(5, AllianceOverrunWP[2][0]+irand(-3,3), AllianceOverrunWP[2][1]+irand(-3,3), AllianceOverrunWP[2][2]);
+ me->SetHomePosition(AllianceOverrunWP[2][0]+irand(-3,3), AllianceOverrunWP[2][1]+irand(-3,3), AllianceOverrunWP[2][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 5;
+ Start(true, true);
+ break;
+ case 1:
+ AddWaypoint(4, AllianceOverrunWP[3][0]+irand(-3,3), AllianceOverrunWP[3][1]+irand(-3,3), AllianceOverrunWP[3][2]);
+ AddWaypoint(5, AllianceOverrunWP[4][0]+irand(-3,3), AllianceOverrunWP[4][1]+irand(-3,3), AllianceOverrunWP[4][2]);
+ AddWaypoint(6, AllianceOverrunWP[5][0]+irand(-3,3), AllianceOverrunWP[5][1]+irand(-3,3), AllianceOverrunWP[5][2]);
+ me->SetHomePosition(AllianceOverrunWP[5][0]+irand(-3,3), AllianceOverrunWP[5][1]+irand(-3,3), AllianceOverrunWP[5][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 6;
+ Start(true, true);
+ break;
+ case 2:
+ AddWaypoint(4, AllianceOverrunWP[6][0]+irand(-3,3), AllianceOverrunWP[6][1]+irand(-3,3), AllianceOverrunWP[6][2]);
+ AddWaypoint(5, AllianceOverrunWP[7][0]+irand(-3,3), AllianceOverrunWP[7][1]+irand(-3,3), AllianceOverrunWP[7][2]);
+ AddWaypoint(6, AllianceOverrunWP[8][0]+irand(-3,3), AllianceOverrunWP[8][1]+irand(-3,3), AllianceOverrunWP[8][2]);
+ AddWaypoint(7, AllianceOverrunWP[9][0]+irand(-3,3), AllianceOverrunWP[9][1]+irand(-3,3), AllianceOverrunWP[9][2]);
+ me->SetHomePosition(AllianceOverrunWP[9][0]+irand(-3,3), AllianceOverrunWP[9][1]+irand(-3,3), AllianceOverrunWP[9][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 7;
+ Start(true, true);
+ break;
+ case 3:
+ AddWaypoint(4, AllianceOverrunWP[10][0]+irand(-3,3), AllianceOverrunWP[10][1]+irand(-3,3), AllianceOverrunWP[10][2]);
+ AddWaypoint(5, AllianceOverrunWP[11][0]+irand(-3,3), AllianceOverrunWP[11][1]+irand(-3,3), AllianceOverrunWP[11][2]);
+ AddWaypoint(6, AllianceOverrunWP[12][0]+irand(-3,3), AllianceOverrunWP[12][1]+irand(-3,3), AllianceOverrunWP[12][2]);
+ me->SetHomePosition(AllianceOverrunWP[12][0]+irand(-3,3), AllianceOverrunWP[12][1]+irand(-3,3), AllianceOverrunWP[12][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 6;
+ Start(true, true);
+ break;
+ case 4:
+ AddWaypoint(4, AllianceOverrunWP[13][0]+irand(-3,3), AllianceOverrunWP[13][1]+irand(-3,3), AllianceOverrunWP[13][2]);
+ AddWaypoint(5, AllianceOverrunWP[14][0]+irand(-3,3), AllianceOverrunWP[14][1]+irand(-3,3), AllianceOverrunWP[14][2]);
+ AddWaypoint(6, AllianceOverrunWP[15][0]+irand(-3,3), AllianceOverrunWP[15][1]+irand(-3,3), AllianceOverrunWP[15][2]);
+ me->SetHomePosition(AllianceOverrunWP[15][0]+irand(-3,3), AllianceOverrunWP[15][1]+irand(-3,3), AllianceOverrunWP[15][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 6;
+ Start(true, true);
+ break;
+ case 5:
+ AddWaypoint(4, AllianceOverrunWP[16][0]+irand(-3,3), AllianceOverrunWP[16][1]+irand(-3,3), AllianceOverrunWP[16][2]);
+ AddWaypoint(5, AllianceOverrunWP[17][0]+irand(-3,3), AllianceOverrunWP[17][1]+irand(-3,3), AllianceOverrunWP[17][2]);
+ AddWaypoint(6, AllianceOverrunWP[18][0]+irand(-3,3), AllianceOverrunWP[18][1]+irand(-3,3), AllianceOverrunWP[18][2]);
+ AddWaypoint(7, AllianceOverrunWP[19][0]+irand(-3,3), AllianceOverrunWP[19][1]+irand(-3,3), AllianceOverrunWP[19][2]);
+ AddWaypoint(8, AllianceOverrunWP[20][0]+irand(-3,3), AllianceOverrunWP[20][1]+irand(-3,3), AllianceOverrunWP[20][2]);
+ AddWaypoint(9, AllianceOverrunWP[21][0]+irand(-3,3), AllianceOverrunWP[21][1]+irand(-3,3), AllianceOverrunWP[21][2]);
+ me->SetHomePosition(AllianceOverrunWP[21][0]+irand(-3,3), AllianceOverrunWP[21][1]+irand(-3,3), AllianceOverrunWP[21][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 9;
+ Start(true, true);
+ break;
+ default:
+ for (uint8 i = 22; i < 36; ++i)
+ AddWaypoint(i-18, AllianceOverrunWP[i][0]+irand(-3,3), AllianceOverrunWP[i][1]+irand(-3,3), AllianceOverrunWP[i][2]);
+ SetDespawnAtEnd(true);
+ LastOverronPos = 17;
+ Start(true, true);
+ break;
+ }
+ }
+ }
+ if (faction == 1)
+ {
+ if (me->GetEntry() == GHOUL)
+ {
+ for (uint8 i = 0; i < 6; ++i)
+ AddWaypoint(i, HordeWPs[i][0]+irand(-3,3), HordeWPs[i][1]+irand(-3,3), HordeWPs[i][2]);
+ switch(OverrunType)
+ {
+ case 0:
+ AddWaypoint(5, HordeOverrunWP[16][0]+irand(-10,10), HordeOverrunWP[16][1]+irand(-10,10), HordeOverrunWP[16][2]);
+ AddWaypoint(6, HordeOverrunWP[17][0]+irand(-10,10), HordeOverrunWP[17][1]+irand(-10,10), HordeOverrunWP[17][2]);
+ AddWaypoint(7, HordeOverrunWP[18][0], HordeOverrunWP[18][1], HordeOverrunWP[18][2]);
+ AddWaypoint(8, HordeOverrunWP[19][0], HordeOverrunWP[19][1], HordeOverrunWP[19][2]);
+ me->SetHomePosition(HordeOverrunWP[19][0], HordeOverrunWP[19][1], HordeOverrunWP[19][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 8;
+ Start(true, true);
+ break;
+ case 1:
+ AddWaypoint(5, HordeOverrunWP[16][0]+irand(-10,10), HordeOverrunWP[16][1]+irand(-10,10), HordeOverrunWP[16][2]);
+ AddWaypoint(6, HordeOverrunWP[17][0]+irand(-10,10), HordeOverrunWP[17][1]+irand(-10,10), HordeOverrunWP[17][2]);
+ AddWaypoint(7, HordeOverrunWP[18][0], HordeOverrunWP[18][1], HordeOverrunWP[18][2]);
+ AddWaypoint(8, HordeOverrunWP[20][0], HordeOverrunWP[20][1], HordeOverrunWP[20][2]);
+ me->SetHomePosition(HordeOverrunWP[20][0], HordeOverrunWP[20][1], HordeOverrunWP[20][2],0);
+ SetDespawnAtEnd(false);
+ LastOverronPos = 8;
+ Start(true, true);
+ break;
+ default:
+ for (uint8 i = 0; i < 16; ++i)
+ AddWaypoint(i+6, HordeOverrunWP[i][0]+irand(-10,10), HordeOverrunWP[i][1]+irand(-10,10), HordeOverrunWP[i][2]);
+ SetDespawnAtEnd(true);
+ LastOverronPos = 21;
+ Start(true, true);
+ break;
+ }
+ }
+ if (me->GetEntry() == ABOMINATION)
+ {
+ for (uint8 i = 0; i < 6; ++i)
+ AddWaypoint(i, HordeWPs[i][0]+irand(-10,10), HordeWPs[i][1]+irand(-10,10), HordeWPs[i][2]);
+ for (uint8 i = 0; i < 16; ++i)
+ AddWaypoint(i+6, HordeOverrunWP[i][0]+irand(-10,10), HordeOverrunWP[i][1]+irand(-10,10), HordeOverrunWP[i][2]);
+ SetDespawnAtEnd(true);
+ LastOverronPos = 21;
+ Start(true, true);
+ }
+ }
+ }
+}
+
+void hyjal_trashAI::JustDied(Unit * /*victim*/)
+{
+ if (!pInstance)
+ return;
+ if (IsEvent && !me->isWorldBoss())
+ pInstance->SetData(DATA_TRASH, 0);//signal trash is dead
+
+ if ((pInstance->GetData(DATA_RAIDDAMAGE) < MINRAIDDAMAGE && !me->isWorldBoss()) || (damageTaken < me->GetMaxHealth()/4 && me->isWorldBoss()))
+ me->RemoveFlag(UNIT_DYNAMIC_FLAGS, UNIT_DYNFLAG_LOOTABLE);//no loot
+}
+
+struct mob_giant_infernalAI : public hyjal_trashAI
+{
+ mob_giant_infernalAI(Creature* c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ meteor = false;//call once!
+ CanMove = false;
+ Delay = rand()%30000;
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ me->SetDisplayId(MODEL_INVIS);
+ pGo = false;
+ pos = 0;
+ Reset();
+ }
+
+ bool meteor;
+ bool CanMove;
+ bool WpEnabled;
+ bool pGo;
+ uint32 pos;
+ uint32 spawnTimer;
+ uint32 FlameBuffetTimer;
+ bool imol;
+
+ void Reset()
+ {
+ spawnTimer = 2000;
+ FlameBuffetTimer= 2000;
+ imol = false;
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 0 && pInstance && !IsOverrun)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, attack thrall
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (Delay <= diff)
+ {
+ Delay=0;
+ }else{
+ Delay-=diff;
+ return;
+ }
+ if (!meteor)
+ {
+ float x,y,z;
+ me->GetPosition(x,y,z);
+ Creature* trigger = me->SummonCreature(NPC_TRIGGER,x+8,y+8,z+25+rand()%10,me->GetOrientation(),TEMPSUMMON_TIMED_DESPAWN,1000);
+ if (trigger)
+ {
+ trigger->SetVisibility(VISIBILITY_OFF);
+ trigger->setFaction(me->getFaction());
+ trigger->AddUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
+ trigger->CastSpell(me,SPELL_METEOR,true);
+ }
+ me->GetMotionMaster()->Clear();
+ meteor = true;
+ } else if (!CanMove){
+ if (spawnTimer <= diff)
+ {
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ me->SetDisplayId(me->GetUInt32Value(UNIT_FIELD_NATIVEDISPLAYID));
+ CanMove = true;
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT) && !pInstance->GetData(DATA_HORDE_RETREAT))
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ } else if (pInstance->GetData(DATA_ALLIANCE_RETREAT) && pInstance->GetData(DATA_HORDE_RETREAT)){
+ //do overrun
+ }
+ }
+ } else spawnTimer -= diff;
+ }
+ if (!CanMove)return;
+ hyjal_trashAI::UpdateAI(diff);
+ if (IsEvent || IsOverrun)
+ npc_escortAI::UpdateAI(diff);
+ if (IsEvent)
+ {
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ AddWaypoint(0, HordeWPs[7][0]+irand(-3,3), HordeWPs[7][1]+irand(-3,3), HordeWPs[7][2]);//HordeWPs[7] infront of thrall
+ Start(true, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+
+ if (!UpdateVictim())
+ return;
+ if (!imol)
+ {
+ DoCast(me, SPELL_IMMOLATION);
+ imol=true;
+ }
+ if (FlameBuffetTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_FLAME_BUFFET, true);
+ FlameBuffetTimer = 7000;
+ } else FlameBuffetTimer -= diff;
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_mob_giant_infernal(Creature* pCreature)
+{
+ return new mob_giant_infernalAI(pCreature);
+}
+
+#define SPELL_DISEASE_CLOUD 31607
+#define SPELL_KNOCKDOWN 31610
+
+struct mob_abominationAI : public hyjal_trashAI
+{
+ mob_abominationAI(Creature* c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ Reset();
+ }
+
+ bool pGo;
+ uint32 KnockDownTimer;
+ uint32 pos;
+ void Reset()
+ {
+ KnockDownTimer = 10000;
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance && !IsOverrun)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, attack thrall
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }else{
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_JAINAPROUDMOORE));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+ if (i == LastOverronPos && IsOverrun)
+ {
+ if ((faction == 0 && LastOverronPos == 17) || (faction == 1 && LastOverronPos == 21))
+ {
+ me->setDeathState(DEAD);
+ me->RemoveCorpse();
+ }
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ hyjal_trashAI::UpdateAI(diff);
+ if (IsEvent || IsOverrun)
+ npc_escortAI::UpdateAI(diff);
+ if (IsEvent)
+ {
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, use horde WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, HordeWPs[i][0]+irand(-3,3), HordeWPs[i][1]+irand(-3,3), HordeWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }else//use alliance WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, AllianceWPs[i][0]+irand(-3,3), AllianceWPs[i][1]+irand(-3,3), AllianceWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+ }
+ if (!me->HasAura(SPELL_DISEASE_CLOUD))
+ DoCast(me, SPELL_DISEASE_CLOUD);
+ if (!UpdateVictim())
+ return;
+ if (KnockDownTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_KNOCKDOWN);
+ KnockDownTimer = 15000+rand()%10000;
+ } else KnockDownTimer -= diff;
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_mob_abomination(Creature* pCreature)
+{
+ return new mob_abominationAI(pCreature);
+}
+
+#define SPELL_FRENZY 31540
+
+struct mob_ghoulAI : public hyjal_trashAI
+{
+ mob_ghoulAI(Creature* c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ Reset();
+ }
+
+ bool pGo;
+ uint32 FrenzyTimer;
+ uint32 pos;
+ uint32 MoveTimer;
+ bool RandomMove;
+ void Reset()
+ {
+ FrenzyTimer = 5000+rand()%5000;
+ MoveTimer = 2000;
+ RandomMove = false;
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance && !IsOverrun)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, attack thrall
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }else{
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_JAINAPROUDMOORE));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+ if (i == LastOverronPos && IsOverrun)
+ {
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_ONESHOT_ATTACKUNARMED);
+ if ((faction == 0 && LastOverronPos == 17) || (faction == 1 && LastOverronPos == 21))
+ {
+ me->setDeathState(DEAD);
+ me->RemoveCorpse();
+ }
+
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ hyjal_trashAI::UpdateAI(diff);
+ if (IsEvent || IsOverrun)
+ npc_escortAI::UpdateAI(diff);
+ if (IsEvent)
+ {
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, use horde WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, HordeWPs[i][0]+irand(-3,3), HordeWPs[i][1]+irand(-3,3), HordeWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }else//use alliance WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, AllianceWPs[i][0]+irand(-3,3), AllianceWPs[i][1]+irand(-3,3), AllianceWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+ }
+ if (FrenzyTimer <= diff)
+ {
+ DoCast(me, SPELL_FRENZY);
+ FrenzyTimer = 15000+rand()%15000;
+ } else FrenzyTimer -= diff;
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_mob_ghoul(Creature* pCreature)
+{
+ return new mob_ghoulAI(pCreature);
+}
+
+#define SPELL_RAISE_DEAD_1 31617
+#define SPELL_RAISE_DEAD_2 31624
+#define SPELL_RAISE_DEAD_3 31625
+#define SPELL_SHADOW_BOLT 31627
+
+struct mob_necromancerAI : public hyjal_trashAI
+{
+ mob_necromancerAI(Creature* c) : hyjal_trashAI(c), summons(me)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ Reset();
+ }
+ SummonList summons;
+ bool pGo;
+ uint32 ShadowBoltTimer;
+ uint32 pos;
+ void Reset()
+ {
+ ShadowBoltTimer = 1000+rand()%5000;
+ summons.DespawnAll();
+ }
+
+ void JustSummoned(Creature* summon)
+ {
+ Unit *pTarget = SelectTarget(SELECT_TARGET_RANDOM,0,30,true);
+ if (pTarget && summon)
+ summon->Attack(pTarget,false);
+ summons.Summon(summon);
+ }
+ void SummonedCreatureDespawn(Creature *summon) {summons.Despawn(summon);}
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance && !IsOverrun)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, attack thrall
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }else{
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_JAINAPROUDMOORE));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+ }
+
+ void KilledUnit(Unit* /*victim*/)
+ {
+ switch (urand(0,2))
+ {
+ case 0:
+ DoSpawnCreature(17902,3,0,0,0,TEMPSUMMON_TIMED_DESPAWN, 60000);
+ DoSpawnCreature(17902,-3,0,0,0,TEMPSUMMON_TIMED_DESPAWN, 60000);
+ break;
+ case 1:
+ DoSpawnCreature(17903,3,0,0,0,TEMPSUMMON_TIMED_DESPAWN, 60000);
+ DoSpawnCreature(17903,-3,0,0,0,TEMPSUMMON_TIMED_DESPAWN, 60000);
+ break;
+ case 2:
+ DoSpawnCreature(RAND(17902,17903),3,0,0,0,TEMPSUMMON_TIMED_DESPAWN, 60000);
+ break;
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ hyjal_trashAI::UpdateAI(diff);
+ if (IsEvent || IsOverrun)
+ npc_escortAI::UpdateAI(diff);
+ if (IsEvent)
+ {
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, use horde WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, HordeWPs[i][0]+irand(-3,3), HordeWPs[i][1]+irand(-3,3), HordeWPs[i][2]);
+ Start(true, true);
+ SetDespawnAtEnd(false);
+ }else//use alliance WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, AllianceWPs[i][0]+irand(-3,3), AllianceWPs[i][1]+irand(-3,3), AllianceWPs[i][2]);
+ Start(true, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+ }
+ if (!UpdateVictim())
+ return;
+ if (ShadowBoltTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_SHADOW_BOLT);
+ ShadowBoltTimer = 20000+rand()%10000;
+ } else ShadowBoltTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_mob_necromancer(Creature* pCreature)
+{
+ return new mob_necromancerAI(pCreature);
+}
+
+#define SPELL_BANSHEE_CURSE 31651
+#define SPELL_BANSHEE_WAIL 38183
+#define SPELL_ANTI_MAGIC_SHELL 31662
+
+struct mob_bansheeAI : public hyjal_trashAI
+{
+ mob_bansheeAI(Creature* c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ Reset();
+ }
+
+ bool pGo;
+ uint32 CourseTimer;
+ uint32 WailTimer;
+ uint32 ShellTimer;
+ uint32 pos;
+ void Reset()
+ {
+ CourseTimer = 20000+rand()%5000;
+ WailTimer = 15000+rand()%5000;
+ ShellTimer = 50000+rand()%10000;
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance && !IsOverrun)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, attack thrall
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }else{
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_JAINAPROUDMOORE));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ hyjal_trashAI::UpdateAI(diff);
+ if (IsEvent || IsOverrun)
+ npc_escortAI::UpdateAI(diff);
+ if (IsEvent)
+ {
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, use horde WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, HordeWPs[i][0]+irand(-3,3), HordeWPs[i][1]+irand(-3,3), HordeWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }else//use alliance WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, AllianceWPs[i][0]+irand(-3,3), AllianceWPs[i][1]+irand(-3,3), AllianceWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+ }
+ if (!UpdateVictim())
+ return;
+ if (CourseTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_BANSHEE_CURSE);
+ CourseTimer = 20000+rand()%5000;
+ } else CourseTimer -= diff;
+ if (WailTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_BANSHEE_WAIL);
+ WailTimer = 15000+rand()%5000;
+ } else WailTimer -= diff;
+ if (ShellTimer <= diff)
+ {
+ DoCast(me, SPELL_ANTI_MAGIC_SHELL);
+ ShellTimer = 50000+rand()%10000;
+ } else ShellTimer -= diff;
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_mob_banshee(Creature* pCreature)
+{
+ return new mob_bansheeAI(pCreature);
+}
+
+#define SPELL_WEB 28991
+
+struct mob_crypt_fiendAI : public hyjal_trashAI
+{
+ mob_crypt_fiendAI(Creature* c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ Reset();
+ }
+
+ bool pGo;
+ uint32 WebTimer;
+ uint32 pos;
+ void Reset()
+ {
+ WebTimer = 20000+rand()%5000;
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance && !IsOverrun)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, attack thrall
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }else{
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_JAINAPROUDMOORE));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ hyjal_trashAI::UpdateAI(diff);
+ if (IsEvent || IsOverrun)
+ npc_escortAI::UpdateAI(diff);
+ if (IsEvent)
+ {
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, use horde WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, HordeWPs[i][0]+irand(-3,3), HordeWPs[i][1]+irand(-3,3), HordeWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }else//use alliance WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, AllianceWPs[i][0]+irand(-3,3), AllianceWPs[i][1]+irand(-3,3), AllianceWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+
+ }
+ }
+ }
+ if (!UpdateVictim())
+ return;
+ if (WebTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_WEB);
+ WebTimer = 20000+rand()%5000;
+ } else WebTimer -= diff;
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_mob_crypt_fiend(Creature* pCreature)
+{
+ return new mob_crypt_fiendAI(pCreature);
+}
+
+#define SPELL_MANA_BURN 31729
+
+struct mob_fel_stalkerAI : public hyjal_trashAI
+{
+ mob_fel_stalkerAI(Creature* c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ Reset();
+ }
+
+ bool pGo;
+ uint32 ManaBurnTimer;
+ uint32 pos;
+ void Reset()
+ {
+ ManaBurnTimer = 9000+rand()%5000;
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 7 && pInstance && !IsOverrun)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, attack thrall
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }else{
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_JAINAPROUDMOORE));
+ if (pTarget && pTarget->isAlive())
+ me->AddThreat(pTarget,0.0);
+ }
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ hyjal_trashAI::UpdateAI(diff);
+ if (IsEvent || IsOverrun)
+ npc_escortAI::UpdateAI(diff);
+ if (IsEvent)
+ {
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_ALLIANCE_RETREAT))//2.alliance boss down, use horde WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, HordeWPs[i][0]+irand(-3,3), HordeWPs[i][1]+irand(-3,3), HordeWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }else//use alliance WPs
+ {
+ for (uint8 i = 0; i < 8; ++i)
+ AddWaypoint(i, AllianceWPs[i][0]+irand(-3,3), AllianceWPs[i][1]+irand(-3,3), AllianceWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+
+ }
+ }
+ }
+ if (!UpdateVictim())
+ return;
+ if (ManaBurnTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_MANA_BURN);
+ ManaBurnTimer = 9000+rand()%5000;
+ } else ManaBurnTimer -= diff;
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_mob_fel_stalker(Creature* pCreature)
+{
+ return new mob_fel_stalkerAI(pCreature);
+}
+
+#define SPELL_FROST_BREATH 31688
+
+struct mob_frost_wyrmAI : public hyjal_trashAI
+{
+ mob_frost_wyrmAI(Creature* c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ Reset();
+ }
+
+ bool pGo;
+ uint32 FrostBreathTimer;
+ uint32 pos;
+ uint32 MoveTimer;
+
+ void Reset()
+ {
+ FrostBreathTimer = 5000;
+ MoveTimer = 0;
+ me->AddUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 2 && pInstance && !IsOverrun)
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ {
+ me->AddThreat(pTarget,0.0);
+ DoCast(pTarget, SPELL_FROST_BREATH, true);
+ }
+ }
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ if (pInstance && IsEvent)
+ pInstance->SetData(DATA_TRASH, 0);//signal trash is dead
+
+ float x,y,z;
+ me->GetPosition(x,y,z);
+ z = me->GetMap()->GetHeight(x, y, z);
+ me->GetMotionMaster()->MovePoint(0,x,y,z);
+ me->GetMap()->CreatureRelocation(me, x,y,z,0);
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ hyjal_trashAI::UpdateAI(diff);
+ if (IsEvent || IsOverrun)
+ {
+ CAST_AI(hyjal_trashAI, me->AI())->SetCanAttack(false);
+ npc_escortAI::UpdateAI(diff);
+ }
+ if (IsEvent)
+ {
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ if (!useFlyPath)
+ {
+ for (uint8 i = 0; i < 3; ++i)
+ AddWaypoint(i, FrostWyrmWPs[i][0], FrostWyrmWPs[i][1], FrostWyrmWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }else{//fly path FlyPathWPs
+ for (uint8 i = 0; i < 3; ++i)
+ AddWaypoint(i, FlyPathWPs[i][0]+irand(-10,10), FlyPathWPs[i][1]+irand(-10,10), FlyPathWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+ }
+ if (!UpdateVictim())
+ return;
+ if (!me->IsWithinDist(me->getVictim(), 25)){
+ if (MoveTimer <= diff)
+ {
+ me->GetMotionMaster()->MoveChase(me->getVictim());
+ MoveTimer = 2000;
+ } else MoveTimer-=diff;
+ }
+
+ if (FrostBreathTimer <= diff)
+ {
+ if (!me->IsWithinDist(me->getVictim(), 25))
+ {
+ DoCast(me->getVictim(), SPELL_FROST_BREATH);
+ me->StopMoving();
+ me->GetMotionMaster()->Clear();
+ FrostBreathTimer = 4000;
+ }
+ } else FrostBreathTimer -= diff;
+ }
+};
+
+CreatureAI* GetAI_mob_frost_wyrm(Creature* pCreature)
+{
+ return new mob_frost_wyrmAI(pCreature);
+}
+
+#define SPELL_GARGOYLE_STRIKE 31664
+
+struct mob_gargoyleAI : public hyjal_trashAI
+{
+ mob_gargoyleAI(Creature* c) : hyjal_trashAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ pGo = false;
+ pos = 0;
+ DummyTarget[0] = 0;DummyTarget[1] = 0;DummyTarget[2] = 0;
+ Reset();
+ }
+
+ bool pGo;
+ uint32 StrikeTimer;
+ uint32 pos;
+ uint32 MoveTimer;
+ float Zpos;
+ bool forcemove;
+
+ void Reset()
+ {
+ forcemove = true;
+ Zpos = 10.0;
+ StrikeTimer = 2000+rand()%5000;
+ MoveTimer = 0;
+ me->AddUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
+ }
+
+ void WaypointReached(uint32 i)
+ {
+ pos = i;
+ if (i == 2 && pInstance && !IsOverrun)
+ {
+ Unit *pTarget = Unit::GetUnit((*me), pInstance->GetData64(DATA_THRALL));
+ if (pTarget && pTarget->isAlive())
+ {
+ me->AddThreat(pTarget,0.0);
+ DoCast(pTarget, SPELL_GARGOYLE_STRIKE, true);
+ }
+ }
+ }
+
+ void JustDied(Unit *victim)
+ {
+ float x,y,z;
+ me->GetPosition(x,y,z);
+ z = me->GetMap()->GetHeight(x, y, z);
+ me->GetMotionMaster()->MovePoint(0,x,y,z);
+ me->GetMap()->CreatureRelocation(me, x,y,z,0);
+ hyjal_trashAI::JustDied(victim);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ hyjal_trashAI::UpdateAI(diff);
+ if (IsEvent || IsOverrun)
+ {
+ CAST_AI(hyjal_trashAI, me->AI())->SetCanAttack(false);
+ npc_escortAI::UpdateAI(diff);
+ }
+ if (IsEvent)
+ {
+ if (!pGo)
+ {
+ pGo = true;
+ if (pInstance)
+ {
+ if (!useFlyPath)
+ {
+ for (uint8 i = 0; i < 3; ++i)
+ AddWaypoint(i, GargoyleWPs[i][0]+irand(-10,10), GargoyleWPs[i][1]+irand(-10,10), GargoyleWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }else{//fly path FlyPathWPs
+ for (uint8 i = 0; i < 3; ++i)
+ AddWaypoint(i, FlyPathWPs[i][0]+irand(-10,10), FlyPathWPs[i][1]+irand(-10,10), FlyPathWPs[i][2]);
+ Start(false, true);
+ SetDespawnAtEnd(false);
+ }
+ }
+ }
+ }
+ if (IsOverrun && !UpdateVictim())
+ {
+ if (faction == 0)//alliance
+ {
+ if (StrikeTimer <= diff)
+ {
+ me->CastSpell(DummyTarget[0],DummyTarget[1],DummyTarget[2],SPELL_GARGOYLE_STRIKE,false);
+ StrikeTimer = 2000+rand()%1000;
+ } else StrikeTimer -= diff;
+ }
+ }
+ if (!UpdateVictim())
+ return;
+ if (!me->IsWithinDist(me->getVictim(), 20) || forcemove)
+ {
+ forcemove = false;
+ if (forcemove)
+ {
+ Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0);
+ if (pTarget)
+ me->Attack(pTarget,false);
+ }
+ if (MoveTimer <= diff)
+ {
+ float x,y,z;
+ me->getVictim()->GetPosition(x,y,z);
+ me->GetMotionMaster()->MovePoint(0,x,y,z+Zpos);
+ Zpos-=1.0;
+ if (Zpos <= 0)Zpos=0;
+ MoveTimer = 2000;
+ } else MoveTimer-=diff;
+ }
+ if (StrikeTimer <= diff)
+ {
+ if (me->IsWithinDist(me->getVictim(), 20))
+ {
+ DoCast(me->getVictim(), SPELL_GARGOYLE_STRIKE);
+ me->StopMoving();
+ me->GetMotionMaster()->Clear();
+ StrikeTimer = 2000+rand()%1000;
+ } else StrikeTimer=0;
+ } else StrikeTimer -= diff;
+ }
+};
+
+CreatureAI* GetAI_mob_gargoyle(Creature* pCreature)
+{
+ return new mob_gargoyleAI(pCreature);
+}
+
+#define SPELL_EXPLODING_SHOT 7896
+
+struct alliance_riflemanAI : public Scripted_NoMovementAI
+{
+ alliance_riflemanAI(Creature *c) : Scripted_NoMovementAI(c)
+ {
+ Reset();
+ }
+
+ uint32 ExplodeTimer;
+
+ void JustDied(Unit* /*who*/)
+ {
+ }
+
+ void Reset()
+ {
+ ExplodeTimer = 5000+rand()%5000;
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ if (!who || me->getVictim())
+ return;
+
+ if (who->isTargetableForAttack() && me->IsHostileTo(who))
+ {
+ //float attackRadius = me->GetAttackDistance(who);
+ if (me->IsWithinDistInMap(who, 30))
+ AttackStart(who);
+ }
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Check if we have a target
+ if (!UpdateVictim())
+ return;
+ if (ExplodeTimer <= diff)
+ {
+ if (!me->IsWithinDistInMap(me->getVictim(), 30))
+ {
+ EnterEvadeMode();
+ return;
+ }
+ int dmg = 500+rand()%700;
+ me->CastCustomSpell(me->getVictim(), SPELL_EXPLODING_SHOT, &dmg, 0, 0, false);
+ ExplodeTimer = 5000+rand()%5000;
+ } else ExplodeTimer -= diff;
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_alliance_rifleman(Creature* pCreature)
+{
+ return new alliance_riflemanAI(pCreature);
+}
+
+void AddSC_hyjal_trash()
+{
+ Script *newscript = new Script;
+ newscript->Name = "mob_giant_infernal";
+ newscript->GetAI = &GetAI_mob_giant_infernal;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_abomination";
+ newscript->GetAI = &GetAI_mob_abomination;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_ghoul";
+ newscript->GetAI = &GetAI_mob_ghoul;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_necromancer";
+ newscript->GetAI = &GetAI_mob_necromancer;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_banshee";
+ newscript->GetAI = &GetAI_mob_banshee;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_crypt_fiend";
+ newscript->GetAI = &GetAI_mob_crypt_fiend;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_fel_stalker";
+ newscript->GetAI = &GetAI_mob_fel_stalker;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_frost_wyrm";
+ newscript->GetAI = &GetAI_mob_frost_wyrm;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_gargoyle";
+ newscript->GetAI = &GetAI_mob_gargoyle;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "alliance_rifleman";
+ newscript->GetAI = &GetAI_alliance_rifleman;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.h b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.h
new file mode 100644
index 00000000000..21ee4bc06cc
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/hyjal_trash.h
@@ -0,0 +1,35 @@
+
+#ifndef SC_HYJAL_TRASH_AI_H
+#define SC_HYJAL_TRASH_AI_H
+
+#include "hyjal.h"
+#include "ScriptedEscortAI.h"
+
+#define MINRAIDDAMAGE 700000//minimal damage before trash can drop loot and reputation, resets if faction leader dies
+
+struct hyjal_trashAI : public npc_escortAI
+{
+ hyjal_trashAI(Creature *c);
+
+ void UpdateAI(const uint32 diff);
+
+ void JustDied(Unit* /*killer*/);
+
+ void DamageTaken(Unit *done_by, uint32 &damage);
+
+ public:
+ ScriptedInstance* pInstance;
+ bool IsEvent;
+ uint32 Delay;
+ uint32 LastOverronPos;
+ bool IsOverrun;
+ bool SetupOverrun;
+ uint32 OverrunType;
+ uint8 faction;
+ bool useFlyPath;
+ uint32 damageTaken;
+ float DummyTarget[3];
+
+ //private:
+};
+#endif
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/hyjal/instance_hyjal.cpp b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/instance_hyjal.cpp
new file mode 100644
index 00000000000..e89d518c5bc
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/hyjal/instance_hyjal.cpp
@@ -0,0 +1,324 @@
+ /* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Instance_Mount_Hyjal
+SD%Complete: 100
+SDComment: Instance Data Scripts and functions to acquire mobs and set encounter status for use in various Hyjal Scripts
+SDCategory: Caverns of Time, Mount Hyjal
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "hyjal.h"
+#include "hyjal_trash.h"
+
+enum eEnums
+{
+ MAX_ENCOUNTER = 5,
+
+ GO_ANCIENT_GEM = 185557
+};
+/* Battle of Mount Hyjal encounters:
+0 - Rage Winterchill event
+1 - Anetheron event
+2 - Kaz'rogal event
+3 - Azgalor event
+4 - Archimonde event
+*/
+
+struct instance_mount_hyjal : public ScriptedInstance
+{
+ instance_mount_hyjal(Map* pMap) : ScriptedInstance(pMap) {Initialize();};
+
+ uint32 m_auiEncounter[MAX_ENCOUNTER];
+ std::string str_data;
+
+ std::list<uint64> m_uiAncientGemGUID;
+
+ uint64 RageWinterchill;
+ uint64 Anetheron;
+ uint64 Kazrogal;
+ uint64 Azgalor;
+ uint64 Archimonde;
+ uint64 JainaProudmoore;
+ uint64 Thrall;
+ uint64 TyrandeWhisperwind;
+ uint64 HordeGate;
+ uint64 ElfGate;
+
+ uint32 Trash;
+
+ uint32 hordeRetreat;
+ uint32 allianceRetreat;
+ bool ArchiYell;
+
+ uint32 RaidDamage;
+
+ #define YELL_EFFORTS "All of your efforts have been in vain, for the draining of the World Tree has already begun. Soon the heart of your world will beat no more."
+ #define YELL_EFFORTS_NAME "Archimonde"
+
+ void Initialize()
+ {
+ memset(&m_auiEncounter, 0, sizeof(m_auiEncounter));
+
+ m_uiAncientGemGUID.clear();
+
+ RageWinterchill = 0;
+ Anetheron = 0;
+ Kazrogal = 0;
+ Azgalor = 0;
+ Archimonde = 0;
+ JainaProudmoore = 0;
+ Thrall = 0;
+ TyrandeWhisperwind = 0;
+ HordeGate = 0;
+ ElfGate = 0;
+ ArchiYell = false;
+ RaidDamage = 0;
+
+ Trash = 0;
+
+ hordeRetreat = 0;
+ allianceRetreat = 0;
+ }
+
+ bool IsEncounterInProgress() const
+ {
+ for (uint8 i = 0; i < MAX_ENCOUNTER; ++i)
+ if (m_auiEncounter[i] == IN_PROGRESS) return true;
+
+ return false;
+ }
+
+ void OnGameObjectCreate(GameObject* pGo, bool /*add*/)
+ {
+ switch(pGo->GetEntry())
+ {
+ case 182060:
+ HordeGate = pGo->GetGUID();
+ if (allianceRetreat)
+ HandleGameObject(0, true, pGo);
+ else
+ HandleGameObject(0, false, pGo);
+ break;
+ case 182061:
+ ElfGate = pGo->GetGUID();
+ if (hordeRetreat)
+ HandleGameObject(0, true, pGo);
+ else
+ HandleGameObject(0, false, pGo);
+ break;
+ case GO_ANCIENT_GEM:
+ m_uiAncientGemGUID.push_back(pGo->GetGUID());
+ break;
+ }
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool /*add*/)
+ {
+ switch(pCreature->GetEntry())
+ {
+ case 17767: RageWinterchill = pCreature->GetGUID(); break;
+ case 17808: Anetheron = pCreature->GetGUID(); break;
+ case 17888: Kazrogal = pCreature->GetGUID(); break;
+ case 17842: Azgalor = pCreature->GetGUID(); break;
+ case 17968: Archimonde = pCreature->GetGUID(); break;
+ case 17772: JainaProudmoore = pCreature->GetGUID(); break;
+ case 17852: Thrall = pCreature->GetGUID(); break;
+ case 17948: TyrandeWhisperwind = pCreature->GetGUID(); break;
+ }
+ }
+
+ uint64 GetData64(uint32 identifier)
+ {
+ switch(identifier)
+ {
+ case DATA_RAGEWINTERCHILL: return RageWinterchill;
+ case DATA_ANETHERON: return Anetheron;
+ case DATA_KAZROGAL: return Kazrogal;
+ case DATA_AZGALOR: return Azgalor;
+ case DATA_ARCHIMONDE: return Archimonde;
+ case DATA_JAINAPROUDMOORE: return JainaProudmoore;
+ case DATA_THRALL: return Thrall;
+ case DATA_TYRANDEWHISPERWIND: return TyrandeWhisperwind;
+ }
+
+ return 0;
+ }
+
+ void SetData(uint32 type, uint32 data)
+ {
+ switch(type)
+ {
+ case DATA_RAGEWINTERCHILLEVENT: m_auiEncounter[0] = data; break;
+ case DATA_ANETHERONEVENT:
+ m_auiEncounter[1] = data;
+ break;
+ case DATA_KAZROGALEVENT: m_auiEncounter[2] = data; break;
+ case DATA_AZGALOREVENT:
+ {
+ m_auiEncounter[3] = data;
+ if (data == DONE)
+ {
+ if (ArchiYell)break;
+ ArchiYell = true;
+
+ Creature* pCreature = instance->GetCreature(Azgalor);
+ if (pCreature)
+ {
+ Creature* pUnit = pCreature->SummonCreature(21987,pCreature->GetPositionX(),pCreature->GetPositionY(),pCreature->GetPositionZ(),0,TEMPSUMMON_TIMED_DESPAWN,10000);
+
+ Map* pMap = pCreature->GetMap();
+ if (pMap->IsDungeon() && pUnit)
+ {
+ pUnit->SetVisibility(VISIBILITY_OFF);
+ Map::PlayerList const &PlayerList = pMap->GetPlayers();
+ if (PlayerList.isEmpty())
+ return;
+
+ for (Map::PlayerList::const_iterator i = PlayerList.begin(); i != PlayerList.end(); ++i)
+ {
+ if (i->getSource())
+ {
+ WorldPacket data(SMSG_MESSAGECHAT, 200);
+ pUnit->BuildMonsterChat(&data,CHAT_MSG_MONSTER_YELL,YELL_EFFORTS,0,YELL_EFFORTS_NAME,i->getSource()->GetGUID());
+ i->getSource()->GetSession()->SendPacket(&data);
+
+ WorldPacket data2(SMSG_PLAY_SOUND, 4);
+ data2 << 10986;
+ i->getSource()->GetSession()->SendPacket(&data2);
+ }
+ }
+ }
+ }
+ }
+ }
+ break;
+ case DATA_ARCHIMONDEEVENT: m_auiEncounter[4] = data; break;
+ case DATA_RESET_TRASH_COUNT: Trash = 0; break;
+
+ case DATA_TRASH:
+ if (data) Trash = data;
+ else Trash--;
+ DoUpdateWorldState(WORLD_STATE_ENEMYCOUNT, Trash);
+ break;
+ case TYPE_RETREAT:
+ if (data == SPECIAL)
+ {
+ if (!m_uiAncientGemGUID.empty())
+ {
+ for (std::list<uint64>::const_iterator itr = m_uiAncientGemGUID.begin(); itr != m_uiAncientGemGUID.end(); ++itr)
+ {
+ //don't know how long it expected
+ DoRespawnGameObject(*itr,DAY);
+ }
+ }
+ }
+ break;
+ case DATA_ALLIANCE_RETREAT:
+ allianceRetreat = data;
+ HandleGameObject(HordeGate, true);
+ SaveToDB();
+ break;
+ case DATA_HORDE_RETREAT:
+ hordeRetreat = data;
+ HandleGameObject(ElfGate, true);
+ SaveToDB();
+ break;
+ case DATA_RAIDDAMAGE:
+ RaidDamage += data;
+ if (RaidDamage >= MINRAIDDAMAGE)
+ RaidDamage = MINRAIDDAMAGE;
+ break;
+ case DATA_RESET_RAIDDAMAGE:
+ RaidDamage = 0;
+ break;
+ }
+
+ debug_log("TSCR: Instance Hyjal: Instance data updated for event %u (Data=%u)",type,data);
+
+ if (data == DONE)
+ {
+ OUT_SAVE_INST_DATA;
+
+ std::ostringstream saveStream;
+ saveStream << m_auiEncounter[0] << " " << m_auiEncounter[1] << " " << m_auiEncounter[2] << " "
+ << m_auiEncounter[3] << " " << m_auiEncounter[4]
+ << " " << allianceRetreat << " " << hordeRetreat
+ << " " << RaidDamage;
+
+ str_data = saveStream.str();
+
+ SaveToDB();
+ OUT_SAVE_INST_DATA_COMPLETE;
+ }
+
+ }
+
+ uint32 GetData(uint32 type)
+ {
+ switch(type)
+ {
+ case DATA_RAGEWINTERCHILLEVENT: return m_auiEncounter[0];
+ case DATA_ANETHERONEVENT: return m_auiEncounter[1];
+ case DATA_KAZROGALEVENT: return m_auiEncounter[2];
+ case DATA_AZGALOREVENT: return m_auiEncounter[3];
+ case DATA_ARCHIMONDEEVENT: return m_auiEncounter[4];
+ case DATA_TRASH: return Trash;
+ case DATA_ALLIANCE_RETREAT: return allianceRetreat;
+ case DATA_HORDE_RETREAT: return hordeRetreat;
+ case DATA_RAIDDAMAGE: return RaidDamage;
+ }
+ return 0;
+ }
+
+ std::string GetSaveData()
+ {
+ return str_data;
+ }
+
+ void Load(const char* in)
+ {
+ if (!in)
+ {
+ OUT_LOAD_INST_DATA_FAIL;
+ return;
+ }
+
+ OUT_LOAD_INST_DATA(in);
+ std::istringstream loadStream(in);
+ loadStream >> m_auiEncounter[0] >> m_auiEncounter[1] >> m_auiEncounter[2] >> m_auiEncounter[3] >> m_auiEncounter[4] >> allianceRetreat >> hordeRetreat >> RaidDamage;
+ for (uint8 i = 0; i < MAX_ENCOUNTER; ++i)
+ if (m_auiEncounter[i] == IN_PROGRESS) // Do not load an encounter as IN_PROGRESS - reset it instead.
+ m_auiEncounter[i] = NOT_STARTED;
+ OUT_LOAD_INST_DATA_COMPLETE;
+ }
+};
+
+InstanceData* GetInstanceData_instance_mount_hyjal(Map* pMap)
+{
+ return new instance_mount_hyjal(pMap);
+}
+
+void AddSC_instance_mount_hyjal()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_hyjal";
+ newscript->GetInstanceData = &GetInstanceData_instance_mount_hyjal;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_captain_skarloc.cpp b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_captain_skarloc.cpp
new file mode 100644
index 00000000000..91c9e274b83
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_captain_skarloc.cpp
@@ -0,0 +1,152 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Captain_Skarloc
+SD%Complete: 75
+SDComment: Missing adds, missing waypoints to move up to Thrall once spawned + speech before enter combat.
+SDCategory: Caverns of Time, Old Hillsbrad Foothills
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "old_hillsbrad.h"
+
+#define SAY_ENTER -1560000
+#define SAY_TAUNT1 -1560001
+#define SAY_TAUNT2 -1560002
+#define SAY_SLAY1 -1560003
+#define SAY_SLAY2 -1560004
+#define SAY_DEATH -1560005
+
+#define SPELL_HOLY_LIGHT 29427
+#define SPELL_CLEANSE 29380
+#define SPELL_HAMMER_OF_JUSTICE 13005
+#define SPELL_HOLY_SHIELD 31904
+#define SPELL_DEVOTION_AURA 8258
+#define SPELL_CONSECRATION 38385
+
+struct boss_captain_skarlocAI : public ScriptedAI
+{
+ boss_captain_skarlocAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 Holy_Light_Timer;
+ uint32 Cleanse_Timer;
+ uint32 HammerOfJustice_Timer;
+ uint32 HolyShield_Timer;
+ uint32 DevotionAura_Timer;
+ uint32 Consecration_Timer;
+
+ void Reset()
+ {
+ Holy_Light_Timer = 20000 + rand()%10000;
+ Cleanse_Timer = 10000;
+ HammerOfJustice_Timer = 20000 + rand()%15000;
+ HolyShield_Timer = 240000;
+ DevotionAura_Timer = 3000;
+ Consecration_Timer = 8000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ //This is not correct. Should taunt Thrall before engage in combat
+ DoScriptText(SAY_TAUNT1, me);
+ DoScriptText(SAY_TAUNT2, me);
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ DoScriptText(RAND(SAY_SLAY1,SAY_SLAY2), me);
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+
+ if (pInstance && pInstance->GetData(TYPE_THRALL_EVENT) == IN_PROGRESS)
+ pInstance->SetData(TYPE_THRALL_PART1, DONE);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Holy_Light
+ if (Holy_Light_Timer <= diff)
+ {
+ DoCast(me, SPELL_HOLY_LIGHT);
+ Holy_Light_Timer = 30000;
+ } else Holy_Light_Timer -= diff;
+
+ //Cleanse
+ if (Cleanse_Timer <= diff)
+ {
+ DoCast(me, SPELL_CLEANSE);
+ Cleanse_Timer = 10000;
+ } else Cleanse_Timer -= diff;
+
+ //Hammer of Justice
+ if (HammerOfJustice_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_HAMMER_OF_JUSTICE);
+ HammerOfJustice_Timer = 60000;
+ } else HammerOfJustice_Timer -= diff;
+
+ //Holy Shield
+ if (HolyShield_Timer <= diff)
+ {
+ DoCast(me, SPELL_HOLY_SHIELD);
+ HolyShield_Timer = 240000;
+ } else HolyShield_Timer -= diff;
+
+ //Devotion_Aura
+ if (DevotionAura_Timer <= diff)
+ {
+ DoCast(me, SPELL_DEVOTION_AURA);
+ DevotionAura_Timer = 45000 + rand()%10000;
+ } else DevotionAura_Timer -= diff;
+
+ //Consecration
+ if (Consecration_Timer <= diff)
+ {
+ //DoCast(me->getVictim(), SPELL_CONSECRATION);
+ Consecration_Timer = 5000 + rand()%5000;
+ } else Consecration_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_captain_skarloc(Creature* pCreature)
+{
+ return new boss_captain_skarlocAI (pCreature);
+}
+
+void AddSC_boss_captain_skarloc()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_captain_skarloc";
+ newscript->GetAI = &GetAI_boss_captain_skarloc;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_epoch_hunter.cpp b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_epoch_hunter.cpp
new file mode 100644
index 00000000000..2c2ad96ddb7
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_epoch_hunter.cpp
@@ -0,0 +1,138 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Epoch_Hunter
+SD%Complete: 60
+SDComment: Missing spawns pre-event, missing speech to be coordinated with rest of escort event.
+SDCategory: Caverns of Time, Old Hillsbrad Foothills
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "old_hillsbrad.h"
+
+#define SAY_ENTER1 -1560013
+#define SAY_ENTER2 -1560014
+#define SAY_ENTER3 -1560015
+#define SAY_AGGRO1 -1560016
+#define SAY_AGGRO2 -1560017
+#define SAY_SLAY1 -1560018
+#define SAY_SLAY2 -1560019
+#define SAY_BREATH1 -1560020
+#define SAY_BREATH2 -1560021
+#define SAY_DEATH -1560022
+
+#define SPELL_SAND_BREATH 31914
+#define SPELL_IMPENDING_DEATH 31916
+#define SPELL_MAGIC_DISRUPTION_AURA 33834
+#define SPELL_WING_BUFFET 31475
+
+struct boss_epoch_hunterAI : public ScriptedAI
+{
+ boss_epoch_hunterAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 SandBreath_Timer;
+ uint32 ImpendingDeath_Timer;
+ uint32 WingBuffet_Timer;
+ uint32 Mda_Timer;
+
+ void Reset()
+ {
+ SandBreath_Timer = 8000 + rand()%8000;
+ ImpendingDeath_Timer = 25000 + rand()%5000;
+ WingBuffet_Timer = 35000;
+ Mda_Timer = 40000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoScriptText(RAND(SAY_AGGRO1,SAY_AGGRO2), me);
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ DoScriptText(RAND(SAY_SLAY1,SAY_SLAY2), me);
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+
+ if (pInstance && pInstance->GetData(TYPE_THRALL_EVENT) == IN_PROGRESS)
+ pInstance->SetData(TYPE_THRALL_PART4, DONE);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Sand Breath
+ if (SandBreath_Timer <= diff)
+ {
+ if (me->IsNonMeleeSpellCasted(false))
+ me->InterruptNonMeleeSpells(false);
+
+ DoCast(me->getVictim(), SPELL_SAND_BREATH);
+
+ DoScriptText(RAND(SAY_BREATH1,SAY_BREATH2), me);
+
+ SandBreath_Timer = 10000 + rand()%10000;
+ } else SandBreath_Timer -= diff;
+
+ if (ImpendingDeath_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_IMPENDING_DEATH);
+ ImpendingDeath_Timer = 25000+rand()%5000;
+ } else ImpendingDeath_Timer -= diff;
+
+ if (WingBuffet_Timer <= diff)
+ {
+ if (Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0))
+ DoCast(pTarget, SPELL_WING_BUFFET);
+ WingBuffet_Timer = 25000+rand()%10000;
+ } else WingBuffet_Timer -= diff;
+
+ if (Mda_Timer <= diff)
+ {
+ DoCast(me, SPELL_MAGIC_DISRUPTION_AURA);
+ Mda_Timer = 15000;
+ } else Mda_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_epoch_hunter(Creature* pCreature)
+{
+ return new boss_epoch_hunterAI (pCreature);
+}
+
+void AddSC_boss_epoch_hunter()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_epoch_hunter";
+ newscript->GetAI = &GetAI_boss_epoch_hunter;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_leutenant_drake.cpp b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_leutenant_drake.cpp
new file mode 100644
index 00000000000..dae0f5390b1
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/boss_leutenant_drake.cpp
@@ -0,0 +1,190 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Luetenant_Drake
+SD%Complete: 70
+SDComment: Missing proper code for patrolling area after being spawned. Script for GO (barrels) quest 10283
+SDCategory: Caverns of Time, Old Hillsbrad Foothills
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "old_hillsbrad.h"
+#include "ScriptedEscortAI.h"
+
+/*######
+## go_barrel_old_hillsbrad
+######*/
+
+bool GOHello_go_barrel_old_hillsbrad(Player* /*pPlayer*/, GameObject* pGO)
+{
+ if (ScriptedInstance* pInstance = pGO->GetInstanceData())
+ {
+ if (pInstance->GetData(TYPE_BARREL_DIVERSION) == DONE)
+ return false;
+
+ pInstance->SetData(TYPE_BARREL_DIVERSION, IN_PROGRESS);
+ }
+
+ return false;
+}
+
+/*######
+## boss_lieutenant_drake
+######*/
+
+#define SAY_ENTER -1560006
+#define SAY_AGGRO -1560007
+#define SAY_SLAY1 -1560008
+#define SAY_SLAY2 -1560009
+#define SAY_MORTAL -1560010
+#define SAY_SHOUT -1560011
+#define SAY_DEATH -1560012
+
+#define SPELL_WHIRLWIND 31909
+#define SPELL_HAMSTRING 9080
+#define SPELL_MORTAL_STRIKE 31911
+#define SPELL_FRIGHTENING_SHOUT 33789
+
+struct Location
+{
+ uint32 wpId;
+ float x;
+ float y;
+ float z;
+};
+
+static Location DrakeWP[]=
+{
+ {0, 2125.84, 88.2535, 54.8830},
+ {1, 2111.01, 93.8022, 52.6356},
+ {2, 2106.70, 114.753, 53.1965},
+ {3, 2107.76, 138.746, 52.5109},
+ {4, 2114.83, 160.142, 52.4738},
+ {5, 2125.24, 178.909, 52.7283},
+ {6, 2151.02, 208.901, 53.1551},
+ {7, 2177.00, 233.069, 52.4409},
+ {8, 2190.71, 227.831, 53.2742},
+ {9, 2178.14, 214.219, 53.0779},
+ {10, 2154.99, 202.795, 52.6446},
+ {11, 2132.00, 191.834, 52.5709},
+ {12, 2117.59, 166.708, 52.7686},
+ {13, 2093.61, 139.441, 52.7616},
+ {14, 2086.29, 104.950, 52.9246},
+ {15, 2094.23, 81.2788, 52.6946},
+ {16, 2108.70, 85.3075, 53.3294},
+ {17, 2125.50, 88.9481, 54.7953},
+ {18, 2128.20, 70.9763, 64.4221}
+};
+
+struct boss_lieutenant_drakeAI : public ScriptedAI
+{
+ boss_lieutenant_drakeAI(Creature *c) : ScriptedAI(c) {}
+
+ bool CanPatrol;
+ uint32 wpId;
+
+ uint32 Whirlwind_Timer;
+ uint32 Fear_Timer;
+ uint32 MortalStrike_Timer;
+ uint32 ExplodingShout_Timer;
+
+ void Reset()
+ {
+ CanPatrol = true;
+ wpId = 0;
+
+ Whirlwind_Timer = 20000;
+ Fear_Timer = 30000;
+ MortalStrike_Timer = 45000;
+ ExplodingShout_Timer = 25000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ DoScriptText(RAND(SAY_SLAY1,SAY_SLAY2), me);
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //TODO: make this work
+ if (CanPatrol && wpId == 0)
+ {
+ me->GetMotionMaster()->MovePoint(DrakeWP[0].wpId, DrakeWP[0].x, DrakeWP[0].y, DrakeWP[0].z);
+ ++wpId;
+ }
+
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Whirlwind
+ if (Whirlwind_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_WHIRLWIND);
+ Whirlwind_Timer = 20000+rand()%5000;
+ } else Whirlwind_Timer -= diff;
+
+ //Fear
+ if (Fear_Timer <= diff)
+ {
+ DoScriptText(SAY_SHOUT, me);
+ DoCast(me->getVictim(), SPELL_FRIGHTENING_SHOUT);
+ Fear_Timer = 25000+rand()%10000;
+ } else Fear_Timer -= diff;
+
+ //Mortal Strike
+ if (MortalStrike_Timer <= diff)
+ {
+ DoScriptText(SAY_MORTAL, me);
+ DoCast(me->getVictim(), SPELL_MORTAL_STRIKE);
+ MortalStrike_Timer = 20000+rand()%10000;
+ } else MortalStrike_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_lieutenant_drake(Creature* pCreature)
+{
+ return new boss_lieutenant_drakeAI (pCreature);
+}
+
+void AddSC_boss_lieutenant_drake()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "go_barrel_old_hillsbrad";
+ newscript->pGOHello = &GOHello_go_barrel_old_hillsbrad;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "boss_lieutenant_drake";
+ newscript->GetAI = &GetAI_boss_lieutenant_drake;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/instance_old_hillsbrad.cpp b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/instance_old_hillsbrad.cpp
new file mode 100644
index 00000000000..fa0b7c14595
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/instance_old_hillsbrad.cpp
@@ -0,0 +1,238 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Instance_Old_Hillsbrad
+SD%Complete: 75
+SDComment: If thrall escort fail, all parts will reset. In future, save sub-parts and continue from last known.
+SDCategory: Caverns of Time, Old Hillsbrad Foothills
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "old_hillsbrad.h"
+
+#define MAX_ENCOUNTER 6
+
+#define THRALL_ENTRY 17876
+#define TARETHA_ENTRY 18887
+#define EPOCH_ENTRY 18096
+
+#define DRAKE_ENTRY 17848
+
+#define QUEST_ENTRY_DIVERSION 10283
+#define LODGE_QUEST_TRIGGER 20155
+
+struct instance_old_hillsbrad : public ScriptedInstance
+{
+ instance_old_hillsbrad(Map* pMap) : ScriptedInstance(pMap) {Initialize();};
+
+ uint32 m_auiEncounter[MAX_ENCOUNTER];
+ uint32 mBarrelCount;
+ uint32 mThrallEventCount;
+
+ uint64 ThrallGUID;
+ uint64 TarethaGUID;
+ uint64 EpochGUID;
+
+ void Initialize()
+ {
+ memset(&m_auiEncounter, 0, sizeof(m_auiEncounter));
+
+ mBarrelCount = 0;
+ mThrallEventCount = 0;
+ ThrallGUID = 0;
+ TarethaGUID = 0;
+ EpochGUID = 0;
+ }
+
+ Player* GetPlayerInMap()
+ {
+ Map::PlayerList const& players = instance->GetPlayers();
+
+ if (!players.isEmpty())
+ {
+ for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr)
+ {
+ if (Player* plr = itr->getSource())
+ return plr;
+ }
+ }
+
+ debug_log("TSCR: Instance Old Hillsbrad: GetPlayerInMap, but PlayerList is empty!");
+ return NULL;
+ }
+
+ void UpdateQuestCredit()
+ {
+ Map::PlayerList const& players = instance->GetPlayers();
+
+ if (!players.isEmpty())
+ {
+ for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr)
+ {
+ if (Player* pPlayer = itr->getSource())
+ pPlayer->KilledMonsterCredit(LODGE_QUEST_TRIGGER,0);
+ }
+ }
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool /*add*/)
+ {
+ switch(pCreature->GetEntry())
+ {
+ case THRALL_ENTRY:
+ ThrallGUID = pCreature->GetGUID();
+ break;
+ case TARETHA_ENTRY:
+ TarethaGUID = pCreature->GetGUID();
+ break;
+ case EPOCH_ENTRY:
+ EpochGUID = pCreature->GetGUID();
+ break;
+ }
+ }
+
+ void SetData(uint32 type, uint32 data)
+ {
+ Player* pPlayer = GetPlayerInMap();
+
+ if (!pPlayer)
+ {
+ debug_log("TSCR: Instance Old Hillsbrad: SetData (Type: %u Data %u) cannot find any player.", type, data);
+ return;
+ }
+
+ switch(type)
+ {
+ case TYPE_BARREL_DIVERSION:
+ {
+ if (data == IN_PROGRESS)
+ {
+ if (mBarrelCount >= 5)
+ return;
+
+ ++mBarrelCount;
+ DoUpdateWorldState(WORLD_STATE_OH, mBarrelCount);
+
+ debug_log("TSCR: Instance Old Hillsbrad: go_barrel_old_hillsbrad count %u",mBarrelCount);
+
+ m_auiEncounter[0] = IN_PROGRESS;
+
+ if (mBarrelCount == 5)
+ {
+ UpdateQuestCredit();
+ pPlayer->SummonCreature(DRAKE_ENTRY, 2128.43, 71.01, 64.42, 1.74, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 1800000);
+ m_auiEncounter[0] = DONE;
+ }
+ }
+ break;
+ }
+ case TYPE_THRALL_EVENT:
+ {
+ if (data == FAIL)
+ {
+ if (mThrallEventCount <= 20)
+ {
+ ++mThrallEventCount;
+ m_auiEncounter[1] = NOT_STARTED;
+ debug_log("TSCR: Instance Old Hillsbrad: Thrall event failed %u times. Resetting all sub-events.",mThrallEventCount);
+ m_auiEncounter[2] = NOT_STARTED;
+ m_auiEncounter[3] = NOT_STARTED;
+ m_auiEncounter[4] = NOT_STARTED;
+ m_auiEncounter[5] = NOT_STARTED;
+ }
+ else if (mThrallEventCount > 20)
+ {
+ m_auiEncounter[1] = data;
+ m_auiEncounter[2] = data;
+ m_auiEncounter[3] = data;
+ m_auiEncounter[4] = data;
+ m_auiEncounter[5] = data;
+ debug_log("TSCR: Instance Old Hillsbrad: Thrall event failed %u times. Resetting all sub-events.",mThrallEventCount);
+ }
+ }
+ else
+ m_auiEncounter[1] = data;
+ debug_log("TSCR: Instance Old Hillsbrad: Thrall escort event adjusted to data %u.",data);
+ break;
+ }
+ case TYPE_THRALL_PART1:
+ m_auiEncounter[2] = data;
+ debug_log("TSCR: Instance Old Hillsbrad: Thrall event part I adjusted to data %u.",data);
+ break;
+ case TYPE_THRALL_PART2:
+ m_auiEncounter[3] = data;
+ debug_log("TSCR: Instance Old Hillsbrad: Thrall event part II adjusted to data %u.",data);
+ break;
+ case TYPE_THRALL_PART3:
+ m_auiEncounter[4] = data;
+ debug_log("TSCR: Instance Old Hillsbrad: Thrall event part III adjusted to data %u.",data);
+ break;
+ case TYPE_THRALL_PART4:
+ m_auiEncounter[5] = data;
+ debug_log("TSCR: Instance Old Hillsbrad: Thrall event part IV adjusted to data %u.",data);
+ break;
+ }
+ }
+
+ uint32 GetData(uint32 data)
+ {
+ switch(data)
+ {
+ case TYPE_BARREL_DIVERSION:
+ return m_auiEncounter[0];
+ case TYPE_THRALL_EVENT:
+ return m_auiEncounter[1];
+ case TYPE_THRALL_PART1:
+ return m_auiEncounter[2];
+ case TYPE_THRALL_PART2:
+ return m_auiEncounter[3];
+ case TYPE_THRALL_PART3:
+ return m_auiEncounter[4];
+ case TYPE_THRALL_PART4:
+ return m_auiEncounter[5];
+ }
+ return 0;
+ }
+
+ uint64 GetData64(uint32 data)
+ {
+ switch(data)
+ {
+ case DATA_THRALL:
+ return ThrallGUID;
+ case DATA_TARETHA:
+ return TarethaGUID;
+ case DATA_EPOCH:
+ return EpochGUID;
+ }
+ return 0;
+ }
+};
+InstanceData* GetInstanceData_instance_old_hillsbrad(Map* pMap)
+{
+ return new instance_old_hillsbrad(pMap);
+}
+
+void AddSC_instance_old_hillsbrad()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_old_hillsbrad";
+ newscript->GetInstanceData = &GetInstanceData_instance_old_hillsbrad;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.cpp b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.cpp
new file mode 100644
index 00000000000..08c63954db5
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.cpp
@@ -0,0 +1,658 @@
+ /* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Old_Hillsbrad
+SD%Complete: 40
+SDComment: Quest support: 10283, 10284. All friendly NPC's. Thrall waypoints fairly complete, missing many details, but possible to complete escort.
+SDCategory: Caverns of Time, Old Hillsbrad Foothills
+EndScriptData */
+
+/* ContentData
+npc_erozion
+npc_thrall_old_hillsbrad
+npc_taretha
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+#include "old_hillsbrad.h"
+
+#define QUEST_ENTRY_HILLSBRAD 10282
+#define QUEST_ENTRY_DIVERSION 10283
+#define QUEST_ENTRY_ESCAPE 10284
+#define QUEST_ENTRY_RETURN 10285
+#define ITEM_ENTRY_BOMBS 25853
+
+#define GOSSIP_HELLO_EROZION1 "I need a pack of Incendiary Bombs."
+#define GOSSIP_HELLO_EROZION2 "[PH] Teleport please, i'm tired."
+
+/*######
+## npc_erozion
+######*/
+
+bool GossipHello_npc_erozion(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ ScriptedInstance* pInstance = pCreature->GetInstanceData();
+ if (pInstance && pInstance->GetData(TYPE_BARREL_DIVERSION) != DONE && !pPlayer->HasItemCount(ITEM_ENTRY_BOMBS,1))
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HELLO_EROZION1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+
+ if (!pPlayer->GetQuestRewardStatus(QUEST_ENTRY_RETURN) && pPlayer->GetQuestStatus(QUEST_ENTRY_RETURN) == QUEST_STATUS_COMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HELLO_EROZION2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+
+ pPlayer->SEND_GOSSIP_MENU(9778, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_erozion(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ ItemPosCountVec dest;
+ uint8 msg = pPlayer->CanStoreNewItem(NULL_BAG, NULL_SLOT, dest, ITEM_ENTRY_BOMBS, 1);
+ if (msg == EQUIP_ERR_OK)
+ {
+ pPlayer->StoreNewItem(dest, ITEM_ENTRY_BOMBS, true);
+ }
+ pPlayer->SEND_GOSSIP_MENU(9515, pCreature->GetGUID());
+ }
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+2)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ }
+ return true;
+}
+
+/*######
+## npc_thrall_old_hillsbrad
+######*/
+
+//Thrall texts
+#define SAY_TH_START_EVENT_PART1 -1560023
+#define SAY_TH_ARMORY -1560024
+#define SAY_TH_SKARLOC_MEET -1560025
+#define SAY_TH_SKARLOC_TAUNT -1560026
+#define SAY_TH_START_EVENT_PART2 -1560027
+#define SAY_TH_MOUNTS_UP -1560028
+#define SAY_TH_CHURCH_END -1560029
+#define SAY_TH_MEET_TARETHA -1560030
+#define SAY_TH_EPOCH_WONDER -1560031
+#define SAY_TH_EPOCH_KILL_TARETHA -1560032
+#define SAY_TH_EVENT_COMPLETE -1560033
+
+#define SAY_TH_RANDOM_LOW_HP1 -1560034
+#define SAY_TH_RANDOM_LOW_HP2 -1560035
+
+#define SAY_TH_RANDOM_DIE1 -1560036
+#define SAY_TH_RANDOM_DIE2 -1560037
+
+#define SAY_TH_RANDOM_AGGRO1 -1560038
+#define SAY_TH_RANDOM_AGGRO2 -1560039
+#define SAY_TH_RANDOM_AGGRO3 -1560040
+#define SAY_TH_RANDOM_AGGRO4 -1560041
+
+#define SAY_TH_RANDOM_KILL1 -1560042
+#define SAY_TH_RANDOM_KILL2 -1560043
+#define SAY_TH_RANDOM_KILL3 -1560044
+
+#define SAY_TH_LEAVE_COMBAT1 -1560045
+#define SAY_TH_LEAVE_COMBAT2 -1560046
+#define SAY_TH_LEAVE_COMBAT3 -1560047
+
+//Taretha texts
+#define SAY_TA_FREE -1560048
+#define SAY_TA_ESCAPED -1560049
+
+//Misc for Thrall
+#define SPELL_STRIKE 14516
+#define SPELL_SHIELD_BLOCK 12169
+#define SPELL_SUMMON_EROZION_IMAGE 33954 //if thrall dies during escort?
+
+#define SPEED_WALK (0.5f)
+#define SPEED_RUN (1.0f)
+#define SPEED_MOUNT (1.6f)
+
+#define THRALL_WEAPON_MODEL 22106
+#define THRALL_WEAPON_INFO 218169346
+#define THRALL_SHIELD_MODEL 18662
+#define THRALL_SHIELD_INFO 234948100
+#define THRALL_MODEL_UNEQUIPPED 17292
+#define THRALL_MODEL_EQUIPPED 18165
+
+//Misc Creature entries
+#define ENTRY_ARMORER 18764
+#define ENTRY_SCARLOC 17862
+
+#define MOB_ENTRY_RIFLE 17820
+#define MOB_ENTRY_WARDEN 17833
+#define MOB_ENTRY_VETERAN 17860
+#define MOB_ENTRY_WATCHMAN 17814
+#define MOB_ENTRY_SENTRY 17815
+
+#define MOB_ENTRY_BARN_GUARDSMAN 18092
+#define MOB_ENTRY_BARN_PROTECTOR 18093
+#define MOB_ENTRY_BARN_LOOKOUT 18094
+
+#define MOB_ENTRY_CHURCH_GUARDSMAN 23175
+#define MOB_ENTRY_CHURCH_PROTECTOR 23179
+#define MOB_ENTRY_CHURCH_LOOKOUT 23177
+
+#define MOB_ENTRY_INN_GUARDSMAN 23176
+#define MOB_ENTRY_INN_PROTECTOR 23180
+#define MOB_ENTRY_INN_LOOKOUT 23178
+
+#define SKARLOC_MOUNT 18798
+#define SKARLOC_MOUNT_MODEL 18223
+#define EROZION_ENTRY 18723
+#define ENTRY_EPOCH 18096
+
+//gossip items
+#define GOSSIP_ID_START 9568
+#define GOSSIP_ID_SKARLOC1 9614 //I'm glad Taretha is alive. We now must find a way to free her...
+#define GOSSIP_ITEM_SKARLOC1 "Taretha cannot see you, Thrall."
+#define GOSSIP_ID_SKARLOC2 9579 //What do you mean by this? Is Taretha in danger?
+#define GOSSIP_ITEM_SKARLOC2 "The situation is rather complicated, Thrall. It would be best for you to head into the mountains now, before more of Blackmoore's men show up. We'll make sure Taretha is safe."
+#define GOSSIP_ID_SKARLOC3 9580
+
+#define GOSSIP_ID_TARREN 9597 //tarren mill is beyond these trees
+#define GOSSIP_ITEM_TARREN "We're ready, Thrall."
+
+#define GOSSIP_ID_COMPLETE 9578 //Thank you friends, I owe my freedom to you. Where is Taretha? I hoped to see her
+
+#define GOSSIP_ITEM_WALKING "[PH] Start walking."
+
+struct npc_thrall_old_hillsbradAI : public npc_escortAI
+{
+ npc_thrall_old_hillsbradAI(Creature *c) : npc_escortAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ HadMount = false;
+ me->setActive(true);
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint64 TarethaGUID;
+
+ bool LowHp;
+ bool HadMount;
+
+ void WaypointReached(uint32 i)
+ {
+ if (!pInstance)
+ return;
+
+ switch(i)
+ {
+ case 8:
+ SetRun(false);
+ me->SummonCreature(18764,2181.87,112.46,89.45,0.26,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ break;
+ case 9:
+ DoScriptText(SAY_TH_ARMORY, me);
+ me->SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_ID, THRALL_WEAPON_MODEL);
+ //me->SetUInt32Value(UNIT_VIRTUAL_ITEM_INFO, THRALL_WEAPON_INFO);
+ //me->SetUInt32Value(UNIT_VIRTUAL_ITEM_INFO+1, 781);
+ me->SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_ID+1, THRALL_SHIELD_MODEL);
+ //me->SetUInt32Value(UNIT_VIRTUAL_ITEM_INFO+2, THRALL_SHIELD_INFO);
+ //me->SetUInt32Value(UNIT_VIRTUAL_ITEM_INFO+3, 1038);
+ break;
+ case 10:
+ me->SetDisplayId(THRALL_MODEL_EQUIPPED);
+ break;
+ case 11:
+ SetRun();
+ break;
+ case 15:
+ me->SummonCreature(MOB_ENTRY_RIFLE,2200.28,137.37,87.93,5.07,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_WARDEN,2197.44,131.83,87.93,0.78,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_VETERAN,2203.62,135.40,87.93,3.70,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_VETERAN,2200.75,130.13,87.93,1.48,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ break;
+ case 21:
+ me->SummonCreature(MOB_ENTRY_RIFLE,2135.80,154.01,67.45,4.98,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_WARDEN,2144.36,151.87,67.74,4.46,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_VETERAN,2142.12,154.41,67.12,4.56,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_VETERAN,2138.08,155.38,67.24,4.60,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ break;
+ case 25:
+ me->SummonCreature(MOB_ENTRY_RIFLE,2102.98,192.17,65.24,6.02,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_WARDEN,2108.48,198.75,65.18,5.15,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_VETERAN,2106.11,197.29,65.18,5.63,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_VETERAN,2104.18,194.82,65.18,5.75,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ break;
+ case 29:
+ DoScriptText(SAY_TH_SKARLOC_MEET, me);
+ me->SummonCreature(ENTRY_SCARLOC,2036.48,271.22,63.43,5.27,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,30000);
+ //temporary,skarloc should rather be triggered to walk up to thrall
+ break;
+ case 30:
+ SetEscortPaused(true);
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ SetRun(false);
+ break;
+ case 31:
+ DoScriptText(SAY_TH_MOUNTS_UP, me);
+ DoMount();
+ SetRun();
+ break;
+ case 37:
+ //possibly regular patrollers? If so, remove this and let database handle them
+ me->SummonCreature(MOB_ENTRY_WATCHMAN,2124.26,522.16,56.87,3.99,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_WATCHMAN,2121.69,525.37,57.11,4.01,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_SENTRY,2124.65,524.55,56.63,3.98,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ break;
+ case 59:
+ me->SummonCreature(SKARLOC_MOUNT,2488.64,625.77,58.26,4.71,TEMPSUMMON_TIMED_DESPAWN,10000);
+ DoUnmount();
+ HadMount = false;
+ SetRun(false);
+ break;
+ case 60:
+ me->HandleEmoteCommand(EMOTE_ONESHOT_EXCLAMATION);
+ //make horsie run off
+ SetEscortPaused(true);
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ pInstance->SetData(TYPE_THRALL_PART2, DONE);
+ SetRun();
+ break;
+ case 64:
+ SetRun(false);
+ break;
+ case 68:
+ me->SummonCreature(MOB_ENTRY_BARN_PROTECTOR,2500.22,692.60,55.50,2.84,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_BARN_LOOKOUT,2500.13,696.55,55.51,3.38,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_BARN_GUARDSMAN,2500.55,693.64,55.50,3.14,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_BARN_GUARDSMAN,2500.94,695.81,55.50,3.14,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ break;
+ case 71:
+ SetRun();
+ break;
+ case 81:
+ SetRun(false);
+ break;
+ case 83:
+ me->SummonCreature(MOB_ENTRY_CHURCH_PROTECTOR,2627.33,646.82,56.03,4.28,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,5000);
+ me->SummonCreature(MOB_ENTRY_CHURCH_LOOKOUT,2624.14,648.03,56.03,4.50,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,5000);
+ me->SummonCreature(MOB_ENTRY_CHURCH_GUARDSMAN,2625.32,649.60,56.03,4.38,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,5000);
+ me->SummonCreature(MOB_ENTRY_CHURCH_GUARDSMAN,2627.22,649.00,56.03,4.34,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,5000);
+ break;
+ case 84:
+ DoScriptText(SAY_TH_CHURCH_END, me);
+ SetRun();
+ break;
+ case 91:
+ me->AddUnitMovementFlag(MOVEMENTFLAG_WALK_MODE);
+ SetRun(false);
+ break;
+ case 93:
+ me->SummonCreature(MOB_ENTRY_INN_PROTECTOR,2652.71,660.31,61.93,1.67,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_INN_LOOKOUT,2648.96,662.59,61.93,0.79,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_INN_GUARDSMAN,2657.36,662.34,61.93,2.68,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ me->SummonCreature(MOB_ENTRY_INN_GUARDSMAN,2656.39,659.77,61.93,2.61,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,5000);
+ break;
+ case 94:
+ if (uint64 TarethaGUID = pInstance->GetData64(DATA_TARETHA))
+ {
+ if (Unit* Taretha = Unit::GetUnit((*me), TarethaGUID))
+ DoScriptText(SAY_TA_ESCAPED, Taretha, me);
+ }
+ break;
+ case 95:
+ DoScriptText(SAY_TH_MEET_TARETHA, me);
+ pInstance->SetData(TYPE_THRALL_PART3,DONE);
+ SetEscortPaused(true);
+ break;
+ case 96:
+ DoScriptText(SAY_TH_EPOCH_WONDER, me);
+ break;
+ case 97:
+ DoScriptText(SAY_TH_EPOCH_KILL_TARETHA, me);
+ SetRun();
+ break;
+ case 98:
+ //trigger epoch Yell("Thrall! Come outside and face your fate! ....")
+ //from here, thrall should not never be allowed to move to point 106 which he currently does.
+ break;
+
+ case 106:
+ {
+ //trigger taretha to run down outside
+ if (Creature* Taretha = pInstance->instance->GetCreature(pInstance->GetData64(DATA_TARETHA)))
+ {
+ if (Player* pPlayer = GetPlayerForEscort())
+ CAST_AI(npc_escortAI, (Taretha->AI()))->Start(false, true, pPlayer->GetGUID());
+ }
+
+ //kill credit Creature for quest
+ Map* pMap = me->GetMap();
+ Map::PlayerList const& players = pMap->GetPlayers();
+ if (!players.isEmpty() && pMap->IsDungeon())
+ {
+ for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr)
+ {
+ if (Player* pPlayer = itr->getSource())
+ pPlayer->KilledMonsterCredit(20156,me->GetGUID());
+ }
+ }
+
+ //alot will happen here, thrall and taretha talk, erozion appear at spot to explain
+ me->SummonCreature(EROZION_ENTRY,2646.47,680.416,55.38,4.16,TEMPSUMMON_TIMED_DESPAWN,120000);
+ }
+ break;
+ case 108:
+ //last waypoint, just set Thrall invisible, respawn is turned off
+ me->SetVisibility(VISIBILITY_OFF);
+ break;
+ }
+ }
+
+ void Reset()
+ {
+ LowHp = false;
+
+ if (HadMount)
+ DoMount();
+
+ if (!HasEscortState(STATE_ESCORT_ESCORTING))
+ {
+ DoUnmount();
+ HadMount = false;
+ me->SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_ID, 0);
+ me->SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_ID+1, 0);
+ me->SetDisplayId(THRALL_MODEL_UNEQUIPPED);
+ }
+ if (HasEscortState(STATE_ESCORT_ESCORTING))
+ {
+ DoScriptText(RAND(SAY_TH_LEAVE_COMBAT1,SAY_TH_LEAVE_COMBAT2,SAY_TH_LEAVE_COMBAT3), me);
+ }
+ }
+ void StartWP()
+ {
+ me->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ SetEscortPaused(false);
+ }
+ void DoMount()
+ {
+ me->Mount(SKARLOC_MOUNT_MODEL);
+ me->SetSpeed(MOVE_RUN,SPEED_MOUNT);
+ }
+ void DoUnmount()
+ {
+ me->Unmount();
+ me->SetSpeed(MOVE_RUN,SPEED_RUN);
+ }
+ void EnterCombat(Unit* /*who*/)
+ {
+ DoScriptText(RAND(SAY_TH_RANDOM_AGGRO1,SAY_TH_RANDOM_AGGRO2,SAY_TH_RANDOM_AGGRO3,SAY_TH_RANDOM_AGGRO4), me);
+ if (me->IsMounted())
+ {
+ DoUnmount();
+ HadMount = true;
+ }
+ }
+
+ void JustSummoned(Creature* summoned)
+ {
+ switch(summoned->GetEntry())
+ {
+ //TODO: make Scarloc start into event instead, and not start attack directly
+ case MOB_ENTRY_BARN_GUARDSMAN:
+ case MOB_ENTRY_BARN_PROTECTOR:
+ case MOB_ENTRY_BARN_LOOKOUT:
+ case SKARLOC_MOUNT:
+ case EROZION_ENTRY:
+ break;
+ default:
+ summoned->AI()->AttackStart(me);
+ break;
+ }
+ }
+
+ void KilledUnit(Unit * /*victim*/)
+ {
+ DoScriptText(RAND(SAY_TH_RANDOM_KILL1,SAY_TH_RANDOM_KILL2,SAY_TH_RANDOM_KILL3), me);
+ }
+ void JustDied(Unit *slayer)
+ {
+ if (pInstance)
+ pInstance->SetData(TYPE_THRALL_EVENT,FAIL);
+
+ // Don't do a yell if he kills self (if player goes too far or at the end).
+ if (slayer == me)
+ return;
+
+ DoScriptText(RAND(SAY_TH_RANDOM_DIE1,SAY_TH_RANDOM_DIE2), me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ npc_escortAI::UpdateAI(diff);
+
+ if (!UpdateVictim())
+ return;
+
+ //TODO: add his abilities'n-crap here
+ if (!LowHp && ((me->GetHealth()*100 / me->GetMaxHealth()) < 20))
+ {
+ DoScriptText(RAND(SAY_TH_RANDOM_LOW_HP1,SAY_TH_RANDOM_LOW_HP2), me);
+ LowHp = true;
+ }
+ }
+};
+
+CreatureAI* GetAI_npc_thrall_old_hillsbrad(Creature* pCreature)
+{
+ return new npc_thrall_old_hillsbradAI(pCreature);
+}
+
+bool GossipHello_npc_thrall_old_hillsbrad(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ {
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+ pPlayer->SendPreparedQuest(pCreature->GetGUID());
+ }
+
+ ScriptedInstance* pInstance = pCreature->GetInstanceData();
+ if (pInstance)
+ {
+ if (pInstance->GetData(TYPE_BARREL_DIVERSION) == DONE && !pInstance->GetData(TYPE_THRALL_EVENT))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_WALKING, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_ID_START, pCreature->GetGUID());
+ }
+
+ if (pInstance->GetData(TYPE_THRALL_PART1) == DONE && !pInstance->GetData(TYPE_THRALL_PART2))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_SKARLOC1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_ID_SKARLOC1, pCreature->GetGUID());
+ }
+
+ if (pInstance->GetData(TYPE_THRALL_PART2) == DONE && !pInstance->GetData(TYPE_THRALL_PART3))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_TARREN, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+3);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_ID_TARREN, pCreature->GetGUID());
+ }
+ }
+ return true;
+}
+
+bool GossipSelect_npc_thrall_old_hillsbrad(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ ScriptedInstance* pInstance = pCreature->GetInstanceData();
+ switch(uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ if (pInstance)
+ {
+ pInstance->SetData(TYPE_THRALL_EVENT,IN_PROGRESS);
+ pInstance->SetData(TYPE_THRALL_PART1,IN_PROGRESS);
+ }
+
+ DoScriptText(SAY_TH_START_EVENT_PART1, pCreature);
+
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_thrall_old_hillsbradAI, pCreature->AI()))
+ pEscortAI->Start(true, true, pPlayer->GetGUID());
+
+ CAST_AI(npc_escortAI, (pCreature->AI()))->SetMaxPlayerDistance(100.0f);//not really needed, because it will not despawn if player is too far
+ CAST_AI(npc_escortAI, (pCreature->AI()))->SetDespawnAtEnd(false);
+ CAST_AI(npc_escortAI, (pCreature->AI()))->SetDespawnAtFar(false);
+ break;
+
+ case GOSSIP_ACTION_INFO_DEF+2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_SKARLOC2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+20);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_ID_SKARLOC2, pCreature->GetGUID());
+ break;
+
+ case GOSSIP_ACTION_INFO_DEF+20:
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_ID_SKARLOC3, pCreature->GetGUID());
+ pCreature->SummonCreature(SKARLOC_MOUNT,2038.81,270.26,63.20,5.41,TEMPSUMMON_TIMED_DESPAWN,12000);
+ if (pInstance)
+ pInstance->SetData(TYPE_THRALL_PART2,IN_PROGRESS);
+
+ DoScriptText(SAY_TH_START_EVENT_PART2, pCreature);
+
+ CAST_AI(npc_thrall_old_hillsbradAI, pCreature->AI())->StartWP();
+ break;
+
+ case GOSSIP_ACTION_INFO_DEF+3:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ if (pInstance)
+ pInstance->SetData(TYPE_THRALL_PART3,IN_PROGRESS);
+ CAST_AI(npc_thrall_old_hillsbradAI, pCreature->AI())->StartWP();
+ break;
+ }
+ return true;
+}
+
+/*######
+## npc_taretha
+######*/
+
+#define GOSSIP_ID_EPOCH1 9610 //Thank you for helping Thrall escape, friends. Now I only hope
+#define GOSSIP_ITEM_EPOCH1 "Strange wizard?"
+#define GOSSIP_ID_EPOCH2 9613 //Yes, friends. This man was no wizard of
+#define GOSSIP_ITEM_EPOCH2 "We'll get you out. Taretha. Don't worry. I doubt the wizard would wander too far away."
+
+struct npc_tarethaAI : public npc_escortAI
+{
+ npc_tarethaAI(Creature *c) : npc_escortAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ void WaypointReached(uint32 i)
+ {
+ switch(i)
+ {
+ case 6:
+ DoScriptText(SAY_TA_FREE, me);
+ break;
+ case 7:
+ me->HandleEmoteCommand(EMOTE_ONESHOT_CHEER);
+ break;
+ }
+ }
+ void Reset() {}
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ npc_escortAI::UpdateAI(diff);
+ }
+};
+CreatureAI* GetAI_npc_taretha(Creature* pCreature)
+{
+ return new npc_tarethaAI(pCreature);
+}
+
+bool GossipHello_npc_taretha(Player* pPlayer, Creature* pCreature)
+{
+ ScriptedInstance* pInstance = pCreature->GetInstanceData();
+ if (pInstance && pInstance->GetData(TYPE_THRALL_PART3) == DONE && pInstance->GetData(TYPE_THRALL_PART4) == NOT_STARTED)
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_EPOCH1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_ID_EPOCH1, pCreature->GetGUID());
+ }
+ return true;
+}
+
+bool GossipSelect_npc_taretha(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ ScriptedInstance* pInstance = pCreature->GetInstanceData();
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_EPOCH2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_ID_EPOCH2, pCreature->GetGUID());
+ }
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+2)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+
+ if (pInstance && pInstance->GetData(TYPE_THRALL_EVENT) == IN_PROGRESS)
+ {
+ pInstance->SetData(TYPE_THRALL_PART4,IN_PROGRESS);
+ if (pInstance->GetData64(DATA_EPOCH) == 0)
+ pCreature->SummonCreature(ENTRY_EPOCH,2639.13,698.55,65.43,4.59,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,120000);
+
+ if (uint64 ThrallGUID = pInstance->GetData64(DATA_THRALL))
+ {
+ Creature* Thrall = (Unit::GetCreature((*pCreature), ThrallGUID));
+ if (Thrall)
+ CAST_AI(npc_thrall_old_hillsbradAI, Thrall->AI())->StartWP();
+ }
+ }
+ }
+ return true;
+}
+
+/*######
+## AddSC
+######*/
+
+void AddSC_old_hillsbrad()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_erozion";
+ newscript->pGossipHello = &GossipHello_npc_erozion;
+ newscript->pGossipSelect = &GossipSelect_npc_erozion;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_thrall_old_hillsbrad";
+ newscript->pGossipHello = &GossipHello_npc_thrall_old_hillsbrad;
+ newscript->pGossipSelect = &GossipSelect_npc_thrall_old_hillsbrad;
+ newscript->GetAI = &GetAI_npc_thrall_old_hillsbrad;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_taretha";
+ newscript->pGossipHello = &GossipHello_npc_taretha;
+ newscript->pGossipSelect = &GossipSelect_npc_taretha;
+ newscript->GetAI = &GetAI_npc_taretha;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.h b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.h
new file mode 100644
index 00000000000..5c398cc2647
--- /dev/null
+++ b/src/server/scripts/Kalimdor/caverns_of_time/old_hillsbrad/old_hillsbrad.h
@@ -0,0 +1,19 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software licensed under GPL version 2
+ * Please see the included DOCS/LICENSE.TXT for more information */
+
+#ifndef DEF_OLD_HILLSBRAD_H
+#define DEF_OLD_HILLSBRAD_H
+
+#define TYPE_BARREL_DIVERSION 1
+#define TYPE_THRALL_EVENT 2
+#define TYPE_THRALL_PART1 3
+#define TYPE_THRALL_PART2 4
+#define TYPE_THRALL_PART3 5
+#define TYPE_THRALL_PART4 6
+#define DATA_THRALL 7
+#define DATA_TARETHA 8
+#define DATA_EPOCH 9
+#define WORLD_STATE_OH 2436
+#endif
+
diff --git a/src/server/scripts/Kalimdor/darkshore.cpp b/src/server/scripts/Kalimdor/darkshore.cpp
new file mode 100644
index 00000000000..26b42a86422
--- /dev/null
+++ b/src/server/scripts/Kalimdor/darkshore.cpp
@@ -0,0 +1,398 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Darkshore
+SD%Complete: 100
+SDComment: Quest support: 731, 2078, 5321
+SDCategory: Darkshore
+EndScriptData */
+
+/* ContentData
+npc_kerlonian
+npc_prospector_remtravel
+npc_threshwackonator
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+#include "ScriptedFollowerAI.h"
+
+/*####
+# npc_kerlonian
+####*/
+
+enum eKerlonian
+{
+ SAY_KER_START = -1000434,
+
+ EMOTE_KER_SLEEP_1 = -1000435,
+ EMOTE_KER_SLEEP_2 = -1000436,
+ EMOTE_KER_SLEEP_3 = -1000437,
+
+ SAY_KER_SLEEP_1 = -1000438,
+ SAY_KER_SLEEP_2 = -1000439,
+ SAY_KER_SLEEP_3 = -1000440,
+ SAY_KER_SLEEP_4 = -1000441,
+
+ EMOTE_KER_AWAKEN = -1000445,
+
+ SAY_KER_ALERT_1 = -1000442,
+ SAY_KER_ALERT_2 = -1000443,
+
+ SAY_KER_END = -1000444,
+
+ SPELL_SLEEP_VISUAL = 25148,
+ SPELL_AWAKEN = 17536,
+ QUEST_SLEEPER_AWAKENED = 5321,
+ NPC_LILADRIS = 11219, //attackers entries unknown
+ FACTION_KER_ESCORTEE = 113
+};
+
+//TODO: make concept similar as "ringo" -escort. Find a way to run the scripted attacks, _if_ player are choosing road.
+struct npc_kerlonianAI : public FollowerAI
+{
+ npc_kerlonianAI(Creature* pCreature) : FollowerAI(pCreature) { }
+
+ uint32 m_uiFallAsleepTimer;
+
+ void Reset()
+ {
+ m_uiFallAsleepTimer = urand(10000, 45000);
+ }
+
+ void MoveInLineOfSight(Unit *pWho)
+ {
+ FollowerAI::MoveInLineOfSight(pWho);
+
+ if (!me->getVictim() && !HasFollowState(STATE_FOLLOW_COMPLETE) && pWho->GetEntry() == NPC_LILADRIS)
+ {
+ if (me->IsWithinDistInMap(pWho, INTERACTION_DISTANCE*5))
+ {
+ if (Player* pPlayer = GetLeaderForFollower())
+ {
+ if (pPlayer->GetQuestStatus(QUEST_SLEEPER_AWAKENED) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->GroupEventHappens(QUEST_SLEEPER_AWAKENED, me);
+
+ DoScriptText(SAY_KER_END, me);
+ }
+
+ SetFollowComplete();
+ }
+ }
+ }
+
+ void SpellHit(Unit* /*pCaster*/, const SpellEntry* pSpell)
+ {
+ if (HasFollowState(STATE_FOLLOW_INPROGRESS | STATE_FOLLOW_PAUSED) && pSpell->Id == SPELL_AWAKEN)
+ ClearSleeping();
+ }
+
+ void SetSleeping()
+ {
+ SetFollowPaused(true);
+
+ DoScriptText(RAND(EMOTE_KER_SLEEP_1,EMOTE_KER_SLEEP_2,EMOTE_KER_SLEEP_3), me);
+
+ DoScriptText(RAND(SAY_KER_SLEEP_1,SAY_KER_SLEEP_2,SAY_KER_SLEEP_3,SAY_KER_SLEEP_4), me);
+
+ me->SetStandState(UNIT_STAND_STATE_SLEEP);
+ DoCast(me, SPELL_SLEEP_VISUAL, false);
+ }
+
+ void ClearSleeping()
+ {
+ me->RemoveAurasDueToSpell(SPELL_SLEEP_VISUAL);
+ me->SetStandState(UNIT_STAND_STATE_STAND);
+
+ DoScriptText(EMOTE_KER_AWAKEN, me);
+
+ SetFollowPaused(false);
+ }
+
+ void UpdateFollowerAI(const uint32 uiDiff)
+ {
+ if (!UpdateVictim())
+ {
+ if (!HasFollowState(STATE_FOLLOW_INPROGRESS))
+ return;
+
+ if (!HasFollowState(STATE_FOLLOW_PAUSED))
+ {
+ if (m_uiFallAsleepTimer <= uiDiff)
+ {
+ SetSleeping();
+ m_uiFallAsleepTimer = urand(25000, 90000);
+ }
+ else
+ m_uiFallAsleepTimer -= uiDiff;
+ }
+
+ return;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_kerlonian(Creature* pCreature)
+{
+ return new npc_kerlonianAI(pCreature);
+}
+
+bool QuestAccept_npc_kerlonian(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_SLEEPER_AWAKENED)
+ {
+ if (npc_kerlonianAI* pKerlonianAI = CAST_AI(npc_kerlonianAI, pCreature->AI()))
+ {
+ pCreature->SetStandState(UNIT_STAND_STATE_STAND);
+ DoScriptText(SAY_KER_START, pCreature, pPlayer);
+ pKerlonianAI->StartFollow(pPlayer, FACTION_KER_ESCORTEE, pQuest);
+ }
+ }
+
+ return true;
+}
+
+/*####
+# npc_prospector_remtravel
+####*/
+
+enum eRemtravel
+{
+ SAY_REM_START = -1000327,
+ SAY_REM_AGGRO = -1000328,
+ SAY_REM_RAMP1_1 = -1000329,
+ SAY_REM_RAMP1_2 = -1000330,
+ SAY_REM_BOOK = -1000331,
+ SAY_REM_TENT1_1 = -1000332,
+ SAY_REM_TENT1_2 = -1000333,
+ SAY_REM_MOSS = -1000334,
+ EMOTE_REM_MOSS = -1000335,
+ SAY_REM_MOSS_PROGRESS = -1000336,
+ SAY_REM_PROGRESS = -1000337,
+ SAY_REM_REMEMBER = -1000338,
+ EMOTE_REM_END = -1000339,
+
+ FACTION_ESCORTEE = 10,
+ QUEST_ABSENT_MINDED_PT2 = 731,
+ NPC_GRAVEL_SCOUT = 2158,
+ NPC_GRAVEL_BONE = 2159,
+ NPC_GRAVEL_GEO = 2160
+};
+
+struct npc_prospector_remtravelAI : public npc_escortAI
+{
+ npc_prospector_remtravelAI(Creature* pCreature) : npc_escortAI(pCreature) {}
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch(i)
+ {
+ case 0:
+ DoScriptText(SAY_REM_START, me, pPlayer);
+ break;
+ case 5:
+ DoScriptText(SAY_REM_RAMP1_1, me, pPlayer);
+ break;
+ case 6:
+ DoSpawnCreature(NPC_GRAVEL_SCOUT, -10.0f, 5.0f, 0.0f, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ DoSpawnCreature(NPC_GRAVEL_BONE, -10.0f, 7.0f, 0.0f, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ break;
+ case 9:
+ DoScriptText(SAY_REM_RAMP1_2, me, pPlayer);
+ break;
+ case 14:
+ //depend quest rewarded?
+ DoScriptText(SAY_REM_BOOK, me, pPlayer);
+ break;
+ case 15:
+ DoScriptText(SAY_REM_TENT1_1, me, pPlayer);
+ break;
+ case 16:
+ DoSpawnCreature(NPC_GRAVEL_SCOUT, -10.0f, 5.0f, 0.0f, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ DoSpawnCreature(NPC_GRAVEL_BONE, -10.0f, 7.0f, 0.0f, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ break;
+ case 17:
+ DoScriptText(SAY_REM_TENT1_2, me, pPlayer);
+ break;
+ case 26:
+ DoScriptText(SAY_REM_MOSS, me, pPlayer);
+ break;
+ case 27:
+ DoScriptText(EMOTE_REM_MOSS, me, pPlayer);
+ break;
+ case 28:
+ DoScriptText(SAY_REM_MOSS_PROGRESS, me, pPlayer);
+ break;
+ case 29:
+ DoSpawnCreature(NPC_GRAVEL_SCOUT, -15.0f, 3.0f, 0.0f, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ DoSpawnCreature(NPC_GRAVEL_BONE, -15.0f, 5.0f, 0.0f, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ DoSpawnCreature(NPC_GRAVEL_GEO, -15.0f, 7.0f, 0.0f, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ break;
+ case 31:
+ DoScriptText(SAY_REM_PROGRESS, me, pPlayer);
+ break;
+ case 41:
+ DoScriptText(SAY_REM_REMEMBER, me, pPlayer);
+ break;
+ case 42:
+ DoScriptText(EMOTE_REM_END, me, pPlayer);
+ pPlayer->GroupEventHappens(QUEST_ABSENT_MINDED_PT2, me);
+ break;
+ }
+ }
+
+ void Reset() {}
+
+ void EnterCombat(Unit* who)
+ {
+ if (rand()%2)
+ DoScriptText(SAY_REM_AGGRO, me, who);
+ }
+
+ void JustSummoned(Creature* /*pSummoned*/)
+ {
+ //unsure if it should be any
+ //pSummoned->AI()->AttackStart(me);
+ }
+};
+
+CreatureAI* GetAI_npc_prospector_remtravel(Creature* pCreature)
+{
+ return new npc_prospector_remtravelAI(pCreature);
+}
+
+bool QuestAccept_npc_prospector_remtravel(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_ABSENT_MINDED_PT2)
+ {
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_prospector_remtravelAI, pCreature->AI()))
+ pEscortAI->Start(false, false, pPlayer->GetGUID());
+
+ pCreature->setFaction(FACTION_ESCORTEE);
+ }
+
+ return true;
+}
+
+/*####
+# npc_threshwackonator
+####*/
+
+enum eThreshwackonator
+{
+ EMOTE_START = -1000413, //signed for 4966
+ SAY_AT_CLOSE = -1000414, //signed for 4966
+ QUEST_GYROMAST_REV = 2078,
+ NPC_GELKAK = 6667,
+ FACTION_HOSTILE = 14
+};
+
+#define GOSSIP_ITEM_INSERT_KEY "[PH] Insert key"
+
+struct npc_threshwackonatorAI : public FollowerAI
+{
+ npc_threshwackonatorAI(Creature* pCreature) : FollowerAI(pCreature) { }
+
+ void Reset() { }
+
+ void MoveInLineOfSight(Unit* pWho)
+ {
+ FollowerAI::MoveInLineOfSight(pWho);
+
+ if (!me->getVictim() && !HasFollowState(STATE_FOLLOW_COMPLETE) && pWho->GetEntry() == NPC_GELKAK)
+ {
+ if (me->IsWithinDistInMap(pWho, 10.0f))
+ {
+ DoScriptText(SAY_AT_CLOSE, pWho);
+ DoAtEnd();
+ }
+ }
+ }
+
+ void DoAtEnd()
+ {
+ me->setFaction(FACTION_HOSTILE);
+
+ if (Player* pHolder = GetLeaderForFollower())
+ me->AI()->AttackStart(pHolder);
+
+ SetFollowComplete();
+ }
+};
+
+CreatureAI* GetAI_npc_threshwackonator(Creature* pCreature)
+{
+ return new npc_threshwackonatorAI(pCreature);
+}
+
+bool GossipHello_npc_threshwackonator(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->GetQuestStatus(QUEST_GYROMAST_REV) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_INSERT_KEY, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_threshwackonator(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+
+ if (npc_threshwackonatorAI* pThreshAI = CAST_AI(npc_threshwackonatorAI, pCreature->AI()))
+ {
+ DoScriptText(EMOTE_START, pCreature);
+ pThreshAI->StartFollow(pPlayer);
+ }
+ }
+
+ return true;
+}
+
+void AddSC_darkshore()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_kerlonian";
+ newscript->GetAI = &GetAI_npc_kerlonian;
+ newscript->pQuestAccept = &QuestAccept_npc_kerlonian;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_prospector_remtravel";
+ newscript->GetAI = &GetAI_npc_prospector_remtravel;
+ newscript->pQuestAccept = &QuestAccept_npc_prospector_remtravel;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_threshwackonator";
+ newscript->GetAI = &GetAI_npc_threshwackonator;
+ newscript->pGossipHello = &GossipHello_npc_threshwackonator;
+ newscript->pGossipSelect = &GossipSelect_npc_threshwackonator;
+ newscript->pGossipSelect = &GossipSelect_npc_threshwackonator;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/desolace.cpp b/src/server/scripts/Kalimdor/desolace.cpp
new file mode 100644
index 00000000000..6b3ec8071dd
--- /dev/null
+++ b/src/server/scripts/Kalimdor/desolace.cpp
@@ -0,0 +1,259 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Desolace
+SD%Complete: 100
+SDComment: Quest support: 5561
+SDCategory: Desolace
+EndScriptData */
+
+/* ContentData
+npc_aged_dying_ancient_kodo
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+
+enum eDyingKodo
+{
+ // signed for 9999
+ SAY_SMEED_HOME_1 = -1000348,
+ SAY_SMEED_HOME_2 = -1000349,
+ SAY_SMEED_HOME_3 = -1000350,
+
+ QUEST_KODO = 5561,
+
+ NPC_SMEED = 11596,
+ NPC_AGED_KODO = 4700,
+ NPC_DYING_KODO = 4701,
+ NPC_ANCIENT_KODO = 4702,
+ NPC_TAMED_KODO = 11627,
+
+ SPELL_KODO_KOMBO_ITEM = 18153,
+ SPELL_KODO_KOMBO_PLAYER_BUFF = 18172, //spells here have unclear function, but using them at least for visual parts and checks
+ SPELL_KODO_KOMBO_DESPAWN_BUFF = 18377,
+ SPELL_KODO_KOMBO_GOSSIP = 18362
+
+};
+
+struct npc_aged_dying_ancient_kodoAI : public ScriptedAI
+{
+ npc_aged_dying_ancient_kodoAI(Creature* pCreature) : ScriptedAI(pCreature) { Reset(); }
+
+ uint32 m_uiDespawnTimer;
+
+ void Reset()
+ {
+ m_uiDespawnTimer = 0;
+ }
+
+ void MoveInLineOfSight(Unit* pWho)
+ {
+ if (pWho->GetEntry() == NPC_SMEED)
+ {
+ if (me->HasFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP))
+ return;
+
+ if (me->IsWithinDistInMap(pWho, 10.0f))
+ {
+ DoScriptText(RAND(SAY_SMEED_HOME_1,SAY_SMEED_HOME_2,SAY_SMEED_HOME_3), pWho);
+
+ //spell have no implemented effect (dummy), so useful to notify spellHit
+ DoCast(me, SPELL_KODO_KOMBO_GOSSIP, true);
+ }
+ }
+ }
+
+ void SpellHit(Unit* /*pCaster*/, SpellEntry const* pSpell)
+ {
+ if (pSpell->Id == SPELL_KODO_KOMBO_GOSSIP)
+ {
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ m_uiDespawnTimer = 60000;
+ }
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //timer should always be == 0 unless we already updated entry of creature. Then not expect this updated to ever be in combat.
+ if (m_uiDespawnTimer && m_uiDespawnTimer <= diff)
+ {
+ if (!me->getVictim() && me->isAlive())
+ {
+ Reset();
+ me->setDeathState(JUST_DIED);
+ me->Respawn();
+ return;
+ }
+ } else m_uiDespawnTimer -= diff;
+
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_aged_dying_ancient_kodo(Creature* pCreature)
+{
+ return new npc_aged_dying_ancient_kodoAI(pCreature);
+}
+
+bool EffectDummyCreature_npc_aged_dying_ancient_kodo(Unit *pCaster, uint32 spellId, uint32 effIndex, Creature *pCreatureTarget)
+{
+ //always check spellid and effectindex
+ if (spellId == SPELL_KODO_KOMBO_ITEM && effIndex == 0)
+ {
+ //no effect if player/creature already have aura from spells
+ if (pCaster->HasAura(SPELL_KODO_KOMBO_PLAYER_BUFF) || pCreatureTarget->HasAura(SPELL_KODO_KOMBO_DESPAWN_BUFF))
+ return true;
+
+ if (pCreatureTarget->GetEntry() == NPC_AGED_KODO ||
+ pCreatureTarget->GetEntry() == NPC_DYING_KODO ||
+ pCreatureTarget->GetEntry() == NPC_ANCIENT_KODO)
+ {
+ pCaster->CastSpell(pCaster,SPELL_KODO_KOMBO_PLAYER_BUFF,true);
+
+ pCreatureTarget->UpdateEntry(NPC_TAMED_KODO);
+ pCreatureTarget->CastSpell(pCreatureTarget,SPELL_KODO_KOMBO_DESPAWN_BUFF,false);
+
+ if (pCreatureTarget->GetMotionMaster()->GetCurrentMovementGeneratorType() == WAYPOINT_MOTION_TYPE)
+ pCreatureTarget->GetMotionMaster()->MoveIdle();
+
+ pCreatureTarget->GetMotionMaster()->MoveFollow(pCaster, PET_FOLLOW_DIST, pCreatureTarget->GetFollowAngle());
+ }
+
+ //always return true when we are handling this spell and effect
+ return true;
+ }
+ return false;
+}
+
+bool GossipHello_npc_aged_dying_ancient_kodo(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->HasAura(SPELL_KODO_KOMBO_PLAYER_BUFF) && pCreature->HasAura(SPELL_KODO_KOMBO_DESPAWN_BUFF))
+ {
+ //the expected quest objective
+ pPlayer->TalkedToCreature(pCreature->GetEntry(), pCreature->GetGUID());
+
+ pPlayer->RemoveAurasDueToSpell(SPELL_KODO_KOMBO_PLAYER_BUFF);
+ pCreature->GetMotionMaster()->MoveIdle();
+ }
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+ return true;
+}
+
+/*######
+## go_iruxos. Quest 5381
+######*/
+
+bool GOHello_go_iruxos(Player *pPlayer, GameObject* /*pGO*/)
+{
+ if (pPlayer->GetQuestStatus(5381) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->SummonCreature(11876, pPlayer->GetInnPosX(),pPlayer->GetInnPosY(),pPlayer->GetInnPosZ(),0,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT,10000);
+
+ return true;
+}
+
+/*######
+## npc_dalinda_malem. Quest 1440
+######*/
+
+#define QUEST_RETURN_TO_VAHLARRIEL 1440
+
+struct npc_dalindaAI : public npc_escortAI
+{
+ npc_dalindaAI(Creature* pCreature) : npc_escortAI(pCreature) { }
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+ switch (i)
+ {
+ case 1:
+ me->IsStandState();
+ break;
+ case 15:
+ if (pPlayer)
+ pPlayer->GroupEventHappens(QUEST_RETURN_TO_VAHLARRIEL, me);
+ break;
+ }
+ }
+
+ void EnterCombat(Unit* /*pWho*/) { }
+
+ void Reset() {}
+
+ void JustDied(Unit* /*pKiller*/)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+ if (pPlayer)
+ pPlayer->FailQuest(QUEST_RETURN_TO_VAHLARRIEL);
+ return;
+ }
+
+ void UpdateAI(const uint32 uiDiff)
+ {
+ npc_escortAI::UpdateAI(uiDiff);
+ if (!UpdateVictim())
+ return;
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_dalinda(Creature* pCreature)
+{
+ return new npc_dalindaAI(pCreature);
+}
+
+bool QuestAccept_npc_dalinda(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_RETURN_TO_VAHLARRIEL)
+ {
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_dalindaAI, pCreature->AI()))
+ {
+ pEscortAI->Start(true, false, pPlayer->GetGUID());
+ pCreature->setFaction(113);
+ }
+ }
+ return true;
+}
+
+void AddSC_desolace()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_aged_dying_ancient_kodo";
+ newscript->GetAI = &GetAI_npc_aged_dying_ancient_kodo;
+ newscript->pEffectDummyCreature = &EffectDummyCreature_npc_aged_dying_ancient_kodo;
+ newscript->pGossipHello = &GossipHello_npc_aged_dying_ancient_kodo;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "go_iruxos";
+ newscript->pGOHello = &GOHello_go_iruxos;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_dalinda";
+ newscript->GetAI = &GetAI_npc_dalinda;
+ newscript->pQuestAccept = &QuestAccept_npc_dalinda;
+ newscript->RegisterSelf();
+
+}
diff --git a/src/server/scripts/Kalimdor/durotar.cpp b/src/server/scripts/Kalimdor/durotar.cpp
new file mode 100644
index 00000000000..9ca6074cad3
--- /dev/null
+++ b/src/server/scripts/Kalimdor/durotar.cpp
@@ -0,0 +1,103 @@
+/* Copyright (C) 2010 TrinityCore <http://www.trinitycore.org/>
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#include "ScriptedPch.h"
+
+#include "ScriptedPch.h"
+
+/*######
+##Quest 5441: Lazy Peons
+##npc_lazy_peon
+######*/
+
+enum LazyPeonYells
+{
+ SAY_SPELL_HIT = -1999900 //Ow! OK, I''ll get back to work, $N!'
+};
+
+enum LazyPeon
+{
+ QUEST_LAZY_PEONS = 5441,
+ GO_LUMBERPILE = 175784,
+ SPELL_BUFF_SLEEP = 17743,
+ SPELL_AWAKEN_PEON = 19938
+};
+
+struct npc_lazy_peonAI : public ScriptedAI
+{
+ npc_lazy_peonAI(Creature *c) : ScriptedAI(c) {}
+
+ uint64 uiPlayerGUID;
+
+ uint32 m_uiRebuffTimer;
+ bool work;
+
+ void Reset ()
+ {
+ uiPlayerGUID = 0;
+ work = false;
+ }
+
+ void MovementInform(uint32 /*type*/, uint32 id)
+ {
+ if (id == 1)
+ work = true;
+ }
+
+ void SpellHit(Unit *caster, const SpellEntry *spell)
+ {
+ if (spell->Id == SPELL_AWAKEN_PEON && caster->GetTypeId() == TYPEID_PLAYER
+ && CAST_PLR(caster)->GetQuestStatus(QUEST_LAZY_PEONS) == QUEST_STATUS_INCOMPLETE)
+ {
+ caster->ToPlayer()->KilledMonsterCredit(me->GetEntry(),me->GetGUID());
+ DoScriptText(SAY_SPELL_HIT, me, caster);
+ me->RemoveAllAuras();
+ if (GameObject* Lumberpile = me->FindNearestGameObject(GO_LUMBERPILE, 20))
+ me->GetMotionMaster()->MovePoint(1,Lumberpile->GetPositionX()-1,Lumberpile->GetPositionY(),Lumberpile->GetPositionZ());
+ }
+ }
+
+ void UpdateAI(const uint32 uiDiff)
+ {
+ if (work == true)
+ me->HandleEmoteCommand(466);
+ if (m_uiRebuffTimer <= uiDiff)
+ {
+ DoCast(me, SPELL_BUFF_SLEEP);
+ m_uiRebuffTimer = 300000; //Rebuff agian in 5 minutes
+ }
+ else
+ m_uiRebuffTimer -= uiDiff;
+ if (!UpdateVictim())
+ return;
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_lazy_peon(Creature* pCreature)
+{
+ return new npc_lazy_peonAI(pCreature);
+}
+
+void AddSC_durotar()
+{
+ Script* newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_lazy_peon";
+ newscript->GetAI = &GetAI_npc_lazy_peon;
+ newscript->RegisterSelf();
+} \ No newline at end of file
diff --git a/src/server/scripts/Kalimdor/dustwallow_marsh.cpp b/src/server/scripts/Kalimdor/dustwallow_marsh.cpp
new file mode 100644
index 00000000000..a80c514eed7
--- /dev/null
+++ b/src/server/scripts/Kalimdor/dustwallow_marsh.cpp
@@ -0,0 +1,425 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Dustwallow_Marsh
+SD%Complete: 95
+SDComment: Quest support: 11180, 558, 11126, 11142, 11180. Vendor Nat Pagle
+SDCategory: Dustwallow Marsh
+EndScriptData */
+
+/* ContentData
+mobs_risen_husk_spirit
+npc_restless_apparition
+npc_deserter_agitator
+npc_lady_jaina_proudmoore
+npc_nat_pagle
+npc_private_hendel
+npc_cassa_crimsonwing - handled by npc_taxi
+EndContentData */
+
+#include "ScriptedPch.h"
+
+/*######
+## mobs_risen_husk_spirit
+######*/
+
+enum eHuskSpirit
+{
+ QUEST_WHATS_HAUNTING_WITCH_HILL = 11180,
+
+ SPELL_SUMMON_RESTLESS_APPARITION = 42511,
+ SPELL_CONSUME_FLESH = 37933, //Risen Husk
+ SPELL_INTANGIBLE_PRESENCE = 43127, //Risen Spirit
+
+ NPC_RISEN_HUSK = 23555,
+ NPC_RISEN_SPIRIT = 23554,
+ NPC_RESTLESS_APPARITION = 23861
+};
+
+struct mobs_risen_husk_spiritAI : public ScriptedAI
+{
+ mobs_risen_husk_spiritAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 m_uiConsumeFlesh_Timer;
+ uint32 m_uiIntangiblePresence_Timer;
+
+ void Reset()
+ {
+ m_uiConsumeFlesh_Timer = 10000;
+ m_uiIntangiblePresence_Timer = 5000;
+ }
+
+ void UpdateAI(const uint32 uiDiff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ if (m_uiConsumeFlesh_Timer <= uiDiff)
+ {
+ if (me->GetEntry() == NPC_RISEN_HUSK)
+ DoCast(me->getVictim(), SPELL_CONSUME_FLESH);
+
+ m_uiConsumeFlesh_Timer = 15000;
+ }
+ else
+ m_uiConsumeFlesh_Timer -= uiDiff;
+
+ if (m_uiIntangiblePresence_Timer <= uiDiff)
+ {
+ if (me->GetEntry() == NPC_RISEN_SPIRIT)
+ DoCast(me->getVictim(), SPELL_INTANGIBLE_PRESENCE);
+
+ m_uiIntangiblePresence_Timer = 20000;
+ }
+ else
+ m_uiIntangiblePresence_Timer -= uiDiff;
+
+ DoMeleeAttackIfReady();
+ }
+
+ void JustDied(Unit* pKiller)
+ {
+ if (pKiller->GetTypeId() == TYPEID_PLAYER)
+ if (CAST_PLR(pKiller)->GetQuestStatus(QUEST_WHATS_HAUNTING_WITCH_HILL) == QUEST_STATUS_INCOMPLETE)
+ {
+ DoCast(pKiller, SPELL_SUMMON_RESTLESS_APPARITION, true);
+ CAST_PLR(pKiller)->KilledMonsterCredit(NPC_RESTLESS_APPARITION,0);
+ }
+ }
+};
+
+CreatureAI* GetAI_mobs_risen_husk_spirit(Creature* pCreature)
+{
+ return new mobs_risen_husk_spiritAI (pCreature);
+}
+
+/*######
+## npc_restless_apparition
+######*/
+
+enum eRestlessApparition
+{
+ SAY_RESTLESS_1 = -1000469,
+ SAY_RESTLESS_2 = -1000470,
+ SAY_RESTLESS_3 = -1000471
+};
+
+struct npc_restless_apparitionAI : public ScriptedAI
+{
+ npc_restless_apparitionAI(Creature* pCreature) : ScriptedAI(pCreature) {}
+
+ void Reset()
+ {
+ DoScriptText(RAND(SAY_RESTLESS_1,SAY_RESTLESS_2,SAY_RESTLESS_3), me);
+ }
+};
+
+CreatureAI* GetAI_npc_restless_apparition(Creature* pCreature)
+{
+ return new npc_restless_apparitionAI (pCreature);
+}
+
+/*######
+## npc_deserter_agitator
+######*/
+
+enum eAgitator
+{
+ QUEST_TRAITORS_AMONG_US = 11126,
+ FACTION_THER_DESERTER = 1883
+};
+
+struct npc_deserter_agitatorAI : public ScriptedAI
+{
+ npc_deserter_agitatorAI(Creature* pCreature) : ScriptedAI(pCreature) { }
+
+ void Reset()
+ {
+ me->RestoreFaction();
+ }
+};
+
+CreatureAI* GetAI_npc_deserter_agitator(Creature* pCreature)
+{
+ return new npc_deserter_agitatorAI (pCreature);
+}
+
+bool GossipHello_npc_deserter_agitator(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->GetQuestStatus(QUEST_TRAITORS_AMONG_US) == QUEST_STATUS_INCOMPLETE)
+ {
+ pCreature->setFaction(FACTION_THER_DESERTER);
+ pPlayer->TalkedToCreature(pCreature->GetEntry(), pCreature->GetGUID());
+ }
+ else
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+
+ return true;
+}
+
+/*######
+## npc_lady_jaina_proudmoore
+######*/
+
+enum eLadyJaina
+{
+ QUEST_JAINAS_AUTOGRAPH = 558,
+ SPELL_JAINAS_AUTOGRAPH = 23122
+};
+
+#define GOSSIP_ITEM_JAINA "I know this is rather silly but i have a young ward who is a bit shy and would like your autograph."
+
+bool GossipHello_npc_lady_jaina_proudmoore(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(QUEST_JAINAS_AUTOGRAPH) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_JAINA, GOSSIP_SENDER_MAIN, GOSSIP_SENDER_INFO);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_lady_jaina_proudmoore(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_SENDER_INFO)
+ {
+ pPlayer->SEND_GOSSIP_MENU(7012, pCreature->GetGUID());
+ pPlayer->CastSpell(pPlayer, SPELL_JAINAS_AUTOGRAPH, false);
+ }
+ return true;
+}
+
+/*######
+## npc_nat_pagle
+######*/
+
+enum eNatPagle
+{
+ QUEST_NATS_MEASURING_TAPE = 8227
+};
+
+bool GossipHello_npc_nat_pagle(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pCreature->isVendor() && pPlayer->GetQuestRewardStatus(QUEST_NATS_MEASURING_TAPE))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_VENDOR, GOSSIP_TEXT_BROWSE_GOODS, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_TRADE);
+ pPlayer->SEND_GOSSIP_MENU(7640, pCreature->GetGUID());
+ }
+ else
+ pPlayer->SEND_GOSSIP_MENU(7638, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_nat_pagle(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_TRADE)
+ pPlayer->SEND_VENDORLIST(pCreature->GetGUID());
+
+ return true;
+}
+
+/*######
+## npc_private_hendel
+######*/
+
+enum eHendel
+{
+ // looks like all this text ids are wrong.
+ SAY_PROGRESS_1_TER = -1000411, // signed for 3568
+ SAY_PROGRESS_2_HEN = -1000412, // signed for 3568
+ SAY_PROGRESS_3_TER = -1000413,
+ SAY_PROGRESS_4_TER = -1000414,
+ EMOTE_SURRENDER = -1000415,
+
+ QUEST_MISSING_DIPLO_PT16 = 1324,
+ FACTION_HOSTILE = 168, //guessed, may be different
+
+ NPC_SENTRY = 5184, //helps hendel
+ NPC_JAINA = 4968, //appears once hendel gives up
+ NPC_TERVOSH = 4967
+};
+
+//TODO: develop this further, end event not created
+struct npc_private_hendelAI : public ScriptedAI
+{
+ npc_private_hendelAI(Creature* pCreature) : ScriptedAI(pCreature) { }
+
+ void Reset()
+ {
+ me->RestoreFaction();
+ }
+
+ void AttackedBy(Unit* pAttacker)
+ {
+ if (me->getVictim())
+ return;
+
+ if (me->IsFriendlyTo(pAttacker))
+ return;
+
+ AttackStart(pAttacker);
+ }
+
+ void DamageTaken(Unit* pDoneBy, uint32 &uiDamage)
+ {
+ if (uiDamage > me->GetHealth() || ((me->GetHealth() - uiDamage)*100 / me->GetMaxHealth() < 20))
+ {
+ uiDamage = 0;
+
+ if (Player* pPlayer = pDoneBy->GetCharmerOrOwnerPlayerOrPlayerItself())
+ pPlayer->GroupEventHappens(QUEST_MISSING_DIPLO_PT16, me);
+
+ DoScriptText(EMOTE_SURRENDER, me);
+ EnterEvadeMode();
+ }
+ }
+};
+
+bool QuestAccept_npc_private_hendel(Player* /*pPlayer*/, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_MISSING_DIPLO_PT16)
+ pCreature->setFaction(FACTION_HOSTILE);
+
+ return true;
+}
+
+CreatureAI* GetAI_npc_private_hendel(Creature* pCreature)
+{
+ return new npc_private_hendelAI(pCreature);
+}
+
+/*######
+## npc_zelfrax
+######*/
+
+const Position MovePosition = {-2967.030,-3872.1799,35.620};
+
+enum eZelfrax
+{
+ SAY_ZELFRAX = -1000472,
+ SAY_ZELFRAX_2 = -1000473
+};
+
+struct npc_zelfraxAI : public ScriptedAI
+{
+ npc_zelfraxAI(Creature* pCreature) : ScriptedAI(pCreature)
+ {
+ MoveToDock();
+ }
+
+ void AttackStart(Unit* pWho)
+ {
+ if (!pWho)
+ return;
+
+ if (me->Attack(pWho, true))
+ {
+ me->SetInCombatWith(pWho);
+ pWho->SetInCombatWith(me);
+
+ if (IsCombatMovement())
+ me->GetMotionMaster()->MoveChase(pWho);
+ }
+ }
+
+ void MovementInform(uint32 uiType, uint32 /*uiId*/)
+ {
+ if (uiType != POINT_MOTION_TYPE)
+ return;
+
+ me->SetHomePosition(me->GetPositionX(),me->GetPositionY(),me->GetPositionZ(),me->GetOrientation());
+ me->RemoveFlag(UNIT_FIELD_FLAGS,UNIT_FLAG_OOC_NOT_ATTACKABLE);
+ SetCombatMovement(true);
+
+ if (me->isInCombat())
+ if (Unit* pUnit = me->getVictim())
+ me->GetMotionMaster()->MoveChase(pUnit);
+ }
+
+ void MoveToDock()
+ {
+ SetCombatMovement(false);
+ me->GetMotionMaster()->MovePoint(0,MovePosition);
+ DoScriptText(SAY_ZELFRAX,me);
+ DoScriptText(SAY_ZELFRAX_2,me);
+ }
+
+ void UpdateAI(uint32 const /*uiDiff*/)
+ {
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_zelfrax(Creature* pCreature)
+{
+ return new npc_zelfraxAI(pCreature);
+}
+
+void AddSC_dustwallow_marsh()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "mobs_risen_husk_spirit";
+ newscript->GetAI = &GetAI_mobs_risen_husk_spirit;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_restless_apparition";
+ newscript->GetAI = &GetAI_npc_restless_apparition;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_deserter_agitator";
+ newscript->GetAI = &GetAI_npc_deserter_agitator;
+ newscript->pGossipHello = &GossipHello_npc_deserter_agitator;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_lady_jaina_proudmoore";
+ newscript->pGossipHello = &GossipHello_npc_lady_jaina_proudmoore;
+ newscript->pGossipSelect = &GossipSelect_npc_lady_jaina_proudmoore;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_nat_pagle";
+ newscript->pGossipHello = &GossipHello_npc_nat_pagle;
+ newscript->pGossipSelect = &GossipSelect_npc_nat_pagle;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_private_hendel";
+ newscript->GetAI = &GetAI_npc_private_hendel;
+ newscript->pQuestAccept = &QuestAccept_npc_private_hendel;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_zelfrax";
+ newscript->GetAI = &GetAI_npc_zelfrax;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/felwood.cpp b/src/server/scripts/Kalimdor/felwood.cpp
new file mode 100644
index 00000000000..01da356a63e
--- /dev/null
+++ b/src/server/scripts/Kalimdor/felwood.cpp
@@ -0,0 +1,90 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Felwood
+SD%Complete: 95
+SDComment: Quest support: 4101, 4102
+SDCategory: Felwood
+EndScriptData */
+
+/* ContentData
+npcs_riverbreeze_and_silversky
+EndContentData */
+
+#include "ScriptedPch.h"
+
+/*######
+## npcs_riverbreeze_and_silversky
+######*/
+
+#define GOSSIP_ITEM_BEACON "Please make me a Cenarion Beacon"
+
+bool GossipHello_npcs_riverbreeze_and_silversky(Player* pPlayer, Creature* pCreature)
+{
+ uint32 eCreature = pCreature->GetEntry();
+
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (eCreature == 9528)
+ {
+ if (pPlayer->GetQuestRewardStatus(4101))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_BEACON, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(2848, pCreature->GetGUID());
+ } else if (pPlayer->GetTeam() == HORDE)
+ pPlayer->SEND_GOSSIP_MENU(2845, pCreature->GetGUID());
+ else
+ pPlayer->SEND_GOSSIP_MENU(2844, pCreature->GetGUID());
+ }
+
+ if (eCreature == 9529)
+ {
+ if (pPlayer->GetQuestRewardStatus(4102))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_BEACON, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(2849, pCreature->GetGUID());
+ } else if (pPlayer->GetTeam() == ALLIANCE)
+ pPlayer->SEND_GOSSIP_MENU(2843, pCreature->GetGUID());
+ else
+ pPlayer->SEND_GOSSIP_MENU(2842, pCreature->GetGUID());
+ }
+
+ return true;
+}
+
+bool GossipSelect_npcs_riverbreeze_and_silversky(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pCreature->CastSpell(pPlayer, 15120, false);
+ }
+ return true;
+}
+
+void AddSC_felwood()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npcs_riverbreeze_and_silversky";
+ newscript->pGossipHello = &GossipHello_npcs_riverbreeze_and_silversky;
+ newscript->pGossipSelect = &GossipSelect_npcs_riverbreeze_and_silversky;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/feralas.cpp b/src/server/scripts/Kalimdor/feralas.cpp
new file mode 100644
index 00000000000..2a87de1a67c
--- /dev/null
+++ b/src/server/scripts/Kalimdor/feralas.cpp
@@ -0,0 +1,206 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Feralas
+SD%Complete: 100
+SDComment: Quest support: 3520, 2767, Special vendor Gregan Brewspewer
+SDCategory: Feralas
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+
+/*######
+## npc_gregan_brewspewer
+######*/
+
+#define GOSSIP_HELLO "Buy somethin', will ya?"
+
+bool GossipHello_npc_gregan_brewspewer(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pCreature->isVendor() && pPlayer->GetQuestStatus(3909) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HELLO, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+
+ pPlayer->SEND_GOSSIP_MENU(2433, pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_gregan_brewspewer(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_VENDOR, GOSSIP_TEXT_BROWSE_GOODS, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_TRADE);
+ pPlayer->SEND_GOSSIP_MENU(2434, pCreature->GetGUID());
+ }
+ if (uiAction == GOSSIP_ACTION_TRADE)
+ pPlayer->SEND_VENDORLIST(pCreature->GetGUID());
+ return true;
+}
+
+/*######
+## npc_oox22fe
+######*/
+
+enum eOOX
+{
+ //signed for 7806
+ SAY_OOX_START = -1000287,
+ SAY_OOX_AGGRO1 = -1000288,
+ SAY_OOX_AGGRO2 = -1000289,
+ SAY_OOX_AMBUSH = -1000290,
+ SAY_OOX_END = -1000292,
+
+ NPC_YETI = 7848,
+ NPC_GORILLA = 5260,
+ NPC_WOODPAW_REAVER = 5255,
+ NPC_WOODPAW_BRUTE = 5253,
+ NPC_WOODPAW_ALPHA = 5258,
+ NPC_WOODPAW_MYSTIC = 5254,
+
+ QUEST_RESCUE_OOX22FE = 2767,
+ FACTION_ESCORTEE_A = 774,
+ FACTION_ESCORTEE_H = 775
+};
+
+struct npc_oox22feAI : public npc_escortAI
+{
+ npc_oox22feAI(Creature* pCreature) : npc_escortAI(pCreature) { }
+
+ void WaypointReached(uint32 i)
+ {
+ switch (i)
+ {
+ // First Ambush(3 Yetis)
+ case 11:
+ DoScriptText(SAY_OOX_AMBUSH, me);
+ me->SummonCreature(NPC_YETI, -4841.01, 1593.91, 73.42, 3.98, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ me->SummonCreature(NPC_YETI, -4837.61, 1568.58, 78.21, 3.13, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ me->SummonCreature(NPC_YETI, -4841.89, 1569.95, 76.53, 0.68, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ break;
+ //Second Ambush(3 Gorillas)
+ case 21:
+ DoScriptText(SAY_OOX_AMBUSH, me);
+ me->SummonCreature(NPC_GORILLA, -4595.81, 2005.99, 53.08, 3.74, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ me->SummonCreature(NPC_GORILLA, -4597.53, 2008.31, 52.70, 3.78, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ me->SummonCreature(NPC_GORILLA, -4599.37, 2010.59, 52.77, 3.84, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ break;
+ //Third Ambush(4 Gnolls)
+ case 30:
+ DoScriptText(SAY_OOX_AMBUSH, me);
+ me->SummonCreature(NPC_WOODPAW_REAVER, -4425.14, 2075.87, 47.77, 3.77, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ me->SummonCreature(NPC_WOODPAW_BRUTE , -4426.68, 2077.98, 47.57, 3.77, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ me->SummonCreature(NPC_WOODPAW_MYSTIC, -4428.33, 2080.24, 47.43, 3.87, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ me->SummonCreature(NPC_WOODPAW_ALPHA , -4430.04, 2075.54, 46.83, 3.81, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 10000);
+ break;
+ case 37:
+ DoScriptText(SAY_OOX_END, me);
+ // Award quest credit
+ if (Player* pPlayer = GetPlayerForEscort())
+ {
+ pPlayer->GroupEventHappens(QUEST_RESCUE_OOX22FE, me);
+ }
+ break;
+ }
+ }
+
+ void Reset()
+ {
+ if (!HasEscortState(STATE_ESCORT_ESCORTING))
+ me->SetStandState(UNIT_STAND_STATE_DEAD);
+ }
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ //For an small probability the npc says something when he get aggro
+ if (urand(0,9) > 7)
+ DoScriptText(RAND(SAY_OOX_AGGRO1,SAY_OOX_AGGRO2), me);
+ }
+
+ void JustSummoned(Creature* summoned)
+ {
+ summoned->AI()->AttackStart(me);
+ }
+};
+
+CreatureAI* GetAI_npc_oox22fe(Creature* pCreature)
+{
+ return new npc_oox22feAI(pCreature);
+}
+
+bool QuestAccept_npc_oox22fe(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_RESCUE_OOX22FE)
+ {
+ DoScriptText(SAY_OOX_START, pCreature);
+ //change that the npc is not lying dead on the ground
+ pCreature->SetStandState(UNIT_STAND_STATE_STAND);
+
+ if (pPlayer->GetTeam() == ALLIANCE)
+ pCreature->setFaction(FACTION_ESCORTEE_A);
+
+ if (pPlayer->GetTeam() == HORDE)
+ pCreature->setFaction(FACTION_ESCORTEE_H);
+
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_oox22feAI, pCreature->AI()))
+ pEscortAI->Start(true, false, pPlayer->GetGUID());
+
+ }
+ return true;
+}
+
+/*######
+## npc_screecher_spirit
+######*/
+
+bool GossipHello_npc_screecher_spirit(Player* pPlayer, Creature* pCreature)
+{
+ pPlayer->SEND_GOSSIP_MENU(2039, pCreature->GetGUID());
+ pPlayer->TalkedToCreature(pCreature->GetEntry(), pCreature->GetGUID());
+ pCreature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+
+ return true;
+}
+
+/*######
+## AddSC
+######*/
+
+void AddSC_feralas()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_gregan_brewspewer";
+ newscript->pGossipHello = &GossipHello_npc_gregan_brewspewer;
+ newscript->pGossipSelect = &GossipSelect_npc_gregan_brewspewer;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_oox22fe";
+ newscript->GetAI = &GetAI_npc_oox22fe;
+ newscript->pQuestAccept = &QuestAccept_npc_oox22fe;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_screecher_spirit";
+ newscript->pGossipHello = &GossipHello_npc_screecher_spirit;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/maraudon/boss_celebras_the_cursed.cpp b/src/server/scripts/Kalimdor/maraudon/boss_celebras_the_cursed.cpp
new file mode 100644
index 00000000000..6f6b9d1baa9
--- /dev/null
+++ b/src/server/scripts/Kalimdor/maraudon/boss_celebras_the_cursed.cpp
@@ -0,0 +1,98 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Celebras_the_Cursed
+SD%Complete: 100
+SDComment:
+SDCategory: Maraudon
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define SPELL_WRATH 21807
+#define SPELL_ENTANGLINGROOTS 12747
+#define SPELL_CORRUPT_FORCES 21968
+
+struct celebras_the_cursedAI : public ScriptedAI
+{
+ celebras_the_cursedAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 Wrath_Timer;
+ uint32 EntanglingRoots_Timer;
+ uint32 CorruptForces_Timer;
+
+ void Reset()
+ {
+ Wrath_Timer = 8000;
+ EntanglingRoots_Timer = 2000;
+ CorruptForces_Timer = 30000;
+ }
+
+ void EnterCombat(Unit * /*who*/) { }
+
+ void JustDied(Unit* /*Killer*/)
+ {
+ me->SummonCreature(13716, me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN, 600000);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ //Wrath
+ if (Wrath_Timer <= diff)
+ {
+ Unit *pTarget = NULL;
+ pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+ if (pTarget)
+ DoCast(pTarget, SPELL_WRATH);
+ Wrath_Timer = 8000;
+ } else Wrath_Timer -= diff;
+
+ //EntanglingRoots
+ if (EntanglingRoots_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_ENTANGLINGROOTS);
+ EntanglingRoots_Timer = 20000;
+ } else EntanglingRoots_Timer -= diff;
+
+ //CorruptForces
+ if (CorruptForces_Timer <= diff)
+ {
+ me->InterruptNonMeleeSpells(false);
+ DoCast(me, SPELL_CORRUPT_FORCES);
+ CorruptForces_Timer = 20000;
+ } else CorruptForces_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_celebras_the_cursed(Creature* pCreature)
+{
+ return new celebras_the_cursedAI (pCreature);
+}
+
+void AddSC_boss_celebras_the_cursed()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "celebras_the_cursed";
+ newscript->GetAI = &GetAI_celebras_the_cursed;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/maraudon/boss_landslide.cpp b/src/server/scripts/Kalimdor/maraudon/boss_landslide.cpp
new file mode 100644
index 00000000000..d5b03ff218f
--- /dev/null
+++ b/src/server/scripts/Kalimdor/maraudon/boss_landslide.cpp
@@ -0,0 +1,95 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Landslide
+SD%Complete: 100
+SDComment:
+SDCategory: Maraudon
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define SPELL_KNOCKAWAY 18670
+#define SPELL_TRAMPLE 5568
+#define SPELL_LANDSLIDE 21808
+
+struct boss_landslideAI : public ScriptedAI
+{
+ boss_landslideAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 KnockAway_Timer;
+ uint32 Trample_Timer;
+ uint32 Landslide_Timer;
+
+ void Reset()
+ {
+ KnockAway_Timer = 8000;
+ Trample_Timer = 2000;
+ Landslide_Timer = 0;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ //KnockAway_Timer
+ if (KnockAway_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_KNOCKAWAY);
+ KnockAway_Timer = 15000;
+ } else KnockAway_Timer -= diff;
+
+ //Trample_Timer
+ if (Trample_Timer <= diff)
+ {
+ DoCast(me, SPELL_TRAMPLE);
+ Trample_Timer = 8000;
+ } else Trample_Timer -= diff;
+
+ //Landslide
+ if (me->GetHealth()*100 / me->GetMaxHealth() < 50)
+ {
+ if (Landslide_Timer <= diff)
+ {
+ me->InterruptNonMeleeSpells(false);
+ DoCast(me, SPELL_LANDSLIDE);
+ Landslide_Timer = 60000;
+ } else Landslide_Timer -= diff;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_boss_landslide(Creature* pCreature)
+{
+ return new boss_landslideAI (pCreature);
+}
+
+void AddSC_boss_landslide()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_landslide";
+ newscript->GetAI = &GetAI_boss_landslide;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/maraudon/boss_noxxion.cpp b/src/server/scripts/Kalimdor/maraudon/boss_noxxion.cpp
new file mode 100644
index 00000000000..b49b1a5d71f
--- /dev/null
+++ b/src/server/scripts/Kalimdor/maraudon/boss_noxxion.cpp
@@ -0,0 +1,131 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Noxxion
+SD%Complete: 100
+SDComment:
+SDCategory: Maraudon
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define SPELL_TOXICVOLLEY 21687
+#define SPELL_UPPERCUT 22916
+
+struct boss_noxxionAI : public ScriptedAI
+{
+ boss_noxxionAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 ToxicVolley_Timer;
+ uint32 Uppercut_Timer;
+ uint32 Adds_Timer;
+ uint32 Invisible_Timer;
+ bool Invisible;
+
+ void Reset()
+ {
+ ToxicVolley_Timer = 7000;
+ Uppercut_Timer = 16000;
+ Adds_Timer = 19000;
+ Invisible_Timer = 15000; //Too much too low?
+ Invisible = false;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void SummonAdds(Unit* pVictim)
+ {
+ if (Creature *Add = DoSpawnCreature(13456, irand(-7,7), irand(-7,7), 0, 0, TEMPSUMMON_TIMED_OR_CORPSE_DESPAWN, 90000))
+ Add->AI()->AttackStart(pVictim);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (Invisible && Invisible_Timer <= diff)
+ {
+ //Become visible again
+ me->setFaction(14);
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ //Noxxion model
+ me->SetDisplayId(11172);
+ Invisible = false;
+ //me->m_canMove = true;
+ } else if (Invisible)
+ {
+ Invisible_Timer -= diff;
+ //Do nothing while invisible
+ return;
+ }
+
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //ToxicVolley_Timer
+ if (ToxicVolley_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_TOXICVOLLEY);
+ ToxicVolley_Timer = 9000;
+ } else ToxicVolley_Timer -= diff;
+
+ //Uppercut_Timer
+ if (Uppercut_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_UPPERCUT);
+ Uppercut_Timer = 12000;
+ } else Uppercut_Timer -= diff;
+
+ //Adds_Timer
+ if (!Invisible && Adds_Timer <= diff)
+ {
+ //Inturrupt any spell casting
+ //me->m_canMove = true;
+ me->InterruptNonMeleeSpells(false);
+ me->setFaction(35);
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ // Invisible Model
+ me->SetDisplayId(11686);
+ SummonAdds(me->getVictim());
+ SummonAdds(me->getVictim());
+ SummonAdds(me->getVictim());
+ SummonAdds(me->getVictim());
+ SummonAdds(me->getVictim());
+ Invisible = true;
+ Invisible_Timer = 15000;
+
+ Adds_Timer = 40000;
+ } else Adds_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_boss_noxxion(Creature* pCreature)
+{
+ return new boss_noxxionAI (pCreature);
+}
+
+void AddSC_boss_noxxion()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_noxxion";
+ newscript->GetAI = &GetAI_boss_noxxion;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/maraudon/boss_princess_theradras.cpp b/src/server/scripts/Kalimdor/maraudon/boss_princess_theradras.cpp
new file mode 100644
index 00000000000..963863e89c8
--- /dev/null
+++ b/src/server/scripts/Kalimdor/maraudon/boss_princess_theradras.cpp
@@ -0,0 +1,109 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Princess_Theradras
+SD%Complete: 100
+SDComment:
+SDCategory: Maraudon
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define SPELL_DUSTFIELD 21909
+#define SPELL_BOULDER 21832
+#define SPELL_THRASH 3391
+#define SPELL_REPULSIVEGAZE 21869
+
+struct boss_ptheradrasAI : public ScriptedAI
+{
+ boss_ptheradrasAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 Dustfield_Timer;
+ uint32 Boulder_Timer;
+ uint32 Thrash_Timer;
+ uint32 RepulsiveGaze_Timer;
+
+ void Reset()
+ {
+ Dustfield_Timer = 8000;
+ Boulder_Timer = 2000;
+ Thrash_Timer = 5000;
+ RepulsiveGaze_Timer = 23000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ me->SummonCreature(12238,28.067,61.875,-123.405,4.67,TEMPSUMMON_TIMED_DESPAWN,600000);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ //Dustfield_Timer
+ if (Dustfield_Timer <= diff)
+ {
+ DoCast(me, SPELL_DUSTFIELD);
+ Dustfield_Timer = 14000;
+ } else Dustfield_Timer -= diff;
+
+ //Boulder_Timer
+ if (Boulder_Timer <= diff)
+ {
+ Unit *pTarget = NULL;
+ pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+ if (pTarget)
+ DoCast(pTarget, SPELL_BOULDER);
+ Boulder_Timer = 10000;
+ } else Boulder_Timer -= diff;
+
+ //RepulsiveGaze_Timer
+ if (RepulsiveGaze_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_REPULSIVEGAZE);
+ RepulsiveGaze_Timer = 20000;
+ } else RepulsiveGaze_Timer -= diff;
+
+ //Thrash_Timer
+ if (Thrash_Timer <= diff)
+ {
+ DoCast(me, SPELL_THRASH);
+ Thrash_Timer = 18000;
+ } else Thrash_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_boss_ptheradras(Creature* pCreature)
+{
+ return new boss_ptheradrasAI (pCreature);
+}
+
+void AddSC_boss_ptheradras()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_princess_theradras";
+ newscript->GetAI = &GetAI_boss_ptheradras;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/moonglade.cpp b/src/server/scripts/Kalimdor/moonglade.cpp
new file mode 100644
index 00000000000..16c78f20812
--- /dev/null
+++ b/src/server/scripts/Kalimdor/moonglade.cpp
@@ -0,0 +1,571 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Moonglade
+SD%Complete: 100
+SDComment: Quest support: 30, 272, 5929, 5930, 10965. Special Flight Paths for Druid class.
+SDCategory: Moonglade
+EndScriptData */
+
+/* ContentData
+npc_bunthen_plainswind
+npc_great_bear_spirit
+npc_silva_filnaveth
+npc_clintar_spirit
+npc_clintar_dreamwalker
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+
+/*######
+## npc_bunthen_plainswind
+######*/
+
+enum eBunthen
+{
+ QUEST_SEA_LION_HORDE = 30,
+ QUEST_SEA_LION_ALLY = 272,
+ TAXI_PATH_ID_ALLY = 315,
+ TAXI_PATH_ID_HORDE = 316
+};
+
+#define GOSSIP_ITEM_THUNDER "I'd like to fly to Thunder Bluff."
+#define GOSSIP_ITEM_AQ_END "Do you know where I can find Half Pendant of Aquatic Endurance?"
+
+bool GossipHello_npc_bunthen_plainswind(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->getClass() != CLASS_DRUID)
+ pPlayer->SEND_GOSSIP_MENU(4916, pCreature->GetGUID());
+ else if (pPlayer->GetTeam() != HORDE)
+ {
+ if (pPlayer->GetQuestStatus(QUEST_SEA_LION_ALLY) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_AQ_END, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
+
+ pPlayer->SEND_GOSSIP_MENU(4917, pCreature->GetGUID());
+ }
+ else if (pPlayer->getClass() == CLASS_DRUID && pPlayer->GetTeam() == HORDE)
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_THUNDER, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+
+ if (pPlayer->GetQuestStatus(QUEST_SEA_LION_HORDE) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_AQ_END, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 3);
+
+ pPlayer->SEND_GOSSIP_MENU(4918, pCreature->GetGUID());
+ }
+ return true;
+}
+
+bool GossipSelect_npc_bunthen_plainswind(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch(uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF + 1:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ if (pPlayer->getClass() == CLASS_DRUID && pPlayer->GetTeam() == HORDE)
+ pPlayer->ActivateTaxiPathTo(TAXI_PATH_ID_HORDE);
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 2:
+ pPlayer->SEND_GOSSIP_MENU(5373, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 3:
+ pPlayer->SEND_GOSSIP_MENU(5376, pCreature->GetGUID());
+ break;
+ }
+ return true;
+}
+
+/*######
+## npc_great_bear_spirit
+######*/
+
+#define GOSSIP_BEAR1 "What do you represent, spirit?"
+#define GOSSIP_BEAR2 "I seek to understand the importance of strength of the body."
+#define GOSSIP_BEAR3 "I seek to understand the importance of strength of the heart."
+#define GOSSIP_BEAR4 "I have heard your words, Great Bear Spirit, and I understand. I now seek your blessings to fully learn the way of the Claw."
+
+bool GossipHello_npc_great_bear_spirit(Player* pPlayer, Creature* pCreature)
+{
+ //ally or horde quest
+ if (pPlayer->GetQuestStatus(5929) == QUEST_STATUS_INCOMPLETE || pPlayer->GetQuestStatus(5930) == QUEST_STATUS_INCOMPLETE)
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_BEAR1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+ pPlayer->SEND_GOSSIP_MENU(4719, pCreature->GetGUID());
+ }
+ else
+ pPlayer->SEND_GOSSIP_MENU(4718, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_great_bear_spirit(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch (uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_BEAR2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+ pPlayer->SEND_GOSSIP_MENU(4721, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 1:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_BEAR3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
+ pPlayer->SEND_GOSSIP_MENU(4733, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_BEAR4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 3);
+ pPlayer->SEND_GOSSIP_MENU(4734, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 3:
+ pPlayer->SEND_GOSSIP_MENU(4735, pCreature->GetGUID());
+ if (pPlayer->GetQuestStatus(5929) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->AreaExploredOrEventHappens(5929);
+ if (pPlayer->GetQuestStatus(5930) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->AreaExploredOrEventHappens(5930);
+ break;
+ }
+ return true;
+}
+
+/*######
+## npc_silva_filnaveth
+######*/
+
+#define GOSSIP_ITEM_RUTHERAN "I'd like to fly to Rut'theran Village."
+#define GOSSIP_ITEM_AQ_AGI "Do you know where I can find Half Pendant of Aquatic Agility?"
+
+bool GossipHello_npc_silva_filnaveth(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->getClass() != CLASS_DRUID)
+ pPlayer->SEND_GOSSIP_MENU(4913, pCreature->GetGUID());
+ else if (pPlayer->GetTeam() != ALLIANCE)
+ {
+ if (pPlayer->GetQuestStatus(QUEST_SEA_LION_HORDE) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_AQ_AGI, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
+
+ pPlayer->SEND_GOSSIP_MENU(4915, pCreature->GetGUID());
+ }
+ else if (pPlayer->getClass() == CLASS_DRUID && pPlayer->GetTeam() == ALLIANCE)
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_RUTHERAN, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+
+ if (pPlayer->GetQuestStatus(QUEST_SEA_LION_ALLY) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_AQ_AGI, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 3);
+
+ pPlayer->SEND_GOSSIP_MENU(4914, pCreature->GetGUID());
+ }
+ return true;
+}
+
+bool GossipSelect_npc_silva_filnaveth(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch(uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF + 1:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ if (pPlayer->getClass() == CLASS_DRUID && pPlayer->GetTeam() == ALLIANCE)
+ pPlayer->ActivateTaxiPathTo(TAXI_PATH_ID_ALLY);
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 2:
+ pPlayer->SEND_GOSSIP_MENU(5374, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 3:
+ pPlayer->SEND_GOSSIP_MENU(5375, pCreature->GetGUID());
+ break;
+ }
+ return true;
+}
+
+/*######
+## npc_clintar_spirit
+######*/
+
+float Clintar_spirit_WP[41][5] =
+{
+ //pos_x pos_y pos_z orien waitTime
+{7465.28, -3115.46, 439.327, 0.83, 4000},
+{7476.49, -3101, 443.457, 0.89, 0},
+{7486.57, -3085.59, 439.478, 1.07, 0},
+{7472.19, -3085.06, 443.142, 3.07, 0},
+{7456.92, -3085.91, 438.862, 3.24, 0},
+{7446.68, -3083.43, 438.245, 2.40, 0},
+{7446.17, -3080.21, 439.826, 1.10, 6000},
+{7452.41, -3085.8, 438.984, 5.78, 0},
+{7469.11, -3084.94, 443.048, 6.25, 0},
+{7483.79, -3085.44, 439.607, 6.25, 0},
+{7491.14, -3090.96, 439.983, 5.44, 0},
+{7497.62, -3098.22, 436.854, 5.44, 0},
+{7498.72, -3113.41, 434.596, 4.84, 0},
+{7500.06, -3122.51, 434.749, 5.17, 0},
+{7504.96, -3131.53, 434.475, 4.74, 0},
+{7504.31, -3133.53, 435.693, 3.84, 6000},
+{7504.55, -3133.27, 435.476, 0.68, 15000},
+{7501.99, -3126.01, 434.93, 1.83, 0},
+{7490.76, -3114.97, 434.431, 2.51, 0},
+{7479.64, -3105.51, 431.123, 1.83, 0},
+{7474.63, -3086.59, 428.994, 1.83, 2000},
+{7472.96, -3074.18, 427.566, 1.57, 0},
+{7472.25, -3063, 428.268, 1.55, 0},
+{7473.46, -3054.22, 427.588, 0.36, 0},
+{7475.08, -3053.6, 428.653, 0.36, 6000},
+{7474.66, -3053.56, 428.433, 3.19, 4000},
+{7471.81, -3058.84, 427.073, 4.29, 0},
+{7472.16, -3064.91, 427.772, 4.95, 0},
+{7471.56, -3085.36, 428.924, 4.72, 0},
+{7473.56, -3093.48, 429.294, 5.04, 0},
+{7478.94, -3104.29, 430.638, 5.23, 0},
+{7484.46, -3109.61, 432.769, 5.79, 0},
+{7490.23, -3111.08, 434.431, 0.02, 0},
+{7496.29, -3108, 434.783, 1.15, 0},
+{7497.46, -3100.66, 436.191, 1.50, 0},
+{7495.64, -3093.39, 438.349, 2.10, 0},
+{7492.44, -3086.01, 440.267, 1.38, 0},
+{7498.26, -3076.44, 440.808, 0.71, 0},
+{7506.4, -3067.35, 443.64, 0.77, 0},
+{7518.37, -3057.42, 445.584, 0.74, 0},
+{7517.51, -3056.3, 444.568, 2.49, 4500}
+};
+
+#define ASPECT_RAVEN 22915
+
+#define ASPECT_RAVEN_SUMMON_X 7472.96
+#define ASPECT_RAVEN_SUMMON_Y -3074.18
+#define ASPECT_RAVEN_SUMMON_Z 427.566
+#define CLINTAR_SPIRIT_SUMMON_X 7459.2275
+#define CLINTAR_SPIRIT_SUMMON_Y -3122.5632
+#define CLINTAR_SPIRIT_SUMMON_Z 438.9842
+#define CLINTAR_SPIRIT_SUMMON_O 0.8594
+
+//from -1000292 to -1000287 are signed for 7806. but all this texts ids wrong.
+#define CLINTAR_SPIRIT_SAY_START -1000286
+#define CLINTAR_SPIRIT_SAY_UNDER_ATTACK_1 -1000287
+#define CLINTAR_SPIRIT_SAY_UNDER_ATTACK_2 -1000288
+#define CLINTAR_SPIRIT_SAY_GET_ONE -1000289
+#define CLINTAR_SPIRIT_SAY_GET_TWO -1000290
+#define CLINTAR_SPIRIT_SAY_GET_THREE -1000291
+#define CLINTAR_SPIRIT_SAY_GET_FINAL -1000292
+
+struct npc_clintar_spiritAI : public npc_escortAI
+{
+public:
+ npc_clintar_spiritAI(Creature *c) : npc_escortAI(c) {}
+
+ uint32 Step;
+ uint32 CurrWP;
+ uint32 Event_Timer;
+ uint32 checkPlayer_Timer;
+
+ uint64 PlayerGUID;
+
+ bool Event_onWait;
+
+ void Reset()
+ {
+ if (!PlayerGUID)
+ {
+ Step = 0;
+ CurrWP = 0;
+ Event_Timer = 0;
+ PlayerGUID = 0;
+ checkPlayer_Timer = 1000;
+ Event_onWait = false;
+ }
+ }
+
+ void JustDied(Unit * /*killer*/)
+ {
+ if (!PlayerGUID)
+ return;
+
+ Player* pPlayer = Unit::GetPlayer(PlayerGUID);
+ if (pPlayer && pPlayer->GetQuestStatus(10965) == QUEST_STATUS_INCOMPLETE)
+ {
+ pPlayer->FailQuest(10965);
+ PlayerGUID = 0;
+ Reset();
+ }
+ }
+
+ void EnterEvadeMode()
+ {
+ Player* pPlayer = Unit::GetPlayer(PlayerGUID);
+ if (pPlayer && pPlayer->isInCombat() && pPlayer->getAttackerForHelper())
+ {
+ AttackStart(pPlayer->getAttackerForHelper());
+ return;
+ }
+ npc_escortAI::EnterEvadeMode();
+ }
+
+ void EnterCombat(Unit* who)
+ {
+ uint32 rnd = rand()%2;
+ switch(rnd)
+ {
+ case 0: DoScriptText(CLINTAR_SPIRIT_SAY_UNDER_ATTACK_1, me, who); break;
+ case 1: DoScriptText(CLINTAR_SPIRIT_SAY_UNDER_ATTACK_2, me, who); break;
+ }
+ }
+
+ void StartEvent(Player* pPlayer)
+ {
+ if (!pPlayer)
+ return;
+ if (pPlayer->GetQuestStatus(10965) == QUEST_STATUS_INCOMPLETE)
+ {
+ for (uint8 i = 0; i < 41; ++i)
+ {
+ AddWaypoint(i, Clintar_spirit_WP[i][0], Clintar_spirit_WP[i][1], Clintar_spirit_WP[i][2], (uint32)Clintar_spirit_WP[i][4]);
+ }
+ PlayerGUID = pPlayer->GetGUID();
+ Start(true,false,PlayerGUID);
+ }
+ return;
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ npc_escortAI::UpdateAI(diff);
+
+ if (!PlayerGUID)
+ {
+ me->setDeathState(JUST_DIED);
+ return;
+ }
+
+ if (!me->isInCombat() && !Event_onWait)
+ {
+ if (checkPlayer_Timer <= diff)
+ {
+ Player* pPlayer = Unit::GetPlayer(PlayerGUID);
+ if (pPlayer && pPlayer->isInCombat() && pPlayer->getAttackerForHelper())
+ AttackStart(pPlayer->getAttackerForHelper());
+ checkPlayer_Timer = 1000;
+ } else checkPlayer_Timer -= diff;
+ }
+
+ if (Event_onWait && Event_Timer <= diff)
+ {
+
+ Player* pPlayer = Unit::GetPlayer(PlayerGUID);
+ if (!pPlayer || (pPlayer && pPlayer->GetQuestStatus(10965) == QUEST_STATUS_NONE))
+ {
+ me->setDeathState(JUST_DIED);
+ return;
+ }
+
+ switch(CurrWP)
+ {
+ case 0:
+ switch(Step)
+ {
+ case 0:
+ me->Say(CLINTAR_SPIRIT_SAY_START,0,PlayerGUID);
+ Event_Timer = 8000;
+ Step = 1;
+ break;
+ case 1:
+ Event_onWait = false;
+ break;
+ }
+ break;
+ case 6:
+ switch(Step)
+ {
+ case 0:
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, 133);
+ Event_Timer = 5000;
+ Step = 1;
+ break;
+ case 1:
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, 0);
+ DoScriptText(CLINTAR_SPIRIT_SAY_GET_ONE, me, pPlayer);
+ Event_onWait = false;
+ break;
+ }
+ break;
+ case 15:
+ switch(Step)
+ {
+ case 0:
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, 133);
+ Event_Timer = 5000;
+ Step = 1;
+ break;
+ case 1:
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, 0);
+ Event_onWait = false;
+ break;
+ }
+ break;
+ case 16:
+ switch(Step)
+ {
+ case 0:
+ DoScriptText(CLINTAR_SPIRIT_SAY_GET_TWO, me, pPlayer);
+ Event_Timer = 15000;
+ Step = 1;
+ break;
+ case 1:
+ Event_onWait = false;
+ break;
+ }
+ break;
+ case 20:
+ switch(Step)
+ {
+ case 0:
+ {
+ Creature *mob = me->SummonCreature(ASPECT_RAVEN, ASPECT_RAVEN_SUMMON_X, ASPECT_RAVEN_SUMMON_Y, ASPECT_RAVEN_SUMMON_Z, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 2000);
+ if (mob)
+ {
+ mob->AddThreat(me,10000.0f);
+ mob->AI()->AttackStart(me);
+ }
+ Event_Timer = 2000;
+ Step = 1;
+ break;
+ }
+ case 1:
+ Event_onWait = false;
+ break;
+ }
+ break;
+ case 24:
+ switch(Step)
+ {
+ case 0:
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, 133);
+ Event_Timer = 5000;
+ Step = 1;
+ break;
+ case 1:
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, 0);
+ Event_onWait = false;
+ break;
+ }
+ break;
+ case 25:
+ switch(Step)
+ {
+ case 0:
+ DoScriptText(CLINTAR_SPIRIT_SAY_GET_THREE, me, pPlayer);
+ Event_Timer = 4000;
+ Step = 1;
+ break;
+ case 1:
+ Event_onWait = false;
+ break;
+ }
+ break;
+ case 40:
+ switch(Step)
+ {
+ case 0:
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, 2);
+ DoScriptText(CLINTAR_SPIRIT_SAY_GET_FINAL, me, pPlayer);
+ pPlayer->CompleteQuest(10965);
+ Event_Timer = 1500;
+ Step = 1;
+ break;
+ case 1:
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, 0);
+ Event_Timer = 3000;
+ Step = 2;
+ break;
+ case 2:
+ pPlayer->TalkedToCreature(me->GetEntry(), me->GetGUID());
+ PlayerGUID = 0;
+ Reset();
+ me->setDeathState(JUST_DIED);
+ break;
+ }
+ break;
+ default:
+ Event_onWait = false;
+ break;
+ }
+
+ } else if (Event_onWait) Event_Timer -= diff;
+ }
+
+ void WaypointReached(uint32 id)
+ {
+ CurrWP = id;
+ Event_Timer = 0;
+ Step = 0;
+ Event_onWait = true;
+ }
+};
+
+CreatureAI* GetAI_npc_clintar_spirit(Creature* pCreature)
+{
+ return new npc_clintar_spiritAI (pCreature);
+}
+
+/*####
+# npc_clintar_dreamwalker
+####*/
+
+#define CLINTAR_SPIRIT 22916
+
+bool QuestAccept_npc_clintar_dreamwalker(Player* pPlayer, Creature* pCreature, Quest const *quest)
+{
+ if (quest->GetQuestId() == 10965)
+ {
+ Creature *clintar_spirit = pCreature->SummonCreature(CLINTAR_SPIRIT, CLINTAR_SPIRIT_SUMMON_X, CLINTAR_SPIRIT_SUMMON_Y, CLINTAR_SPIRIT_SUMMON_Z, CLINTAR_SPIRIT_SUMMON_O, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 100000);
+ if (clintar_spirit)
+ CAST_AI(npc_clintar_spiritAI, clintar_spirit->AI())->StartEvent(pPlayer);
+ }
+ return true;
+}
+
+/*####
+#
+####*/
+
+void AddSC_moonglade()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_bunthen_plainswind";
+ newscript->pGossipHello = &GossipHello_npc_bunthen_plainswind;
+ newscript->pGossipSelect = &GossipSelect_npc_bunthen_plainswind;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_great_bear_spirit";
+ newscript->pGossipHello = &GossipHello_npc_great_bear_spirit;
+ newscript->pGossipSelect = &GossipSelect_npc_great_bear_spirit;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_silva_filnaveth";
+ newscript->pGossipHello = &GossipHello_npc_silva_filnaveth;
+ newscript->pGossipSelect = &GossipSelect_npc_silva_filnaveth;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_clintar_dreamwalker";
+ newscript->pQuestAccept = &QuestAccept_npc_clintar_dreamwalker;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_clintar_spirit";
+ newscript->GetAI = &GetAI_npc_clintar_spirit;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/mulgore.cpp b/src/server/scripts/Kalimdor/mulgore.cpp
new file mode 100644
index 00000000000..c87e5e36dad
--- /dev/null
+++ b/src/server/scripts/Kalimdor/mulgore.cpp
@@ -0,0 +1,316 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Mulgore
+SD%Complete: 100
+SDComment: Support for quest: 11129, 772
+SDCategory: Mulgore
+EndScriptData */
+
+/* ContentData
+npc_skorn_whitecloud
+npc_kyle_frenzied
+npc_plains_vision
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+
+/*######
+# npc_skorn_whitecloud
+######*/
+
+#define GOSSIP_SW "Tell me a story, Skorn."
+
+bool GossipHello_npc_skorn_whitecloud(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (!pPlayer->GetQuestRewardStatus(770))
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SW, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+
+ pPlayer->SEND_GOSSIP_MENU(522, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_skorn_whitecloud(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF)
+ pPlayer->SEND_GOSSIP_MENU(523, pCreature->GetGUID());
+
+ return true;
+}
+
+/*#####
+# npc_kyle_frenzied
+######*/
+
+enum eKyleFrenzied
+{
+ //emote signed for 7780 but propably thats wrong id.
+ EMOTE_SEE_LUNCH = -1000340,
+ EMOTE_EAT_LUNCH = -1000341,
+ EMOTE_DANCE = -1000342,
+
+ SPELL_LUNCH = 42222,
+ NPC_KYLE_FRENZIED = 23616,
+ NPC_KYLE_FRIENDLY = 23622,
+ POINT_ID = 1
+};
+
+struct npc_kyle_frenziedAI : public ScriptedAI
+{
+ npc_kyle_frenziedAI(Creature *c) : ScriptedAI(c) {}
+
+ bool bEvent;
+ bool m_bIsMovingToLunch;
+ uint64 uiPlayerGUID;
+ uint32 uiEventTimer;
+ uint8 uiEventPhase;
+
+ void Reset()
+ {
+ bEvent = false;
+ m_bIsMovingToLunch = false;
+ uiPlayerGUID = 0;
+ uiEventTimer = 5000;
+ uiEventPhase = 0;
+
+ if (me->GetEntry() == NPC_KYLE_FRIENDLY)
+ me->UpdateEntry(NPC_KYLE_FRENZIED);
+ }
+
+ void SpellHit(Unit* pCaster, SpellEntry const* pSpell)
+ {
+ if (!me->getVictim() && !bEvent && pSpell->Id == SPELL_LUNCH)
+ {
+ if (pCaster->GetTypeId() == TYPEID_PLAYER)
+ uiPlayerGUID = pCaster->GetGUID();
+
+ if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() == WAYPOINT_MOTION_TYPE)
+ {
+ me->GetMotionMaster()->MovementExpired();
+ me->GetMotionMaster()->MoveIdle();
+ me->StopMoving();
+ }
+
+ bEvent = true;
+ DoScriptText(EMOTE_SEE_LUNCH, me);
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_ONESHOT_CREATURE_SPECIAL);
+ }
+ }
+
+ void MovementInform(uint32 uiType, uint32 uiPointId)
+ {
+ if (uiType != POINT_MOTION_TYPE || !bEvent)
+ return;
+
+ if (uiPointId == POINT_ID)
+ m_bIsMovingToLunch = false;
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (bEvent)
+ {
+ if (m_bIsMovingToLunch)
+ return;
+
+ if (uiEventTimer <= diff)
+ {
+ uiEventTimer = 5000;
+ ++uiEventPhase;
+
+ switch(uiEventPhase)
+ {
+ case 1:
+ if (Unit* pUnit = Unit::GetUnit(*me,uiPlayerGUID))
+ {
+ if (GameObject* pGo = pUnit->GetGameObject(SPELL_LUNCH))
+ {
+ m_bIsMovingToLunch = true;
+ me->GetMotionMaster()->MovePoint(POINT_ID, pGo->GetPositionX(), pGo->GetPositionY(), pGo->GetPositionZ());
+ }
+ }
+ break;
+ case 2:
+ DoScriptText(EMOTE_EAT_LUNCH, me);
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_STATE_USESTANDING);
+ break;
+ case 3:
+ if (Player* pUnit = Unit::GetPlayer(uiPlayerGUID))
+ pUnit->TalkedToCreature(me->GetEntry(), me->GetGUID());
+
+ me->UpdateEntry(NPC_KYLE_FRIENDLY);
+ break;
+ case 4:
+ uiEventTimer = 30000;
+ DoScriptText(EMOTE_DANCE, me);
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_STATE_DANCESPECIAL);
+ break;
+ case 5:
+ me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_STATE_NONE);
+ Reset();
+ me->GetMotionMaster()->Clear();
+ break;
+ }
+ }
+ else
+ uiEventTimer -= diff;
+ }
+ }
+};
+
+CreatureAI* GetAI_npc_kyle_frenzied(Creature* pCreature)
+{
+ return new npc_kyle_frenziedAI (pCreature);
+}
+
+/*#####
+# npc_plains_vision
+######*/
+
+float wp_plain_vision[50][3] =
+{
+ {-2226.32, -408.095, -9.36235},
+ {-2203.04, -437.212, -5.72498},
+ {-2163.91, -457.851, -7.09049},
+ {-2123.87, -448.137, -9.29591},
+ {-2104.66, -427.166, -6.49513},
+ {-2101.48, -422.826, -5.3567},
+ {-2097.56, -417.083, -7.16716},
+ {-2084.87, -398.626, -9.88973},
+ {-2072.71, -382.324, -10.2488},
+ {-2054.05, -356.728, -6.22468},
+ {-2051.8, -353.645, -5.35791},
+ {-2049.08, -349.912, -6.15723},
+ {-2030.6, -310.724, -9.59302},
+ {-2002.15, -249.308, -10.8124},
+ {-1972.85, -195.811, -10.6316},
+ {-1940.93, -147.652, -11.7055},
+ {-1888.06, -81.943, -11.4404},
+ {-1837.05, -34.0109, -12.258},
+ {-1796.12, -14.6462, -10.3581},
+ {-1732.61, -4.27746, -10.0213},
+ {-1688.94, -0.829945, -11.7103},
+ {-1681.32, 13.0313, -9.48056},
+ {-1677.04, 36.8349, -7.10318},
+ {-1675.2, 68.559, -8.95384},
+ {-1676.57, 89.023, -9.65104},
+ {-1678.16, 110.939, -10.1782},
+ {-1677.86, 128.681, -5.73869},
+ {-1675.27, 144.324, -3.47916},
+ {-1671.7, 163.169, -1.23098},
+ {-1666.61, 181.584, 5.26145},
+ {-1661.51, 196.154, 8.95252},
+ {-1655.47, 210.811, 8.38727},
+ {-1647.07, 226.947, 5.27755},
+ {-1621.65, 232.91, 2.69579},
+ {-1600.23, 237.641, 2.98539},
+ {-1576.07, 242.546, 4.66541},
+ {-1554.57, 248.494, 6.60377},
+ {-1547.53, 259.302, 10.6741},
+ {-1541.7, 269.847, 16.4418},
+ {-1539.83, 278.989, 21.0597},
+ {-1540.16, 290.219, 27.8247},
+ {-1538.99, 298.983, 34.0032},
+ {-1540.38, 307.337, 41.3557},
+ {-1536.61, 314.884, 48.0179},
+ {-1532.42, 323.277, 55.6667},
+ {-1528.77, 329.774, 61.1525},
+ {-1525.65, 333.18, 63.2161},
+ {-1517.01, 350.713, 62.4286},
+ {-1511.39, 362.537, 62.4539},
+ {-1508.68, 366.822, 62.733}
+};
+
+struct npc_plains_visionAI : public ScriptedAI
+{
+ npc_plains_visionAI(Creature *c) : ScriptedAI(c) {}
+
+ bool newWaypoint;
+ uint8 WayPointId;
+ uint8 amountWP;
+
+ void Reset()
+ {
+ WayPointId = 0;
+ newWaypoint = true;
+ amountWP = 49;
+ }
+
+ void EnterCombat(Unit* /*who*/){}
+
+ void MovementInform(uint32 type, uint32 id)
+ {
+ if (type != POINT_MOTION_TYPE)
+ return;
+
+ if (id < amountWP)
+ {
+ ++WayPointId;
+ newWaypoint = true;
+ }
+ else
+ {
+ me->setDeathState(JUST_DIED);
+ me->RemoveCorpse();
+ }
+ }
+
+ void UpdateAI(const uint32 /*diff*/)
+ {
+ if (newWaypoint)
+ {
+ me->GetMotionMaster()->MovePoint(WayPointId, wp_plain_vision[WayPointId][0], wp_plain_vision[WayPointId][1], wp_plain_vision[WayPointId][2]);
+ newWaypoint = false;
+ }
+ }
+};
+
+CreatureAI* GetAI_npc_plains_vision(Creature* pCreature)
+{
+ return new npc_plains_visionAI (pCreature);
+}
+
+/*#####
+#
+######*/
+
+void AddSC_mulgore()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_skorn_whitecloud";
+ newscript->pGossipHello = &GossipHello_npc_skorn_whitecloud;
+ newscript->pGossipSelect = &GossipSelect_npc_skorn_whitecloud;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_kyle_frenzied";
+ newscript->GetAI = &GetAI_npc_kyle_frenzied;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_plains_vision";
+ newscript->GetAI = &GetAI_npc_plains_vision;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/onyxias_lair/boss_onyxia.cpp b/src/server/scripts/Kalimdor/onyxias_lair/boss_onyxia.cpp
new file mode 100644
index 00000000000..2d351d6c6a2
--- /dev/null
+++ b/src/server/scripts/Kalimdor/onyxias_lair/boss_onyxia.cpp
@@ -0,0 +1,500 @@
+/* Copyright (C) 2008 - 2010 Trinity <http://www.trinitycore.org/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Onyxia
+SD%Complete: 95
+SDComment: <Known bugs>
+ Ground visual for Deep Breath effect;
+ Wing Buffet not ignoring armor;
+ Not summoning whelps on phase 3 (lacks info)
+ </Known bugs>
+SDCategory: Onyxia's Lair
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "onyxias_lair.h"
+
+enum eYells
+{
+ SAY_AGGRO = -1249000,
+ SAY_KILL = -1249001,
+ SAY_PHASE_2_TRANS = -1249002,
+ SAY_PHASE_3_TRANS = -1249003,
+ EMOTE_BREATH = -1249004,
+};
+
+enum eSpells
+{
+ // Phase 1 spells
+ SPELL_WING_BUFFET = 18500,
+ SPELL_FLAME_BREATH = 18435,
+ SPELL_CLEAVE = 68868,
+ SPELL_TAIL_SWEEP = 68867,
+
+ // Phase 2 spells
+ SPELL_DEEP_BREATH = 23461,
+ SPELL_FIREBALL = 18392,
+
+ //Not much choise about these. We have to make own defintion on the direction/start-end point
+ SPELL_BREATH_NORTH_TO_SOUTH = 17086, // 20x in "array"
+ SPELL_BREATH_SOUTH_TO_NORTH = 18351, // 11x in "array"
+
+ SPELL_BREATH_EAST_TO_WEST = 18576, // 7x in "array"
+ SPELL_BREATH_WEST_TO_EAST = 18609, // 7x in "array"
+
+ SPELL_BREATH_SE_TO_NW = 18564, // 12x in "array"
+ SPELL_BREATH_NW_TO_SE = 18584, // 12x in "array"
+ SPELL_BREATH_SW_TO_NE = 18596, // 12x in "array"
+ SPELL_BREATH_NE_TO_SW = 18617, // 12x in "array"
+
+ //SPELL_BREATH = 21131, // 8x in "array", different initial cast than the other arrays
+
+ // Phase 3 spells
+ SPELL_BELLOWING_ROAR = 18431,
+};
+
+struct sOnyxMove
+{
+ uint32 uiLocId;
+ uint32 uiLocIdEnd;
+ uint32 uiSpellId;
+ float fX, fY, fZ;
+};
+
+static sOnyxMove aMoveData[]=
+{
+ {0, 1, SPELL_BREATH_WEST_TO_EAST, -33.5561f, -182.682f, -56.9457f},//west
+ {1, 0, SPELL_BREATH_EAST_TO_WEST, -31.4963f, -250.123f, -55.1278f},//east
+ {2, 4, SPELL_BREATH_NW_TO_SE, 6.8951f, -180.246f, -55.896f},//north-west
+ {3, 5, SPELL_BREATH_NE_TO_SW, 10.2191f, -247.912f, -55.896f},//north-east
+ {4, 2, SPELL_BREATH_SE_TO_NW, -63.5156f, -240.096f, -55.477f},//south-east
+ {5, 3, SPELL_BREATH_SW_TO_NE, -58.2509f, -189.020f, -55.790f},//south-west
+ {6, 7, SPELL_BREATH_SOUTH_TO_NORTH, -65.8444f, -213.809f, -55.2985f},//south
+ {7, 6, SPELL_BREATH_NORTH_TO_SOUTH, 22.8763f, -217.152f, -55.0548f},//north
+};
+
+const Position MiddleRoomLocation = {-23.6155, -215.357, -55.7344};
+
+static Position aSpawnLocations[3]=
+{
+ //Whelps
+ {-30.127, -254.463, -89.440},
+ {-30.817, -177.106, -89.258},
+ //Lair Guard
+ {-145.950, -212.831, -68.659}
+};
+
+struct boss_onyxiaAI : public ScriptedAI
+{
+ boss_onyxiaAI(Creature* pCreature) : ScriptedAI(pCreature), Summons(me)
+ {
+ m_pInstance = pCreature->GetInstanceData();
+ Reset();
+ }
+
+ ScriptedInstance* m_pInstance;
+ SummonList Summons;
+
+ uint32 m_uiPhase;
+
+ uint32 m_uiFlameBreathTimer;
+ uint32 m_uiCleaveTimer;
+ uint32 m_uiTailSweepTimer;
+ uint32 m_uiWingBuffetTimer;
+
+ uint32 m_uiMovePoint;
+ uint32 m_uiMovementTimer;
+ sOnyxMove* m_pPointData;
+
+ uint32 m_uiFireballTimer;
+ uint32 m_uiWhelpTimer;
+ uint32 m_uiLairGuardTimer;
+ uint32 m_uiDeepBreathTimer;
+
+ uint32 m_uiBellowingRoarTimer;
+
+ uint8 m_uiSummonWhelpCount;
+ uint8 m_uiSummonLairGuardCount;
+ bool m_bIsMoving;
+
+ void Reset()
+ {
+ if (!IsCombatMovement())
+ SetCombatMovement(true);
+
+ m_uiPhase = PHASE_START;
+
+ m_uiFlameBreathTimer = urand(10000, 20000);
+ m_uiTailSweepTimer = urand(15000, 20000);
+ m_uiCleaveTimer = urand(2000, 5000);
+ m_uiWingBuffetTimer = urand(10000, 20000);
+
+ m_uiMovePoint = urand(0, 5);
+ m_uiMovementTimer = 20000;
+ m_pPointData = GetMoveData();
+
+ m_uiFireballTimer = 15000;
+ m_uiWhelpTimer = 1000;
+ m_uiLairGuardTimer = 15000;
+ m_uiDeepBreathTimer = 85000;
+
+ m_uiBellowingRoarTimer = 30000;
+
+ Summons.DespawnAll();
+ m_uiSummonWhelpCount = 0;
+ m_uiSummonLairGuardCount = 0;
+ m_bIsMoving = false;
+
+ if (m_pInstance)
+ {
+ m_pInstance->SetData(DATA_ONYXIA, NOT_STARTED);
+ m_pInstance->SetData(DATA_ONYXIA_PHASE, m_uiPhase);
+ m_pInstance->DoStopTimedAchievement(ACHIEVEMENT_TIMED_TYPE_EVENT, ACHIEV_TIMED_START_EVENT);
+ }
+ }
+
+ void EnterCombat(Unit* pWho)
+ {
+ DoScriptText(SAY_AGGRO, me);
+ me->SetInCombatWithZone();
+
+ if (m_pInstance)
+ {
+ m_pInstance->SetData(DATA_ONYXIA, IN_PROGRESS);
+ m_pInstance->DoStartTimedAchievement(ACHIEVEMENT_TIMED_TYPE_EVENT, ACHIEV_TIMED_START_EVENT);
+ sLog.outBasic("[Onyxia] DoStartTimedAchievement(%u,%u)",ACHIEVEMENT_TIMED_TYPE_EVENT, ACHIEV_TIMED_START_EVENT);
+ }
+ }
+
+ void JustDied(Unit* killer)
+ {
+ if (m_pInstance)
+ m_pInstance->SetData(DATA_ONYXIA, DONE);
+
+ Summons.DespawnAll();
+ }
+
+ void JustSummoned(Creature *pSummoned)
+ {
+ pSummoned->SetInCombatWithZone();
+ if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM,0))
+ pSummoned->AI()->AttackStart(pTarget);
+
+ switch (pSummoned->GetEntry())
+ {
+ case NPC_WHELP:
+ ++m_uiSummonWhelpCount;
+ break;
+ case NPC_LAIRGUARD:
+ pSummoned->setActive(true);
+ ++m_uiSummonLairGuardCount;
+ break;
+ }
+ Summons.Summon(pSummoned);
+ }
+
+ void SummonedCreatureDespawn(Creature *summon)
+ {
+ Summons.Despawn(summon);
+ }
+
+ void KilledUnit(Unit* pVictim)
+ {
+ DoScriptText(SAY_KILL, me);
+ }
+
+ void SpellHit(Unit *pCaster, const SpellEntry* pSpell)
+ {
+ if (pSpell->Id == SPELL_BREATH_EAST_TO_WEST ||
+ pSpell->Id == SPELL_BREATH_WEST_TO_EAST ||
+ pSpell->Id == SPELL_BREATH_SE_TO_NW ||
+ pSpell->Id == SPELL_BREATH_NW_TO_SE ||
+ pSpell->Id == SPELL_BREATH_SW_TO_NE ||
+ pSpell->Id == SPELL_BREATH_NE_TO_SW)
+ {
+ m_pPointData = GetMoveData();
+ m_uiMovePoint = m_pPointData->uiLocIdEnd;
+
+ me->SetSpeed(MOVE_FLIGHT, 1.5f);
+ me->GetMotionMaster()->MovePoint(8, MiddleRoomLocation);
+ }
+ }
+
+ void MovementInform(uint32 type, uint32 id)
+ {
+ if (type == POINT_MOTION_TYPE)
+ {
+ switch (id)
+ {
+ case 8:
+ m_pPointData = GetMoveData();
+ if (m_pPointData)
+ {
+ me->SetSpeed(MOVE_FLIGHT, 1.0f);
+ me->GetMotionMaster()->MovePoint(m_pPointData->uiLocId, m_pPointData->fX, m_pPointData->fY, m_pPointData->fZ);
+ }
+ break;
+ case 9:
+ me->GetMotionMaster()->MoveChase(me->getVictim());
+ m_uiBellowingRoarTimer = 1000;
+ break;
+ default:
+ m_bIsMoving = false;
+ break;
+ }
+ }
+ }
+
+ void SpellHitTarget(Unit* target, const SpellEntry* pSpell)
+ {
+ //Workaround - Couldn't find a way to group this spells (All Eruption)
+ if (((pSpell->Id >= 17086 && pSpell->Id <= 17095) ||
+ (pSpell->Id == 17097) ||
+ (pSpell->Id >= 18351 && pSpell->Id <= 18361) ||
+ (pSpell->Id >= 18564 && pSpell->Id <= 18576) ||
+ (pSpell->Id >= 18578 && pSpell->Id <= 18607) ||
+ (pSpell->Id == 18609) ||
+ (pSpell->Id >= 18611 && pSpell->Id <= 18628) ||
+ (pSpell->Id >= 21132 && pSpell->Id <= 21133) ||
+ (pSpell->Id >= 21135 && pSpell->Id <= 21139) ||
+ (pSpell->Id >= 22191 && pSpell->Id <= 22202) ||
+ (pSpell->Id >= 22267 && pSpell->Id <= 22268)) &&
+ (target->GetTypeId() == TYPEID_PLAYER))
+ {
+ if (m_pInstance)
+ {
+ m_pInstance->SetData(DATA_SHE_DEEP_BREATH_MORE, FAIL);
+ }
+ }
+ }
+
+ sOnyxMove* GetMoveData()
+ {
+ uint32 uiMaxCount = sizeof(aMoveData)/sizeof(sOnyxMove);
+
+ for (uint32 i = 0; i < uiMaxCount; ++i)
+ {
+ if (aMoveData[i].uiLocId == m_uiMovePoint)
+ return &aMoveData[i];
+ }
+
+ return NULL;
+ }
+
+ void SetNextRandomPoint()
+ {
+ uint32 uiMaxCount = sizeof(aMoveData)/sizeof(sOnyxMove);
+
+ int iTemp = rand()%(uiMaxCount-1);
+
+ if (iTemp >= m_uiMovePoint)
+ ++iTemp;
+
+ m_uiMovePoint = iTemp;
+ }
+
+ void UpdateAI(const uint32 uiDiff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ //Common to PHASE_START && PHASE_END
+ if (m_uiPhase == PHASE_START || m_uiPhase == PHASE_END)
+ {
+ //Specific to PHASE_START || PHASE_END
+ if (m_uiPhase == PHASE_START)
+ {
+ if (me->GetHealth()*100 / me->GetMaxHealth() < 60)
+ {
+ m_uiPhase = PHASE_BREATH;
+
+ if (m_pInstance)
+ m_pInstance->SetData(DATA_ONYXIA_PHASE, m_uiPhase);
+
+ SetCombatMovement(false);
+ me->GetMotionMaster()->Clear(false);
+ me->GetMotionMaster()->MoveIdle();
+ me->SetFlying(true);
+
+ DoScriptText(SAY_PHASE_2_TRANS, me);
+
+ if (m_pPointData)
+ me->GetMotionMaster()->MovePoint(m_pPointData->uiLocId, m_pPointData->fX, m_pPointData->fY, m_pPointData->fZ);
+
+ m_uiWhelpTimer = 1000;
+ return;
+ }
+ }
+ else
+ {
+ if (m_uiBellowingRoarTimer <= uiDiff)
+ {
+ DoCastVictim(SPELL_BELLOWING_ROAR);
+ // Eruption
+ GameObject* pFloor = NULL;
+ Trinity::GameObjectInRangeCheck check(me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(), 15);
+ Trinity::GameObjectLastSearcher<Trinity::GameObjectInRangeCheck> searcher(me, pFloor, check);
+ me->VisitNearbyGridObject(30, searcher);
+ if (m_pInstance && pFloor)
+ m_pInstance->SetData64(DATA_FLOOR_ERUPTION_GUID, pFloor->GetGUID());
+ m_uiBellowingRoarTimer = 30000;
+ }
+ else
+ m_uiBellowingRoarTimer -= uiDiff;
+ }
+
+ if (m_uiFlameBreathTimer <= uiDiff)
+ {
+ DoCastVictim(SPELL_FLAME_BREATH);
+ m_uiFlameBreathTimer = urand(10000, 20000);
+ }
+ else
+ m_uiFlameBreathTimer -= uiDiff;
+
+ if (m_uiTailSweepTimer <= uiDiff)
+ {
+ DoCastAOE(SPELL_TAIL_SWEEP);
+ m_uiTailSweepTimer = urand(15000, 20000);
+ }
+ else
+ m_uiTailSweepTimer -= uiDiff;
+
+ if (m_uiCleaveTimer <= uiDiff)
+ {
+ DoCastVictim(SPELL_CLEAVE);
+ m_uiCleaveTimer = urand(2000, 5000);
+ }
+ else
+ m_uiCleaveTimer -= uiDiff;
+
+ if (m_uiWingBuffetTimer <= uiDiff)
+ {
+ DoCastVictim(SPELL_WING_BUFFET);
+ m_uiWingBuffetTimer = urand(15000, 30000);
+ }
+ else
+ m_uiWingBuffetTimer -= uiDiff;
+
+ DoMeleeAttackIfReady();
+ }
+ else
+ {
+ if (me->GetHealth()*100 / me->GetMaxHealth() < 40)
+ {
+ m_uiPhase = PHASE_END;
+ if (m_pInstance)
+ m_pInstance->SetData(DATA_ONYXIA_PHASE, m_uiPhase);
+ DoScriptText(SAY_PHASE_3_TRANS, me);
+
+ SetCombatMovement(true);
+ me->SetFlying(false);
+ m_bIsMoving = false;
+ me->GetMotionMaster()->MovePoint(9,me->GetHomePosition());
+ return;
+ }
+
+ if (m_uiDeepBreathTimer <= uiDiff)
+ {
+ if (!m_bIsMoving)
+ {
+ if (me->IsNonMeleeSpellCasted(false))
+ me->InterruptNonMeleeSpells(false);
+
+ DoScriptText(EMOTE_BREATH, me);
+ DoCast(me, m_pPointData->uiSpellId);
+ m_uiDeepBreathTimer = 70000;
+ }
+ }
+ else
+ m_uiDeepBreathTimer -= uiDiff;
+
+ if (m_uiMovementTimer <= uiDiff)
+ {
+ if (!m_bIsMoving)
+ {
+ SetNextRandomPoint();
+ m_pPointData = GetMoveData();
+
+ if (!m_pPointData)
+ return;
+
+ me->GetMotionMaster()->MovePoint(m_pPointData->uiLocId, m_pPointData->fX, m_pPointData->fY, m_pPointData->fZ);
+ m_bIsMoving = true;
+ m_uiMovementTimer = 25000;
+ }
+ }
+ else
+ m_uiMovementTimer -= uiDiff;
+
+ if (m_uiFireballTimer <= uiDiff)
+ {
+ if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() != POINT_MOTION_TYPE)
+ {
+ if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0))
+ DoCast(pTarget, SPELL_FIREBALL);
+
+ m_uiFireballTimer = 8000;
+ }
+ }
+ else
+ m_uiFireballTimer -= uiDiff;
+
+ if (m_uiLairGuardTimer <= uiDiff)
+ {
+ me->SummonCreature(NPC_LAIRGUARD, aSpawnLocations[2].GetPositionX(), aSpawnLocations[2].GetPositionY(), aSpawnLocations[2].GetPositionZ(), 0.0f, TEMPSUMMON_CORPSE_DESPAWN);
+ if (m_uiSummonLairGuardCount >= RAID_MODE(1,2))
+ {
+ m_uiSummonLairGuardCount = 0;
+ m_uiLairGuardTimer = 30000;
+ }
+ else
+ m_uiLairGuardTimer = 2000;
+ }
+ else
+ m_uiLairGuardTimer -= uiDiff;
+
+ if (m_uiWhelpTimer <= uiDiff)
+ {
+ me->SummonCreature(NPC_WHELP, aSpawnLocations[0].GetPositionX(), aSpawnLocations[0].GetPositionY(), aSpawnLocations[0].GetPositionZ(), 0.0f, TEMPSUMMON_CORPSE_DESPAWN);
+ me->SummonCreature(NPC_WHELP, aSpawnLocations[1].GetPositionX(), aSpawnLocations[1].GetPositionY(), aSpawnLocations[1].GetPositionZ(), 0.0f, TEMPSUMMON_CORPSE_DESPAWN);
+ if (m_uiSummonWhelpCount >= RAID_MODE(20,40))
+ {
+ m_uiSummonWhelpCount = 0;
+ m_uiWhelpTimer = 90000;
+ }
+ else
+ m_uiWhelpTimer = 500;
+ }
+ else
+ m_uiWhelpTimer -= uiDiff;
+ }
+ }
+};
+
+CreatureAI* GetAI_boss_onyxiaAI(Creature* pCreature)
+{
+ return new boss_onyxiaAI (pCreature);
+}
+
+void AddSC_boss_onyxia()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_onyxia";
+ newscript->GetAI = &GetAI_boss_onyxiaAI;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/onyxias_lair/instance_onyxias_lair.cpp b/src/server/scripts/Kalimdor/onyxias_lair/instance_onyxias_lair.cpp
new file mode 100644
index 00000000000..cfd66bf80f4
--- /dev/null
+++ b/src/server/scripts/Kalimdor/onyxias_lair/instance_onyxias_lair.cpp
@@ -0,0 +1,249 @@
+/* Copyright (C) 2008 - 2010 Trinity <http://www.trinitycore.org/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Instance_Onyxias_Lair
+SD%Complete: 100
+SDComment:
+SDCategory: Onyxia's Lair
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "onyxias_lair.h"
+
+struct instance_onyxias_lair : public ScriptedInstance
+{
+ instance_onyxias_lair(Map* pMap) : ScriptedInstance(pMap) {Initialize();};
+
+ //Eruption is a BFS graph problem
+ //One map to remember all floor, one map to keep floor that still need to erupt and one queue to know what needs to be removed
+ std::map<uint64,uint32> FloorEruptionGUID[2];
+ std::queue<uint64> FloorEruptionGUIDQueue;
+
+ uint64 m_uiOnyxiasGUID;
+ uint32 m_uiOnyxiaLiftoffTimer;
+ uint32 m_uiManyWhelpsCounter;
+ uint32 m_uiEruptTimer;
+
+ uint8 m_auiEncounter[MAX_ENCOUNTER];
+
+ bool m_bAchievManyWhelpsHandleIt;
+ bool m_bAchievSheDeepBreathMore;
+
+ void Initialize()
+ {
+ memset(&m_auiEncounter, 0, sizeof(m_auiEncounter));
+
+ m_uiOnyxiasGUID = 0;
+ m_uiOnyxiaLiftoffTimer = 0;
+ m_uiManyWhelpsCounter = 0;
+ m_bAchievManyWhelpsHandleIt = false;
+ m_bAchievSheDeepBreathMore = true;
+
+ m_uiEruptTimer = 0;
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool add)
+ {
+ switch (pCreature->GetEntry())
+ {
+ case NPC_ONYXIA:
+ m_uiOnyxiasGUID = pCreature->GetGUID();
+ break;
+ }
+ }
+
+ void OnGameObjectCreate(GameObject* pGo, bool add)
+ {
+ if ((pGo->GetGOInfo()->displayId == 4392 || pGo->GetGOInfo()->displayId == 4472) && pGo->GetGOInfo()->trap.spellId == 17731)
+ {
+ if (add)
+ FloorEruptionGUID[0].insert(std::make_pair(pGo->GetGUID(),0));
+ else
+ FloorEruptionGUID[0].erase(pGo->GetGUID());
+ return;
+ }
+
+ switch(pGo->GetEntry())
+ {
+ case GO_WHELP_SPAWNER:
+ Position pGoPos;
+ pGo->GetPosition(&pGoPos);
+ if (Creature* pTemp = pGo->SummonCreature(NPC_WHELP,pGoPos,TEMPSUMMON_CORPSE_DESPAWN))
+ {
+ pTemp->SetInCombatWithZone();
+ ++m_uiManyWhelpsCounter;
+ }
+ break;
+ }
+ }
+
+ void FloorEruption(uint64 floorEruptedGUID)
+ {
+ if (GameObject *pFloorEruption = instance->GetGameObject(floorEruptedGUID))
+ {
+ //THIS GOB IS A TRAP - What shall i do? =(
+ //Cast it spell? Copyed Heigan method
+ pFloorEruption->SendCustomAnim();
+ pFloorEruption->CastSpell(NULL, Difficulty(instance->GetSpawnMode()) == RAID_DIFFICULTY_10MAN_NORMAL ? 17731 : 69294); //pFloorEruption->GetGOInfo()->trap.spellId
+
+ //Get all immediatly nearby floors
+ std::list<GameObject*> nearFloorList;
+ Trinity::GameObjectInRangeCheck check(pFloorEruption->GetPositionX(), pFloorEruption->GetPositionY(), pFloorEruption->GetPositionZ(), 15);
+ Trinity::GameObjectListSearcher<Trinity::GameObjectInRangeCheck> searcher(pFloorEruption, nearFloorList, check);
+ pFloorEruption->VisitNearbyGridObject(999, searcher);
+ //remove all that are not present on FloorEruptionGUID[1] and update treeLen on each GUID
+ for (std::list<GameObject*>::const_iterator itr = nearFloorList.begin(); itr != nearFloorList.end(); ++itr)
+ {
+ if (((*itr)->GetGOInfo()->displayId == 4392 || (*itr)->GetGOInfo()->displayId == 4472) && (*itr)->GetGOInfo()->trap.spellId == 17731)
+ {
+ uint64 nearFloorGUID = (*itr)->GetGUID();
+ if (FloorEruptionGUID[1].find(nearFloorGUID) != FloorEruptionGUID[1].end() && (*FloorEruptionGUID[1].find(nearFloorGUID)).second == 0)
+ {
+ (*FloorEruptionGUID[1].find(nearFloorGUID)).second = (*FloorEruptionGUID[1].find(floorEruptedGUID)).second+1;
+ FloorEruptionGUIDQueue.push(nearFloorGUID);
+ }
+ }
+ }
+ }
+ FloorEruptionGUID[1].erase(floorEruptedGUID);
+ }
+
+ void SetData(uint32 uiType, uint32 uiData)
+ {
+ switch(uiType)
+ {
+ case DATA_ONYXIA:
+ m_auiEncounter[0] = uiData;
+ if (uiData == IN_PROGRESS)
+ SetData(DATA_SHE_DEEP_BREATH_MORE, IN_PROGRESS);
+ break;
+ case DATA_ONYXIA_PHASE:
+ if (uiData == PHASE_BREATH) //Used to mark the liftoff phase
+ {
+ m_bAchievManyWhelpsHandleIt = false;
+ m_uiManyWhelpsCounter = 0;
+ m_uiOnyxiaLiftoffTimer = 10*IN_MILISECONDS;
+ }
+ break;
+ case DATA_SHE_DEEP_BREATH_MORE:
+ if (uiData == IN_PROGRESS)
+ {
+ m_bAchievSheDeepBreathMore = true;
+ }
+ else if (uiData == FAIL)
+ {
+ m_bAchievSheDeepBreathMore = false;
+ }
+ break;
+ }
+
+ if (uiType < MAX_ENCOUNTER && uiData == DONE)
+ SaveToDB();
+ }
+
+ void SetData64(uint32 uiType, uint64 uiData)
+ {
+ switch(uiType)
+ {
+ case DATA_FLOOR_ERUPTION_GUID:
+ FloorEruptionGUID[1] = FloorEruptionGUID[0];
+ FloorEruptionGUIDQueue.push(uiData);
+ m_uiEruptTimer = 2500;
+ break;
+ }
+ }
+
+ uint32 GetData(uint32 uiType)
+ {
+ switch(uiType)
+ {
+ case DATA_ONYXIA:
+ return m_auiEncounter[0];
+ }
+
+ return 0;
+ }
+
+ uint64 GetData64(uint32 uiData)
+ {
+ switch(uiData)
+ {
+ case DATA_ONYXIA_GUID:
+ return m_uiOnyxiasGUID;
+ }
+
+ return 0;
+ }
+
+ void Update(uint32 uiDiff)
+ {
+ if (GetData(DATA_ONYXIA) == IN_PROGRESS)
+ {
+ if (m_uiOnyxiaLiftoffTimer && m_uiOnyxiaLiftoffTimer <= uiDiff)
+ {
+ m_uiOnyxiaLiftoffTimer = 0;
+ if (m_uiManyWhelpsCounter >= 50)
+ m_bAchievManyWhelpsHandleIt = true;
+ } else m_uiOnyxiaLiftoffTimer -= uiDiff;
+ }
+
+ if (!FloorEruptionGUIDQueue.empty())
+ {
+ if (m_uiEruptTimer <= uiDiff)
+ {
+ uint32 treeHeight = 0;
+ do
+ {
+ treeHeight = (*FloorEruptionGUID[1].find(FloorEruptionGUIDQueue.front())).second;
+ FloorEruption(FloorEruptionGUIDQueue.front());
+ FloorEruptionGUIDQueue.pop();
+ } while (!FloorEruptionGUIDQueue.empty() && (*FloorEruptionGUID[1].find(FloorEruptionGUIDQueue.front())).second == treeHeight);
+ m_uiEruptTimer = 1000;
+ }
+ else
+ m_uiEruptTimer -= uiDiff;
+ }
+ }
+
+ bool CheckAchievementCriteriaMeet(uint32 criteria_id, Player const* source, Unit const* target = NULL, uint32 miscvalue1 = 0)
+ {
+ switch(criteria_id)
+ {
+ case ACHIEV_CRITERIA_MANY_WHELPS_10_PLAYER: // Criteria for achievement 4403: Many Whelps! Handle It! (10 player) Hatch 50 eggs in 10s
+ case ACHIEV_CRITERIA_MANY_WHELPS_25_PLAYER: // Criteria for achievement 4406: Many Whelps! Handle It! (25 player) Hatch 50 eggs in 10s
+ return m_bAchievManyWhelpsHandleIt;
+ case ACHIEV_CRITERIA_DEEP_BREATH_10_PLAYER: // Criteria for achievement 4404: She Deep Breaths More (10 player) Everybody evade Deep Breath
+ case ACHIEV_CRITERIA_DEEP_BREATH_25_PLAYER: // Criteria for achievement 4407: She Deep Breaths More (25 player) Everybody evade Deep Breath
+ return m_bAchievSheDeepBreathMore;
+ }
+ return false;
+ }
+};
+
+InstanceData* GetInstanceData_instance_onyxias_lair(Map* pMap)
+{
+ return new instance_onyxias_lair(pMap);
+}
+
+void AddSC_instance_onyxias_lair()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_onyxias_lair";
+ newscript->GetInstanceData = &GetInstanceData_instance_onyxias_lair;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/onyxias_lair/onyxias_lair.h b/src/server/scripts/Kalimdor/onyxias_lair/onyxias_lair.h
new file mode 100644
index 00000000000..cadd5b5a2d5
--- /dev/null
+++ b/src/server/scripts/Kalimdor/onyxias_lair/onyxias_lair.h
@@ -0,0 +1,65 @@
+/* Copyright (C) 2008 - 2010 Trinity <http://www.trinitycore.org/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#ifndef DEF_ONYXIAS_LAIR_H
+#define DEF_ONYXIAS_LAIR_H
+
+enum eData64
+{
+ DATA_ONYXIA_GUID,
+ DATA_FLOOR_ERUPTION_GUID
+};
+
+enum eInstanceData
+{
+ DATA_ONYXIA,
+ MAX_ENCOUNTER,
+
+ DATA_ONYXIA_PHASE,
+ DATA_SHE_DEEP_BREATH_MORE,
+ DATA_MANY_WHELPS_COUNT
+};
+
+enum eCreatures
+{
+ NPC_WHELP = 11262,
+ NPC_LAIRGUARD = 36561,
+
+ NPC_ONYXIA = 10184
+};
+
+enum eOnyxiaPhases
+{
+ PHASE_START = 1,
+ PHASE_BREATH = 2,
+ PHASE_END = 3
+};
+
+enum eGameObjects
+{
+ GO_WHELP_SPAWNER = 176510,
+ GO_WHELP_EGG = 176511
+};
+
+enum eAchievementData
+{
+ ACHIEV_CRITERIA_MANY_WHELPS_10_PLAYER = 12565, // Criteria for achievement 4403: Many Whelps! Handle It! (10 player) Hatch 50 eggs in 10s
+ ACHIEV_CRITERIA_MANY_WHELPS_25_PLAYER = 12568, // Criteria for achievement 4406: Many Whelps! Handle It! (25 player) Hatch 50 eggs in 10s
+ ACHIEV_CRITERIA_DEEP_BREATH_10_PLAYER = 12566, // Criteria for achievement 4404: She Deep Breaths More (10 player) Everybody evade Deep Breath
+ ACHIEV_CRITERIA_DEEP_BREATH_25_PLAYER = 12569, // Criteria for achievement 4407: She Deep Breaths More (25 player) Everybody evade Deep Breath
+ ACHIEV_TIMED_START_EVENT = 6601, // Timed event for achievement 4402, 4005: More Dots! (10,25 player) 5 min kill
+};
+#endif
diff --git a/src/server/scripts/Kalimdor/orgrimmar.cpp b/src/server/scripts/Kalimdor/orgrimmar.cpp
new file mode 100644
index 00000000000..71fa4381e9d
--- /dev/null
+++ b/src/server/scripts/Kalimdor/orgrimmar.cpp
@@ -0,0 +1,286 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Orgrimmar
+SD%Complete: 100
+SDComment: Quest support: 2460, 5727, 6566
+SDCategory: Orgrimmar
+EndScriptData */
+
+/* ContentData
+npc_neeru_fireblade npc_text + gossip options text missing
+npc_shenthul
+npc_thrall_warchief
+EndContentData */
+
+#include "ScriptedPch.h"
+
+/*######
+## npc_neeru_fireblade
+######*/
+
+#define QUEST_5727 5727
+
+#define GOSSIP_HNF "You may speak frankly, Neeru..."
+#define GOSSIP_SNF "[PH] ..."
+bool GossipHello_npc_neeru_fireblade(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(QUEST_5727) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HNF, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+
+ pPlayer->SEND_GOSSIP_MENU(4513, pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_neeru_fireblade(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch (uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SNF, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+ pPlayer->SEND_GOSSIP_MENU(4513, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+2:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pPlayer->AreaExploredOrEventHappens(QUEST_5727);
+ break;
+ }
+ return true;
+}
+
+/*######
+## npc_shenthul
+######*/
+
+enum eShenthul
+{
+ QUEST_SHATTERED_SALUTE = 2460
+};
+
+struct npc_shenthulAI : public ScriptedAI
+{
+ npc_shenthulAI(Creature* c) : ScriptedAI(c) {}
+
+ bool CanTalk;
+ bool CanEmote;
+ uint32 Salute_Timer;
+ uint32 Reset_Timer;
+ uint64 PlayerGUID;
+
+ void Reset()
+ {
+ CanTalk = false;
+ CanEmote = false;
+ Salute_Timer = 6000;
+ Reset_Timer = 0;
+ PlayerGUID = 0;
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (CanEmote)
+ {
+ if (Reset_Timer <= diff)
+ {
+ if (Player* pPlayer = Unit::GetPlayer(PlayerGUID))
+ {
+ if (pPlayer->GetTypeId() == TYPEID_PLAYER && pPlayer->GetQuestStatus(QUEST_SHATTERED_SALUTE) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->FailQuest(QUEST_SHATTERED_SALUTE);
+ }
+ Reset();
+ } else Reset_Timer -= diff;
+ }
+
+ if (CanTalk && !CanEmote)
+ {
+ if (Salute_Timer <= diff)
+ {
+ me->HandleEmoteCommand(EMOTE_ONESHOT_SALUTE);
+ CanEmote = true;
+ Reset_Timer = 60000;
+ } else Salute_Timer -= diff;
+ }
+
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+
+ void ReceiveEmote(Player* pPlayer, uint32 emote)
+ {
+ if (emote == TEXTEMOTE_SALUTE && pPlayer->GetQuestStatus(QUEST_SHATTERED_SALUTE) == QUEST_STATUS_INCOMPLETE)
+ {
+ if (CanEmote)
+ {
+ pPlayer->AreaExploredOrEventHappens(QUEST_SHATTERED_SALUTE);
+ Reset();
+ }
+ }
+ }
+};
+
+CreatureAI* GetAI_npc_shenthul(Creature* pCreature)
+{
+ return new npc_shenthulAI (pCreature);
+}
+
+bool QuestAccept_npc_shenthul(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_SHATTERED_SALUTE)
+ {
+ CAST_AI(npc_shenthulAI, pCreature->AI())->CanTalk = true;
+ CAST_AI(npc_shenthulAI, pCreature->AI())->PlayerGUID = pPlayer->GetGUID();
+ }
+ return true;
+}
+
+/*######
+## npc_thrall_warchief
+######*/
+
+#define QUEST_6566 6566
+
+#define SPELL_CHAIN_LIGHTNING 16033
+#define SPELL_SHOCK 16034
+
+#define GOSSIP_HTW "Please share your wisdom with me, Warchief."
+#define GOSSIP_STW1 "What discoveries?"
+#define GOSSIP_STW2 "Usurper?"
+#define GOSSIP_STW3 "With all due respect, Warchief - why not allow them to be destroyed? Does this not strengthen our position?"
+#define GOSSIP_STW4 "I... I did not think of it that way, Warchief."
+#define GOSSIP_STW5 "I live only to serve, Warchief! My life is empty and meaningless without your guidance."
+#define GOSSIP_STW6 "Of course, Warchief!"
+
+//TODO: verify abilities/timers
+struct npc_thrall_warchiefAI : public ScriptedAI
+{
+ npc_thrall_warchiefAI(Creature* c) : ScriptedAI(c) {}
+
+ uint32 ChainLightning_Timer;
+ uint32 Shock_Timer;
+
+ void Reset()
+ {
+ ChainLightning_Timer = 2000;
+ Shock_Timer = 8000;
+ }
+
+ void EnterCombat(Unit * /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ if (ChainLightning_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_CHAIN_LIGHTNING);
+ ChainLightning_Timer = 9000;
+ } else ChainLightning_Timer -= diff;
+
+ if (Shock_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_SHOCK);
+ Shock_Timer = 15000;
+ } else Shock_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_npc_thrall_warchief(Creature* pCreature)
+{
+ return new npc_thrall_warchiefAI (pCreature);
+}
+
+bool GossipHello_npc_thrall_warchief(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(QUEST_6566) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HTW, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_thrall_warchief(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch (uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_STW1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+ pPlayer->SEND_GOSSIP_MENU(5733, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_STW2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+3);
+ pPlayer->SEND_GOSSIP_MENU(5734, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+3:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_STW3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+4);
+ pPlayer->SEND_GOSSIP_MENU(5735, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+4:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_STW4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+5);
+ pPlayer->SEND_GOSSIP_MENU(5736, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+5:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_STW5, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+6);
+ pPlayer->SEND_GOSSIP_MENU(5737, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+6:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_STW6, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+7);
+ pPlayer->SEND_GOSSIP_MENU(5738, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+7:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pPlayer->AreaExploredOrEventHappens(QUEST_6566);
+ break;
+ }
+ return true;
+}
+
+void AddSC_orgrimmar()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_neeru_fireblade";
+ newscript->pGossipHello = &GossipHello_npc_neeru_fireblade;
+ newscript->pGossipSelect = &GossipSelect_npc_neeru_fireblade;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_shenthul";
+ newscript->GetAI = &GetAI_npc_shenthul;
+ newscript->pQuestAccept = &QuestAccept_npc_shenthul;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_thrall_warchief";
+ newscript->GetAI = &GetAI_npc_thrall_warchief;
+ newscript->pGossipHello = &GossipHello_npc_thrall_warchief;
+ newscript->pGossipSelect = &GossipSelect_npc_thrall_warchief;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/razorfen_downs/boss_amnennar_the_coldbringer.cpp b/src/server/scripts/Kalimdor/razorfen_downs/boss_amnennar_the_coldbringer.cpp
new file mode 100644
index 00000000000..711c4f0b2c1
--- /dev/null
+++ b/src/server/scripts/Kalimdor/razorfen_downs/boss_amnennar_the_coldbringer.cpp
@@ -0,0 +1,130 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Amnennar_the_coldbringer
+SD%Complete: 100
+SDComment:
+SDCategory: Razorfen Downs
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define SAY_AGGRO -1129000
+#define SAY_SUMMON60 -1129001
+#define SAY_SUMMON30 -1129002
+#define SAY_HP -1129003
+#define SAY_KILL -1129004
+
+#define SPELL_AMNENNARSWRATH 13009
+#define SPELL_FROSTBOLT 15530
+#define SPELL_FROST_NOVA 15531
+#define SPELL_FROST_SPECTRES 12642
+
+struct boss_amnennar_the_coldbringerAI : public ScriptedAI
+{
+ boss_amnennar_the_coldbringerAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 AmnenarsWrath_Timer;
+ uint32 FrostBolt_Timer;
+ uint32 FrostNova_Timer;
+ bool Spectrals60;
+ bool Spectrals30;
+ bool Hp;
+
+ void Reset()
+ {
+ AmnenarsWrath_Timer = 8000;
+ FrostBolt_Timer = 1000;
+ FrostNova_Timer = 10000 + rand()%5000;
+ Spectrals30 = false;
+ Spectrals60 = false;
+ Hp = false;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+ }
+
+ void KilledUnit()
+ {
+ DoScriptText(SAY_KILL, me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ //AmnenarsWrath_Timer
+ if (AmnenarsWrath_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_AMNENNARSWRATH);
+ AmnenarsWrath_Timer = 12000;
+ } else AmnenarsWrath_Timer -= diff;
+
+ //FrostBolt_Timer
+ if (FrostBolt_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_FROSTBOLT);
+ FrostBolt_Timer = 8000;
+ } else FrostBolt_Timer -= diff;
+
+ if (FrostNova_Timer <= diff)
+ {
+ DoCast(me, SPELL_FROST_NOVA);
+ FrostNova_Timer = 15000;
+ } else FrostNova_Timer -= diff;
+
+ if (!Spectrals60 && me->GetHealth()*100 / me->GetMaxHealth() < 60)
+ {
+ DoScriptText(SAY_SUMMON60, me);
+ DoCast(me->getVictim(), SPELL_FROST_SPECTRES);
+ Spectrals60 = true;
+ }
+
+ if (!Hp && me->GetHealth()*100 / me->GetMaxHealth() < 50)
+ {
+ DoScriptText(SAY_HP, me);
+ Hp = true;
+ }
+
+ if (!Spectrals30 && me->GetHealth()*100 / me->GetMaxHealth() < 30)
+ {
+ DoScriptText(SAY_SUMMON30, me);
+ DoCast(me->getVictim(), SPELL_FROST_SPECTRES);
+ Spectrals30 = true;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_amnennar_the_coldbringer(Creature* pCreature)
+{
+ return new boss_amnennar_the_coldbringerAI (pCreature);
+}
+
+void AddSC_boss_amnennar_the_coldbringer()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_amnennar_the_coldbringer";
+ newscript->GetAI = &GetAI_boss_amnennar_the_coldbringer;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/razorfen_downs/instance_razorfen_downs.cpp b/src/server/scripts/Kalimdor/razorfen_downs/instance_razorfen_downs.cpp
new file mode 100644
index 00000000000..04904f08a57
--- /dev/null
+++ b/src/server/scripts/Kalimdor/razorfen_downs/instance_razorfen_downs.cpp
@@ -0,0 +1,215 @@
+/*
+ * Copyright (C) 2010 Trinity <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#include "ScriptedPch.h"
+#include "razorfen_downs.h"
+
+#define MAX_ENCOUNTER 1
+
+struct instance_razorfen_downs : public ScriptedInstance
+{
+ instance_razorfen_downs(Map* pMap) : ScriptedInstance(pMap)
+ {
+ Initialize();
+ };
+
+ uint64 uiGongGUID;
+
+ uint32 m_auiEncounter[MAX_ENCOUNTER];
+
+ uint8 uiGongWaves;
+
+ std::string str_data;
+
+ void Initialize()
+ {
+ uiGongGUID = 0;
+
+ uiGongWaves = 0;
+
+ memset(&m_auiEncounter, 0, sizeof(m_auiEncounter));
+ }
+
+ std::string GetSaveData()
+ {
+ OUT_SAVE_INST_DATA;
+
+ std::ostringstream saveStream;
+
+ saveStream << "T C " << m_auiEncounter[0]
+ << " " << uiGongWaves;
+
+ str_data = saveStream.str();
+
+ OUT_SAVE_INST_DATA_COMPLETE;
+ return str_data;
+ }
+
+ void Load(const char* in)
+ {
+ if (!in)
+ {
+ OUT_LOAD_INST_DATA_FAIL;
+ return;
+ }
+
+ OUT_LOAD_INST_DATA(in);
+
+ char dataHead1, dataHead2;
+ uint16 data0, data1;
+
+ std::istringstream loadStream(in);
+ loadStream >> dataHead1 >> dataHead2 >> data0 >> data1;
+
+ if (dataHead1 == 'T' && dataHead2 == 'C')
+ {
+ m_auiEncounter[0] = data0;
+
+ for (uint8 i = 0; i < MAX_ENCOUNTER; ++i)
+ if (m_auiEncounter[i] == IN_PROGRESS)
+ m_auiEncounter[i] = NOT_STARTED;
+
+ uiGongWaves = data1;
+ } else OUT_LOAD_INST_DATA_FAIL;
+
+ OUT_LOAD_INST_DATA_COMPLETE;
+ }
+
+ void OnGameObjectCreate(GameObject* pGo, bool /*bAdd*/)
+ {
+ switch(pGo->GetEntry())
+ {
+ case GO_GONG:
+ uiGongGUID = pGo->GetGUID();
+ if (m_auiEncounter[0] == DONE)
+ pGo->SetFlag(GAMEOBJECT_FLAGS,GO_FLAG_UNK1);
+ break;
+ default:
+ break;
+ }
+ }
+
+ void SetData(uint32 uiType, uint32 uiData)
+ {
+ if (uiType == DATA_GONG_WAVES)
+ {
+ uiGongWaves = uiData;
+
+ switch(uiGongWaves)
+ {
+ case 9:
+ case 14:
+ if (GameObject* pGo = instance->GetGameObject(uiGongGUID))
+ pGo->RemoveFlag(GAMEOBJECT_FLAGS,GO_FLAG_UNK1);
+ break;
+ case 1:
+ case 10:
+ case 16:
+ {
+ GameObject* pGo = instance->GetGameObject(uiGongGUID);
+
+ if (!pGo)
+ return;
+
+ pGo->SetFlag(GAMEOBJECT_FLAGS,GO_FLAG_UNK1);
+
+ uint32 uiCreature = 0;
+ uint8 uiSummonTimes = 0;
+
+ switch(uiGongWaves)
+ {
+ case 1:
+ uiCreature = CREATURE_TOMB_FIEND;
+ uiSummonTimes = 7;
+ break;
+ case 10:
+ uiCreature = CREATURE_TOMB_REAVER;
+ uiSummonTimes = 3;
+ break;
+ case 16:
+ uiCreature = CREATURE_TUTEN_KASH;
+ break;
+ default:
+ break;
+ }
+
+
+ if (Creature* pCreature = pGo->SummonCreature(uiCreature,2502.635,844.140,46.896,0.633))
+ {
+ if (uiGongWaves == 10 || uiGongWaves == 1)
+ {
+ for (uint8 i = 0; i < uiSummonTimes; ++i)
+ {
+ if (Creature* pSummon = pGo->SummonCreature(uiCreature,2502.635 + float(irand(-5,5)),844.140 + float(irand(-5,5)),46.896,0.633))
+ pSummon->GetMotionMaster()->MovePoint(0,2533.479 + float(irand(-5,5)),870.020 + float(irand(-5,5)),47.678);
+ }
+ }
+ pCreature->GetMotionMaster()->MovePoint(0,2533.479 + float(irand(-5,5)),870.020 + float(irand(-5,5)),47.678);
+ }
+ break;
+ }
+ default:
+ break;
+ }
+ }
+
+ if (uiType == BOSS_TUTEN_KASH)
+ {
+ m_auiEncounter[0] = uiData;
+
+ if (uiData == DONE)
+ SaveToDB();
+ }
+ }
+
+ uint32 GetData(uint32 uiType)
+ {
+ switch(uiType)
+ {
+ case DATA_GONG_WAVES:
+ return uiGongWaves;
+ }
+
+ return 0;
+ }
+
+ uint64 GetData64(uint32 uiType)
+ {
+ switch(uiType)
+ {
+ case DATA_GONG: return uiGongGUID;
+ }
+
+ return 0;
+ }
+};
+
+InstanceData* GetInstanceData_instance_razorfen_downs(Map* pMap)
+{
+ return new instance_razorfen_downs(pMap);
+}
+
+void AddSC_instance_razorfen_downs()
+{
+ Script* newscript;
+
+ newscript = new Script;
+ newscript->Name = "instance_razorfen_downs";
+ newscript->GetInstanceData = &GetInstanceData_instance_razorfen_downs;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.cpp b/src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.cpp
new file mode 100644
index 00000000000..3e8f4049a37
--- /dev/null
+++ b/src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.cpp
@@ -0,0 +1,165 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Razorfen_Downs
+SD%Complete: 100
+SDComment: Support for Henry Stern(2 recipes)
+SDCategory: Razorfen Downs
+EndScriptData */
+
+/* ContentData
+npc_henry_stern
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "razorfen_downs.h"
+
+/*###
+# npc_henry_stern
+####*/
+
+enum eEnums
+{
+ SPELL_GOLDTHORN_TEA = 13028,
+ SPELL_TEACHING_GOLDTHORN_TEA = 13029,
+ SPELL_MIGHT_TROLLS_BLOOD_POTION = 3451,
+ SPELL_TEACHING_MIGHTY_TROLLS_BLOOD_POTION = 13030,
+ GOSSIP_TEXT_TEA_ANSWER = 2114,
+ GOSSIP_TEXT_POTION_ANSWER = 2115,
+};
+
+#define GOSSIP_ITEM_TEA "Teach me the cooking recipe"
+#define GOSSIP_ITEM_POTION "Teach me the alchemy recipe"
+
+bool GossipHello_npc_henry_stern (Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->GetBaseSkillValue(SKILL_COOKING) >= 175 && !pPlayer->HasSpell(SPELL_GOLDTHORN_TEA))
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_TEA, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+
+ if (pPlayer->GetBaseSkillValue(SKILL_ALCHEMY) >= 180 && !pPlayer->HasSpell(SPELL_MIGHT_TROLLS_BLOOD_POTION))
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_POTION, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_henry_stern (Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF + 1)
+ {
+ pPlayer->CastSpell(pPlayer, SPELL_TEACHING_GOLDTHORN_TEA, true);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_TEXT_TEA_ANSWER, pCreature->GetGUID());
+ }
+
+ if (uiAction == GOSSIP_ACTION_INFO_DEF + 2)
+ {
+ pPlayer->CastSpell(pPlayer, SPELL_TEACHING_MIGHTY_TROLLS_BLOOD_POTION, true);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_TEXT_POTION_ANSWER, pCreature->GetGUID());
+ }
+
+ return true;
+}
+
+/*######
+## go_gong
+######*/
+
+bool GOHello_go_gong(Player* /*pPlayer*/, GameObject* pGO)
+{
+ //basic support, not blizzlike data is missing...
+ ScriptedInstance* pInstance = pGO->GetInstanceData();
+
+ if (pInstance)
+ {
+ pInstance->SetData(DATA_GONG_WAVES,pInstance->GetData(DATA_GONG_WAVES)+1);
+ return true;
+ }
+
+ return false;
+}
+
+enum eTombCreature
+{
+ SPELL_WEB = 745
+};
+
+struct npc_tomb_creatureAI : public ScriptedAI
+{
+ npc_tomb_creatureAI(Creature* pCreature) : ScriptedAI(pCreature)
+ {
+ pInstance = pCreature->GetInstanceData();
+ }
+
+ ScriptedInstance* pInstance;
+
+ uint32 uiWebTimer;
+
+ void Reset()
+ {
+ uiWebTimer = urand(5000,8000);
+ }
+
+ void UpdateAI(const uint32 uiDiff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ //from acid
+ if (me->GetEntry() == CREATURE_TOMB_REAVER)
+ {
+ if (uiWebTimer <= uiDiff)
+ {
+ DoCast(me->getVictim(), SPELL_WEB);
+ uiWebTimer = urand(7000,16000);
+ } else uiWebTimer -= uiDiff;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+
+ void JustDied(Unit* /*pKiller*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_GONG_WAVES,pInstance->GetData(DATA_GONG_WAVES)+1);
+ }
+};
+
+CreatureAI* GetAI_npc_tomb_creature(Creature* pCreature)
+{
+ return new npc_tomb_creatureAI (pCreature);
+}
+
+void AddSC_razorfen_downs()
+{
+ Script* newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_henry_stern";
+ newscript->pGossipHello = &GossipHello_npc_henry_stern;
+ newscript->pGossipSelect = &GossipSelect_npc_henry_stern;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "go_gong";
+ newscript->pGOHello = &GOHello_go_gong;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_tomb_creature";
+ newscript->GetAI = &GetAI_npc_tomb_creature;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.h b/src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.h
new file mode 100644
index 00000000000..a67b4223c4a
--- /dev/null
+++ b/src/server/scripts/Kalimdor/razorfen_downs/razorfen_downs.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2010 Trinity <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#ifndef DEF_RAZORFEN_DOWNS_H
+#define DEF_RAZORFEN_DOWNS_H
+
+enum eData
+{
+ BOSS_TUTEN_KASH,
+ DATA_GONG_WAVES
+};
+
+enum eData64
+{
+ DATA_GONG
+};
+
+enum eGameObject
+{
+ GO_GONG = 148917
+};
+
+enum eCreature
+{
+ CREATURE_TOMB_FIEND = 7349,
+ CREATURE_TOMB_REAVER = 7351,
+ CREATURE_TUTEN_KASH = 7355
+};
+
+#endif
diff --git a/src/server/scripts/Kalimdor/razorfen_kraul/instance_razorfen_kraul.cpp b/src/server/scripts/Kalimdor/razorfen_kraul/instance_razorfen_kraul.cpp
new file mode 100644
index 00000000000..8a92d3d4d89
--- /dev/null
+++ b/src/server/scripts/Kalimdor/razorfen_kraul/instance_razorfen_kraul.cpp
@@ -0,0 +1,104 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Instance_Razorfen_Kraul
+SD%Complete:
+SDComment:
+SDCategory: Razorfen Kraul
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "razorfen_kraul.h"
+
+#define WARD_KEEPERS_NR 2
+
+struct instance_razorfen_kraul : public ScriptedInstance
+{
+ instance_razorfen_kraul(Map* pMap) : ScriptedInstance(pMap) {Initialize();};
+
+ uint64 DoorWardGUID;
+ uint32 WardCheck_Timer;
+ int WardKeeperAlive;
+
+ void Initialize()
+ {
+ WardKeeperAlive = 1;
+ WardCheck_Timer = 4000;
+ DoorWardGUID = 0;
+ }
+
+ Player* GetPlayerInMap()
+ {
+ Map::PlayerList const& players = instance->GetPlayers();
+
+ if (!players.isEmpty())
+ {
+ for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr)
+ {
+ if (Player* plr = itr->getSource())
+ return plr;
+ }
+ }
+ debug_log("TSCR: Instance Razorfen Kraul: GetPlayerInMap, but PlayerList is empty!");
+ return NULL;
+ }
+
+ void OnGameObjectCreate(GameObject* pGo, bool /*apply*/)
+ {
+ switch(pGo->GetEntry())
+ {
+ case 21099: DoorWardGUID = pGo->GetGUID(); break;
+ }
+ }
+
+ void Update(uint32 diff)
+ {
+ if (WardCheck_Timer <= diff)
+ {
+ HandleGameObject(DoorWardGUID, WardKeeperAlive);
+ WardKeeperAlive = 0;
+ WardCheck_Timer = 4000;
+ }else
+ WardCheck_Timer -= diff;
+ }
+
+ void SetData(uint32 type, uint32 data)
+ {
+ switch(type)
+ {
+ case TYPE_WARD_KEEPERS:
+ if (data == NOT_STARTED)
+ WardKeeperAlive = 1;
+ break;
+ }
+ }
+
+};
+
+InstanceData* GetInstanceData_instance_razorfen_kraul(Map* pMap)
+{
+ return new instance_razorfen_kraul(pMap);
+}
+
+void AddSC_instance_razorfen_kraul()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_razorfen_kraul";
+ newscript->GetInstanceData = &GetInstanceData_instance_razorfen_kraul;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.cpp b/src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.cpp
new file mode 100644
index 00000000000..8470fa6c7ac
--- /dev/null
+++ b/src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.cpp
@@ -0,0 +1,194 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Razorfen Kraul
+SD%Complete: 100
+SDComment: Quest support: 1144
+SDCategory: Razorfen Kraul
+EndScriptData */
+
+/* ContentData
+npc_willix
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+#include "razorfen_kraul.h"
+
+#define SAY_READY -1047000
+#define SAY_POINT -1047001
+#define SAY_AGGRO1 -1047002
+#define SAY_BLUELEAF -1047003
+#define SAY_DANGER -1047004
+#define SAY_BAD -1047005
+#define SAY_THINK -1047006
+#define SAY_SOON -1047007
+#define SAY_FINALY -1047008
+#define SAY_WIN -1047009
+#define SAY_END -1047010
+
+#define QUEST_WILLIX_THE_IMPORTER 1144
+#define ENTRY_BOAR 4514
+#define SPELL_QUILLBOAR_CHANNELING 7083
+
+struct npc_willixAI : public npc_escortAI
+{
+ npc_willixAI(Creature *c) : npc_escortAI(c) {}
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch (i)
+ {
+ case 3:
+ me->HandleEmoteCommand(EMOTE_STATE_POINT);
+ DoScriptText(SAY_POINT, me, pPlayer);
+ break;
+ case 4:
+ me->SummonCreature(ENTRY_BOAR, 2137.66, 1843.98, 48.08, 1.54, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ break;
+ case 8:
+ DoScriptText(SAY_BLUELEAF, me, pPlayer);
+ break;
+ case 9:
+ DoScriptText(SAY_DANGER, me, pPlayer);
+ break;
+ case 13:
+ DoScriptText(SAY_BAD, me, pPlayer);
+ break;
+ case 14:
+ me->SummonCreature(ENTRY_BOAR, 2078.91, 1704.54, 56.77, 1.54, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ break;
+ case 25:
+ DoScriptText(SAY_THINK, me, pPlayer);
+ break;
+ case 31:
+ DoScriptText(SAY_SOON, me, pPlayer);
+ break;
+ case 42:
+ DoScriptText(SAY_FINALY, me, pPlayer);
+ break;
+ case 43:
+ me->SummonCreature(ENTRY_BOAR, 1956.43, 1596.97, 81.75, 1.54,TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ break;
+ case 45:
+ DoScriptText(SAY_WIN, me, pPlayer);
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_QUESTGIVER);
+ if (pPlayer && pPlayer->GetTypeId() == TYPEID_PLAYER)
+ CAST_PLR(pPlayer)->GroupEventHappens(QUEST_WILLIX_THE_IMPORTER,me);
+ break;
+ case 46:
+ DoScriptText(SAY_END, me, pPlayer);
+ break;
+ }
+ }
+
+ void Reset() {}
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ DoScriptText(SAY_AGGRO1, me, NULL);
+ }
+
+ void JustSummoned(Creature* summoned)
+ {
+ summoned->AI()->AttackStart(me);
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ if (Player* pPlayer = GetPlayerForEscort())
+ CAST_PLR(pPlayer)->FailQuest(QUEST_WILLIX_THE_IMPORTER);
+ }
+};
+
+bool QuestAccept_npc_willix(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_WILLIX_THE_IMPORTER)
+ {
+ CAST_AI(npc_escortAI, (pCreature->AI()))->Start(true, false, pPlayer->GetGUID());
+ DoScriptText(SAY_READY, pCreature, pPlayer);
+ pCreature->setFaction(113);
+ }
+
+ return true;
+}
+
+struct npc_deaths_head_ward_keeperAI : public ScriptedAI
+{
+ npc_deaths_head_ward_keeperAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+ uint32 QuillboarChanneling_Timer;
+
+ void Reset()
+ {
+ QuillboarChanneling_Timer = 1500;
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!me->isAlive())
+ return;
+
+ if (pInstance)
+ pInstance->SetData(TYPE_WARD_KEEPERS, NOT_STARTED);
+
+ if (QuillboarChanneling_Timer <= diff)
+ {
+ if (me->IsNonMeleeSpellCasted(false))
+ me->InterruptNonMeleeSpells(true);
+ DoCast(me, SPELL_QUILLBOAR_CHANNELING);
+ QuillboarChanneling_Timer = 1100;
+ } else QuillboarChanneling_Timer -= diff;
+
+ }
+};
+
+CreatureAI* GetAI_npc_deaths_head_ward_keeper(Creature* pCreature)
+{
+ return new npc_deaths_head_ward_keeperAI(pCreature);
+}
+
+CreatureAI* GetAI_npc_willix(Creature* pCreature)
+{
+ return new npc_willixAI(pCreature);
+}
+
+void AddSC_razorfen_kraul()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_willix";
+ newscript->GetAI = &GetAI_npc_willix;
+ newscript->pQuestAccept = &QuestAccept_npc_willix;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_deaths_head_ward_keeper";
+ newscript->GetAI = &GetAI_npc_deaths_head_ward_keeper;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.h b/src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.h
new file mode 100644
index 00000000000..e2219986f63
--- /dev/null
+++ b/src/server/scripts/Kalimdor/razorfen_kraul/razorfen_kraul.h
@@ -0,0 +1,21 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#ifndef DEF_RAZORFEN_KRAUL_H
+#define DEF_RAZORFEN_KRAUL_H
+
+#define TYPE_WARD_KEEPERS 1
+#endif
diff --git a/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ayamiss.cpp b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ayamiss.cpp
new file mode 100644
index 00000000000..f6dc75558c8
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ayamiss.cpp
@@ -0,0 +1,125 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Ayamiss
+SD%Complete: 50
+SDComment: VERIFY SCRIPT
+SDCategory: Ruins of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "ruins_of_ahnqiraj.h"
+
+/*
+To do:
+make him fly from 70-100%
+*/
+
+enum Spells
+{
+ SPELL_STINGERSPRAY = 25749,
+ SPELL_POISONSTINGER = 25748, //only used in phase1
+ SPELL_SUMMONSWARMER = 25844, //might be 25708
+ SPELL_PARALYZE = 23414 //doesnt work correct (core)
+};
+
+struct boss_ayamissAI : public ScriptedAI
+{
+ boss_ayamissAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ uint32 STINGERSPRAY_Timer;
+ uint32 POISONSTINGER_Timer;
+ uint32 SUMMONSWARMER_Timer;
+ uint32 phase;
+
+ ScriptedInstance *pInstance;
+
+ void Reset()
+ {
+ STINGERSPRAY_Timer = 30000;
+ POISONSTINGER_Timer = 30000;
+ SUMMONSWARMER_Timer = 60000;
+ phase=1;
+
+ if (pInstance)
+ pInstance->SetData(DATA_AYAMISS_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_AYAMISS_EVENT, IN_PROGRESS);
+ }
+
+ void JustDied(Unit * /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_AYAMISS_EVENT, DONE);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ //If he is 70% start phase 2
+ if (phase == 1 && me->GetHealth()*100 / me->GetMaxHealth() <= 70 && !me->IsNonMeleeSpellCasted(false))
+ {
+ phase=2;
+ }
+
+ //STINGERSPRAY_Timer (only in phase2)
+ if (phase == 2 && STINGERSPRAY_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_STINGERSPRAY);
+ STINGERSPRAY_Timer = 30000;
+ } else STINGERSPRAY_Timer -= diff;
+
+ //POISONSTINGER_Timer (only in phase1)
+ if (phase == 1 && POISONSTINGER_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_POISONSTINGER);
+ POISONSTINGER_Timer = 30000;
+ } else POISONSTINGER_Timer -= diff;
+
+ //SUMMONSWARMER_Timer (only in phase1)
+ if (SUMMONSWARMER_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_SUMMONSWARMER);
+ SUMMONSWARMER_Timer = 60000;
+ } else SUMMONSWARMER_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_boss_ayamiss(Creature* pCreature)
+{
+ return new boss_ayamissAI (pCreature);
+}
+
+void AddSC_boss_ayamiss()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_ayamiss";
+ newscript->GetAI = &GetAI_boss_ayamiss;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_buru.cpp b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_buru.cpp
new file mode 100644
index 00000000000..86a2c559543
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_buru.cpp
@@ -0,0 +1,72 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Buru
+SD%Complete: 0
+SDComment: Place Holder
+SDCategory: Ruins of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "ruins_of_ahnqiraj.h"
+
+enum Yells
+{
+ EMOTE_TARGET = -1509002
+};
+
+struct boss_buruAI : public ScriptedAI
+{
+ boss_buruAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ void Reset()
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_BURU_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_BURU_EVENT, IN_PROGRESS);
+ }
+
+ void JustDied(Unit * /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_BURU_EVENT, DONE);
+ }
+};
+CreatureAI* GetAI_boss_buru(Creature* pCreature)
+{
+ return new boss_buruAI (pCreature);
+}
+
+void AddSC_boss_buru()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_buru";
+ newscript->GetAI = &GetAI_boss_buru;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_kurinnaxx.cpp b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_kurinnaxx.cpp
new file mode 100644
index 00000000000..44f11bf4b60
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_kurinnaxx.cpp
@@ -0,0 +1,143 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Kurinnaxx
+SD%Complete: 100
+SDComment: VERIFY SCRIPT AND SQL
+SDCategory: Ruins of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "ruins_of_ahnqiraj.h"
+
+enum Spells
+{
+ SPELL_MORTALWOUND = 25646,
+ SPELL_SANDTRAP = 25656,
+ SPELL_ENRAGE = 28798,
+ SPELL_SUMMON_PLAYER = 26446,
+ SPELL_TRASH = 3391,
+ SPELL_WIDE_SLASH = 25814
+};
+
+struct boss_kurinnaxxAI : public ScriptedAI
+{
+ boss_kurinnaxxAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ uint32 uiMortalWoundTimer;
+ uint32 uiSandtrapTimer;
+ uint32 uiWideSlashTimer;
+ uint32 uiSummonPlayerTimer;
+ uint32 uiTrashTimer;
+ bool bIsEnraged;
+
+ ScriptedInstance* pInstance;
+
+ void Reset()
+ {
+ bIsEnraged = false;
+ uiMortalWoundTimer = urand(2000,7000);
+ uiSandtrapTimer = urand(20000,30000);
+ uiWideSlashTimer = urand(10000,15000);
+ uiTrashTimer = urand(20000,25000);
+ uiSummonPlayerTimer = urand(30000,40000);
+
+ if (pInstance)
+ pInstance->SetData(DATA_KURINNAXX_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_KURINNAXX_EVENT, IN_PROGRESS);
+ }
+
+ void JustDied(Unit * /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_KURINNAXX_EVENT, DONE);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ //If we are <30% cast enrage
+ if (!bIsEnraged && me->GetHealth()*100 / me->GetMaxHealth() <= 30 && !me->IsNonMeleeSpellCasted(false))
+ {
+ bIsEnraged = true;
+ DoCast(me, SPELL_ENRAGE);
+ }
+
+ //Mortal Wound spell
+ if (uiMortalWoundTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_MORTALWOUND);
+ uiMortalWoundTimer = urand(2000,7000);
+ } else uiMortalWoundTimer -= diff;
+
+ //Santrap spell
+ if (uiSandtrapTimer <= diff)
+ {
+ if (Unit* pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ DoCast(pTarget, SPELL_SANDTRAP);
+ uiSandtrapTimer = 30000;
+ } else uiSandtrapTimer -= diff;
+
+ //Wide Slash spell
+ if (uiWideSlashTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_WIDE_SLASH);
+ uiWideSlashTimer = urand(10000,15000);
+ } else uiWideSlashTimer -= diff;
+
+ //Trash spell
+ if (uiTrashTimer <= diff)
+ {
+ DoCast(me, SPELL_TRASH);
+ uiTrashTimer = urand(20000,25000);
+ } else uiTrashTimer -= diff;
+
+ //Summon Player spell
+ if (uiSummonPlayerTimer <= diff)
+ {
+ if (Unit* pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ DoCast(pTarget, SPELL_SUMMON_PLAYER);
+ uiSummonPlayerTimer = urand(30000,40000);
+ } else uiSummonPlayerTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_boss_kurinnaxx(Creature* pCreature)
+{
+ return new boss_kurinnaxxAI (pCreature);
+}
+
+void AddSC_boss_kurinnaxx()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_kurinnaxx";
+ newscript->GetAI = &GetAI_boss_kurinnaxx;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_moam.cpp b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_moam.cpp
new file mode 100644
index 00000000000..1882adc8fbb
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_moam.cpp
@@ -0,0 +1,162 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Moam
+SD%Complete: 90
+SDComment: TODO: Adjust timer, correct Stone phase buff
+SDCategory: Ruins of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "ruins_of_ahnqiraj.h"
+
+enum Emotes
+{
+ EMOTE_AGGRO = -1509000,
+ EMOTE_MANA_FULL = -1509001
+};
+
+enum Spells
+{
+ SPELL_TRAMPLE = 15550,
+ SPELL_DRAINMANA = 27256, //Doesn't exist ?
+ SPELL_ARCANEERUPTION = 25672,
+ SPELL_SUMMONMANA = 25681, //Summon Mana fiend. It only summons one so exec it three times
+ SPELL_GRDRSLEEP = 24360 //Greater Dreamless Sleep
+};
+
+enum Creatures
+{
+ CREATURE_MANA_FIEND = 15527
+};
+
+enum CombatPhase
+{
+ NORMAL,
+ STONE
+};
+
+struct boss_moamAI : public ScriptedAI
+{
+ boss_moamAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ uint32 uiTrampleTimer;
+ uint32 uiDrainManaTimer;
+ uint32 uiPhaseTimer;
+ CombatPhase Phase;
+
+ ScriptedInstance *pInstance;
+
+ void Reset()
+ {
+ uiTrampleTimer = urand(3000,7000);
+ uiDrainManaTimer = urand(3000,7000);
+ uiPhaseTimer = 90000;
+ Phase = NORMAL;
+ me->SetPower(POWER_MANA,0);
+
+ if (pInstance)
+ pInstance->SetData(DATA_MOAM_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoScriptText(EMOTE_AGGRO, me);
+
+ if (pInstance)
+ pInstance->SetData(DATA_MOAM_EVENT, IN_PROGRESS);
+ }
+
+ void JustDied(Unit * /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_MOAM_EVENT, DONE);
+ }
+
+ void DrainMana()
+ {
+ for (uint8 i=0;i<6;++i)
+ {
+ if (Unit* pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true))
+ {
+ pTarget->ModifyPower(POWER_MANA, -500);
+ me->ModifyPower(POWER_MANA, 1000);
+ }
+ }
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (Phase == NORMAL)
+ {
+ if (!UpdateVictim())
+ return;
+
+ //If we are 100%MANA cast Arcane Erruption
+ if (me->GetPower(POWER_MANA) == me->GetMaxPower(POWER_MANA))
+ {
+ DoCast(me->getVictim(), SPELL_ARCANEERUPTION);
+ DoScriptText(EMOTE_MANA_FULL, me);
+ me->SetPower(POWER_MANA,0);
+ }
+
+ //Trample Spell
+ if (uiTrampleTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_TRAMPLE);
+ uiTrampleTimer = urand(3000,7000);
+ } else uiTrampleTimer -= diff;
+
+ //Drain Mana
+ if (uiDrainManaTimer <= diff)
+ {
+ DrainMana();
+ uiDrainManaTimer = urand(3000,7000);
+ } else uiDrainManaTimer -= diff;
+
+ DoMeleeAttackIfReady();
+
+ //After 90secs change phase
+ if (uiPhaseTimer <= diff)
+ {
+ Phase = STONE;
+ DoCast(me, SPELL_SUMMONMANA);
+ DoCast(me, SPELL_SUMMONMANA);
+ DoCast(me, SPELL_SUMMONMANA);
+ DoCast(me, SPELL_GRDRSLEEP);
+ } else uiPhaseTimer -= diff;
+ }
+ }
+};
+
+CreatureAI* GetAI_boss_moam(Creature* pCreature)
+{
+ return new boss_moamAI (pCreature);
+}
+
+void AddSC_boss_moam()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_moam";
+ newscript->GetAI = &GetAI_boss_moam;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ossirian.cpp b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ossirian.cpp
new file mode 100644
index 00000000000..57ba8d9da7f
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_ossirian.cpp
@@ -0,0 +1,79 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Ossirian
+SD%Complete: 0
+SDComment: Place holder
+SDCategory: Ruins of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "ruins_of_ahnqiraj.h"
+
+enum Yells
+{
+ SAY_SURPREME2 = -1509019,
+ SAY_SURPREME3 = -1509020,
+ SAY_RAND_INTRO1 = -1509021,
+ SAY_RAND_INTRO2 = -1509022,
+ SAY_RAND_INTRO3 = -1509023,
+ SAY_RAND_INTRO4 = -1509024, //possibly old?
+ SAY_AGGRO = -1509025,
+ SAY_SLAY = -1509026,
+ SAY_DEATH = -1509027
+};
+
+struct boss_ossirianAI : public ScriptedAI
+{
+ boss_ossirianAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ void Reset()
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_OSSIRIAN_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_OSSIRIAN_EVENT, IN_PROGRESS);
+ }
+
+ void JustDied(Unit * /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_OSSIRIAN_EVENT, DONE);
+ }
+};
+CreatureAI* GetAI_boss_ossirian(Creature* pCreature)
+{
+ return new boss_ossirianAI (pCreature);
+}
+
+void AddSC_boss_ossirian()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_ossirian";
+ newscript->GetAI = &GetAI_boss_ossirian;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_rajaxx.cpp b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_rajaxx.cpp
new file mode 100644
index 00000000000..5be60dc0ca0
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/boss_rajaxx.cpp
@@ -0,0 +1,85 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Rajaxx
+SD%Complete: 0
+SDComment: Place Holder
+SDCategory: Ruins of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "ruins_of_ahnqiraj.h"
+
+enum Yells
+{
+ SAY_ANDOROV_INTRO = -1509003,
+ SAY_ANDOROV_ATTACK = -1509004,
+ SAY_WAVE3 = -1509005,
+ SAY_WAVE4 = -1509006,
+ SAY_WAVE5 = -1509007,
+ SAY_WAVE6 = -1509008,
+ SAY_WAVE7 = -1509009,
+ SAY_INTRO = -1509010,
+ SAY_UNK1 = -1509011,
+ SAY_UNK2 = -1509012,
+ SAY_UNK3 = -1509013,
+ SAY_UNK4 = -1509014,
+ SAY_DEAGGRO = -1509015,
+ SAY_KILLS_ANDOROV = -1509016,
+ SAY_COMPLETE_QUEST = -1509017 //Yell when realm complete quest 8743 for world event
+};
+
+struct boss_rajaxxAI : public ScriptedAI
+{
+ boss_rajaxxAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ void Reset()
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_RAJAXX_EVENT, NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_RAJAXX_EVENT, IN_PROGRESS);
+ }
+
+ void JustDied(Unit * /*killer*/)
+ {
+ if (pInstance)
+ pInstance->SetData(DATA_RAJAXX_EVENT, DONE);
+ }
+};
+CreatureAI* GetAI_boss_rajaxx(Creature* pCreature)
+{
+ return new boss_rajaxxAI (pCreature);
+}
+
+void AddSC_boss_rajaxx()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_rajaxx";
+ newscript->GetAI = &GetAI_boss_rajaxx;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/instance_ruins_of_ahnqiraj.cpp b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/instance_ruins_of_ahnqiraj.cpp
new file mode 100644
index 00000000000..ba7471bdbd2
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/instance_ruins_of_ahnqiraj.cpp
@@ -0,0 +1,213 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Instance_Ruins_of_Ahnqiraj
+SD%Complete: 0
+SDComment: Place holder
+SDCategory: Ruins of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "ruins_of_ahnqiraj.h"
+
+#define MAX_ENCOUNTER 6
+
+/* Ruins of Ahn'Qiraj encounters:
+0 - Kurinnaxx
+1 - General Rajaxx
+2 - Moam
+3 - Buru the Gorger
+4 - Ayamiss the Hunter
+5 - Ossirian the Unscarred */
+
+struct instance_ruins_of_ahn_qiraj : public ScriptedInstance
+{
+ instance_ruins_of_ahn_qiraj(Map* pMap) : ScriptedInstance(pMap) { Initialize(); }
+
+ uint64 uiKurinaxx;
+ uint64 uiRajaxx;
+ uint64 uiMoam;
+ uint64 uiBuru;
+ uint64 uiAyamiss;
+ uint64 uiOssirian;
+
+ uint8 m_auiEncounter[MAX_ENCOUNTER];
+ std::string str_data;
+
+ void Initialize()
+ {
+ memset(&m_auiEncounter, 0, sizeof(m_auiEncounter));
+
+ uiKurinaxx = 0;
+ uiRajaxx = 0;
+ uiMoam = 0;
+ uiBuru = 0;
+ uiAyamiss = 0;
+ uiOssirian = 0;
+ }
+
+ bool IsEncounterInProgress() const
+ {
+ for (uint8 i = 0; i < MAX_ENCOUNTER; ++i)
+ if (m_auiEncounter[i] == IN_PROGRESS) return true;
+
+ return false;
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool /*add*/)
+ {
+ switch (pCreature->GetEntry())
+ {
+ case CREATURE_KURINAXX:
+ uiKurinaxx = pCreature->GetGUID();
+ break;
+ case CREATURE_RAJAXX:
+ uiRajaxx = pCreature->GetGUID();
+ break;
+ case CREATURE_MOAM:
+ uiMoam = pCreature->GetGUID();
+ break;
+ case CREATURE_BURU:
+ uiBuru = pCreature->GetGUID();
+ break;
+ case CREATURE_AYAMISS:
+ uiAyamiss = pCreature->GetGUID();
+ break;
+ case CREATURE_OSSIRIAN:
+ uiOssirian = pCreature->GetGUID();
+ break;
+ }
+ }
+
+ uint32 GetData(uint32 identifier)
+ {
+ switch(identifier)
+ {
+ case DATA_KURINNAXX_EVENT: return m_auiEncounter[0];
+ case DATA_RAJAXX_EVENT: return m_auiEncounter[1];
+ case DATA_MOAM_EVENT: return m_auiEncounter[2];
+ case DATA_BURU_EVENT: return m_auiEncounter[3];
+ case DATA_AYAMISS_EVENT: return m_auiEncounter[4];
+ case DATA_OSSIRIAN_EVENT: return m_auiEncounter[5];
+ }
+
+ return 0;
+ }
+
+ void SetData(uint32 identifier, uint32 data)
+ {
+ switch(identifier)
+ {
+ case DATA_KURINNAXX_EVENT:
+ m_auiEncounter[0] = data;
+ break;
+ case DATA_RAJAXX_EVENT:
+ m_auiEncounter[1] = data;
+ break;
+ case DATA_MOAM_EVENT:
+ m_auiEncounter[2] = data;
+ break;
+ case DATA_BURU_EVENT:
+ m_auiEncounter[3] = data;
+ break;
+ case DATA_AYAMISS_EVENT:
+ m_auiEncounter[4] = data;
+ break;
+ case DATA_OSSIRIAN_EVENT:
+ m_auiEncounter[5] = data;
+ break;
+ }
+
+ if (data == DONE)
+ SaveToDB();
+ }
+
+ uint64 GetData64(uint32 uiIdentifier)
+ {
+ switch(uiIdentifier)
+ {
+ case DATA_KURINNAXX: return uiKurinaxx;
+ case DATA_RAJAXX: return uiRajaxx;
+ case DATA_MOAM: return uiMoam;
+ case DATA_BURU: return uiBuru;
+ case DATA_AYAMISS: return uiAyamiss;
+ case DATA_OSSIRIAN: return uiOssirian;
+ }
+
+ return 0;
+ }
+
+ std::string GetSaveData()
+ {
+ OUT_SAVE_INST_DATA;
+
+ std::ostringstream saveStream;
+ saveStream << "R A " << m_auiEncounter[0] << " " << m_auiEncounter[1] << " "
+ << m_auiEncounter[2] << " " << m_auiEncounter[3] << " " << m_auiEncounter[4] << " " << m_auiEncounter[5];
+
+ str_data = saveStream.str();
+
+ OUT_SAVE_INST_DATA_COMPLETE;
+ return str_data;
+ }
+
+ void Load(const char* in)
+ {
+ if (!in)
+ {
+ OUT_LOAD_INST_DATA_FAIL;
+ return;
+ }
+
+ OUT_LOAD_INST_DATA(in);
+
+ char dataHead1, dataHead2;
+ uint16 data0, data1, data2, data3, data4, data5;
+
+ std::istringstream loadStream(in);
+ loadStream >> dataHead1 >> dataHead2 >> data0 >> data1 >> data2 >> data3 >> data4 >> data5;
+
+ if (dataHead1 == 'R' && dataHead2 == 'A')
+ {
+ m_auiEncounter[0] = data0;
+ m_auiEncounter[1] = data1;
+ m_auiEncounter[2] = data2;
+ m_auiEncounter[3] = data3;
+ m_auiEncounter[4] = data4;
+ m_auiEncounter[5] = data5;
+
+ for (uint8 i = 0; i < MAX_ENCOUNTER; ++i)
+ if (m_auiEncounter[i] == IN_PROGRESS)
+ m_auiEncounter[i] = NOT_STARTED;
+
+ } else OUT_LOAD_INST_DATA_FAIL;
+ }
+};
+
+InstanceData* GetInstanceData_instance_ruins_of_ahn_qiraj(Map* pMap)
+{
+ return new instance_ruins_of_ahn_qiraj(pMap);
+}
+
+void AddSC_instance_ruins_of_ahnqiraj()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_ruins_of_ahnqiraj";
+ newscript->GetInstanceData = &GetInstanceData_instance_ruins_of_ahn_qiraj;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/ruins_of_ahnqiraj.h b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/ruins_of_ahnqiraj.h
new file mode 100644
index 00000000000..33fd75d557a
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ruins_of_ahnqiraj/ruins_of_ahnqiraj.h
@@ -0,0 +1,34 @@
+#ifndef DEF_RUINS_OF_AHNQIRAJ_H
+#define DEF_RUINS_OF_AHNQIRAJ_H
+
+enum Data
+{
+ DATA_KURINNAXX_EVENT,
+ DATA_RAJAXX_EVENT,
+ DATA_MOAM_EVENT,
+ DATA_BURU_EVENT,
+ DATA_AYAMISS_EVENT,
+ DATA_OSSIRIAN_EVENT
+};
+
+enum Data64
+{
+ DATA_KURINNAXX,
+ DATA_RAJAXX,
+ DATA_MOAM,
+ DATA_BURU,
+ DATA_AYAMISS,
+ DATA_OSSIRIAN
+};
+
+enum Bosses
+{
+ CREATURE_KURINAXX = 15348,
+ CREATURE_RAJAXX = 15341,
+ CREATURE_MOAM = 15340,
+ CREATURE_BURU = 15370,
+ CREATURE_AYAMISS = 15369,
+ CREATURE_OSSIRIAN = 15339
+};
+
+#endif
diff --git a/src/server/scripts/Kalimdor/silithus.cpp b/src/server/scripts/Kalimdor/silithus.cpp
new file mode 100644
index 00000000000..6383284011f
--- /dev/null
+++ b/src/server/scripts/Kalimdor/silithus.cpp
@@ -0,0 +1,1140 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Silithus
+SD%Complete: 100
+SDComment: Quest support: 7785, 8304, 8507.
+SDCategory: Silithus
+EndScriptData */
+
+/* ContentData
+npc_highlord_demitrian
+npcs_rutgar_and_frankal
+quest_a_pawn_on_the_eternal_pawn
+EndContentData */
+
+#include "ScriptedPch.h"
+
+/*###
+## npc_highlord_demitrian
+###*/
+
+#define GOSSIP_DEMITRIAN1 "What do you know of it?"
+#define GOSSIP_DEMITRIAN2 "I am listening , Demitrian."
+#define GOSSIP_DEMITRIAN3 "Continue, please."
+#define GOSSIP_DEMITRIAN4 "A battle?"
+#define GOSSIP_DEMITRIAN5 "<Nod>"
+#define GOSSIP_DEMITRIAN6 "Caught unaware? How?"
+#define GOSSIP_DEMITRIAN7 "So what did Ragnaros do next?"
+
+bool GossipHello_npc_highlord_demitrian(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(7785) == QUEST_STATUS_NONE &&
+ (pPlayer->HasItemCount(18563,1,false) || pPlayer->HasItemCount(18564,1,false)))
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_DEMITRIAN1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+
+ pPlayer->SEND_GOSSIP_MENU(6812, pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_highlord_demitrian(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch (uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_DEMITRIAN2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(6842, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_DEMITRIAN3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+ pPlayer->SEND_GOSSIP_MENU(6843, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_DEMITRIAN4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+3);
+ pPlayer->SEND_GOSSIP_MENU(6844, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+3:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_DEMITRIAN5, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+4);
+ pPlayer->SEND_GOSSIP_MENU(6867, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+4:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_DEMITRIAN6, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+5);
+ pPlayer->SEND_GOSSIP_MENU(6868, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+5:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_DEMITRIAN7, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+6);
+ pPlayer->SEND_GOSSIP_MENU(6869, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+6:
+ pPlayer->SEND_GOSSIP_MENU(6870, pCreature->GetGUID());
+
+ ItemPosCountVec dest;
+ uint8 msg = pPlayer->CanStoreNewItem(NULL_BAG, NULL_SLOT, dest, 19016, 1);
+ if (msg == EQUIP_ERR_OK)
+ pPlayer->StoreNewItem(dest, 19016, true);
+ break;
+ }
+ return true;
+}
+
+/*###
+## npcs_rutgar_and_frankal
+###*/
+
+//gossip item text best guess
+#define GOSSIP_ITEM1 "I seek information about Natalia"
+
+#define GOSSIP_ITEM2 "That sounds dangerous!"
+#define GOSSIP_ITEM3 "What did you do?"
+#define GOSSIP_ITEM4 "Who?"
+#define GOSSIP_ITEM5 "Women do that. What did she demand?"
+#define GOSSIP_ITEM6 "What do you mean?"
+#define GOSSIP_ITEM7 "What happened next?"
+
+#define GOSSIP_ITEM11 "Yes, please continue"
+#define GOSSIP_ITEM12 "What language?"
+#define GOSSIP_ITEM13 "The Priestess attacked you?!"
+#define GOSSIP_ITEM14 "I should ask the monkey about this"
+#define GOSSIP_ITEM15 "Then what..."
+
+//trigger creatures to kill
+#define TRIGGER_RUTGAR 15222
+#define TRIGGER_FRANKAL 15221
+
+bool GossipHello_npcs_rutgar_and_frankal(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(8304) == QUEST_STATUS_INCOMPLETE &&
+ pCreature->GetEntry() == 15170 &&
+ !pPlayer->GetReqKillOrCastCurrentCount(8304, TRIGGER_RUTGAR))
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+
+ if (pPlayer->GetQuestStatus(8304) == QUEST_STATUS_INCOMPLETE &&
+ pCreature->GetEntry() == 15171 &&
+ pPlayer->GetReqKillOrCastCurrentCount(8304, TRIGGER_RUTGAR))
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+9);
+
+ pPlayer->SEND_GOSSIP_MENU(7754, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npcs_rutgar_and_frankal(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch (uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+ pPlayer->SEND_GOSSIP_MENU(7755, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 1:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
+ pPlayer->SEND_GOSSIP_MENU(7756, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 3);
+ pPlayer->SEND_GOSSIP_MENU(7757, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 3:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM5, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 4);
+ pPlayer->SEND_GOSSIP_MENU(7758, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 4:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM6, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 5);
+ pPlayer->SEND_GOSSIP_MENU(7759, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 5:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM7, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 6);
+ pPlayer->SEND_GOSSIP_MENU(7760, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 6:
+ pPlayer->SEND_GOSSIP_MENU(7761, pCreature->GetGUID());
+ //'kill' our trigger to update quest status
+ pPlayer->KilledMonsterCredit(TRIGGER_RUTGAR, pCreature->GetGUID());
+ break;
+
+ case GOSSIP_ACTION_INFO_DEF + 9:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM11, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 11);
+ pPlayer->SEND_GOSSIP_MENU(7762, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 10:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM12, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 11);
+ pPlayer->SEND_GOSSIP_MENU(7763, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 11:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM13, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 12);
+ pPlayer->SEND_GOSSIP_MENU(7764, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 12:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM14, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 13);
+ pPlayer->SEND_GOSSIP_MENU(7765, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 13:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM15, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 14);
+ pPlayer->SEND_GOSSIP_MENU(7766, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF + 14:
+ pPlayer->SEND_GOSSIP_MENU(7767, pCreature->GetGUID());
+ //'kill' our trigger to update quest status
+ pPlayer->KilledMonsterCredit(TRIGGER_FRANKAL, pCreature->GetGUID());
+ break;
+ }
+ return true;
+}
+
+/*####
+# quest_a_pawn_on_the_eternal_board (Defines)
+####*/
+enum eEternalBoard
+{
+ QUEST_A_PAWN_ON_THE_ETERNAL_BOARD = 8519,
+
+ FACTION_HOSTILE = 14,
+ FACTION_FRIENDLY = 35,
+
+ C_ANACHRONOS = 15381,
+ C_FANDRAL_STAGHELM = 15382,
+ C_ARYGOS = 15380,
+ C_MERITHRA = 15378,
+ C_CAELESTRASZ = 15379,
+
+ ANACHRONOS_SAY_1 = -1350000,
+ ANACHRONOS_SAY_2 = -1350001,
+ ANACHRONOS_SAY_3 = -1350002,
+ ANACHRONOS_SAY_4 = -1350003,
+ ANACHRONOS_SAY_5 = -1350004,
+ ANACHRONOS_SAY_6 = -1350005,
+ ANACHRONOS_SAY_7 = -1350006,
+ ANACHRONOS_SAY_8 = -1350007,
+ ANACHRONOS_SAY_9 = -1350008,
+ ANACHRONOS_SAY_10 = -1350009,
+ ANACHRONOS_EMOTE_1 = -1350010,
+ ANACHRONOS_EMOTE_2 = -1350011,
+ ANACHRONOS_EMOTE_3 = -1350012,
+
+ FANDRAL_SAY_1 = -1350013,
+ FANDRAL_SAY_2 = -1350014,
+ FANDRAL_SAY_3 = -1350015,
+ FANDRAL_SAY_4 = -1350016,
+ FANDRAL_SAY_5 = -1350017,
+ FANDRAL_SAY_6 = -1350018,
+ FANDRAL_EMOTE_1 = -1350019,
+ FANDRAL_EMOTE_2 = -1350020,
+
+ CAELESTRASZ_SAY_1 = -1350021,
+ CAELESTRASZ_SAY_2 = -1350022,
+ CAELESTRASZ_YELL_1 = -1350023,
+
+ ARYGOS_SAY_1 = -1350024,
+ ARYGOS_YELL_1 = -1350025,
+ ARYGOS_EMOTE_1 = -1350026,
+
+ MERITHRA_SAY_1 = -1350027,
+ MERITHRA_SAY_2 = -1350028,
+ MERITHRA_YELL_1 = -1350029,
+ MERITHRA_EMOTE_1 = -1350030,
+
+ GO_GATE_OF_AHN_QIRAJ = 176146,
+ GO_GLYPH_OF_AHN_QIRAJ = 176148,
+ GO_ROOTS_OF_AHN_QIRAJ = 176147
+};
+/*#####
+# Quest: A Pawn on the Eternal Board
+#####*/
+
+/* ContentData
+A Pawn on the Eternal Board - creatures, gameobjects and defines
+mob_qiraj_war_spawn : Adds that are summoned in the Qiraj gates battle.
+npc_anachronos_the_ancient : Creature that controls the event.
+npc_anachronos_quest_trigger: controls the spawning of the BG War mobs.
+go_crystalline_tear : GameObject that begins the event and hands out quest
+TO DO: get correct spell IDs and timings for spells cast upon dragon transformations
+TO DO: Dragons should use the HandleEmoteCommand(EMOTE_ONESHOT_LIFTOFF) after transformation,but for some unknown reason it doesnt work.
+EndContentData */
+
+#define QUEST_A_PAWN_ON_THE_ETERNAL_BOARD 8519
+#define EVENT_AREA_RADIUS 65 //65yds
+#define EVENT_COOLDOWN 500000 //in ms. appear after event completed or failed (should be = Adds despawn time)
+
+struct QuestCinematic
+{
+ int32 TextId;
+ uint32 Creature, Timer;
+};
+
+// Creature 0 - Anachronos, 1 - Fandral, 2 - Arygos, 3 - Merithra, 4 - Caelestrasz
+static QuestCinematic EventAnim[]=
+{
+ {ANACHRONOS_SAY_1, 0, 2000},
+ {FANDRAL_SAY_1, 1, 4000},
+ {MERITHRA_EMOTE_1, 3, 500},
+ {MERITHRA_SAY_1, 3, 500},
+ {ARYGOS_EMOTE_1, 2, 2000},
+ {CAELESTRASZ_SAY_1, 4, 8000},
+ {MERITHRA_SAY_2, 3, 6000},
+ {NULL,3,2000},
+ {MERITHRA_YELL_1, 3, 2500},
+ {NULL, 3, 3000},//Morph
+ {NULL,3,4000},//EmoteLiftoff
+ {NULL, 3, 4000},// spell
+ {NULL, 3, 1250},//fly
+ {NULL, 3, 250},//remove flags
+ {ARYGOS_SAY_1, 2, 3000},
+ {NULL,3,2000},
+ {ARYGOS_YELL_1, 2, 3000},
+ {NULL, 3, 3000},//Morph
+ {NULL,3,4000},//EmoteLiftoff
+ {NULL, 3, 4000},// spell
+ {NULL, 3, 1000},//fly
+ {NULL, 3, 1000},//remove flags
+ {CAELESTRASZ_SAY_2, 4, 5000},
+ {NULL,3,3000},
+ {CAELESTRASZ_YELL_1, 4, 3000},
+ {NULL, 3, 3000},//Morph
+ {NULL,3,4000},//EmoteLiftoff
+ {NULL, 3, 2500},// spell
+ {ANACHRONOS_SAY_2, 0, 2000},
+ {NULL, 3, 250},//fly
+ {NULL, 3, 25},//remove flags
+ {FANDRAL_SAY_2, 1, 3000},
+ {ANACHRONOS_SAY_3, 0, 10000},//Both run through the armies
+ {NULL,3,2000},// Sands will stop
+ {NULL,3,8000},// Summon Gate
+ {ANACHRONOS_SAY_4, 0, 4000},
+ {NULL, 0, 2000},//spell 1-> Arcane cosmetic (Mobs freeze)
+ {NULL, 0, 5000}, //Spell 2-> Arcane long cosmetic (barrier appears) (Barrier -> Glyphs)
+ {NULL, 0, 7000},//BarrieR
+ {NULL, 0, 4000},//Glyphs
+ {ANACHRONOS_SAY_5, 0, 2000},
+ {NULL, 0, 4000},// Roots
+ {FANDRAL_SAY_3, 1, 3000},//Root Text
+ {FANDRAL_EMOTE_1, 1, 3000},//falls knee
+ {ANACHRONOS_SAY_6, 0, 3000},
+ {ANACHRONOS_SAY_7, 0, 3000},
+ {ANACHRONOS_SAY_8, 0, 8000},
+ {ANACHRONOS_EMOTE_1, 0, 1000},//Give Scepter
+ {FANDRAL_SAY_4, 1, 3000},
+ {FANDRAL_SAY_5, 1, 3000},//->Equip hammer~Scepter, throw it at door
+ {FANDRAL_EMOTE_2, 1, 3000},//Throw hammer at door.
+ {ANACHRONOS_SAY_9, 0, 3000},
+ {FANDRAL_SAY_6, 1, 3000}, //fandral goes away
+ {ANACHRONOS_EMOTE_2, 0, 3000},
+ {ANACHRONOS_EMOTE_3, 0, 3000},
+ {NULL, 0, 2000},
+ {NULL, 0, 2000},
+ {NULL, 0, 4000},
+ {ANACHRONOS_SAY_10, 0, 3000},
+ {NULL, 0, 2000},
+ {NULL, 0, 3000},
+ {NULL, 0, 15000},
+ {NULL, 0, 5000},
+ {NULL, 0, 3500},
+ {NULL, 0, 5000},
+ {NULL, 0, 3500},
+ {NULL, 0, 5000},
+ {NULL, 0, NULL}
+};
+
+struct Location
+{
+ float x, y, z, o;
+};
+
+//Cordinates for Spawns
+static Location SpawnLocation[]=
+{
+ {-8085, 1528, 2.61, 3.141592},//Kaldorei Infantry
+ {-8080, 1526, 2.61, 3.141592},//Kaldorei Infantry
+ {-8085, 1524, 2.61, 3.141592},//Kaldorei Infantry
+ {-8080, 1522, 2.61, 3.141592},//Kaldorei Infantry
+ {-8085, 1520, 2.61, 3.141592},//Kaldorei Infantry
+
+ {-8085, 1524, 2.61, 3.141592},//Kaldorei Infantry
+ {-8080, 1522, 2.61, 3.141592},//Kaldorei Infantry
+ {-8085, 1520, 2.61, 3.141592},//Kaldorei Infantry
+ {-8080, 1518, 2.61, 3.141592},//Kaldorei Infantry
+ {-8085, 1516, 2.61, 3.141592},//Kaldorei Infantry
+
+ {-8085, 1518, 2.61, 3.141592},//Kaldorei Infantry
+ {-8080, 1516, 2.61, 3.141592},//Kaldorei Infantry
+ {-8080, 1520, 2.61, 3.141592},//Kaldorei Infantry
+ {-8080, 1424, 2.61, 3.141592},//Kaldorei Infantry
+ {-8085, 1422, 2.61, 3.141592},//Kaldorei Infantry
+ // 2 waves of warriors
+ {-8082, 1528, 2.61, 3.141592},//Kaldorei Infantry
+ {-8078, 1525, 2.61, 3.141592},//Kaldorei Infantry
+ {-8082, 1524, 2.61, 3.141592},//Kaldorei Infantry
+ {-8078, 1526, 2.61, 3.141592},//Kaldorei Infantry
+ {-8082, 1527, 2.61, 3.141592},//Kaldorei Infantry
+
+ {-8082, 1524, 2.61, 3.141592},//Kaldorei Infantry
+ {-8078, 1522, 2.61, 3.141592},//Kaldorei Infantry
+ {-8082, 1520, 2.61, 3.141592},//Kaldorei Infantry
+ {-8078, 1518, 2.61, 3.141592},//Kaldorei Infantry
+ {-8082, 1516, 2.61, 3.141592},//Kaldorei Infantry
+
+ {-8082, 1523, 2.61, 3.141592},//Kaldorei Infantry
+ {-8078, 1521, 2.61, 3.141592},//Kaldorei Infantry
+ {-8082, 1528, 2.61, 3.141592},//Kaldorei Infantry
+ {-8078, 1519, 2.61, 3.141592},//Kaldorei Infantry
+ {-8082, 1526, 2.61, 3.141592},//Kaldorei Infantry
+
+ {-8082, 1524, 2.61, 3.141592},//Kaldorei Infantry
+ {-8078, 1522, 2.61, 3.141592},//Kaldorei Infantry
+ {-8082, 1520, 2.61, 3.141592},//Kaldorei Infantry
+ {-8078, 1518, 2.61, 3.141592},//Kaldorei Infantry
+ {-8082, 1516, 2.61, 3.141592},//Kaldorei Infantry
+
+ {-8088, 1510, 2.61, 0},//Anubisath Conqueror
+ {-8084, 1520, 2.61, 0},//Anubisath Conqueror
+ {-8088, 1530, 2.61, 0},//Anubisath Conqueror
+
+ {-8080, 1513, 2.61, 0},//Qiraj Wasp
+ {-8082, 1523, 2.61, 0},//Qiraj Wasp
+ {-8085, 1518, 2.61, 0},//Qiraj Wasp
+ {-8082, 1516, 2.61, 0},//Qiraj Wasp
+ {-8085, 1520, 2.61, 0},//Qiraj Wasp
+ {-8080, 1528, 2.61, 0},//Qiraj Wasp
+
+ {-8082, 1513, 2.61, 0},//Qiraj Wasp
+ {-8079, 1523, 2.61, 0},//Qiraj Wasp
+ {-8080, 1531, 2.61, 0},//Qiraj Wasp
+ {-8079, 1516, 2.61, 0},//Qiraj Wasp
+ {-8082, 1520, 2.61, 0},//Qiraj Wasp
+ {-8080, 1518, 2.61, 0},//Qiraj Wasp
+
+ {-8081, 1514, 2.61, 0},//Qiraj Tank
+ {-8081, 1520, 2.61, 0},//Qiraj Tank
+ {-8081, 1526, 2.61, 0},//Qiraj Tank
+ {-8081, 1512, 2.61, 0},//Qiraj Tank
+ {-8082, 1520, 2.61, 0},//Qiraj Tank
+ {-8081, 1528, 2.61, 0},//Qiraj Tank
+
+ {-8082, 1513, 2.61, 3.141592},//Anubisath Conqueror
+ {-8082, 1520, 2.61, 3.141592},//Anubisath Conqueror
+ {-8082, 1527, 2.61, 3.141592},//Anubisath Conqueror
+};
+
+struct WaveData
+{
+ uint8 SpawnCount, UsedSpawnPoint;
+ uint32 CreatureId, SpawnTimer, YellTimer, DespTimer;
+ int32 WaveTextId;
+};
+
+static WaveData WavesInfo[] =
+{
+ {30, 0, 15423, 0, 0,24000, NULL}, //Kaldorei Soldier
+ {3, 35, 15424, 0, 0,24000, NULL}, //Anubisath Conqueror
+ {12, 38, 15414, 0, 0,24000, NULL}, //Qiraji Wasps
+ {6, 50, 15422, 0, 0,24000, NULL}, //Qiraji Tanks
+ {15, 15, 15423, 0, 0,24000, NULL} //Kaldorei Soldier
+
+};
+
+struct SpawnSpells
+{
+ uint32 Timer1, Timer2, SpellId;
+};
+
+static SpawnSpells SpawnCast[]=//
+{
+ {100000, 2000, 33652}, // Stop Time
+ {38500, 300000, 28528}, // Poison Cloud
+ {58000, 300000, 35871}, // Frost Debuff (need correct spell)
+ {80950, 300000, 42075}, // Fire Explosion (need correct spell however this one looks cool)
+};
+/*#####
+# npc_anachronos_the_ancient
+######*/
+struct npc_anachronos_the_ancientAI : public ScriptedAI
+{
+ npc_anachronos_the_ancientAI(Creature* c) : ScriptedAI(c) {}
+
+ uint32 AnimationTimer;
+ uint8 AnimationCount;
+
+ uint64 AnachronosQuestTriggerGUID;
+ uint64 MerithraGUID;
+ uint64 ArygosGUID;
+ uint64 CaelestraszGUID;
+ uint64 FandralGUID;
+ uint64 PlayerGUID;
+ bool eventEnd;
+
+ void Reset()
+ {
+ AnimationTimer = 1500;
+ AnimationCount = 0;
+ AnachronosQuestTriggerGUID = 0;
+ MerithraGUID = 0;
+ ArygosGUID = 0;
+ CaelestraszGUID = 0;
+ FandralGUID = 0;
+ PlayerGUID = 0;
+ eventEnd = false;
+
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ }
+
+ void HandleAnimation()
+ {
+ Player* plr = Unit::GetPlayer(PlayerGUID);
+ if (!plr)
+ return;
+
+ Unit* Fandral = plr->FindNearestCreature(C_FANDRAL_STAGHELM, 100, me);
+ Unit* Arygos = plr->FindNearestCreature(C_ARYGOS, 100,me);
+ Unit* Caelestrasz = plr->FindNearestCreature(C_CAELESTRASZ, 100, me);
+ Unit* Merithra = plr->FindNearestCreature(C_MERITHRA, 100,me);
+
+ if (!Fandral || !Arygos || !Caelestrasz || !Merithra)
+ return;
+
+ Unit* mob;
+ AnimationTimer = EventAnim[AnimationCount].Timer;
+ if (eventEnd == false)
+ {
+ switch(AnimationCount)
+ {
+ case 0:
+ DoScriptText(ANACHRONOS_SAY_1, me , Fandral);
+ break;
+ case 1:
+ Fandral->SetUInt64Value(UNIT_FIELD_TARGET, me->GetGUID());
+ DoScriptText(FANDRAL_SAY_1, Fandral,me);
+ break;
+ case 2:
+ Fandral->SetUInt64Value(UNIT_FIELD_TARGET,NULL);
+ DoScriptText(MERITHRA_EMOTE_1,Merithra);
+ break;
+ case 3:
+ DoScriptText(MERITHRA_SAY_1,Merithra);
+ break;
+ case 4:
+ DoScriptText(ARYGOS_EMOTE_1,Arygos);
+ break;
+ case 5:
+ Caelestrasz->SetUInt64Value(UNIT_FIELD_TARGET, Fandral->GetGUID());
+ DoScriptText(CAELESTRASZ_SAY_1, Caelestrasz);
+ break;
+ case 6:
+ DoScriptText(MERITHRA_SAY_2, Merithra);
+ break;
+ case 7:
+ Caelestrasz->SetUInt64Value(UNIT_FIELD_TARGET, NULL);
+ Merithra->GetMotionMaster()->MoveCharge(-8065,1530,2.61,10);
+ break;
+ case 8:
+ DoScriptText(MERITHRA_YELL_1,Merithra);
+ break;
+ case 9:
+ Merithra->CastSpell(Merithra,25105,true);
+ break;
+ case 10:
+ Merithra->HandleEmoteCommand(EMOTE_ONESHOT_LIFTOFF);
+ Merithra->AddUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
+ Merithra->GetMotionMaster()->MoveCharge(-8065,1530,6.61,3);
+ break;
+ case 11:
+ Merithra->CastSpell(Merithra,24818,false);
+ break;
+ case 12:
+ Merithra->GetMotionMaster()->MoveCharge(-8100,1530,50,42);
+ break;
+ case 13:
+ break;
+ case 14:
+ DoScriptText(ARYGOS_SAY_1,Arygos);
+ Merithra->SetVisibility(VISIBILITY_OFF);
+ break;
+ case 15:
+ Arygos->GetMotionMaster()->MoveCharge(-8065,1530,2.61,10);
+ Merithra->GetMotionMaster()->MoveCharge(-8034.535,1535.14,2.61,42);
+ break;
+ case 16:
+ DoScriptText(ARYGOS_YELL_1, Arygos);
+ break;
+ case 17:
+ Arygos->CastSpell(Arygos,25107,true);
+ break;
+ case 18:
+ Arygos->HandleEmoteCommand(EMOTE_ONESHOT_LIFTOFF);
+ Arygos->AddUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
+ Arygos->GetMotionMaster()->MoveCharge(-8065,1530,6.61,42);
+ break;
+ case 19:
+ Arygos->CastSpell(Arygos,50505,false);
+ break;
+ case 20:
+ Arygos->GetMotionMaster()->MoveCharge(-8095,1530,50,42);
+ break;
+ case 21:
+ break;
+ case 22:
+ DoScriptText(CAELESTRASZ_SAY_2,Caelestrasz, Fandral);
+ break;
+ case 23:
+ Caelestrasz->GetMotionMaster()->MoveCharge(-8065,1530,2.61,10);
+ Arygos->SetVisibility(VISIBILITY_OFF);
+ Arygos->GetMotionMaster()->MoveCharge(-8034.535,1535.14,2.61,10);
+ break;
+ case 24:
+ DoScriptText(CAELESTRASZ_YELL_1, Caelestrasz);
+ break;
+ case 25:
+ Caelestrasz->CastSpell(Caelestrasz,25106,true);
+ break;
+ case 26:
+ Caelestrasz->HandleEmoteCommand(254);
+ Caelestrasz->AddUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
+ Caelestrasz->GetMotionMaster()->MoveCharge(-8065,1530,7.61,4);
+ break;
+ case 27:
+ Caelestrasz->CastSpell(Caelestrasz,54293,false);
+ break;
+ case 28:
+ DoScriptText(ANACHRONOS_SAY_2,me, Fandral);
+ break;
+ case 29:
+ Caelestrasz->GetMotionMaster()->MoveCharge(-8095,1530,50,42);
+ DoScriptText(FANDRAL_SAY_2, Fandral, me);
+ break;
+ case 30:
+ break;
+ case 31:
+ DoScriptText(ANACHRONOS_SAY_3, me, Fandral);
+ break;
+ case 32:
+ Caelestrasz->SetVisibility(VISIBILITY_OFF);
+ Caelestrasz->GetMotionMaster()->MoveCharge(-8034.535,1535.14,2.61,42);
+ Fandral->GetMotionMaster()->MoveCharge(-8108,1529,2.77,8);
+ me->GetMotionMaster()->MoveCharge(-8113,1525,2.77,8);
+ break;//both run to the gate
+ case 33:
+ DoScriptText(ANACHRONOS_SAY_4, me);
+ Caelestrasz->GetMotionMaster()->MoveCharge(-8050,1473,65,15);
+ break; //Text: sands will stop
+ case 34:
+ DoCast(plr, 23017, true);//Arcane Channeling
+ break;
+ case 35:
+ me->CastSpell(-8088,1520.43,2.67,25158,true);
+ break;
+ case 36:
+ DoCast(plr, 25159, true);
+ break;
+ case 37:
+ me->SummonGameObject(GO_GATE_OF_AHN_QIRAJ,-8130,1525,17.5,0,0,0,0,0,0);
+ break;
+ case 38:
+ DoCast(plr, 25166, true);
+ me->SummonGameObject(GO_GLYPH_OF_AHN_QIRAJ,-8130,1525,17.5,0,0,0,0,0,0);
+ break;
+ case 39:
+ DoScriptText(ANACHRONOS_SAY_5, me, Fandral);
+ break;
+ case 40:
+ Fandral->CastSpell(me, 25167, true);
+ break;
+ case 41:
+ Fandral->SummonGameObject(GO_ROOTS_OF_AHN_QIRAJ,-8130,1525,17.5,0,0,0,0,0,0);
+ DoScriptText(FANDRAL_SAY_3, Fandral);
+ break;
+ case 42:
+ me->CastStop();
+ DoScriptText(FANDRAL_EMOTE_1, Fandral);
+ break;
+ case 43:
+ Fandral->CastStop();
+ break;
+ case 44:
+ DoScriptText(ANACHRONOS_SAY_6, me);
+ break;
+ case 45:
+ DoScriptText(ANACHRONOS_SAY_7, me);
+ break;
+ case 46:
+ DoScriptText(ANACHRONOS_SAY_8, me);
+ me->GetMotionMaster()->MoveCharge(-8110,1527,2.77,4);
+ break;
+ case 47:
+ DoScriptText(ANACHRONOS_EMOTE_1, me);
+ break;
+ case 48:
+ DoScriptText(FANDRAL_SAY_4,Fandral,me);
+ break;
+ case 49:
+ DoScriptText(FANDRAL_SAY_5,Fandral,me);
+ break;
+ case 50:
+ DoScriptText(FANDRAL_EMOTE_2,Fandral);
+ Fandral->CastSpell(-8127,1525,17.5,33806,true);
+ break;
+ case 51:
+ {
+ uint32 entries[4] = { 15423, 15424, 15414, 15422 };
+ for (uint8 i = 0; i < 4; ++i)
+ {
+ mob = plr->FindNearestCreature(entries[i],50,me);
+ while (mob)
+ {
+ mob->RemoveFromWorld();
+ mob = plr->FindNearestCreature(15423,50,me);
+ }
+ }
+ break;
+ }
+ case 52:
+ Fandral->GetMotionMaster()->MoveCharge(-8028.75, 1538.795, 2.61,4);
+ DoScriptText(ANACHRONOS_SAY_9, me,Fandral);
+ break;
+ case 53:
+ DoScriptText(FANDRAL_SAY_6,Fandral);
+ break;
+ case 54:
+ DoScriptText(ANACHRONOS_EMOTE_2,me);
+ break;
+ case 55:
+ Fandral->SetVisibility(VISIBILITY_OFF);
+ break;
+ case 56:
+ DoScriptText(ANACHRONOS_EMOTE_3, me);
+ me->GetMotionMaster()->MoveCharge(-8116,1522,3.65,4);
+ break;
+ case 57:
+ me->GetMotionMaster()->MoveCharge(-8116.7,1527,3.7,4);
+ break;
+ case 58:
+ me->GetMotionMaster()->MoveCharge(-8112.67,1529.9,2.86,4);
+ break;
+ case 59:
+ me->GetMotionMaster()->MoveCharge(-8117.99,1532.24,3.94,4);
+ break;
+ case 60:
+ if (plr)
+ DoScriptText(ANACHRONOS_SAY_10, me,plr);
+ me->GetMotionMaster()->MoveCharge(-8113.46,1524.16,2.89,4);
+ break;
+ case 61:
+ me->GetMotionMaster()->MoveCharge(-8057.1,1470.32,2.61,6);
+ if (plr->IsInRange(me,0,15))
+ plr->GroupEventHappens(QUEST_A_PAWN_ON_THE_ETERNAL_BOARD ,me);
+ break;
+ case 62:
+ me->SetDisplayId(15500);
+ break;
+ case 63:
+ me->HandleEmoteCommand(254);
+ me->AddUnitMovementFlag(MOVEMENTFLAG_LEVITATING);
+ break;
+ case 64:
+ me->GetMotionMaster()->MoveCharge(-8000,1400,150,9);
+ break;
+ case 65:
+ me->SetVisibility(VISIBILITY_OFF);
+ if (Creature* AnachronosQuestTrigger = (Unit::GetCreature(*me, AnachronosQuestTriggerGUID)))
+ {
+ DoScriptText(ARYGOS_YELL_1,me);
+ AnachronosQuestTrigger->AI()->EnterEvadeMode();
+ eventEnd=true;
+ }
+ break;
+ }
+ }
+ ++AnimationCount;
+ }
+ void UpdateAI(const uint32 diff)
+ {
+ if (AnimationTimer)
+ {
+ if (AnimationTimer <= diff)
+ HandleAnimation();
+ else AnimationTimer -= diff;
+ }
+ if (AnimationCount < 65)
+ me->CombatStop();
+ if (AnimationCount == 65 || eventEnd)
+ me->AI()->EnterEvadeMode();
+ }
+};
+
+/*######
+# mob_qiraj_war_spawn
+######*/
+
+struct mob_qiraj_war_spawnAI : public ScriptedAI
+{
+ mob_qiraj_war_spawnAI(Creature* c) : ScriptedAI(c) {}
+
+ uint64 MobGUID;
+ uint64 PlayerGUID;
+ uint32 SpellTimer1, SpellTimer2, SpellTimer3,SpellTimer4;
+ bool Timers;
+ bool hasTarget;
+
+ void Reset()
+ {
+ MobGUID = 0;
+ PlayerGUID = 0;
+ Timers = false;
+ hasTarget = false;
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+ void JustDied(Unit* slayer);
+
+ void UpdateAI(const uint32 diff)
+ {
+ Unit *pTarget = NULL;
+ //Player* plr = me->GetPlayer(PlayerGUID);
+
+ if (!Timers)
+ {
+ if (me->GetEntry() == 15424 || me->GetEntry() == 15422 || me->GetEntry() == 15414) //all but Kaldorei Soldiers
+ {
+ SpellTimer1 = SpawnCast[1].Timer1;
+ SpellTimer2 = SpawnCast[2].Timer1;
+ SpellTimer3 = SpawnCast[3].Timer1;
+ }
+ if (me->GetEntry() == 15423 || me->GetEntry() == 15424 || me->GetEntry() == 15422 || me->GetEntry() == 15414)
+ SpellTimer4 = SpawnCast[0].Timer1;
+ Timers = true;
+ }
+ if (me->GetEntry() == 15424 || me->GetEntry() == 15422|| me->GetEntry() == 15414)
+ {
+ if (SpellTimer1 <= diff)
+ {
+ DoCast(me, SpawnCast[1].SpellId);
+ DoCast(me, 24319);
+ SpellTimer1 = SpawnCast[1].Timer2;
+ } else SpellTimer1 -= diff;
+ if (SpellTimer2 <= diff)
+ {
+ DoCast(me, SpawnCast[2].SpellId);
+ SpellTimer2 = SpawnCast[2].Timer2;
+ } else SpellTimer2 -= diff;
+ if (SpellTimer3 <= diff)
+ {
+ DoCast(me, SpawnCast[3].SpellId);
+ SpellTimer3 = SpawnCast[3].Timer2;
+ } else SpellTimer3 -= diff;
+ }
+ if (me->GetEntry() == 15423 || me->GetEntry() == 15424 || me->GetEntry() == 15422 || me->GetEntry() == 15414)
+ {
+ if (SpellTimer4 <= diff)
+ {
+ me->RemoveAllAttackers();
+ me->AttackStop();
+ DoCast(me, 15533);
+ SpellTimer4 = SpawnCast[0].Timer2;
+ } else SpellTimer4 -= diff;
+ }
+ if (!hasTarget)
+ {
+ if (me->GetEntry() == 15424 || me->GetEntry() == 15422 || me->GetEntry() == 15414)
+ pTarget = me->FindNearestCreature(15423,20,true);
+ if (me->GetEntry() == 15423)
+ {
+ uint8 tar = urand(0,2);
+
+ if (tar == 0)
+ pTarget = me->FindNearestCreature(15422,20,true);
+ else if (tar == 1)
+ pTarget = me->FindNearestCreature(15424,20,true);
+ else if (tar == 2)
+ pTarget = me->FindNearestCreature(15414,20,true);
+ }
+ hasTarget = true;
+ if (pTarget)
+ me->AI()->AttackStart(pTarget);
+ }
+ if (!(me->FindNearestCreature(15379,60)))
+ DoCast(me, 33652);
+
+ if (!UpdateVictim())
+ {
+ hasTarget = false;
+ return;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+/*#####
+# npc_anachronos_quest_trigger
+#####*/
+
+struct npc_anachronos_quest_triggerAI : public ScriptedAI
+{
+ npc_anachronos_quest_triggerAI(Creature* c) : ScriptedAI(c) {}
+
+ uint64 PlayerGUID;
+
+ uint32 WaveTimer;
+ uint32 AnnounceTimer;
+
+ int8 LiveCount;
+ uint8 WaveCount;
+
+ bool EventStarted;
+ bool Announced;
+ bool Failed;
+
+ void Reset()
+ {
+ PlayerGUID = 0;
+
+ WaveTimer = 2000;
+ AnnounceTimer = 1000;
+ LiveCount = 0;
+ WaveCount = 0;
+
+ EventStarted = false;
+ Announced = false;
+ Failed = false;
+
+ me->SetVisibility(VISIBILITY_OFF);
+ }
+
+ void SummonNextWave()
+ {
+ //uint8 count = WavesInfo[WaveCount].SpawnCount;
+ uint8 locIndex = WavesInfo[WaveCount].UsedSpawnPoint;
+ srand(time(NULL));//initializing random seed
+ //uint8 KaldoreiSoldierCount = 0;
+ //uint8 AnubisathConquerorCount = 0;
+ //uint8 QirajiWaspCount = 0;
+ for (uint8 i = 0; i < 67; ++i)
+ {
+ Creature* Spawn = NULL;
+ float X = SpawnLocation[locIndex + i].x;
+ float Y = SpawnLocation[locIndex + i].y;
+ float Z = SpawnLocation[locIndex + i].z;
+ float O = SpawnLocation[locIndex + i].o;
+ uint32 desptimer = WavesInfo[WaveCount].DespTimer;
+ Spawn = me->SummonCreature(WavesInfo[WaveCount].CreatureId, X, Y, Z, O, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, desptimer);
+
+ if (Spawn)
+ {
+ Spawn->LoadCreaturesAddon();
+ if (Spawn->GetGUID() == 15423)
+ Spawn->SetUInt32Value(UNIT_FIELD_DISPLAYID,15427+rand()%4);
+ if (i >= 30) WaveCount = 1;
+ if (i >= 33) WaveCount = 2;
+ if (i >= 45) WaveCount = 3;
+ if (i >= 51) WaveCount = 4;
+
+ if (WaveCount < 5) //1-4 Wave
+ {
+ CAST_AI(mob_qiraj_war_spawnAI, Spawn->AI())->MobGUID = me->GetGUID();
+ CAST_AI(mob_qiraj_war_spawnAI, Spawn->AI())->PlayerGUID = PlayerGUID;
+ }
+ }
+ }
+ WaveTimer = WavesInfo[WaveCount].SpawnTimer;
+ AnnounceTimer = WavesInfo[WaveCount].YellTimer;
+ }
+
+ void CheckEventFail()
+ {
+ Player* pPlayer = Unit::GetPlayer(PlayerGUID);
+
+ if (!pPlayer)
+ return;
+
+ if (Group *EventGroup = pPlayer->GetGroup())
+ {
+ Player* GroupMember;
+
+ uint8 GroupMemberCount = 0;
+ uint8 DeadMemberCount = 0;
+ uint8 FailedMemberCount = 0;
+
+ const Group::MemberSlotList members = EventGroup->GetMemberSlots();
+
+ for (Group::member_citerator itr = members.begin(); itr!= members.end(); ++itr)
+ {
+ GroupMember = (Unit::GetPlayer(itr->guid));
+ if (!GroupMember)
+ continue;
+ if (!GroupMember->IsWithinDistInMap(me, EVENT_AREA_RADIUS) && GroupMember->GetQuestStatus(QUEST_A_PAWN_ON_THE_ETERNAL_BOARD) == QUEST_STATUS_INCOMPLETE)
+ {
+ GroupMember->FailQuest(QUEST_A_PAWN_ON_THE_ETERNAL_BOARD);
+ GroupMember->SetQuestStatus(QUEST_A_PAWN_ON_THE_ETERNAL_BOARD, QUEST_STATUS_NONE);
+ ++FailedMemberCount;
+ }
+ ++GroupMemberCount;
+
+ if (GroupMember->isDead())
+ ++DeadMemberCount;
+ }
+
+ if (GroupMemberCount == FailedMemberCount || !pPlayer->IsWithinDistInMap(me, EVENT_AREA_RADIUS))
+ Failed = true; //only so event can restart
+ }
+ }
+
+ void LiveCounter()
+ {
+ --LiveCount;
+ if (!LiveCount)
+ Announced = false;
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!PlayerGUID || !EventStarted)
+ return;
+
+ if (WaveCount < 4)
+ {
+ if (!Announced && AnnounceTimer <= diff)
+ {
+ DoScriptText(WavesInfo[WaveCount].WaveTextId, me);
+ Announced = true;
+ } else AnnounceTimer -= diff;
+
+ if (WaveTimer <= diff)
+ SummonNextWave();
+ else WaveTimer -= diff;
+ }
+ CheckEventFail();
+ if (WaveCount == 4 || Failed)
+ EnterEvadeMode();
+ };
+};
+void mob_qiraj_war_spawnAI::JustDied(Unit* /*slayer*/)
+{
+ me->RemoveCorpse();
+ if (Creature* Mob = (Unit::GetCreature(*me, MobGUID)))
+ CAST_AI(npc_anachronos_quest_triggerAI, Mob->AI())->LiveCounter();
+
+};
+/*#####
+# go_crystalline_tear
+######*/
+
+bool GOQuestAccept_GO_crystalline_tear(Player* plr, GameObject* go, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_A_PAWN_ON_THE_ETERNAL_BOARD)
+ {
+
+ if (Unit* Anachronos_Quest_Trigger = go->FindNearestCreature(15454, 100, plr))
+ {
+
+ Unit *Merithra = Anachronos_Quest_Trigger->SummonCreature(15378,-8034.535,1535.14,2.61,0,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,220000);
+ Unit *Caelestrasz = Anachronos_Quest_Trigger->SummonCreature(15379,-8032.767, 1533.148,2.61, 1.5,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,220000);
+ Unit *Arygos = Anachronos_Quest_Trigger->SummonCreature(15380,-8034.52, 1537.843, 2.61, 5.7,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,220000);
+ /* Unit *Fandral = */ Anachronos_Quest_Trigger->SummonCreature(15382,-8028.462, 1535.843, 2.61, 3.141592,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,220000);
+ Creature *Anachronos = Anachronos_Quest_Trigger->SummonCreature(15381,-8028.75, 1538.795, 2.61, 4,TEMPSUMMON_TIMED_OR_DEAD_DESPAWN,220000);
+
+ if (Merithra)
+ {
+ Merithra->SetUInt32Value(UNIT_NPC_FLAGS, 0);
+ Merithra->SetUInt32Value(UNIT_FIELD_BYTES_1,0);
+ Merithra->SetUInt32Value(UNIT_FIELD_DISPLAYID,15420);
+ Merithra->setFaction(35);
+ }
+
+ if (Caelestrasz)
+ {
+ Caelestrasz->SetUInt32Value(UNIT_NPC_FLAGS, 0);
+ Caelestrasz->SetUInt32Value(UNIT_FIELD_BYTES_1,0);
+ Caelestrasz->SetUInt32Value(UNIT_FIELD_DISPLAYID,15419);
+ Caelestrasz->setFaction(35);
+ }
+
+ if (Arygos)
+ {
+ Arygos->SetUInt32Value(UNIT_NPC_FLAGS, 0);
+ Arygos->SetUInt32Value(UNIT_FIELD_BYTES_1,0);
+ Arygos->SetUInt32Value(UNIT_FIELD_DISPLAYID,15418);
+ Arygos->setFaction(35);
+ }
+
+ if (Anachronos)
+ {
+ CAST_AI(npc_anachronos_the_ancientAI, Anachronos->AI())->PlayerGUID = plr->GetGUID();
+ CAST_AI(npc_anachronos_quest_triggerAI, CAST_CRE(Anachronos_Quest_Trigger)->AI())->Failed=false;
+ CAST_AI(npc_anachronos_quest_triggerAI, CAST_CRE(Anachronos_Quest_Trigger)->AI())->PlayerGUID = plr->GetGUID();
+ CAST_AI(npc_anachronos_quest_triggerAI, CAST_CRE(Anachronos_Quest_Trigger)->AI())->EventStarted=true;
+ CAST_AI(npc_anachronos_quest_triggerAI, CAST_CRE(Anachronos_Quest_Trigger)->AI())->Announced=true;
+ }
+ }
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_anachronos_quest_trigger(Creature* c)
+{
+ return new npc_anachronos_quest_triggerAI(c);
+}
+
+CreatureAI* GetAI_mob_qiraj_war_spawn(Creature* c)
+{
+ return new mob_qiraj_war_spawnAI(c);
+}
+
+CreatureAI* GetAI_npc_anachronos_the_ancient(Creature* c)
+{
+ return new npc_anachronos_the_ancientAI(c);
+}
+
+void AddSC_silithus()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "go_crystalline_tear";
+ newscript->pGOQuestAccept = &GOQuestAccept_GO_crystalline_tear;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_anachronos_quest_trigger";
+ newscript->GetAI = &GetAI_npc_anachronos_quest_trigger;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_anachronos_the_ancient";
+ newscript->GetAI = &GetAI_npc_anachronos_the_ancient;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_qiraj_war_spawn";
+ newscript->GetAI = &GetAI_mob_qiraj_war_spawn;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_highlord_demitrian";
+ newscript->pGossipHello = &GossipHello_npc_highlord_demitrian;
+ newscript->pGossipSelect = &GossipSelect_npc_highlord_demitrian;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npcs_rutgar_and_frankal";
+ newscript->pGossipHello = &GossipHello_npcs_rutgar_and_frankal;
+ newscript->pGossipSelect = &GossipSelect_npcs_rutgar_and_frankal;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/stonetalon_mountains.cpp b/src/server/scripts/Kalimdor/stonetalon_mountains.cpp
new file mode 100644
index 00000000000..6e627948788
--- /dev/null
+++ b/src/server/scripts/Kalimdor/stonetalon_mountains.cpp
@@ -0,0 +1,172 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Stonetalon_Mountains
+SD%Complete: 95
+SDComment: Quest support: 6627, 6523
+SDCategory: Stonetalon Mountains
+EndScriptData */
+
+/* ContentData
+npc_braug_dimspirit
+npc_kaya_flathoof
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+
+/*######
+## npc_braug_dimspirit
+######*/
+
+#define GOSSIP_HBD1 "Ysera"
+#define GOSSIP_HBD2 "Neltharion"
+#define GOSSIP_HBD3 "Nozdormu"
+#define GOSSIP_HBD4 "Alexstrasza"
+#define GOSSIP_HBD5 "Malygos"
+
+bool GossipHello_npc_braug_dimspirit(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(6627) == QUEST_STATUS_INCOMPLETE)
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HBD1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HBD2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HBD3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HBD4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HBD5, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+
+ pPlayer->SEND_GOSSIP_MENU(5820, pCreature->GetGUID());
+ }
+ else
+ pPlayer->SEND_GOSSIP_MENU(5819, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_braug_dimspirit(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pCreature->CastSpell(pPlayer,6766,false);
+
+ }
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+2)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pPlayer->AreaExploredOrEventHappens(6627);
+ }
+ return true;
+}
+
+/*######
+## npc_kaya_flathoof
+######*/
+
+enum eKaya
+{
+ FACTION_ESCORTEE_H = 775,
+
+ NPC_GRIMTOTEM_RUFFIAN = 11910,
+ NPC_GRIMTOTEM_BRUTE = 11912,
+ NPC_GRIMTOTEM_SORCERER = 11913,
+
+ SAY_START = -1000357,
+ SAY_AMBUSH = -1000358,
+ SAY_END = -1000359,
+
+ QUEST_PROTECT_KAYA = 6523
+};
+
+struct npc_kaya_flathoofAI : public npc_escortAI
+{
+ npc_kaya_flathoofAI(Creature* c) : npc_escortAI(c) {}
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch(i)
+ {
+ case 16:
+ DoScriptText(SAY_AMBUSH, me);
+ me->SummonCreature(NPC_GRIMTOTEM_BRUTE, -48.53, -503.34, -46.31, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ me->SummonCreature(NPC_GRIMTOTEM_RUFFIAN, -38.85, -503.77, -45.90, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ me->SummonCreature(NPC_GRIMTOTEM_SORCERER, -36.37, -496.23, -45.71, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ break;
+ case 18: me->SetInFront(pPlayer);
+ DoScriptText(SAY_END, me, pPlayer);
+ if (pPlayer)
+ pPlayer->GroupEventHappens(QUEST_PROTECT_KAYA, me);
+ break;
+ }
+ }
+
+ void JustSummoned(Creature* summoned)
+ {
+ summoned->AI()->AttackStart(me);
+ }
+
+ void Reset(){}
+};
+
+bool QuestAccept_npc_kaya_flathoof(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_PROTECT_KAYA)
+ {
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_kaya_flathoofAI, pCreature->AI()))
+ pEscortAI->Start(true, false, pPlayer->GetGUID());
+
+ DoScriptText(SAY_START, pCreature);
+ pCreature->setFaction(113);
+ pCreature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE);
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_kaya_flathoofAI(Creature* pCreature)
+{
+ return new npc_kaya_flathoofAI(pCreature);
+}
+
+/*######
+## AddSC
+######*/
+
+void AddSC_stonetalon_mountains()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_braug_dimspirit";
+ newscript->pGossipHello = &GossipHello_npc_braug_dimspirit;
+ newscript->pGossipSelect = &GossipSelect_npc_braug_dimspirit;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_kaya_flathoof";
+ newscript->GetAI = &GetAI_npc_kaya_flathoofAI;
+ newscript->pQuestAccept = &QuestAccept_npc_kaya_flathoof;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/tanaris.cpp b/src/server/scripts/Kalimdor/tanaris.cpp
new file mode 100644
index 00000000000..bb82dea64cf
--- /dev/null
+++ b/src/server/scripts/Kalimdor/tanaris.cpp
@@ -0,0 +1,635 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Tanaris
+SD%Complete: 80
+SDComment: Quest support: 648, 1560, 2954, 4005, 10277, 10279(Special flight path). Noggenfogger vendor
+SDCategory: Tanaris
+EndScriptData */
+
+/* ContentData
+mob_aquementas
+npc_custodian_of_time
+npc_marin_noggenfogger
+npc_steward_of_time
+npc_stone_watcher_of_norgannon
+npc_OOX17
+npc_tooga
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+#include "ScriptedFollowerAI.h"
+
+/*######
+## mob_aquementas
+######*/
+
+#define AGGRO_YELL_AQUE -1000350
+
+#define SPELL_AQUA_JET 13586
+#define SPELL_FROST_SHOCK 15089
+
+struct mob_aquementasAI : public ScriptedAI
+{
+ mob_aquementasAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 SendItem_Timer;
+ uint32 SwitchFaction_Timer;
+ bool isFriendly;
+
+ uint32 FrostShock_Timer;
+ uint32 AquaJet_Timer;
+
+ void Reset()
+ {
+ SendItem_Timer = 0;
+ SwitchFaction_Timer = 10000;
+ me->setFaction(35);
+ isFriendly = true;
+
+ AquaJet_Timer = 5000;
+ FrostShock_Timer = 1000;
+ }
+
+ void SendItem(Unit* receiver)
+ {
+ if (CAST_PLR(receiver)->HasItemCount(11169,1,false) &&
+ CAST_PLR(receiver)->HasItemCount(11172,11,false) &&
+ CAST_PLR(receiver)->HasItemCount(11173,1,false) &&
+ !CAST_PLR(receiver)->HasItemCount(11522,1,true))
+ {
+ ItemPosCountVec dest;
+ uint8 msg = CAST_PLR(receiver)->CanStoreNewItem(NULL_BAG, NULL_SLOT, dest, 11522, 1, false);
+ if (msg == EQUIP_ERR_OK)
+ CAST_PLR(receiver)->StoreNewItem(dest, 11522, 1, true);
+ }
+ }
+
+ void EnterCombat(Unit* who)
+ {
+ DoScriptText(AGGRO_YELL_AQUE, me, who);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (isFriendly)
+ {
+ if (SwitchFaction_Timer <= diff)
+ {
+ me->setFaction(91);
+ isFriendly = false;
+ } else SwitchFaction_Timer -= diff;
+ }
+
+ if (!UpdateVictim())
+ return;
+
+ if (!isFriendly)
+ {
+ if (SendItem_Timer <= diff)
+ {
+ if (me->getVictim()->GetTypeId() == TYPEID_PLAYER)
+ SendItem(me->getVictim());
+ SendItem_Timer = 5000;
+ } else SendItem_Timer -= diff;
+ }
+
+ if (FrostShock_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_FROST_SHOCK);
+ FrostShock_Timer = 15000;
+ } else FrostShock_Timer -= diff;
+
+ if (AquaJet_Timer <= diff)
+ {
+ DoCast(me, SPELL_AQUA_JET);
+ AquaJet_Timer = 15000;
+ } else AquaJet_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_mob_aquementas(Creature* pCreature)
+{
+ return new mob_aquementasAI (pCreature);
+}
+
+/*######
+## npc_custodian_of_time
+######*/
+
+#define WHISPER_CUSTODIAN_1 -1000217
+#define WHISPER_CUSTODIAN_2 -1000218
+#define WHISPER_CUSTODIAN_3 -1000219
+#define WHISPER_CUSTODIAN_4 -1000220
+#define WHISPER_CUSTODIAN_5 -1000221
+#define WHISPER_CUSTODIAN_6 -1000222
+#define WHISPER_CUSTODIAN_7 -1000223
+#define WHISPER_CUSTODIAN_8 -1000224
+#define WHISPER_CUSTODIAN_9 -1000225
+#define WHISPER_CUSTODIAN_10 -1000226
+#define WHISPER_CUSTODIAN_11 -1000227
+#define WHISPER_CUSTODIAN_12 -1000228
+#define WHISPER_CUSTODIAN_13 -1000229
+#define WHISPER_CUSTODIAN_14 -1000230
+
+struct npc_custodian_of_timeAI : public npc_escortAI
+{
+ npc_custodian_of_timeAI(Creature *c) : npc_escortAI(c) {}
+
+ void WaypointReached(uint32 i)
+ {
+ Player *pPlayer = GetPlayerForEscort();
+ if (!pPlayer)
+ return;
+
+ switch(i)
+ {
+ case 0: DoScriptText(WHISPER_CUSTODIAN_1, me, pPlayer); break;
+ case 1: DoScriptText(WHISPER_CUSTODIAN_2, me, pPlayer); break;
+ case 2: DoScriptText(WHISPER_CUSTODIAN_3, me, pPlayer); break;
+ case 3: DoScriptText(WHISPER_CUSTODIAN_4, me, pPlayer); break;
+ case 5: DoScriptText(WHISPER_CUSTODIAN_5, me, pPlayer); break;
+ case 6: DoScriptText(WHISPER_CUSTODIAN_6, me, pPlayer); break;
+ case 7: DoScriptText(WHISPER_CUSTODIAN_7, me, pPlayer); break;
+ case 8: DoScriptText(WHISPER_CUSTODIAN_8, me, pPlayer); break;
+ case 9: DoScriptText(WHISPER_CUSTODIAN_9, me, pPlayer); break;
+ case 10: DoScriptText(WHISPER_CUSTODIAN_4, me, pPlayer); break;
+ case 13: DoScriptText(WHISPER_CUSTODIAN_10, me, pPlayer); break;
+ case 14: DoScriptText(WHISPER_CUSTODIAN_4, me, pPlayer); break;
+ case 16: DoScriptText(WHISPER_CUSTODIAN_11, me, pPlayer); break;
+ case 17: DoScriptText(WHISPER_CUSTODIAN_12, me, pPlayer); break;
+ case 18: DoScriptText(WHISPER_CUSTODIAN_4, me, pPlayer); break;
+ case 22: DoScriptText(WHISPER_CUSTODIAN_13, me, pPlayer); break;
+ case 23: DoScriptText(WHISPER_CUSTODIAN_4, me, pPlayer); break;
+ case 24:
+ DoScriptText(WHISPER_CUSTODIAN_14, me, pPlayer);
+ DoCast(pPlayer, 34883);
+ // below here is temporary workaround, to be removed when spell works properly
+ pPlayer->AreaExploredOrEventHappens(10277);
+ break;
+ }
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ if (HasEscortState(STATE_ESCORT_ESCORTING))
+ return;
+
+ if (who->GetTypeId() == TYPEID_PLAYER)
+ {
+ if (who->HasAura(34877) && CAST_PLR(who)->GetQuestStatus(10277) == QUEST_STATUS_INCOMPLETE)
+ {
+ float Radius = 10.0;
+ if (me->IsWithinDistInMap(who, Radius))
+ {
+ Start(false, false, who->GetGUID());
+ }
+ }
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+ void Reset() { }
+
+ void UpdateAI(const uint32 diff)
+ {
+ npc_escortAI::UpdateAI(diff);
+ }
+};
+
+CreatureAI* GetAI_npc_custodian_of_time(Creature* pCreature)
+{
+ return new npc_custodian_of_timeAI(pCreature);
+}
+
+/*######
+## npc_marin_noggenfogger
+######*/
+
+bool GossipHello_npc_marin_noggenfogger(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pCreature->isVendor() && pPlayer->GetQuestRewardStatus(2662))
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_VENDOR, GOSSIP_TEXT_BROWSE_GOODS, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_TRADE);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_marin_noggenfogger(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_TRADE)
+ pPlayer->SEND_VENDORLIST(pCreature->GetGUID());
+
+ return true;
+}
+
+/*######
+## npc_steward_of_time
+######*/
+
+#define GOSSIP_ITEM_FLIGHT "Please take me to the master's lair."
+
+bool GossipHello_npc_steward_of_time(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(10279) == QUEST_STATUS_INCOMPLETE || pPlayer->GetQuestRewardStatus(10279))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_FLIGHT, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+ pPlayer->SEND_GOSSIP_MENU(9978, pCreature->GetGUID());
+ }
+ else
+ pPlayer->SEND_GOSSIP_MENU(9977, pCreature->GetGUID());
+
+ return true;
+}
+
+bool QuestAccept_npc_steward_of_time(Player* pPlayer, Creature* /*pCreature*/, Quest const *quest)
+{
+ if (quest->GetQuestId() == 10279) //Quest: To The Master's Lair
+ pPlayer->CastSpell(pPlayer,34891,true); //(Flight through Caverns)
+
+ return false;
+}
+
+bool GossipSelect_npc_steward_of_time(Player* pPlayer, Creature* /*pCreature*/, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF + 1)
+ pPlayer->CastSpell(pPlayer,34891,true); //(Flight through Caverns)
+
+ return true;
+}
+
+/*######
+## npc_stone_watcher_of_norgannon
+######*/
+
+#define GOSSIP_ITEM_NORGANNON_1 "What function do you serve?"
+#define GOSSIP_ITEM_NORGANNON_2 "What are the Plates of Uldum?"
+#define GOSSIP_ITEM_NORGANNON_3 "Where are the Plates of Uldum?"
+#define GOSSIP_ITEM_NORGANNON_4 "Excuse me? We've been \"reschedueled for visitations\"? What does that mean?!"
+#define GOSSIP_ITEM_NORGANNON_5 "So, what's inside Uldum?"
+#define GOSSIP_ITEM_NORGANNON_6 "I will return when i have the Plates of Uldum."
+
+bool GossipHello_npc_stone_watcher_of_norgannon(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(2954) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_NORGANNON_1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+
+ pPlayer->SEND_GOSSIP_MENU(1674, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_stone_watcher_of_norgannon(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch (uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_NORGANNON_2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(1675, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_NORGANNON_3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+2);
+ pPlayer->SEND_GOSSIP_MENU(1676, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_NORGANNON_4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+3);
+ pPlayer->SEND_GOSSIP_MENU(1677, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+3:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_NORGANNON_5, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+4);
+ pPlayer->SEND_GOSSIP_MENU(1678, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+4:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_NORGANNON_6, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+5);
+ pPlayer->SEND_GOSSIP_MENU(1679, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+5:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pPlayer->AreaExploredOrEventHappens(2954);
+ break;
+ }
+ return true;
+}
+
+/*######
+## npc_OOX17
+######*/
+
+enum e00X17
+{
+ //texts are signed for 7806
+ SAY_OOX_START = -1000287,
+ SAY_OOX_AGGRO1 = -1000288,
+ SAY_OOX_AGGRO2 = -1000289,
+ SAY_OOX_AMBUSH = -1000290,
+ SAY_OOX17_AMBUSH_REPLY = -1000291,
+ SAY_OOX_END = -1000292,
+
+ Q_OOX17 = 648,
+ SPAWN_FIRST = 7803,
+ SPAWN_SECOND_1 = 5617,
+ SPAWN_SECOND_2 = 7805
+};
+
+struct npc_OOX17AI : public npc_escortAI
+{
+ npc_OOX17AI(Creature *c) : npc_escortAI(c) {}
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch(i) {
+ case 23:
+ me->SummonCreature(SPAWN_FIRST, -8350.96, -4445.79, 10.10, 6.20, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ me->SummonCreature(SPAWN_FIRST, -8355.96, -4447.79, 10.10, 6.27, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ me->SummonCreature(SPAWN_FIRST, -8353.96, -4442.79, 10.10, 6.08, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ DoScriptText(SAY_OOX_AMBUSH, me);
+ break;
+
+ case 56:
+ me->SummonCreature(SPAWN_SECOND_1, -7510.07, -4795.50, 9.35, 6.06, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ me->SummonCreature(SPAWN_SECOND_2, -7515.07, -4797.50, 9.35, 6.22, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ me->SummonCreature(SPAWN_SECOND_2, -7518.07, -4792.50, 9.35, 6.22, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ DoScriptText(SAY_OOX_AMBUSH, me);
+ if (Unit* scoff = me->FindNearestCreature(SPAWN_SECOND_2, 30))
+ DoScriptText(SAY_OOX17_AMBUSH_REPLY, scoff);
+ break;
+
+ case 86:
+ if (pPlayer)
+ {
+ DoScriptText(SAY_OOX_END, me);
+ pPlayer->GroupEventHappens(Q_OOX17, me);
+ }
+ break;
+ }
+ }
+
+ void Reset(){}
+
+ void EnterCombat(Unit* /*who*/)
+ {
+ DoScriptText(RAND(SAY_OOX_AGGRO1,SAY_OOX_AGGRO2), me);
+ }
+
+ void JustSummoned(Creature* summoned)
+ {
+ summoned->AI()->AttackStart(me);
+ }
+};
+
+bool QuestAccept_npc_OOX17(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == Q_OOX17)
+ {
+ pCreature->setFaction(113);
+ pCreature->SetHealth(pCreature->GetMaxHealth());
+ pCreature->SetUInt32Value(UNIT_FIELD_BYTES_1,0);
+ pCreature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE);
+ DoScriptText(SAY_OOX_START, pCreature);
+
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_OOX17AI, pCreature->AI()))
+ pEscortAI->Start(true, false, pPlayer->GetGUID());
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_OOX17(Creature* pCreature)
+{
+ return new npc_OOX17AI(pCreature);
+}
+
+/*####
+# npc_tooga
+####*/
+
+enum eTooga
+{
+ SAY_TOOG_THIRST = -1000391,
+ SAY_TOOG_WORRIED = -1000392,
+ SAY_TOOG_POST_1 = -1000393,
+ SAY_TORT_POST_2 = -1000394,
+ SAY_TOOG_POST_3 = -1000395,
+ SAY_TORT_POST_4 = -1000396,
+ SAY_TOOG_POST_5 = -1000397,
+ SAY_TORT_POST_6 = -1000398,
+
+ QUEST_TOOGA = 1560,
+ NPC_TORTA = 6015,
+
+ POINT_ID_TO_WATER = 1,
+ FACTION_TOOG_ESCORTEE = 113
+};
+
+const float m_afToWaterLoc[] = {-7032.664551, -4906.199219, -1.606446};
+
+struct npc_toogaAI : public FollowerAI
+{
+ npc_toogaAI(Creature* pCreature) : FollowerAI(pCreature) { }
+
+ uint32 m_uiCheckSpeechTimer;
+ uint32 m_uiPostEventTimer;
+ uint32 m_uiPhasePostEvent;
+
+ uint64 TortaGUID;
+
+ void Reset()
+ {
+ m_uiCheckSpeechTimer = 2500;
+ m_uiPostEventTimer = 1000;
+ m_uiPhasePostEvent = 0;
+
+ TortaGUID = 0;
+ }
+
+ void MoveInLineOfSight(Unit *pWho)
+ {
+ FollowerAI::MoveInLineOfSight(pWho);
+
+ if (!me->getVictim() && !HasFollowState(STATE_FOLLOW_COMPLETE | STATE_FOLLOW_POSTEVENT) && pWho->GetEntry() == NPC_TORTA)
+ {
+ if (me->IsWithinDistInMap(pWho, INTERACTION_DISTANCE))
+ {
+ if (Player* pPlayer = GetLeaderForFollower())
+ {
+ if (pPlayer->GetQuestStatus(QUEST_TOOGA) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->GroupEventHappens(QUEST_TOOGA, me);
+ }
+
+ TortaGUID = pWho->GetGUID();
+ SetFollowComplete(true);
+ }
+ }
+ }
+
+ void MovementInform(uint32 uiMotionType, uint32 uiPointId)
+ {
+ FollowerAI::MovementInform(uiMotionType, uiPointId);
+
+ if (uiMotionType != POINT_MOTION_TYPE)
+ return;
+
+ if (uiPointId == POINT_ID_TO_WATER)
+ SetFollowComplete();
+ }
+
+ void UpdateFollowerAI(const uint32 uiDiff)
+ {
+ if (!UpdateVictim())
+ {
+ //we are doing the post-event, or...
+ if (HasFollowState(STATE_FOLLOW_POSTEVENT))
+ {
+ if (m_uiPostEventTimer <= uiDiff)
+ {
+ m_uiPostEventTimer = 5000;
+
+ Unit *pTorta = Unit::GetUnit(*me, TortaGUID);
+ if (!pTorta || !pTorta->isAlive())
+ {
+ //something happened, so just complete
+ SetFollowComplete();
+ return;
+ }
+
+ switch(m_uiPhasePostEvent)
+ {
+ case 1:
+ DoScriptText(SAY_TOOG_POST_1, me);
+ break;
+ case 2:
+ DoScriptText(SAY_TORT_POST_2, pTorta);
+ break;
+ case 3:
+ DoScriptText(SAY_TOOG_POST_3, me);
+ break;
+ case 4:
+ DoScriptText(SAY_TORT_POST_4, pTorta);
+ break;
+ case 5:
+ DoScriptText(SAY_TOOG_POST_5, me);
+ break;
+ case 6:
+ DoScriptText(SAY_TORT_POST_6, pTorta);
+ me->GetMotionMaster()->MovePoint(POINT_ID_TO_WATER, m_afToWaterLoc[0], m_afToWaterLoc[1], m_afToWaterLoc[2]);
+ break;
+ }
+
+ ++m_uiPhasePostEvent;
+ }
+ else
+ m_uiPostEventTimer -= uiDiff;
+ }
+ //...we are doing regular speech check
+ else if (HasFollowState(STATE_FOLLOW_INPROGRESS))
+ {
+ if (m_uiCheckSpeechTimer <= uiDiff)
+ {
+ m_uiCheckSpeechTimer = 5000;
+
+ if (urand(0,9) > 8)
+ DoScriptText(RAND(SAY_TOOG_THIRST,SAY_TOOG_WORRIED), me);
+ }
+ else
+ m_uiCheckSpeechTimer -= uiDiff;
+ }
+
+ return;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_tooga(Creature* pCreature)
+{
+ return new npc_toogaAI(pCreature);
+}
+
+bool QuestAccept_npc_tooga(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_TOOGA)
+ {
+ if (npc_toogaAI* pToogaAI = CAST_AI(npc_toogaAI, pCreature->AI()))
+ pToogaAI->StartFollow(pPlayer, FACTION_TOOG_ESCORTEE, pQuest);
+ }
+
+ return true;
+}
+
+void AddSC_tanaris()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "mob_aquementas";
+ newscript->GetAI = &GetAI_mob_aquementas;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_custodian_of_time";
+ newscript->GetAI = &GetAI_npc_custodian_of_time;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_marin_noggenfogger";
+ newscript->pGossipHello = &GossipHello_npc_marin_noggenfogger;
+ newscript->pGossipSelect = &GossipSelect_npc_marin_noggenfogger;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_steward_of_time";
+ newscript->pGossipHello = &GossipHello_npc_steward_of_time;
+ newscript->pGossipSelect = &GossipSelect_npc_steward_of_time;
+ newscript->pQuestAccept = &QuestAccept_npc_steward_of_time;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_stone_watcher_of_norgannon";
+ newscript->pGossipHello = &GossipHello_npc_stone_watcher_of_norgannon;
+ newscript->pGossipSelect = &GossipSelect_npc_stone_watcher_of_norgannon;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_OOX17";
+ newscript->GetAI = &GetAI_npc_OOX17;
+ newscript->pQuestAccept = &QuestAccept_npc_OOX17;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_tooga";
+ newscript->GetAI = &GetAI_npc_tooga;
+ newscript->pQuestAccept = &QuestAccept_npc_tooga;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/teldrassil.cpp b/src/server/scripts/Kalimdor/teldrassil.cpp
new file mode 100644
index 00000000000..1607ab904a8
--- /dev/null
+++ b/src/server/scripts/Kalimdor/teldrassil.cpp
@@ -0,0 +1,114 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Teldrassil
+SD%Complete: 100
+SDComment: Quest support: 938
+SDCategory: Teldrassil
+EndScriptData */
+
+/* ContentData
+npc_mist
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedFollowerAI.h"
+
+/*####
+# npc_mist
+####*/
+
+enum eMist
+{
+ SAY_AT_HOME = -1000323,
+ EMOTE_AT_HOME = -1000324,
+ QUEST_MIST = 938,
+ NPC_ARYNIA = 3519,
+ FACTION_DARNASSUS = 79
+};
+
+struct npc_mistAI : public FollowerAI
+{
+ npc_mistAI(Creature* pCreature) : FollowerAI(pCreature) { }
+
+ void Reset() { }
+
+ void MoveInLineOfSight(Unit *pWho)
+ {
+ FollowerAI::MoveInLineOfSight(pWho);
+
+ if (!me->getVictim() && !HasFollowState(STATE_FOLLOW_COMPLETE) && pWho->GetEntry() == NPC_ARYNIA)
+ {
+ if (me->IsWithinDistInMap(pWho, 10.0f))
+ {
+ DoScriptText(SAY_AT_HOME, pWho);
+ DoComplete();
+ }
+ }
+ }
+
+ void DoComplete()
+ {
+ DoScriptText(EMOTE_AT_HOME, me);
+
+ if (Player* pPlayer = GetLeaderForFollower())
+ {
+ if (pPlayer->GetQuestStatus(QUEST_MIST) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->GroupEventHappens(QUEST_MIST, me);
+ }
+
+ //The follow is over (and for later development, run off to the woods before really end)
+ SetFollowComplete();
+ }
+
+ //call not needed here, no known abilities
+ /*void UpdateFollowerAI(const uint32 uiDiff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }*/
+};
+
+CreatureAI* GetAI_npc_mist(Creature* pCreature)
+{
+ return new npc_mistAI(pCreature);
+}
+
+bool QuestAccept_npc_mist(Player* pPlayer, Creature* pCreature, Quest const* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_MIST)
+ {
+ if (npc_mistAI* pMistAI = CAST_AI(npc_mistAI, pCreature->AI()))
+ pMistAI->StartFollow(pPlayer, FACTION_DARNASSUS, pQuest);
+ }
+
+ return true;
+}
+
+void AddSC_teldrassil()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_mist";
+ newscript->GetAI = &GetAI_npc_mist;
+ newscript->pQuestAccept = &QuestAccept_npc_mist;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_bug_trio.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_bug_trio.cpp
new file mode 100644
index 00000000000..f6e3b0c741b
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_bug_trio.cpp
@@ -0,0 +1,346 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: boss_kri, boss_yauj, boss_vem : The Bug Trio
+SD%Complete: 100
+SDComment:
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "temple_of_ahnqiraj.h"
+
+#define SPELL_CLEAVE 26350
+#define SPELL_TOXIC_VOLLEY 25812
+#define SPELL_POISON_CLOUD 38718 //Only Spell with right dmg.
+#define SPELL_ENRAGE 34624 //Changed cause 25790 is casted on gamers too. Same prob with old explosion of twin emperors.
+
+#define SPELL_CHARGE 26561
+#define SPELL_KNOCKBACK 26027
+
+#define SPELL_HEAL 25807
+#define SPELL_FEAR 19408
+
+struct boss_kriAI : public ScriptedAI
+{
+ boss_kriAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 Cleave_Timer;
+ uint32 ToxicVolley_Timer;
+ uint32 Check_Timer;
+
+ bool VemDead;
+ bool Death;
+
+ void Reset()
+ {
+ Cleave_Timer = 4000 + rand()%4000;
+ ToxicVolley_Timer = 6000 + rand()%6000;
+ Check_Timer = 2000;
+
+ VemDead = false;
+ Death = false;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_BUG_TRIO_DEATH) < 2)
+ // Unlootable if death
+ me->RemoveFlag(UNIT_DYNAMIC_FLAGS, UNIT_DYNFLAG_LOOTABLE);
+
+ pInstance->SetData(DATA_BUG_TRIO_DEATH, 1);
+ }
+ }
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Cleave_Timer
+ if (Cleave_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_CLEAVE);
+ Cleave_Timer = 5000 + rand()%7000;
+ } else Cleave_Timer -= diff;
+
+ //ToxicVolley_Timer
+ if (ToxicVolley_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_TOXIC_VOLLEY);
+ ToxicVolley_Timer = 10000 + rand()%5000;
+ } else ToxicVolley_Timer -= diff;
+
+ if (me->GetHealth() <= me->GetMaxHealth() * 0.05 && !Death)
+ {
+ DoCast(me->getVictim(), SPELL_POISON_CLOUD);
+ Death = true;
+ }
+
+ if (!VemDead)
+ {
+ //Checking if Vem is dead. If yes we will enrage.
+ if (Check_Timer <= diff)
+ {
+ if (pInstance && pInstance->GetData(DATA_VEMISDEAD))
+ {
+ DoCast(me, SPELL_ENRAGE);
+ VemDead = true;
+ }
+ Check_Timer = 2000;
+ } else Check_Timer -=diff;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+struct boss_vemAI : public ScriptedAI
+{
+ boss_vemAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 Charge_Timer;
+ uint32 KnockBack_Timer;
+ uint32 Enrage_Timer;
+
+ bool Enraged;
+
+ void Reset()
+ {
+ Charge_Timer = 15000 + rand()%12000;
+ KnockBack_Timer = 8000 + rand()%12000;
+ Enrage_Timer = 120000;
+
+ Enraged = false;
+ }
+
+ void JustDied(Unit* /*Killer*/)
+ {
+ if (pInstance)
+ {
+ pInstance->SetData(DATA_VEM_DEATH, 0);
+ if (pInstance->GetData(DATA_BUG_TRIO_DEATH) < 2)
+ // Unlootable if death
+ me->RemoveFlag(UNIT_DYNAMIC_FLAGS, UNIT_DYNFLAG_LOOTABLE);
+ pInstance->SetData(DATA_BUG_TRIO_DEATH, 1);
+ }
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Charge_Timer
+ if (Charge_Timer <= diff)
+ {
+ Unit *pTarget = NULL;
+ pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+ if (pTarget)
+ {
+ DoCast(pTarget, SPELL_CHARGE);
+ //me->SendMonsterMove(pTarget->GetPositionX(), pTarget->GetPositionY(), pTarget->GetPositionZ(), 0, true,1);
+ AttackStart(pTarget);
+ }
+
+ Charge_Timer = 8000 + rand()%8000;
+ } else Charge_Timer -= diff;
+
+ //KnockBack_Timer
+ if (KnockBack_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_KNOCKBACK);
+ if (DoGetThreat(me->getVictim()))
+ DoModifyThreatPercent(me->getVictim(),-80);
+ KnockBack_Timer = 15000 + rand()%10000;
+ } else KnockBack_Timer -= diff;
+
+ //Enrage_Timer
+ if (!Enraged && Enrage_Timer <= diff)
+ {
+ DoCast(me, SPELL_ENRAGE);
+ Enraged = true;
+ } else Charge_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+struct boss_yaujAI : public ScriptedAI
+{
+ boss_yaujAI(Creature *c) : ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 Heal_Timer;
+ uint32 Fear_Timer;
+ uint32 Check_Timer;
+
+ bool VemDead;
+
+ void Reset()
+ {
+ Heal_Timer = 25000 + rand()%15000;
+ Fear_Timer = 12000 + rand()%12000;
+ Check_Timer = 2000;
+
+ VemDead = false;
+ }
+
+ void JustDied(Unit* /*Killer*/)
+ {
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_BUG_TRIO_DEATH) < 2)
+ // Unlootable if death
+ me->RemoveFlag(UNIT_DYNAMIC_FLAGS, UNIT_DYNFLAG_LOOTABLE);
+ pInstance->SetData(DATA_BUG_TRIO_DEATH, 1);
+ }
+
+ for (uint8 i = 0; i < 10; ++i)
+ {
+ Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+ Creature* Summoned = me->SummonCreature(15621,me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(),0,TEMPSUMMON_TIMED_OR_CORPSE_DESPAWN,90000);
+ if (Summoned && pTarget)
+ Summoned->AI()->AttackStart(pTarget);
+ }
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Fear_Timer
+ if (Fear_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_FEAR);
+ DoResetThreat();
+ Fear_Timer = 20000;
+ } else Fear_Timer -= diff;
+
+ //Casting Heal to other twins or herself.
+ if (Heal_Timer <= diff)
+ {
+ if (pInstance)
+ {
+ Unit *pKri = Unit::GetUnit((*me), pInstance->GetData64(DATA_KRI));
+ Unit *pVem = Unit::GetUnit((*me), pInstance->GetData64(DATA_VEM));
+
+ switch (urand(0,2))
+ {
+ case 0:
+ if (pKri)
+ DoCast(pKri, SPELL_HEAL);
+ break;
+ case 1:
+ if (pVem)
+ DoCast(pVem, SPELL_HEAL);
+ break;
+ case 2:
+ DoCast(me, SPELL_HEAL);
+ break;
+ }
+ }
+
+ Heal_Timer = 15000+rand()%15000;
+ } else Heal_Timer -= diff;
+
+ //Checking if Vem is dead. If yes we will enrage.
+ if (Check_Timer <= diff)
+ {
+ if (!VemDead)
+ {
+ if (pInstance)
+ {
+ if (pInstance->GetData(DATA_VEMISDEAD))
+ {
+ DoCast(me, SPELL_ENRAGE);
+ VemDead = true;
+ }
+ }
+ }
+ Check_Timer = 2000;
+ } else Check_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_yauj(Creature* pCreature)
+{
+ return new boss_yaujAI (pCreature);
+}
+
+CreatureAI* GetAI_boss_vem(Creature* pCreature)
+{
+ return new boss_vemAI (pCreature);
+}
+
+CreatureAI* GetAI_boss_kri(Creature* pCreature)
+{
+ return new boss_kriAI (pCreature);
+}
+
+void AddSC_bug_trio()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_kri";
+ newscript->GetAI = &GetAI_boss_kri;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "boss_vem";
+ newscript->GetAI = &GetAI_boss_vem;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "boss_yauj";
+ newscript->GetAI = &GetAI_boss_yauj;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_cthun.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_cthun.cpp
new file mode 100644
index 00000000000..3e42d16be3a
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_cthun.cpp
@@ -0,0 +1,1307 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Cthun
+SD%Complete: 95
+SDComment: Darkglare tracking issue
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "temple_of_ahnqiraj.h"
+
+/*
+ * This is a 2 phases events. Here follows an explanation of the main events and transition between phases and sub-phases.
+ *
+ * The first phase is the EYE phase: the Eye of C'Thun is active and C'thun is not active.
+ * During this phase, the "Eye of C'Thun" alternates between 2 sub-phases:
+ * - PHASE_EYE_GREEN_BEAM:
+ * 50 sec phase during which the Eye mainly casts its Green Beam every 3 sec.
+ * - PHASE_EYE_RED_BEAM:
+ * 35 sec phase during which the Eye casts its red beam every sec.
+ * This EYE phase ends when the "Eye of C'Thun" is killed. Then starts the CTHUN phase.
+ *
+ * The second phase is the CTHUN phase. The Eye of C'Thun is not active and C'Thun is active.
+ * This phase starts with the transformation of the Eye into C'Thun (PHASE_CTHUN_TRANSITION).
+ * After the transformation, C'Thun alternates between 2 sub-phases:
+ * - PHASE_CTHUN_STOMACH:
+ * - C'Thun is almost insensible to all damage (99% damage reduction).
+ * - It spawns 2 tentacles in its stomach.
+ * - C'Thun swallows players.
+ * - This sub-phase ends when the 2 tentacles are killed. Swallowed players are regurgitate.
+ *
+ * - PHASE_CTHUN_WEAK:
+ * - weakened C'Thun takes normal damage.
+ * - This sub-phase ends after 45 secs.
+ *
+ * This CTHUN phase ends when C'Thun is killed
+ *
+ * Note:
+ * - the current phase is stored in the instance data to be easily shared between the eye and cthun.
+ */
+
+#define PI 3.14
+
+enum Phases
+{
+ PHASE_NOT_STARTED = 0,
+
+ // Main Phase 1 - EYE
+ PHASE_EYE_GREEN_BEAM = 1,
+ PHASE_EYE_RED_BEAM = 2,
+
+ // Main Phase 2 - CTHUN
+ PHASE_CTHUN_TRANSITION = 3,
+ PHASE_CTHUN_STOMACH = 4,
+ PHASE_CTHUN_WEAK = 5,
+
+ PHASE_CTHUN_DONE = 6,
+};
+
+enum Creatures
+{
+ MOB_CTHUN_PORTAL = 15896,
+
+ //***** Main Phase 1 ********
+ BOSS_EYE_OF_CTHUN = 15589,
+ MOB_CLAW_TENTACLE = 15725,
+ MOB_EYE_TENTACLE = 15726,
+ MOB_SMALL_PORTAL = 15904,
+
+ //***** Main Phase 2 ********
+ MOB_BODY_OF_CTHUN = 15809,
+ MOB_GIANT_CLAW_TENTACLE = 15728,
+ MOB_GIANT_EYE_TENTACLE = 15334,
+ MOB_FLESH_TENTACLE = 15802,
+ MOB_GIANT_PORTAL = 15910,
+};
+
+enum Spells
+{
+ //***** Main Phase 1 ********
+ //Eye Spells
+ SPELL_FREEZE_ANIM = 16245,
+ SPELL_GREEN_BEAM = 26134,
+ SPELL_DARK_GLARE = 26029,
+ SPELL_RED_COLORATION = 22518, //Probably not the right spell but looks similar
+
+ //Eye Tentacles Spells
+ SPELL_MIND_FLAY = 26143,
+
+ //Claw Tentacles Spells
+ SPELL_GROUND_RUPTURE = 26139,
+ SPELL_HAMSTRING = 26141,
+
+ //***** Main Phase 2 ******
+ //Body spells
+ //#define SPELL_CARAPACE_CTHUN 26156 //Was removed from client dbcs
+ SPELL_TRANSFORM = 26232,
+ SPELL_PURPLE_COLORATION = 22581, //Probably not the right spell but looks similar
+
+ //Eye Tentacles Spells
+ //SAME AS PHASE1
+
+ //Giant Claw Tentacles
+ SPELL_MASSIVE_GROUND_RUPTURE = 26100,
+
+ //Also casts Hamstring
+ SPELL_THRASH = 3391,
+
+ //Giant Eye Tentacles
+ //CHAIN CASTS "SPELL_GREEN_BEAM"
+
+ //Stomach Spells
+ SPELL_MOUTH_TENTACLE = 26332,
+ SPELL_EXIT_STOMACH_KNOCKBACK = 25383,
+ SPELL_DIGESTIVE_ACID = 26476,
+};
+
+enum Actions
+{
+ ACTION_FLESH_TENTACLE_KILLED = 1,
+};
+
+enum Yells
+{
+ //Text emote
+ EMOTE_WEAKENED = -1531011,
+
+ //****** Out of Combat ******
+ // Random Wispers - No txt only sound
+ // The random sound is chosen by the client.
+ RANDOM_SOUND_WHISPER = 8663,
+};
+
+//Stomach Teleport positions
+#define STOMACH_X -8562.0f
+#define STOMACH_Y 2037.0f
+#define STOMACH_Z -70.0f
+#define STOMACH_O 5.05f
+
+//Flesh tentacle positions
+const Position FleshTentaclePos[2] =
+{
+ { -8571.0f, 1990.0f, -98.0f, 1.22f},
+ { -8525.0f, 1994.0f, -98.0f, 2.12f},
+};
+
+//Kick out position
+const Position KickPos = { -8545.0f, 1984.0f, -96.0f};
+
+struct eye_of_cthunAI : public Scripted_NoMovementAI
+{
+ eye_of_cthunAI(Creature *c) : Scripted_NoMovementAI(c)
+ {
+ pInst = c->GetInstanceData();
+ if (!pInst)
+ error_log("TSCR: No Instance eye_of_cthunAI");
+ }
+
+ ScriptedInstance* pInst;
+
+ //Global variables
+ uint32 PhaseTimer;
+
+ //Eye beam phase
+ uint32 BeamTimer;
+ uint32 EyeTentacleTimer;
+ uint32 ClawTentacleTimer;
+
+ //Dark Glare phase
+ uint32 DarkGlareTick;
+ uint32 DarkGlareTickTimer;
+ float DarkGlareAngle;
+ bool ClockWise;
+
+ void Reset()
+ {
+ //Phase information
+ PhaseTimer = 50000; //First dark glare in 50 seconds
+
+ //Eye beam phase 50 seconds
+ BeamTimer = 3000;
+ EyeTentacleTimer = 45000; //Always spawns 5 seconds before Dark Beam
+ ClawTentacleTimer = 12500; //4 per Eye beam phase (unsure if they spawn during Dark beam)
+
+ //Dark Beam phase 35 seconds (each tick = 1 second, 35 ticks)
+ DarkGlareTick = 0;
+ DarkGlareTickTimer = 1000;
+ DarkGlareAngle = 0;
+ ClockWise = false;
+
+ //Reset flags
+ me->RemoveAurasDueToSpell(SPELL_RED_COLORATION);
+ me->RemoveAurasDueToSpell(SPELL_FREEZE_ANIM);
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE | UNIT_FLAG_NON_ATTACKABLE);
+ me->SetVisibility(VISIBILITY_ON);
+
+ //Reset Phase
+ if (pInst)
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_NOT_STARTED);
+
+ //to avoid having a following void zone
+ Creature* pPortal= me->FindNearestCreature(MOB_CTHUN_PORTAL, 10);
+ if (pPortal)
+ pPortal->SetReactState(REACT_PASSIVE);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoZoneInCombat();
+ if (pInst)
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_EYE_GREEN_BEAM);
+ }
+
+ void SpawnEyeTentacle(float x, float y)
+ {
+ if (Creature* Spawned = DoSpawnCreature(MOB_EYE_TENTACLE, x, y, 0, 0, TEMPSUMMON_CORPSE_DESPAWN, 500))
+ if (Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0))
+ if (Spawned->AI())
+ Spawned->AI()->AttackStart(pTarget);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Check if we have a target
+ if (!UpdateVictim())
+ return;
+
+ //No instance
+ if (!pInst)
+ return;
+
+ uint32 currentPhase = pInst->GetData(DATA_CTHUN_PHASE);
+ if (currentPhase == PHASE_EYE_GREEN_BEAM || currentPhase == PHASE_EYE_RED_BEAM)
+ {
+ // EyeTentacleTimer
+ if (EyeTentacleTimer <= diff)
+ {
+ //Spawn the 8 Eye Tentacles in the corret spots
+ SpawnEyeTentacle(0, 20); //south
+ SpawnEyeTentacle(10, 10); //south west
+ SpawnEyeTentacle(20, 0); //west
+ SpawnEyeTentacle(10, -10); //north west
+
+ SpawnEyeTentacle(0, -20); //north
+ SpawnEyeTentacle(-10, -10); //north east
+ SpawnEyeTentacle(-20, 0); // east
+ SpawnEyeTentacle(-10, 10); // south east
+
+ EyeTentacleTimer = 45000;
+ } else EyeTentacleTimer -= diff;
+ }
+
+ switch (currentPhase)
+ {
+ case PHASE_EYE_GREEN_BEAM:
+ //BeamTimer
+ if (BeamTimer <= diff)
+ {
+ //SPELL_GREEN_BEAM
+ if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM,0))
+ {
+ me->InterruptNonMeleeSpells(false);
+ DoCast(pTarget, SPELL_GREEN_BEAM);
+
+ //Correctly update our target
+ me->SetUInt64Value(UNIT_FIELD_TARGET, pTarget->GetGUID());
+ }
+
+ //Beam every 3 seconds
+ BeamTimer = 3000;
+ } else BeamTimer -= diff;
+
+ //ClawTentacleTimer
+ if (ClawTentacleTimer <= diff)
+ {
+ if (Unit* pTarget = SelectUnit(SELECT_TARGET_RANDOM,0))
+ {
+ Creature* Spawned = NULL;
+
+ //Spawn claw tentacle on the random target
+ Spawned = me->SummonCreature(MOB_CLAW_TENTACLE, *pTarget, TEMPSUMMON_CORPSE_DESPAWN, 500);
+
+ if (Spawned && Spawned->AI())
+ Spawned->AI()->AttackStart(pTarget);
+ }
+
+ //One claw tentacle every 12.5 seconds
+ ClawTentacleTimer = 12500;
+ } else ClawTentacleTimer -= diff;
+
+ //PhaseTimer
+ if (PhaseTimer <= diff)
+ {
+ //Switch to Dark Beam
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_EYE_RED_BEAM);
+
+ me->InterruptNonMeleeSpells(false);
+ me->SetReactState(REACT_PASSIVE);
+
+ //Remove any target
+ me->SetUInt64Value(UNIT_FIELD_TARGET, 0);
+
+ //Select random target for dark beam to start on
+ if (Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0))
+ {
+ //Face our target
+ DarkGlareAngle = me->GetAngle(pTarget);
+ DarkGlareTickTimer = 1000;
+ DarkGlareTick = 0;
+ ClockWise = RAND(true, false);
+ }
+
+ //Add red coloration to C'thun
+ DoCast(me, SPELL_RED_COLORATION, true);
+
+ //Freeze animation
+ DoCast(me, SPELL_FREEZE_ANIM);
+ me->SetOrientation(DarkGlareAngle);
+ me->StopMoving();
+
+ //Darkbeam for 35 seconds
+ PhaseTimer = 35000;
+ } else PhaseTimer -= diff;
+
+ break;
+
+ case PHASE_EYE_RED_BEAM:
+ if (DarkGlareTick < 35)
+ if (DarkGlareTickTimer <= diff)
+ {
+ //Set angle and cast
+ if (ClockWise)
+ me->SetOrientation(DarkGlareAngle + ((float)DarkGlareTick*PI/35));
+ else
+ me->SetOrientation(DarkGlareAngle - ((float)DarkGlareTick*PI/35));
+
+ me->StopMoving();
+
+ //Actual dark glare cast, maybe something missing here?
+ DoCast(me, SPELL_DARK_GLARE, false);
+
+ //Increase tick
+ ++DarkGlareTick;
+
+ //1 second per tick
+ DarkGlareTickTimer = 1000;
+ } else DarkGlareTickTimer -= diff;
+
+ //PhaseTimer
+ if (PhaseTimer <= diff)
+ {
+ //Switch to Eye Beam
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_EYE_GREEN_BEAM);
+
+ BeamTimer = 3000;
+ ClawTentacleTimer = 12500; //4 per Eye beam phase (unsure if they spawn during Dark beam)
+
+ me->InterruptNonMeleeSpells(false);
+
+ //Remove Red coloration from c'thun
+ me->RemoveAurasDueToSpell(SPELL_RED_COLORATION);
+ me->RemoveAurasDueToSpell(SPELL_FREEZE_ANIM);
+
+ //set it back to aggressive
+ me->SetReactState(REACT_AGGRESSIVE);
+
+ //Eye Beam for 50 seconds
+ PhaseTimer = 50000;
+ } else PhaseTimer -= diff;
+
+ break;
+
+ //Transition phase
+ case PHASE_CTHUN_TRANSITION:
+ //Remove any target
+ me->SetUInt64Value(UNIT_FIELD_TARGET, 0);
+ me->SetHealth(0);
+ me->SetVisibility(VISIBILITY_OFF);
+ break;
+
+ //Dead phase
+ case PHASE_CTHUN_DONE:
+ Creature* pPortal= me->FindNearestCreature(MOB_CTHUN_PORTAL, 10);
+ if (pPortal)
+ pPortal->ForcedDespawn();
+
+ me->ForcedDespawn();
+ break;
+ }
+ }
+
+ void DamageTaken(Unit * /*done_by*/, uint32 &damage)
+ {
+ //No instance
+ if (!pInst)
+ return;
+
+ switch (pInst->GetData(DATA_CTHUN_PHASE))
+ {
+ case PHASE_EYE_GREEN_BEAM:
+ case PHASE_EYE_RED_BEAM:
+ //Only if it will kill
+ if (damage < me->GetHealth())
+ return;
+
+ //Fake death in phase 0 or 1 (green beam or dark glare phase)
+ me->InterruptNonMeleeSpells(false);
+
+ //Remove Red coloration from c'thun
+ me->RemoveAurasDueToSpell(SPELL_RED_COLORATION);
+
+ //Reset to normal emote state and prevent select and attack
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE | UNIT_FLAG_NON_ATTACKABLE);
+
+ //Remove Target field
+ me->SetUInt64Value(UNIT_FIELD_TARGET, 0);
+
+ //Death animation/respawning;
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_CTHUN_TRANSITION);
+
+ me->SetHealth(0);
+ damage = 0;
+
+ me->InterruptNonMeleeSpells(true);
+ me->RemoveAllAuras();
+ break;
+
+ case PHASE_CTHUN_DONE:
+ //Allow death here
+ return;
+
+ default:
+ //Prevent death in these phases
+ damage = 0;
+ return;
+ }
+ }
+};
+
+struct cthunAI : public Scripted_NoMovementAI
+{
+ cthunAI(Creature *c) : Scripted_NoMovementAI(c)
+ {
+ SetCombatMovement(false);
+
+ pInst = c->GetInstanceData();
+ if (!pInst)
+ error_log("TSCR: No Instance eye_of_cthunAI");
+ }
+
+ ScriptedInstance* pInst;
+
+ //Out of combat whisper timer
+ uint32 WisperTimer;
+
+ //Global variables
+ uint32 PhaseTimer;
+
+ //-------------------
+
+ //Phase transition
+ uint64 HoldPlayer;
+
+ //Body Phase
+ uint32 EyeTentacleTimer;
+ uint8 FleshTentaclesKilled;
+ uint32 GiantClawTentacleTimer;
+ uint32 GiantEyeTentacleTimer;
+ uint32 StomachAcidTimer;
+ uint32 StomachEnterTimer;
+ uint32 StomachEnterVisTimer;
+ uint64 StomachEnterTarget;
+
+ //Stomach map, bool = true then in stomach
+ UNORDERED_MAP<uint64, bool> Stomach_Map;
+
+ void Reset()
+ {
+ //One random wisper every 90 - 300 seconds
+ WisperTimer = 90000;
+
+ //Phase information
+ PhaseTimer = 10000; //Emerge in 10 seconds
+
+ //No hold player for transition
+ HoldPlayer = 0;
+
+ //Body Phase
+ EyeTentacleTimer = 30000;
+ FleshTentaclesKilled = 0;
+ GiantClawTentacleTimer = 15000; //15 seconds into body phase (1 min repeat)
+ GiantEyeTentacleTimer = 45000; //15 seconds into body phase (1 min repeat)
+ StomachAcidTimer = 4000; //Every 4 seconds
+ StomachEnterTimer = 10000; //Every 10 seconds
+ StomachEnterVisTimer = 0; //Always 3.5 seconds after Stomach Enter Timer
+ StomachEnterTarget = 0; //Target to be teleported to stomach
+
+ //Clear players in stomach and outside
+ Stomach_Map.clear();
+
+ //Reset flags
+ me->RemoveAurasDueToSpell(SPELL_TRANSFORM);
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE | UNIT_FLAG_NON_ATTACKABLE);
+ me->SetVisibility(VISIBILITY_OFF);
+
+ if (pInst)
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_NOT_STARTED);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoZoneInCombat();
+ }
+
+ void SpawnEyeTentacle(float x, float y)
+ {
+ Creature* Spawned;
+ Spawned = DoSpawnCreature(MOB_EYE_TENTACLE, x, y, 0, 0, TEMPSUMMON_CORPSE_DESPAWN, 500);
+ if (Spawned && Spawned->AI())
+ if (Unit *pTarget = SelectRandomNotStomach())
+ Spawned->AI()->AttackStart(pTarget);
+ }
+
+ Unit* SelectRandomNotStomach()
+ {
+ if (Stomach_Map.empty())
+ return NULL;
+
+ UNORDERED_MAP<uint64, bool>::const_iterator i = Stomach_Map.begin();
+
+ std::list<Unit*> temp;
+ std::list<Unit*>::const_iterator j;
+
+ //Get all players in map
+ while (i != Stomach_Map.end())
+ {
+ //Check for valid player
+ Unit* pUnit = Unit::GetUnit(*me, i->first);
+
+ //Only units out of stomach
+ if (pUnit && i->second == false)
+ temp.push_back(pUnit);
+
+ ++i;
+ }
+
+ if (temp.empty())
+ return NULL;
+
+ j = temp.begin();
+
+ //Get random but only if we have more than one unit on threat list
+ if (temp.size() > 1)
+ advance (j , rand() % (temp.size() - 1));
+
+ return (*j);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Check if we have a target
+ if (!UpdateVictim())
+ {
+ //No target so we'll use this section to do our random wispers instance wide
+ //WisperTimer
+ if (WisperTimer <= diff)
+ {
+ Map* pMap = me->GetMap();
+ if (!pMap->IsDungeon()) return;
+
+ //Play random sound to the zone
+ Map::PlayerList const &PlayerList = pMap->GetPlayers();
+
+ if (!PlayerList.isEmpty())
+ {
+ for (Map::PlayerList::const_iterator itr = PlayerList.begin(); itr != PlayerList.end(); ++itr)
+ {
+ if (Player* pPlr = itr->getSource())
+ pPlr->PlayDirectSound(RANDOM_SOUND_WHISPER,pPlr);
+ }
+ }
+
+ //One random wisper every 90 - 300 seconds
+ WisperTimer = urand(90000,300000);
+ } else WisperTimer -= diff;
+
+ return;
+ }
+
+ me->SetUInt64Value(UNIT_FIELD_TARGET, 0);
+
+ //No instance
+ if (!pInst)
+ return;
+
+ uint32 currentPhase = pInst->GetData(DATA_CTHUN_PHASE);
+ if (currentPhase == PHASE_CTHUN_STOMACH || currentPhase == PHASE_CTHUN_WEAK)
+ {
+ // EyeTentacleTimer
+ if (EyeTentacleTimer <= diff)
+ {
+ //Spawn the 8 Eye Tentacles in the corret spots
+ SpawnEyeTentacle(0, 20); //south
+ SpawnEyeTentacle(10, 10); //south west
+ SpawnEyeTentacle(20, 0); //west
+ SpawnEyeTentacle(10, -10); //north west
+
+ SpawnEyeTentacle(0, -20); //north
+ SpawnEyeTentacle(-10, -10); //north east
+ SpawnEyeTentacle(-20, 0); // east
+ SpawnEyeTentacle(-10, 10); // south east
+
+ EyeTentacleTimer = 30000; // every 30sec in phase 2
+ } else EyeTentacleTimer -= diff;
+ }
+
+ switch (currentPhase)
+ {
+ //Transition phase
+ case PHASE_CTHUN_TRANSITION:
+ //PhaseTimer
+ if (PhaseTimer <= diff)
+ {
+ //Switch
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_CTHUN_STOMACH);
+
+ //Switch to c'thun model
+ me->InterruptNonMeleeSpells(false);
+ DoCast(me, SPELL_TRANSFORM, false);
+ me->SetHealth(me->GetMaxHealth());
+
+ me->SetVisibility(VISIBILITY_ON);
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE | UNIT_FLAG_NON_ATTACKABLE);
+
+ //Emerging phase
+ //AttackStart(Unit::GetUnit(*me, HoldpPlayer));
+ DoZoneInCombat();
+
+ //Place all units in threat list on outside of stomach
+ Stomach_Map.clear();
+
+ std::list<HostileReference*>::const_iterator i = me->getThreatManager().getThreatList().begin();
+ for (; i != me->getThreatManager().getThreatList().end(); ++i)
+ {
+ //Outside stomach
+ Stomach_Map[(*i)->getUnitGuid()] = false;
+ }
+
+ //Spawn 2 flesh tentacles
+ FleshTentaclesKilled = 0;
+
+ //Spawn flesh tentacle
+ for (uint8 i = 0; i < 2; i++)
+ {
+ Creature* spawned = me->SummonCreature(MOB_FLESH_TENTACLE, FleshTentaclePos[i], TEMPSUMMON_CORPSE_DESPAWN);
+ if (!spawned)
+ ++FleshTentaclesKilled;
+ }
+
+ PhaseTimer = 0;
+ } else PhaseTimer -= diff;
+
+ break;
+
+ //Body Phase
+ case PHASE_CTHUN_STOMACH:
+ //Remove Target field
+ me->SetUInt64Value(UNIT_FIELD_TARGET, 0);
+
+ //Weaken
+ if (FleshTentaclesKilled > 1)
+ {
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_CTHUN_WEAK);
+
+ DoScriptText(EMOTE_WEAKENED, me);
+ PhaseTimer = 45000;
+
+ DoCast(me, SPELL_PURPLE_COLORATION, true);
+
+ UNORDERED_MAP<uint64, bool>::iterator i = Stomach_Map.begin();
+
+ //Kick all players out of stomach
+ while (i != Stomach_Map.end())
+ {
+ //Check for valid player
+ Unit* pUnit = Unit::GetUnit(*me, i->first);
+
+ //Only move units in stomach
+ if (pUnit && i->second == true)
+ {
+ //Teleport each player out
+ DoTeleportPlayer(pUnit, me->GetPositionX(), me->GetPositionY(), me->GetPositionZ()+10, rand()%6);
+
+ //Cast knockback on them
+ DoCast(pUnit, SPELL_EXIT_STOMACH_KNOCKBACK, true);
+
+ //Remove the acid debuff
+ pUnit->RemoveAurasDueToSpell(SPELL_DIGESTIVE_ACID);
+
+ i->second = false;
+ }
+ ++i;
+ }
+
+ return;
+ }
+
+ //Stomach acid
+ if (StomachAcidTimer <= diff)
+ {
+ //Apply aura to all players in stomach
+ UNORDERED_MAP<uint64, bool>::iterator i = Stomach_Map.begin();
+
+ while (i != Stomach_Map.end())
+ {
+ //Check for valid player
+ Unit* pUnit = Unit::GetUnit(*me, i->first);
+
+ //Only apply to units in stomach
+ if (pUnit && i->second == true)
+ {
+ //Cast digestive acid on them
+ DoCast(pUnit, SPELL_DIGESTIVE_ACID, true);
+
+ //Check if player should be kicked from stomach
+ if (pUnit->IsWithinDist3d(&KickPos, 15.0f))
+ {
+ //Teleport each player out
+ DoTeleportPlayer(pUnit, me->GetPositionX(), me->GetPositionY(), me->GetPositionZ()+10, rand()%6);
+
+ //Cast knockback on them
+ DoCast(pUnit, SPELL_EXIT_STOMACH_KNOCKBACK, true);
+
+ //Remove the acid debuff
+ pUnit->RemoveAurasDueToSpell(SPELL_DIGESTIVE_ACID);
+
+ i->second = false;
+ }
+ }
+ ++i;
+ }
+
+ StomachAcidTimer = 4000;
+ } else StomachAcidTimer -= diff;
+
+ //Stomach Enter Timer
+ if (StomachEnterTimer <= diff)
+ {
+ if (Unit *pTarget = SelectRandomNotStomach())
+ {
+ //Set target in stomach
+ Stomach_Map[pTarget->GetGUID()] = true;
+ pTarget->InterruptNonMeleeSpells(false);
+ pTarget->CastSpell(pTarget, SPELL_MOUTH_TENTACLE, true, NULL, NULL, me->GetGUID());
+ StomachEnterTarget = pTarget->GetGUID();
+ StomachEnterVisTimer = 3800;
+ }
+
+ StomachEnterTimer = 13800;
+ } else StomachEnterTimer -= diff;
+
+ if (StomachEnterVisTimer && StomachEnterTarget)
+ if (StomachEnterVisTimer <= diff)
+ {
+ //Check for valid player
+ Unit* pUnit = Unit::GetUnit(*me, StomachEnterTarget);
+
+ if (pUnit)
+ {
+ DoTeleportPlayer(pUnit, STOMACH_X, STOMACH_Y, STOMACH_Z, STOMACH_O);
+ }
+
+ StomachEnterTarget = 0;
+ StomachEnterVisTimer = 0;
+ } else StomachEnterVisTimer -= diff;
+
+ //GientClawTentacleTimer
+ if (GiantClawTentacleTimer <= diff)
+ {
+ if (Unit *pTarget = SelectRandomNotStomach())
+ {
+ //Spawn claw tentacle on the random target
+ if (Creature* spawned = me->SummonCreature(MOB_GIANT_CLAW_TENTACLE, *pTarget, TEMPSUMMON_CORPSE_DESPAWN, 500))
+ if (spawned->AI())
+ spawned->AI()->AttackStart(pTarget);
+ }
+
+ //One giant claw tentacle every minute
+ GiantClawTentacleTimer = 60000;
+ } else GiantClawTentacleTimer -= diff;
+
+ //GiantEyeTentacleTimer
+ if (GiantEyeTentacleTimer <= diff)
+ {
+ if (Unit *pTarget = SelectRandomNotStomach())
+ {
+ //Spawn claw tentacle on the random target
+ if (Creature* spawned = me->SummonCreature(MOB_GIANT_EYE_TENTACLE, *pTarget, TEMPSUMMON_CORPSE_DESPAWN, 500))
+ if (spawned->AI())
+ spawned->AI()->AttackStart(pTarget);
+ }
+
+ //One giant eye tentacle every minute
+ GiantEyeTentacleTimer = 60000;
+ } else GiantEyeTentacleTimer -= diff;
+
+ break;
+
+ //Weakened state
+ case PHASE_CTHUN_WEAK:
+ //PhaseTimer
+ if (PhaseTimer <= diff)
+ {
+ //Switch
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_CTHUN_STOMACH);
+
+ //Remove purple coloration
+ me->RemoveAurasDueToSpell(SPELL_PURPLE_COLORATION);
+
+ //Spawn 2 flesh tentacles
+ FleshTentaclesKilled = 0;
+
+ //Spawn flesh tentacle
+ for (uint8 i = 0; i < 2; i++)
+ {
+ Creature* spawned = me->SummonCreature(MOB_FLESH_TENTACLE, FleshTentaclePos[i], TEMPSUMMON_CORPSE_DESPAWN);
+ if (!spawned)
+ ++FleshTentaclesKilled;
+ }
+
+ PhaseTimer = 0;
+ } else PhaseTimer -= diff;
+
+ break;
+ }
+ }
+
+ void JustDied(Unit* /*pKiller*/)
+ {
+ if (pInst)
+ pInst->SetData(DATA_CTHUN_PHASE, PHASE_CTHUN_DONE);
+ }
+
+ void DamageTaken(Unit * /*done_by*/, uint32 &damage)
+ {
+ //No instance
+ if (!pInst)
+ return;
+
+ switch (pInst->GetData(DATA_CTHUN_PHASE))
+ {
+ case PHASE_CTHUN_STOMACH:
+ //Not weakened so reduce damage by 99%
+ damage /= 100;
+ if (damage == 0)
+ damage = 1;
+
+ //Prevent death in non-weakened state
+ if (damage >= me->GetHealth())
+ damage = 0;
+
+ return;
+
+ case PHASE_CTHUN_WEAK:
+ //Weakened - takes normal damage
+ return;
+
+ default:
+ damage = 0;
+ break;
+ }
+ }
+
+ void DoAction(const int32 param)
+ {
+ switch(param)
+ {
+ case ACTION_FLESH_TENTACLE_KILLED:
+ ++FleshTentaclesKilled;
+ break;
+ }
+ }
+};
+
+struct eye_tentacleAI : public Scripted_NoMovementAI
+{
+ eye_tentacleAI(Creature *c) : Scripted_NoMovementAI(c)
+ {
+ if (Creature* pPortal = me->SummonCreature(MOB_SMALL_PORTAL, *me, TEMPSUMMON_CORPSE_DESPAWN))
+ {
+ pPortal->SetReactState(REACT_PASSIVE);
+ Portal = pPortal->GetGUID();
+ }
+ }
+
+ uint32 MindflayTimer;
+ uint32 KillSelfTimer;
+ uint64 Portal;
+
+ void JustDied(Unit* /*who*/)
+ {
+ if (Unit* p = Unit::GetUnit(*me, Portal))
+ p->Kill(p);
+ }
+
+ void Reset()
+ {
+ //Mind flay half a second after we spawn
+ MindflayTimer = 500;
+
+ //This prevents eyes from overlapping
+ KillSelfTimer = 35000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoZoneInCombat();
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Check if we have a target
+ if (!UpdateVictim())
+ return;
+
+ //KillSelfTimer
+ if (KillSelfTimer <= diff)
+ {
+ me->Kill(me);
+ return;
+ } else KillSelfTimer -= diff;
+
+ //MindflayTimer
+ if (MindflayTimer <= diff)
+ {
+ Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+ if (pTarget && !pTarget->HasAura(SPELL_DIGESTIVE_ACID))
+ DoCast(pTarget, SPELL_MIND_FLAY);
+
+ //Mindflay every 10 seconds
+ MindflayTimer = 10000;
+ } else MindflayTimer -= diff;
+ }
+};
+
+struct claw_tentacleAI : public Scripted_NoMovementAI
+{
+ claw_tentacleAI(Creature *c) : Scripted_NoMovementAI(c)
+ {
+ SetCombatMovement(false);
+
+ if (Creature* pPortal = me->SummonCreature(MOB_SMALL_PORTAL, *me, TEMPSUMMON_CORPSE_DESPAWN))
+ {
+ pPortal->SetReactState(REACT_PASSIVE);
+ Portal = pPortal->GetGUID();
+ }
+ }
+
+ uint32 GroundRuptureTimer;
+ uint32 HamstringTimer;
+ uint32 EvadeTimer;
+ uint64 Portal;
+
+ void JustDied(Unit* /*who*/)
+ {
+ if (Unit* p = Unit::GetUnit(*me, Portal))
+ p->Kill(p);
+ }
+
+ void Reset()
+ {
+ //First rupture should happen half a second after we spawn
+ GroundRuptureTimer = 500;
+ HamstringTimer = 2000;
+ EvadeTimer = 5000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoZoneInCombat();
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Check if we have a target
+ if (!UpdateVictim())
+ return;
+
+ //EvadeTimer
+ if (!me->IsWithinMeleeRange(me->getVictim()))
+ if (EvadeTimer <= diff)
+ {
+ if (Unit* p = Unit::GetUnit(*me, Portal))
+ p->Kill(p);
+
+ //Dissapear and reappear at new position
+ me->SetVisibility(VISIBILITY_OFF);
+
+ Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+ if (!pTarget)
+ {
+ me->Kill(me);
+ return;
+ }
+
+ if (!pTarget->HasAura(SPELL_DIGESTIVE_ACID))
+ {
+ me->GetMap()->CreatureRelocation(me, pTarget->GetPositionX(), pTarget->GetPositionY(), pTarget->GetPositionZ(), 0);
+ if (Creature* pPortal = me->SummonCreature(MOB_SMALL_PORTAL, *me, TEMPSUMMON_CORPSE_DESPAWN))
+ {
+ pPortal->SetReactState(REACT_PASSIVE);
+ Portal = pPortal->GetGUID();
+ }
+
+ GroundRuptureTimer = 500;
+ HamstringTimer = 2000;
+ EvadeTimer = 5000;
+ AttackStart(pTarget);
+ }
+
+ me->SetVisibility(VISIBILITY_ON);
+ } else EvadeTimer -= diff;
+
+ //GroundRuptureTimer
+ if (GroundRuptureTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_GROUND_RUPTURE);
+ GroundRuptureTimer = 30000;
+ } else GroundRuptureTimer -= diff;
+
+ //HamstringTimer
+ if (HamstringTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_HAMSTRING);
+ HamstringTimer = 5000;
+ } else HamstringTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+struct giant_claw_tentacleAI : public Scripted_NoMovementAI
+{
+ giant_claw_tentacleAI(Creature *c) : Scripted_NoMovementAI(c)
+ {
+ SetCombatMovement(false);
+
+ if (Creature* pPortal = me->SummonCreature(MOB_GIANT_PORTAL, *me, TEMPSUMMON_CORPSE_DESPAWN))
+ {
+ pPortal->SetReactState(REACT_PASSIVE);
+ Portal = pPortal->GetGUID();
+ }
+ }
+
+ uint32 GroundRuptureTimer;
+ uint32 ThrashTimer;
+ uint32 HamstringTimer;
+ uint32 EvadeTimer;
+ uint64 Portal;
+
+ void JustDied(Unit* /*who*/)
+ {
+ if (Unit* p = Unit::GetUnit(*me, Portal))
+ p->Kill(p);
+ }
+
+ void Reset()
+ {
+ //First rupture should happen half a second after we spawn
+ GroundRuptureTimer = 500;
+ HamstringTimer = 2000;
+ ThrashTimer = 5000;
+ EvadeTimer = 5000;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoZoneInCombat();
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Check if we have a target
+ if (!UpdateVictim())
+ return;
+
+ //EvadeTimer
+ if (!me->IsWithinMeleeRange(me->getVictim()))
+ if (EvadeTimer <= diff)
+ {
+ if (Unit* p = Unit::GetUnit(*me, Portal))
+ p->Kill(p);
+
+ //Dissapear and reappear at new position
+ me->SetVisibility(VISIBILITY_OFF);
+
+ Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM, 0);
+ if (!pTarget)
+ {
+ me->Kill(me);
+ return;
+ }
+
+ if (!pTarget->HasAura(SPELL_DIGESTIVE_ACID))
+ {
+ me->GetMap()->CreatureRelocation(me, pTarget->GetPositionX(), pTarget->GetPositionY(), pTarget->GetPositionZ(), 0);
+ if (Creature* pPortal = me->SummonCreature(MOB_GIANT_PORTAL, *me, TEMPSUMMON_CORPSE_DESPAWN))
+ {
+ pPortal->SetReactState(REACT_PASSIVE);
+ Portal = pPortal->GetGUID();
+ }
+
+ GroundRuptureTimer = 500;
+ HamstringTimer = 2000;
+ ThrashTimer = 5000;
+ EvadeTimer = 5000;
+ AttackStart(pTarget);
+ }
+
+ me->SetVisibility(VISIBILITY_ON);
+
+ } else EvadeTimer -= diff;
+
+ //GroundRuptureTimer
+ if (GroundRuptureTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_GROUND_RUPTURE);
+ GroundRuptureTimer = 30000;
+ } else GroundRuptureTimer -= diff;
+
+ //ThrashTimer
+ if (ThrashTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_THRASH);
+ ThrashTimer = 10000;
+ } else ThrashTimer -= diff;
+
+ //HamstringTimer
+ if (HamstringTimer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_HAMSTRING);
+ HamstringTimer = 10000;
+ } else HamstringTimer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+struct giant_eye_tentacleAI : public Scripted_NoMovementAI
+{
+ giant_eye_tentacleAI(Creature *c) : Scripted_NoMovementAI(c)
+ {
+ SetCombatMovement(false);
+
+ if (Creature* pPortal = me->SummonCreature(MOB_GIANT_PORTAL, *me, TEMPSUMMON_CORPSE_DESPAWN))
+ {
+ pPortal->SetReactState(REACT_PASSIVE);
+ Portal = pPortal->GetGUID();
+ }
+ }
+
+ uint32 BeamTimer;
+ uint64 Portal;
+
+ void JustDied(Unit* /*who*/)
+ {
+ if (Unit* p = Unit::GetUnit(*me, Portal))
+ p->Kill(p);
+ }
+
+ void Reset()
+ {
+ //Green Beam half a second after we spawn
+ BeamTimer = 500;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoZoneInCombat();
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Check if we have a target
+ if (!UpdateVictim())
+ return;
+
+ //BeamTimer
+ if (BeamTimer <= diff)
+ {
+ Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+ if (pTarget && !pTarget->HasAura(SPELL_DIGESTIVE_ACID))
+ DoCast(pTarget, SPELL_GREEN_BEAM);
+
+ //Beam every 2 seconds
+ BeamTimer = 2100;
+ } else BeamTimer -= diff;
+ }
+};
+
+struct flesh_tentacleAI : public Scripted_NoMovementAI
+{
+ flesh_tentacleAI(Creature *c) : Scripted_NoMovementAI(c)
+ {
+ SetCombatMovement(false);
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ if (CAST_SUM(me))
+ if (Creature* pSummoner = CAST_CRE(CAST_SUM(me)->GetSummoner()))
+ if (pSummoner->AI())
+ pSummoner->AI()->DoAction(ACTION_FLESH_TENTACLE_KILLED);
+ }
+};
+
+//GetAIs
+CreatureAI* GetAI_eye_of_cthun(Creature* pCreature)
+{
+ return new eye_of_cthunAI (pCreature);
+}
+
+CreatureAI* GetAI_cthun(Creature* pCreature)
+{
+ return new cthunAI (pCreature);
+}
+
+CreatureAI* GetAI_eye_tentacle(Creature* pCreature)
+{
+ return new eye_tentacleAI (pCreature);
+}
+
+CreatureAI* GetAI_claw_tentacle(Creature* pCreature)
+{
+ return new claw_tentacleAI (pCreature);
+}
+
+CreatureAI* GetAI_giant_claw_tentacle(Creature* pCreature)
+{
+ return new giant_claw_tentacleAI (pCreature);
+}
+
+CreatureAI* GetAI_giant_eye_tentacle(Creature* pCreature)
+{
+ return new giant_eye_tentacleAI (pCreature);
+}
+
+CreatureAI* GetAI_flesh_tentacle(Creature* pCreature)
+{
+ return new flesh_tentacleAI (pCreature);
+}
+
+void AddSC_boss_cthun()
+{
+ Script *newscript;
+
+ //Eye
+ newscript = new Script;
+ newscript->Name = "boss_eye_of_cthun";
+ newscript->GetAI = &GetAI_eye_of_cthun;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "boss_cthun";
+ newscript->GetAI = &GetAI_cthun;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_eye_tentacle";
+ newscript->GetAI = &GetAI_eye_tentacle;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_claw_tentacle";
+ newscript->GetAI = &GetAI_claw_tentacle;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_giant_claw_tentacle";
+ newscript->GetAI = &GetAI_giant_claw_tentacle;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_giant_eye_tentacle";
+ newscript->GetAI = &GetAI_giant_eye_tentacle;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_giant_flesh_tentacle";
+ newscript->GetAI = &GetAI_flesh_tentacle;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_fankriss.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_fankriss.cpp
new file mode 100644
index 00000000000..32d5ec1c3df
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_fankriss.cpp
@@ -0,0 +1,206 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Fankriss
+SD%Complete: 100
+SDComment: sound not implemented
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define SOUND_SENTENCE_YOU 8588
+#define SOUND_SERVE_TO 8589
+#define SOUND_LAWS 8590
+#define SOUND_TRESPASS 8591
+#define SOUND_WILL_BE 8592
+
+#define SPELL_MORTAL_WOUND 28467
+#define SPELL_ROOT 28858
+
+// Enrage for his spawns
+#define SPELL_ENRAGE 28798
+
+struct boss_fankrissAI : public ScriptedAI
+{
+ boss_fankrissAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 MortalWound_Timer;
+ uint32 SpawnHatchlings_Timer;
+ uint32 SpawnSpawns_Timer;
+ int Rand;
+ int RandX;
+ int RandY;
+
+ Creature* Hatchling;
+ Creature* Spawn;
+
+ void Reset()
+ {
+ MortalWound_Timer = 10000 + rand()%5000;
+ SpawnHatchlings_Timer = 6000 + rand()%6000;
+ SpawnSpawns_Timer = 15000 + rand()%30000;
+ }
+
+ void SummonSpawn(Unit* victim)
+ {
+ if (!victim)
+ return;
+
+ Rand = 10 + (rand()%10);
+ switch (rand()%2)
+ {
+ case 0: RandX = 0 - Rand; break;
+ case 1: RandX = 0 + Rand; break;
+ }
+ Rand = 0;
+ Rand = 10 + (rand()%10);
+ switch (rand()%2)
+ {
+ case 0: RandY = 0 - Rand; break;
+ case 1: RandY = 0 + Rand; break;
+ }
+ Rand = 0;
+ Spawn = DoSpawnCreature(15630, RandX, RandY, 0, 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 30000);
+ if (Spawn)
+ Spawn->AI()->AttackStart(victim);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //MortalWound_Timer
+ if (MortalWound_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_MORTAL_WOUND);
+ MortalWound_Timer = 10000 + rand()%10000;
+ } else MortalWound_Timer -= diff;
+
+ //Summon 1-3 Spawns of Fankriss at random time.
+ if (SpawnSpawns_Timer <= diff)
+ {
+ switch (urand(0,2))
+ {
+ case 0:
+ SummonSpawn(SelectUnit(SELECT_TARGET_RANDOM,0));
+ break;
+ case 1:
+ SummonSpawn(SelectUnit(SELECT_TARGET_RANDOM,0));
+ SummonSpawn(SelectUnit(SELECT_TARGET_RANDOM,0));
+ break;
+ case 2:
+ SummonSpawn(SelectUnit(SELECT_TARGET_RANDOM,0));
+ SummonSpawn(SelectUnit(SELECT_TARGET_RANDOM,0));
+ SummonSpawn(SelectUnit(SELECT_TARGET_RANDOM,0));
+ break;
+ }
+ SpawnSpawns_Timer = 30000 + rand()%30000;
+ } else SpawnSpawns_Timer -= diff;
+
+ // Teleporting Random Target to one of the three tunnels and spawn 4 hatchlings near the gamer.
+ //We will only telport if fankriss has more than 3% of hp so teleported gamers can always loot.
+ if (me->GetHealth()*100 / me->GetMaxHealth() > 3)
+ {
+ if (SpawnHatchlings_Timer <= diff)
+ {
+ Unit *pTarget = NULL;
+ pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+ if (pTarget && pTarget->GetTypeId() == TYPEID_PLAYER)
+ {
+ DoCast(pTarget, SPELL_ROOT);
+
+ if (DoGetThreat(pTarget))
+ DoModifyThreatPercent(pTarget, -100);
+
+ switch(urand(0,2))
+ {
+ case 0:
+ DoTeleportPlayer(pTarget, -8106.0142,1289.2900,-74.419533,5.112);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-3, pTarget->GetPositionY()-3, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-3, pTarget->GetPositionY()+3, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-5, pTarget->GetPositionY()-5, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-5, pTarget->GetPositionY()+5, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ break;
+ case 1:
+ DoTeleportPlayer(pTarget, -7990.135354,1155.1907,-78.849319,2.608);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-3, pTarget->GetPositionY()-3, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-3, pTarget->GetPositionY()+3, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-5, pTarget->GetPositionY()-5, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-5, pTarget->GetPositionY()+5, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ break;
+ case 2:
+ DoTeleportPlayer(pTarget,-8159.7753,1127.9064,-76.868660,0.675);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-3, pTarget->GetPositionY()-3, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-3, pTarget->GetPositionY()+3, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-5, pTarget->GetPositionY()-5, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ Hatchling = me->SummonCreature(15962, pTarget->GetPositionX()-5, pTarget->GetPositionY()+5, pTarget->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 15000);
+ if (Hatchling)
+ Hatchling->AI()->AttackStart(pTarget);
+ break;
+ }
+ }
+ SpawnHatchlings_Timer = 45000 + rand()%15000;
+ } else SpawnHatchlings_Timer -= diff;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_fankriss(Creature* pCreature)
+{
+ return new boss_fankrissAI (pCreature);
+}
+
+void AddSC_boss_fankriss()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_fankriss";
+ newscript->GetAI = &GetAI_boss_fankriss;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_huhuran.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_huhuran.cpp
new file mode 100644
index 00000000000..f0e3a425edd
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_huhuran.cpp
@@ -0,0 +1,148 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Huhuran
+SD%Complete: 100
+SDComment:
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define EMOTE_GENERIC_FRENZY_KILL -1000001
+#define EMOTE_GENERIC_BERSERK -1000004
+
+#define SPELL_FRENZY 26051
+#define SPELL_BERSERK 26068
+#define SPELL_POISONBOLT 26052
+#define SPELL_NOXIOUSPOISON 26053
+#define SPELL_WYVERNSTING 26180
+#define SPELL_ACIDSPIT 26050
+
+struct boss_huhuranAI : public ScriptedAI
+{
+ boss_huhuranAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 Frenzy_Timer;
+ uint32 Wyvern_Timer;
+ uint32 Spit_Timer;
+ uint32 PoisonBolt_Timer;
+ uint32 NoxiousPoison_Timer;
+ uint32 FrenzyBack_Timer;
+
+ bool Frenzy;
+ bool Berserk;
+
+ void Reset()
+ {
+ Frenzy_Timer = 25000 + rand()%10000;
+ Wyvern_Timer = 18000 + rand()%10000;
+ Spit_Timer = 8000;
+ PoisonBolt_Timer = 4000;
+ NoxiousPoison_Timer = 10000 + rand()%10000;
+ FrenzyBack_Timer = 15000;
+
+ Frenzy = false;
+ Berserk = false;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Frenzy_Timer
+ if (!Frenzy && Frenzy_Timer <= diff)
+ {
+ DoCast(me, SPELL_FRENZY);
+ DoScriptText(EMOTE_GENERIC_FRENZY_KILL, me);
+ Frenzy = true;
+ PoisonBolt_Timer = 3000;
+ Frenzy_Timer = 25000 + rand()%10000;
+ } else Frenzy_Timer -= diff;
+
+ // Wyvern Timer
+ if (Wyvern_Timer <= diff)
+ {
+ if (Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0))
+ DoCast(pTarget, SPELL_WYVERNSTING);
+ Wyvern_Timer = 15000 + rand()%17000;
+ } else Wyvern_Timer -= diff;
+
+ //Spit Timer
+ if (Spit_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_ACIDSPIT);
+ Spit_Timer = 5000 + rand()%5000;
+ } else Spit_Timer -= diff;
+
+ //NoxiousPoison_Timer
+ if (NoxiousPoison_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_NOXIOUSPOISON);
+ NoxiousPoison_Timer = 12000 + rand()%12000;
+ } else NoxiousPoison_Timer -= diff;
+
+ //PoisonBolt only if frenzy or berserk
+ if (Frenzy || Berserk)
+ {
+ if (PoisonBolt_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_POISONBOLT);
+ PoisonBolt_Timer = 3000;
+ } else PoisonBolt_Timer -= diff;
+ }
+
+ //FrenzyBack_Timer
+ if (Frenzy && FrenzyBack_Timer <= diff)
+ {
+ me->InterruptNonMeleeSpells(false);
+ Frenzy = false;
+ FrenzyBack_Timer = 15000;
+ } else FrenzyBack_Timer -= diff;
+
+ if (!Berserk && me->GetHealth()*100 / me->GetMaxHealth() < 31)
+ {
+ me->InterruptNonMeleeSpells(false);
+ DoScriptText(EMOTE_GENERIC_BERSERK, me);
+ DoCast(me, SPELL_BERSERK);
+ Berserk = true;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_huhuran(Creature* pCreature)
+{
+ return new boss_huhuranAI (pCreature);
+}
+
+void AddSC_boss_huhuran()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_huhuran";
+ newscript->GetAI = &GetAI_boss_huhuran;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_ouro.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_ouro.cpp
new file mode 100644
index 00000000000..1dd642c38f4
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_ouro.cpp
@@ -0,0 +1,140 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Ouro
+SD%Complete: 85
+SDComment: No model for submerging. Currently just invisible.
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "temple_of_ahnqiraj.h"
+
+#define SPELL_SWEEP 26103
+#define SPELL_SANDBLAST 26102
+#define SPELL_GROUND_RUPTURE 26100
+#define SPELL_BIRTH 26262 //The Birth Animation
+
+#define SPELL_DIRTMOUND_PASSIVE 26092
+
+struct boss_ouroAI : public ScriptedAI
+{
+ boss_ouroAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 Sweep_Timer;
+ uint32 SandBlast_Timer;
+ uint32 Submerge_Timer;
+ uint32 Back_Timer;
+ uint32 ChangeTarget_Timer;
+ uint32 Spawn_Timer;
+
+ bool Enrage;
+ bool Submerged;
+
+ void Reset()
+ {
+ Sweep_Timer = 5000 + rand()%5000;
+ SandBlast_Timer = 20000 + rand()%15000;
+ Submerge_Timer = 90000 + rand()%60000;
+ Back_Timer = 30000 + rand()%15000;
+ ChangeTarget_Timer = 5000 + rand()%3000;
+ Spawn_Timer = 10000 + rand()%10000;
+
+ Enrage = false;
+ Submerged = false;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoCast(me->getVictim(), SPELL_BIRTH);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //Sweep_Timer
+ if (!Submerged && Sweep_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_SWEEP);
+ Sweep_Timer = 15000 + rand()%15000;
+ } else Sweep_Timer -= diff;
+
+ //SandBlast_Timer
+ if (!Submerged && SandBlast_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_SANDBLAST);
+ SandBlast_Timer = 20000 + rand()%15000;
+ } else SandBlast_Timer -= diff;
+
+ //Submerge_Timer
+ if (!Submerged && Submerge_Timer <= diff)
+ {
+ //Cast
+ me->HandleEmoteCommand(EMOTE_ONESHOT_SUBMERGE);
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ me->setFaction(35);
+ DoCast(me, SPELL_DIRTMOUND_PASSIVE);
+
+ Submerged = true;
+ Back_Timer = 30000 + rand()%15000;
+ } else Submerge_Timer -= diff;
+
+ //ChangeTarget_Timer
+ if (Submerged && ChangeTarget_Timer <= diff)
+ {
+ Unit *pTarget = NULL;
+ pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+
+ if (pTarget)
+ DoTeleportTo(pTarget->GetPositionX(), pTarget->GetPositionY(), pTarget->GetPositionZ());
+
+ ChangeTarget_Timer = 10000 + rand()%10000;
+ } else ChangeTarget_Timer -= diff;
+
+ //Back_Timer
+ if (Submerged && Back_Timer <= diff)
+ {
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ me->setFaction(14);
+
+ DoCast(me->getVictim(), SPELL_GROUND_RUPTURE);
+
+ Submerged = false;
+ Submerge_Timer = 60000 + rand()%60000;
+ } else Back_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_ouro(Creature* pCreature)
+{
+ return new boss_ouroAI (pCreature);
+}
+
+void AddSC_boss_ouro()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_ouro";
+ newscript->GetAI = &GetAI_boss_ouro;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_sartura.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_sartura.cpp
new file mode 100644
index 00000000000..282a25b7215
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_sartura.cpp
@@ -0,0 +1,297 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Sartura
+SD%Complete: 95
+SDComment:
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define SAY_AGGRO -1531008
+#define SAY_SLAY -1531009
+#define SAY_DEATH -1531010
+
+#define SPELL_WHIRLWIND 26083
+#define SPELL_ENRAGE 28747 //Not sure if right ID.
+#define SPELL_ENRAGEHARD 28798
+
+//Guard Spell
+#define SPELL_WHIRLWINDADD 26038
+#define SPELL_KNOCKBACK 26027
+
+struct boss_sarturaAI : public ScriptedAI
+{
+ boss_sarturaAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 WhirlWind_Timer;
+ uint32 WhirlWindRandom_Timer;
+ uint32 WhirlWindEnd_Timer;
+ uint32 AggroReset_Timer;
+ uint32 AggroResetEnd_Timer;
+ uint32 EnrageHard_Timer;
+
+ bool Enraged;
+ bool EnragedHard;
+ bool WhirlWind;
+ bool AggroReset;
+
+ void Reset()
+ {
+ WhirlWind_Timer = 30000;
+ WhirlWindRandom_Timer = 3000 + rand()%4000;
+ WhirlWindEnd_Timer = 15000;
+ AggroReset_Timer = 45000 + rand()%10000;
+ AggroResetEnd_Timer = 5000;
+ EnrageHard_Timer = 10*60000;
+
+ WhirlWind = false;
+ AggroReset = false;
+ Enraged = false;
+ EnragedHard = false;
+
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ DoScriptText(SAY_AGGRO, me);
+ }
+
+ void JustDied(Unit* /*Killer*/)
+ {
+ DoScriptText(SAY_DEATH, me);
+ }
+
+ void KilledUnit(Unit* /*victim*/)
+ {
+ DoScriptText(SAY_SLAY, me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (WhirlWind)
+ {
+ if (WhirlWindRandom_Timer <= diff)
+ {
+ //Attack random Gamers
+ Unit *pTarget = NULL;
+ pTarget = SelectUnit(SELECT_TARGET_RANDOM,1);
+ if (pTarget)
+ me->AddThreat(pTarget, 1.0f);
+ me->TauntApply(pTarget);
+ AttackStart(pTarget);
+
+ WhirlWindRandom_Timer = 3000 + rand()%4000;
+ } else WhirlWindRandom_Timer -= diff;
+
+ if (WhirlWindEnd_Timer <= diff)
+ {
+ WhirlWind = false;
+ WhirlWind_Timer = 25000 + rand()%15000;
+ } else WhirlWindEnd_Timer -= diff;
+ }
+
+ if (!WhirlWind)
+ {
+ if (WhirlWind_Timer <= diff)
+ {
+ DoCast(me, SPELL_WHIRLWIND);
+ WhirlWind = true;
+ WhirlWindEnd_Timer = 15000;
+ } else WhirlWind_Timer -= diff;
+
+ if (AggroReset_Timer <= diff)
+ {
+ //Attack random Gamers
+ Unit *pTarget = NULL;
+ pTarget = SelectUnit(SELECT_TARGET_RANDOM,1);
+ if (pTarget)
+ me->AddThreat(pTarget, 1.0f);
+ me->TauntApply(pTarget);
+ AttackStart(pTarget);
+
+ AggroReset = true;
+ AggroReset_Timer = 2000 + rand()%3000;
+ } else AggroReset_Timer -= diff;
+
+ if (AggroReset)
+ {
+ if (AggroResetEnd_Timer <= diff)
+ {
+ AggroReset = false;
+ AggroResetEnd_Timer = 5000;
+ AggroReset_Timer = 35000 + rand()%10000;
+ } else AggroResetEnd_Timer -= diff;
+ }
+
+ //If she is 20% enrage
+ if (!Enraged)
+ {
+ if (me->GetHealth()*100 / me->GetMaxHealth() <= 20 && !me->IsNonMeleeSpellCasted(false))
+ {
+ DoCast(me, SPELL_ENRAGE);
+ Enraged = true;
+ }
+ }
+
+ //After 10 minutes hard enrage
+ if (!EnragedHard)
+ {
+ if (EnrageHard_Timer <= diff)
+ {
+ DoCast(me, SPELL_ENRAGEHARD);
+ EnragedHard = true;
+ } else EnrageHard_Timer -= diff;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+ }
+};
+
+struct mob_sartura_royal_guardAI : public ScriptedAI
+{
+ mob_sartura_royal_guardAI(Creature *c) : ScriptedAI(c) {}
+
+ uint32 WhirlWind_Timer;
+ uint32 WhirlWindRandom_Timer;
+ uint32 WhirlWindEnd_Timer;
+ uint32 AggroReset_Timer;
+ uint32 AggroResetEnd_Timer;
+ uint32 KnockBack_Timer;
+
+ bool WhirlWind;
+ bool AggroReset;
+
+ void Reset()
+ {
+ WhirlWind_Timer = 30000;
+ WhirlWindRandom_Timer = 3000 + rand()%4000;
+ WhirlWindEnd_Timer = 15000;
+ AggroReset_Timer = 45000 + rand()%10000;
+ AggroResetEnd_Timer = 5000;
+ KnockBack_Timer = 10000;
+
+ WhirlWind = false;
+ AggroReset = false;
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (!WhirlWind && WhirlWind_Timer <= diff)
+ {
+ DoCast(me, SPELL_WHIRLWINDADD);
+ WhirlWind = true;
+ WhirlWind_Timer = 25000 + rand()%15000;
+ WhirlWindEnd_Timer = 15000;
+ } else WhirlWind_Timer -= diff;
+
+ if (WhirlWind)
+ {
+ if (WhirlWindRandom_Timer <= diff)
+ {
+ //Attack random Gamers
+ Unit *pTarget = NULL;
+ pTarget = SelectUnit(SELECT_TARGET_RANDOM,1);
+ if (pTarget)
+ me->AddThreat(pTarget, 1.0f);
+ me->TauntApply(pTarget);
+ AttackStart(pTarget);
+
+ WhirlWindRandom_Timer = 3000 + rand()%4000;
+ } else WhirlWindRandom_Timer -= diff;
+
+ if (WhirlWindEnd_Timer <= diff)
+ {
+ WhirlWind = false;
+ } else WhirlWindEnd_Timer -= diff;
+ }
+
+ if (!WhirlWind)
+ {
+ if (AggroReset_Timer <= diff)
+ {
+ //Attack random Gamers
+ Unit *pTarget = NULL;
+ pTarget = SelectUnit(SELECT_TARGET_RANDOM,1);
+ if (pTarget)
+ me->AddThreat(pTarget, 1.0f);
+ me->TauntApply(pTarget);
+ AttackStart(pTarget);
+
+ AggroReset = true;
+ AggroReset_Timer = 2000 + rand()%3000;
+ } else AggroReset_Timer -= diff;
+
+ if (KnockBack_Timer <= diff)
+ {
+ DoCast(me, SPELL_WHIRLWINDADD);
+ KnockBack_Timer = 10000 + rand()%10000;
+ } else KnockBack_Timer -= diff;
+ }
+
+ if (AggroReset)
+ {
+ if (AggroResetEnd_Timer <= diff)
+ {
+ AggroReset = false;
+ AggroResetEnd_Timer = 5000;
+ AggroReset_Timer = 30000 + rand()%10000;
+ } else AggroResetEnd_Timer -= diff;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_boss_sartura(Creature* pCreature)
+{
+ return new boss_sarturaAI (pCreature);
+}
+
+CreatureAI* GetAI_mob_sartura_royal_guard(Creature* pCreature)
+{
+ return new mob_sartura_royal_guardAI (pCreature);
+}
+
+void AddSC_boss_sartura()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_sartura";
+ newscript->GetAI = &GetAI_boss_sartura;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "mob_sartura_royal_guard";
+ newscript->GetAI = &GetAI_mob_sartura_royal_guard;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_skeram.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_skeram.cpp
new file mode 100644
index 00000000000..7e52bed750c
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_skeram.cpp
@@ -0,0 +1,298 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Skeram
+SD%Complete: 75
+SDComment: Mind Control buggy.
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "temple_of_ahnqiraj.h"
+#include "Group.h"
+
+#define SAY_AGGRO1 -1531000
+#define SAY_AGGRO2 -1531001
+#define SAY_AGGRO3 -1531002
+#define SAY_SLAY1 -1531003
+#define SAY_SLAY2 -1531004
+#define SAY_SLAY3 -1531005
+#define SAY_SPLIT -1531006
+#define SAY_DEATH -1531007
+
+#define SPELL_ARCANE_EXPLOSION 25679
+#define SPELL_EARTH_SHOCK 26194
+#define SPELL_TRUE_FULFILLMENT4 26526
+#define SPELL_BLINK 28391
+
+class ov_mycoordinates
+{
+ public:
+ float x,y,z,r;
+ ov_mycoordinates(float cx, float cy, float cz, float cr)
+ {
+ x = cx; y = cy; z = cz; r = cr;
+ }
+};
+
+struct boss_skeramAI : public ScriptedAI
+{
+ boss_skeramAI(Creature *c) : ScriptedAI(c)
+ {
+ IsImage = false;
+ }
+
+ uint32 ArcaneExplosion_Timer;
+ uint32 EarthShock_Timer;
+ uint32 FullFillment_Timer;
+ uint32 Blink_Timer;
+ uint32 Invisible_Timer;
+
+ bool Images75;
+ bool Images50;
+ bool Images25;
+ bool IsImage;
+ bool Invisible;
+
+ void Reset()
+ {
+ ArcaneExplosion_Timer = 6000 + rand()%6000;
+ EarthShock_Timer = 2000;
+ FullFillment_Timer = 15000;
+ Blink_Timer = 8000 + rand()%12000;
+ Invisible_Timer = 500;
+
+ Images75 = false;
+ Images50 = false;
+ Images25 = false;
+ Invisible = false;
+
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ me->SetVisibility(VISIBILITY_ON);
+
+ if (IsImage)
+ me->setDeathState(JUST_DIED);
+ }
+
+ void KilledUnit(Unit* /*victim*/)
+ {
+ DoScriptText(RAND(SAY_SLAY1,SAY_SLAY2,SAY_SLAY3), me);
+ }
+
+ void JustDied(Unit* /*Killer*/)
+ {
+ if (!IsImage)
+ DoScriptText(SAY_DEATH, me);
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ if (IsImage || Images75)
+ return;
+ DoScriptText(RAND(SAY_AGGRO1,SAY_AGGRO2,SAY_AGGRO3), me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ //ArcaneExplosion_Timer
+ if (ArcaneExplosion_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_ARCANE_EXPLOSION);
+ ArcaneExplosion_Timer = 8000 + rand()%10000;
+ } else ArcaneExplosion_Timer -= diff;
+
+ //If we are within range melee the target
+ if (me->IsWithinMeleeRange(me->getVictim()))
+ {
+ //Make sure our attack is ready and we arn't currently casting
+ if (me->isAttackReady() && !me->IsNonMeleeSpellCasted(false))
+ {
+ me->AttackerStateUpdate(me->getVictim());
+ me->resetAttackTimer();
+ }
+ }else
+ {
+ //EarthShock_Timer
+ if (EarthShock_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_EARTH_SHOCK);
+ EarthShock_Timer = 1000;
+ } else EarthShock_Timer -= diff;
+ }
+
+ //Blink_Timer
+ if (Blink_Timer <= diff)
+ {
+ //DoCast(me, SPELL_BLINK);
+ switch (urand(0,2))
+ {
+ case 0:
+ me->GetMap()->CreatureRelocation(me, -8340.782227,2083.814453,125.648788,0.0f);
+ DoResetThreat();
+ break;
+ case 1:
+ me->GetMap()->CreatureRelocation(me, -8341.546875,2118.504639,133.058151,0.0f);
+ DoResetThreat();
+ break;
+ case 2:
+ me->GetMap()->CreatureRelocation(me, -8318.822266,2058.231201,133.058151,0.0f);
+ DoResetThreat();
+ break;
+ }
+ DoStopAttack();
+
+ Blink_Timer= 20000 + rand()%20000;
+ } else Blink_Timer -= diff;
+
+ int procent = (int) (me->GetHealth()*100 / me->GetMaxHealth() +0.5);
+
+ //Summoning 2 Images and teleporting to a random position on 75% health
+ if ((!Images75 && !IsImage) && (procent <= 75 && procent > 70))
+ DoSplit(75);
+
+ //Summoning 2 Images and teleporting to a random position on 50% health
+ if ((!Images50 && !IsImage) &&
+ (procent <= 50 && procent > 45))
+ DoSplit(50);
+
+ //Summoning 2 Images and teleporting to a random position on 25% health
+ if ((!Images25 && !IsImage) && (procent <= 25 && procent > 20))
+ DoSplit(25);
+
+ //Invisible_Timer
+ if (Invisible)
+ {
+ if (Invisible_Timer <= diff)
+ {
+ //Making Skeram visible after telporting
+ me->SetVisibility(VISIBILITY_ON);
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+
+ Invisible_Timer = 2500;
+ Invisible = false;
+ } else Invisible_Timer -= diff;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+
+ void DoSplit(int atPercent /* 75 50 25 */)
+ {
+ DoScriptText(SAY_SPLIT, me);
+
+ ov_mycoordinates *place1 = new ov_mycoordinates(-8340.782227,2083.814453,125.648788,0);
+ ov_mycoordinates *place2 = new ov_mycoordinates(-8341.546875,2118.504639,133.058151,0);
+ ov_mycoordinates *place3 = new ov_mycoordinates(-8318.822266,2058.231201,133.058151,0);
+
+ ov_mycoordinates *bossc=place1, *i1=place2, *i2=place3;
+
+ switch (urand(0,2))
+ {
+ case 0:
+ bossc=place1;
+ i1=place2;
+ i2=place3;
+ break;
+ case 1:
+ bossc=place2;
+ i1=place1;
+ i2=place3;
+ break;
+ case 2:
+ bossc=place3;
+ i1=place1;
+ i2=place2;
+ break;
+ }
+
+ for (uint16 i = 0; i < 41; ++i)
+ {
+ if (Player *pTarget = CAST_PLR(SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)))
+ {
+ if (Group *pGrp = pTarget->GetGroup())
+ for (uint8 ico = 0; ico < TARGETICONCOUNT; ++ico)
+ {
+ //if (grp->m_targetIcons[ico] == me->GetGUID()) -- private member :(
+ pGrp->SetTargetIcon(ico, 0, 0);
+ }
+
+ break;
+ }
+ }
+
+ me->RemoveAllAuras();
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ me->SetVisibility(VISIBILITY_OFF);
+ me->GetMap()->CreatureRelocation(me, bossc->x, bossc->y, bossc->z, bossc->r);
+ Invisible = true;
+ delete place1;
+ delete place2;
+ delete place3;
+ DoResetThreat();
+ DoStopAttack();
+
+ switch (atPercent)
+ {
+ case 75: Images75 = true; break;
+ case 50: Images50 = true; break;
+ case 25: Images25 = true; break;
+ }
+
+ Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+
+ Creature *Image1 = me->SummonCreature(15263, i1->x, i1->y, i1->z, i1->r, TEMPSUMMON_CORPSE_DESPAWN, 30000);
+ if (Image1)
+ {
+ Image1->SetMaxHealth(me->GetMaxHealth() / 5);
+ Image1->SetHealth(me->GetHealth() / 5);
+ if (pTarget)
+ Image1->AI()->AttackStart(pTarget);
+ CAST_AI(boss_skeramAI, Image1->AI())->IsImage = true;
+ }
+
+ Creature *Image2 = me->SummonCreature(15263,i2->x, i2->y, i2->z, i2->r, TEMPSUMMON_CORPSE_DESPAWN, 30000);
+ if (Image2)
+ {
+ Image2->SetMaxHealth(me->GetMaxHealth() / 5);
+ Image2->SetHealth(me->GetHealth() / 5);
+ if (pTarget)
+ Image2->AI()->AttackStart(pTarget);
+ CAST_AI(boss_skeramAI, Image2->AI())->IsImage = true;
+ }
+ Invisible = true;
+ }
+
+};
+
+CreatureAI* GetAI_boss_skeram(Creature* pCreature)
+{
+ return new boss_skeramAI (pCreature);
+}
+
+void AddSC_boss_skeram()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "boss_skeram";
+ newscript->GetAI = &GetAI_boss_skeram;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_twinemperors.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_twinemperors.cpp
new file mode 100644
index 00000000000..73f17485f7f
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_twinemperors.cpp
@@ -0,0 +1,596 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Twinemperors
+SD%Complete: 95
+SDComment:
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "temple_of_ahnqiraj.h"
+#include "WorldPacket.h"
+
+#include "Item.h"
+#include "Spell.h"
+
+#define SPELL_HEAL_BROTHER 7393
+#define SPELL_TWIN_TELEPORT 800 // CTRA watches for this spell to start its teleport timer
+#define SPELL_TWIN_TELEPORT_VISUAL 26638 // visual
+
+#define SPELL_EXPLODEBUG 804
+#define SPELL_MUTATE_BUG 802
+
+#define SOUND_VN_DEATH 8660 //8660 - Death - Feel
+#define SOUND_VN_AGGRO 8661 //8661 - Aggro - Let none
+#define SOUND_VN_KILL 8662 //8661 - Kill - your fate
+
+#define SOUND_VL_AGGRO 8657 //8657 - Aggro - To Late
+#define SOUND_VL_KILL 8658 //8658 - Kill - You will not
+#define SOUND_VL_DEATH 8659 //8659 - Death
+
+#define PULL_RANGE 50
+#define ABUSE_BUG_RANGE 20
+#define SPELL_BERSERK 26662
+#define TELEPORTTIME 30000
+
+#define SPELL_UPPERCUT 26007
+#define SPELL_UNBALANCING_STRIKE 26613
+
+#define VEKLOR_DIST 20 // VL will not come to melee when attacking
+
+#define SPELL_SHADOWBOLT 26006
+#define SPELL_BLIZZARD 26607
+#define SPELL_ARCANEBURST 568
+
+struct boss_twinemperorsAI : public ScriptedAI
+{
+ boss_twinemperorsAI(Creature *c): ScriptedAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ }
+
+ ScriptedInstance *pInstance;
+
+ uint32 Heal_Timer;
+ uint32 Teleport_Timer;
+ bool AfterTeleport;
+ uint32 AfterTeleportTimer;
+ bool DontYellWhenDead;
+ uint32 Abuse_Bug_Timer, BugsTimer;
+ bool tspellcasted;
+ uint32 EnrageTimer;
+
+ virtual bool IAmVeklor() = 0;
+ virtual void Reset() = 0;
+ virtual void CastSpellOnBug(Creature *pTarget) = 0;
+
+ void TwinReset()
+ {
+ Heal_Timer = 0; // first heal immediately when they get close together
+ Teleport_Timer = TELEPORTTIME;
+ AfterTeleport = false;
+ tspellcasted = false;
+ AfterTeleportTimer = 0;
+ Abuse_Bug_Timer = 10000 + rand()%7000;
+ BugsTimer = 2000;
+ me->clearUnitState(UNIT_STAT_STUNNED);
+ DontYellWhenDead = false;
+ EnrageTimer = 15*60000;
+ }
+
+ Creature *GetOtherBoss()
+ {
+ if (pInstance)
+ return Unit::GetCreature(*me, pInstance->GetData64(IAmVeklor() ? DATA_VEKNILASH : DATA_VEKLOR));
+ else
+ return NULL;
+ }
+
+ void DamageTaken(Unit * /*done_by*/, uint32 &damage)
+ {
+ Unit *pOtherBoss = GetOtherBoss();
+ if (pOtherBoss)
+ {
+ float dPercent = ((float)damage) / ((float)me->GetMaxHealth());
+ int odmg = (int)(dPercent * ((float)pOtherBoss->GetMaxHealth()));
+ int ohealth = pOtherBoss->GetHealth()-odmg;
+ pOtherBoss->SetHealth(ohealth > 0 ? ohealth : 0);
+ if (ohealth <= 0)
+ {
+ pOtherBoss->setDeathState(JUST_DIED);
+ pOtherBoss->SetFlag(UNIT_DYNAMIC_FLAGS, UNIT_DYNFLAG_LOOTABLE);
+ }
+ }
+ }
+
+ void JustDied(Unit* /*Killer*/)
+ {
+ Creature *pOtherBoss = GetOtherBoss();
+ if (pOtherBoss)
+ {
+ pOtherBoss->SetHealth(0);
+ pOtherBoss->setDeathState(JUST_DIED);
+ pOtherBoss->SetFlag(UNIT_DYNAMIC_FLAGS, UNIT_DYNFLAG_LOOTABLE);
+ CAST_AI(boss_twinemperorsAI, pOtherBoss->AI())->DontYellWhenDead = true;
+ }
+ if (!DontYellWhenDead) // I hope AI is not threaded
+ DoPlaySoundToSet(me, IAmVeklor() ? SOUND_VL_DEATH : SOUND_VN_DEATH);
+ }
+
+ void KilledUnit(Unit* /*victim*/)
+ {
+ DoPlaySoundToSet(me, IAmVeklor() ? SOUND_VL_KILL : SOUND_VN_KILL);
+ }
+
+ void EnterCombat(Unit * who)
+ {
+ DoZoneInCombat();
+ Creature *pOtherBoss = GetOtherBoss();
+ if (pOtherBoss)
+ {
+ // TODO: we should activate the other boss location so he can start attackning even if nobody
+ // is near I dont know how to do that
+ ScriptedAI *otherAI = CAST_AI(ScriptedAI, pOtherBoss->AI());
+ if (!pOtherBoss->isInCombat())
+ {
+ DoPlaySoundToSet(me, IAmVeklor() ? SOUND_VL_AGGRO : SOUND_VN_AGGRO);
+ otherAI->AttackStart(who);
+ otherAI->DoZoneInCombat();
+ }
+ }
+ }
+
+ void SpellHit(Unit *caster, const SpellEntry *entry)
+ {
+ if (caster == me)
+ return;
+
+ Creature *pOtherBoss = GetOtherBoss();
+ if (entry->Id != SPELL_HEAL_BROTHER || !pOtherBoss)
+ return;
+
+ // add health so we keep same percentage for both brothers
+ uint32 mytotal = me->GetMaxHealth(), histotal = pOtherBoss->GetMaxHealth();
+ float mult = ((float)mytotal) / ((float)histotal);
+ if (mult < 1)
+ mult = 1.0f/mult;
+ #define HEAL_BROTHER_AMOUNT 30000.0f
+ uint32 largerAmount = (uint32)((HEAL_BROTHER_AMOUNT * mult) - HEAL_BROTHER_AMOUNT);
+
+ if (mytotal > histotal)
+ {
+ uint32 h = me->GetHealth()+largerAmount;
+ me->SetHealth(std::min(mytotal, h));
+ }
+ else
+ {
+ uint32 h = pOtherBoss->GetHealth()+largerAmount;
+ pOtherBoss->SetHealth(std::min(histotal, h));
+ }
+ }
+
+ void TryHealBrother(uint32 diff)
+ {
+ if (IAmVeklor()) // this spell heals caster and the other brother so let VN cast it
+ return;
+
+ if (Heal_Timer <= diff)
+ {
+ Unit *pOtherBoss = GetOtherBoss();
+ if (pOtherBoss && pOtherBoss->IsWithinDist(me,60))
+ {
+ DoCast(pOtherBoss, SPELL_HEAL_BROTHER);
+ Heal_Timer = 1000;
+ }
+ } else Heal_Timer -= diff;
+ }
+
+ void TeleportToMyBrother()
+ {
+ if (!pInstance)
+ return;
+
+ Teleport_Timer = TELEPORTTIME;
+
+ if (IAmVeklor())
+ return; // mechanics handled by veknilash so they teleport exactly at the same time and to correct coordinates
+
+ Creature *pOtherBoss = GetOtherBoss();
+ if (pOtherBoss)
+ {
+ //me->MonsterYell("Teleporting ...", LANG_UNIVERSAL, 0);
+ float other_x = pOtherBoss->GetPositionX();
+ float other_y = pOtherBoss->GetPositionY();
+ float other_z = pOtherBoss->GetPositionZ();
+ float other_o = pOtherBoss->GetOrientation();
+
+ Map *thismap = me->GetMap();
+ thismap->CreatureRelocation(pOtherBoss, me->GetPositionX(),
+ me->GetPositionY(), me->GetPositionZ(), me->GetOrientation());
+ thismap->CreatureRelocation(me, other_x, other_y, other_z, other_o);
+
+ SetAfterTeleport();
+ CAST_AI(boss_twinemperorsAI, pOtherBoss->AI())->SetAfterTeleport();
+ }
+ }
+
+ void SetAfterTeleport()
+ {
+ me->InterruptNonMeleeSpells(false);
+ DoStopAttack();
+ DoResetThreat();
+ DoCast(me, SPELL_TWIN_TELEPORT_VISUAL);
+ me->addUnitState(UNIT_STAT_STUNNED);
+ AfterTeleport = true;
+ AfterTeleportTimer = 2000;
+ tspellcasted = false;
+ }
+
+ bool TryActivateAfterTTelep(uint32 diff)
+ {
+ if (AfterTeleport)
+ {
+ if (!tspellcasted)
+ {
+ me->clearUnitState(UNIT_STAT_STUNNED);
+ DoCast(me, SPELL_TWIN_TELEPORT);
+ me->addUnitState(UNIT_STAT_STUNNED);
+ }
+
+ tspellcasted = true;
+
+ if (AfterTeleportTimer <= diff)
+ {
+ AfterTeleport = false;
+ me->clearUnitState(UNIT_STAT_STUNNED);
+ if (Unit *nearu = me->SelectNearestTarget(100))
+ {
+ //DoYell(nearu->GetName(), LANG_UNIVERSAL, 0);
+ AttackStart(nearu);
+ me->AddThreat(nearu, 10000);
+ }
+ return true;
+ }
+ else
+ {
+ AfterTeleportTimer -= diff;
+ // update important timers which would otherwise get skipped
+ if (EnrageTimer > diff)
+ EnrageTimer -= diff;
+ else
+ EnrageTimer = 0;
+ if (Teleport_Timer > diff)
+ Teleport_Timer -= diff;
+ else
+ Teleport_Timer = 0;
+ return false;
+ }
+ }
+ else
+ {
+ return true;
+ }
+ }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ if (!who || me->getVictim())
+ return;
+
+ if (who->isTargetableForAttack() && who->isInAccessiblePlaceFor(me) && me->IsHostileTo(who))
+ {
+ float attackRadius = me->GetAttackDistance(who);
+ if (attackRadius < PULL_RANGE)
+ attackRadius = PULL_RANGE;
+ if (me->IsWithinDistInMap(who, attackRadius) && me->GetDistanceZ(who) <= /*CREATURE_Z_ATTACK_RANGE*/7 /*there are stairs*/)
+ {
+ //if (who->HasStealthAura())
+ // who->RemoveSpellsCausingAura(SPELL_AURA_MOD_STEALTH);
+ AttackStart(who);
+ }
+ }
+ }
+
+ Creature *RespawnNearbyBugsAndGetOne()
+ {
+ std::list<Creature*> lUnitList;
+ me->GetCreatureListWithEntryInGrid(lUnitList,15316,150.0f);
+ me->GetCreatureListWithEntryInGrid(lUnitList,15317,150.0f);
+
+ if (lUnitList.empty())
+ return NULL;
+
+ Creature *nearb = NULL;
+
+ for (std::list<Creature*>::const_iterator iter = lUnitList.begin(); iter != lUnitList.end(); ++iter)
+ {
+ Creature *c = *iter;
+ if (c)
+ {
+ if (c->isDead())
+ {
+ c->Respawn();
+ c->setFaction(7);
+ c->RemoveAllAuras();
+ }
+ if (c->IsWithinDistInMap(me, ABUSE_BUG_RANGE))
+ {
+ if (!nearb || (rand()%4) == 0)
+ nearb = c;
+ }
+ }
+ }
+ return nearb;
+ }
+
+ void HandleBugs(uint32 diff)
+ {
+ if (BugsTimer < diff || Abuse_Bug_Timer <= diff)
+ {
+ Creature *c = RespawnNearbyBugsAndGetOne();
+ if (Abuse_Bug_Timer <= diff)
+ {
+ if (c)
+ {
+ CastSpellOnBug(c);
+ Abuse_Bug_Timer = 10000 + rand()%7000;
+ }
+ else
+ {
+ Abuse_Bug_Timer = 1000;
+ }
+ }
+ else
+ {
+ Abuse_Bug_Timer -= diff;
+ }
+ BugsTimer = 2000;
+ }
+ else
+ {
+ BugsTimer -= diff;
+ Abuse_Bug_Timer -= diff;
+ }
+ }
+
+ void CheckEnrage(uint32 diff)
+ {
+ if (EnrageTimer <= diff)
+ {
+ if (!me->IsNonMeleeSpellCasted(true))
+ {
+ DoCast(me, SPELL_BERSERK);
+ EnrageTimer = 60*60000;
+ } else EnrageTimer = 0;
+ } else EnrageTimer-=diff;
+ }
+};
+
+struct boss_veknilashAI : public boss_twinemperorsAI
+{
+ bool IAmVeklor() {return false;}
+ boss_veknilashAI(Creature *c) : boss_twinemperorsAI(c) {}
+
+ uint32 UpperCut_Timer;
+ uint32 UnbalancingStrike_Timer;
+ uint32 Scarabs_Timer;
+ int Rand;
+ int RandX;
+ int RandY;
+
+ Creature* Summoned;
+
+ void Reset()
+ {
+ TwinReset();
+ UpperCut_Timer = 14000 + rand()%15000;
+ UnbalancingStrike_Timer = 8000 + rand()%10000;
+ Scarabs_Timer = 7000 + rand()%7000;
+
+ //Added. Can be removed if its included in DB.
+ me->ApplySpellImmune(0, IMMUNITY_DAMAGE, SPELL_SCHOOL_MASK_MAGIC, true);
+ }
+
+ void CastSpellOnBug(Creature *pTarget)
+ {
+ pTarget->setFaction(14);
+ pTarget->AI()->AttackStart(me->getThreatManager().getHostilTarget());
+ pTarget->AddAura(SPELL_MUTATE_BUG, pTarget);
+ pTarget->SetHealth(pTarget->GetMaxHealth());
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ if (!TryActivateAfterTTelep(diff))
+ return;
+
+ //UnbalancingStrike_Timer
+ if (UnbalancingStrike_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_UNBALANCING_STRIKE);
+ UnbalancingStrike_Timer = 8000+rand()%12000;
+ } else UnbalancingStrike_Timer -= diff;
+
+ if (UpperCut_Timer <= diff)
+ {
+ Unit* randomMelee = SelectTarget(SELECT_TARGET_RANDOM, 0, NOMINAL_MELEE_RANGE, true);
+ if (randomMelee)
+ DoCast(randomMelee, SPELL_UPPERCUT);
+ UpperCut_Timer = 15000+rand()%15000;
+ } else UpperCut_Timer -= diff;
+
+ HandleBugs(diff);
+
+ //Heal brother when 60yrds close
+ TryHealBrother(diff);
+
+ //Teleporting to brother
+ if (Teleport_Timer <= diff)
+ {
+ TeleportToMyBrother();
+ } else Teleport_Timer -= diff;
+
+ CheckEnrage(diff);
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+struct boss_veklorAI : public boss_twinemperorsAI
+{
+ bool IAmVeklor() {return true;}
+ boss_veklorAI(Creature *c) : boss_twinemperorsAI(c) {}
+
+ uint32 ShadowBolt_Timer;
+ uint32 Blizzard_Timer;
+ uint32 ArcaneBurst_Timer;
+ uint32 Scorpions_Timer;
+ int Rand;
+ int RandX;
+ int RandY;
+
+ Creature* Summoned;
+
+ void Reset()
+ {
+ TwinReset();
+ ShadowBolt_Timer = 0;
+ Blizzard_Timer = 15000 + rand()%5000;
+ ArcaneBurst_Timer = 1000;
+ Scorpions_Timer = 7000 + rand()%7000;
+
+ //Added. Can be removed if its included in DB.
+ me->ApplySpellImmune(0, IMMUNITY_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, true);
+ me->SetBaseWeaponDamage(BASE_ATTACK, MINDAMAGE, 0);
+ me->SetBaseWeaponDamage(BASE_ATTACK, MAXDAMAGE, 0);
+ }
+
+ void CastSpellOnBug(Creature *pTarget)
+ {
+ pTarget->setFaction(14);
+ pTarget->AddAura(SPELL_EXPLODEBUG, pTarget);
+ pTarget->SetHealth(pTarget->GetMaxHealth());
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ //Return since we have no target
+ if (!UpdateVictim())
+ return;
+
+ // reset arcane burst after teleport - we need to do this because
+ // when VL jumps to VN's location there will be a warrior who will get only 2s to run away
+ // which is almost impossible
+ if (AfterTeleport)
+ ArcaneBurst_Timer = 5000;
+ if (!TryActivateAfterTTelep(diff))
+ return;
+
+ //ShadowBolt_Timer
+ if (ShadowBolt_Timer <= diff)
+ {
+ if (!me->IsWithinDist(me->getVictim(), 45.0f))
+ me->GetMotionMaster()->MoveChase(me->getVictim(), VEKLOR_DIST, 0);
+ else
+ DoCast(me->getVictim(), SPELL_SHADOWBOLT);
+ ShadowBolt_Timer = 2000;
+ } else ShadowBolt_Timer -= diff;
+
+ //Blizzard_Timer
+ if (Blizzard_Timer <= diff)
+ {
+ Unit *pTarget = NULL;
+ pTarget = SelectTarget(SELECT_TARGET_RANDOM, 0, 45, true);
+ if (pTarget)
+ DoCast(pTarget, SPELL_BLIZZARD);
+ Blizzard_Timer = 15000+rand()%15000;
+ } else Blizzard_Timer -= diff;
+
+ if (ArcaneBurst_Timer <= diff)
+ {
+ Unit *mvic;
+ if ((mvic=SelectTarget(SELECT_TARGET_NEAREST, 0, NOMINAL_MELEE_RANGE, true)) != NULL)
+ {
+ DoCast(mvic, SPELL_ARCANEBURST);
+ ArcaneBurst_Timer = 5000;
+ }
+ } else ArcaneBurst_Timer -= diff;
+
+ HandleBugs(diff);
+
+ //Heal brother when 60yrds close
+ TryHealBrother(diff);
+
+ //Teleporting to brother
+ if (Teleport_Timer <= diff)
+ {
+ TeleportToMyBrother();
+ } else Teleport_Timer -= diff;
+
+ CheckEnrage(diff);
+
+ //VL doesn't melee
+ //DoMeleeAttackIfReady();
+ }
+
+ void AttackStart(Unit* who)
+ {
+ if (!who)
+ return;
+
+ if (who->isTargetableForAttack())
+ {
+ // VL doesn't melee
+ if (me->Attack(who, false))
+ {
+ me->GetMotionMaster()->MoveChase(who, VEKLOR_DIST, 0);
+ me->AddThreat(who, 0.0f);
+ }
+ }
+ }
+};
+
+CreatureAI* GetAI_boss_veknilash(Creature* pCreature)
+{
+ return new boss_veknilashAI (pCreature);
+}
+
+CreatureAI* GetAI_boss_veklor(Creature* pCreature)
+{
+ return new boss_veklorAI (pCreature);
+}
+
+void AddSC_boss_twinemperors()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "boss_veknilash";
+ newscript->GetAI = &GetAI_boss_veknilash;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "boss_veklor";
+ newscript->GetAI = &GetAI_boss_veklor;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_viscidus.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_viscidus.cpp
new file mode 100644
index 00000000000..f5e71a35bae
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/boss_viscidus.cpp
@@ -0,0 +1,30 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Boss_Viscidus
+SD%Complete: 0
+SDComment: place holder
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+#define SPELL_POISON_SHOCK 25993
+#define SPELL_POISONBOLT_VOLLEY 25991
+
+#define SPELL_TOXIN_CLOUD 25989
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/instance_temple_of_ahnqiraj.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/instance_temple_of_ahnqiraj.cpp
new file mode 100644
index 00000000000..1125a0c8623
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/instance_temple_of_ahnqiraj.cpp
@@ -0,0 +1,166 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Instance_Temple_of_Ahnqiraj
+SD%Complete: 80
+SDComment:
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "temple_of_ahnqiraj.h"
+
+struct instance_temple_of_ahnqiraj : public ScriptedInstance
+{
+ instance_temple_of_ahnqiraj(Map* pMap) : ScriptedInstance(pMap) {Initialize();};
+
+ //If Vem is dead...
+ bool IsBossDied[3];
+
+ //Storing Skeram, Vem and Kri.
+ uint64 SkeramGUID;
+ uint64 VemGUID;
+ uint64 KriGUID;
+ uint64 VeklorGUID;
+ uint64 VeknilashGUID;
+
+ uint32 BugTrioDeathCount;
+
+ uint32 CthunPhase;
+
+ void Initialize()
+ {
+ IsBossDied[0] = false;
+ IsBossDied[1] = false;
+ IsBossDied[2] = false;
+
+ SkeramGUID = 0;
+ VemGUID = 0;
+ KriGUID = 0;
+ VeklorGUID = 0;
+ VeknilashGUID = 0;
+
+ BugTrioDeathCount = 0;
+
+ CthunPhase = 0;
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool /*add*/)
+ {
+ switch (pCreature->GetEntry())
+ {
+ case 15263: SkeramGUID = pCreature->GetGUID(); break;
+ case 15544: VemGUID = pCreature->GetGUID(); break;
+ case 15511: KriGUID = pCreature->GetGUID(); break;
+ case 15276: VeklorGUID = pCreature->GetGUID(); break;
+ case 15275: VeknilashGUID = pCreature->GetGUID(); break;
+ }
+ }
+
+ bool IsEncounterInProgress() const
+ {
+ //not active in AQ40
+ return false;
+ }
+
+ uint32 GetData(uint32 type)
+ {
+ switch(type)
+ {
+ case DATA_VEMISDEAD:
+ if (IsBossDied[0])
+ return 1;
+ break;
+
+ case DATA_VEKLORISDEAD:
+ if (IsBossDied[1])
+ return 1;
+ break;
+
+ case DATA_VEKNILASHISDEAD:
+ if (IsBossDied[2])
+ return 1;
+ break;
+
+ case DATA_BUG_TRIO_DEATH:
+ return BugTrioDeathCount;
+
+ case DATA_CTHUN_PHASE:
+ return CthunPhase;
+ }
+ return 0;
+ }
+
+ uint64 GetData64 (uint32 identifier)
+ {
+ switch(identifier)
+ {
+ case DATA_SKERAM:
+ return SkeramGUID;
+ case DATA_VEM:
+ return VemGUID;
+ case DATA_KRI:
+ return KriGUID;
+ case DATA_VEKLOR:
+ return VeklorGUID;
+ case DATA_VEKNILASH:
+ return VeknilashGUID;
+ }
+ return 0;
+ } // end GetData64
+
+ void SetData(uint32 type, uint32 data)
+ {
+ switch(type)
+ {
+ case DATA_VEM_DEATH:
+ IsBossDied[0] = true;
+ break;
+
+ case DATA_BUG_TRIO_DEATH:
+ ++BugTrioDeathCount;
+ break;
+
+ case DATA_VEKLOR_DEATH:
+ IsBossDied[1] = true;
+ break;
+
+ case DATA_VEKNILASH_DEATH:
+ IsBossDied[2] = true;
+ break;
+
+ case DATA_CTHUN_PHASE:
+ CthunPhase = data;
+ break;
+ }
+ }
+};
+
+InstanceData* GetInstanceData_instance_temple_of_ahnqiraj(Map* pMap)
+{
+ return new instance_temple_of_ahnqiraj(pMap);
+}
+
+void AddSC_instance_temple_of_ahnqiraj()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_temple_of_ahnqiraj";
+ newscript->GetInstanceData = &GetInstanceData_instance_temple_of_ahnqiraj;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/mob_anubisath_sentinel.cpp b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/mob_anubisath_sentinel.cpp
new file mode 100644
index 00000000000..074f9ed68ae
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/mob_anubisath_sentinel.cpp
@@ -0,0 +1,296 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: mob_anubisath_sentinel
+SD%Complete: 95
+SDComment: Shadow storm is not properly implemented in core it should only pTarget ppl outside of melee range.
+SDCategory: Temple of Ahn'Qiraj
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "WorldPacket.h"
+
+#include "Item.h"
+#include "Player.h"
+#include "Spell.h"
+
+#include "Cell.h"
+#include "CellImpl.h"
+#include "GridNotifiers.h"
+#include "GridNotifiersImpl.h"
+
+#define SPELL_MENDING_BUFF 2147
+
+#define SPELL_KNOCK_BUFF 21737
+#define SPELL_KNOCK 25778
+#define SPELL_MANAB_BUFF 812
+#define SPELL_MANAB 25779
+
+#define SPELL_REFLECTAF_BUFF 13022
+#define SPELL_REFLECTSFr_BUFF 19595
+#define SPELL_THORNS_BUFF 25777
+
+#define SPELL_THUNDER_BUFF 2834
+#define SPELL_THUNDER 8732
+
+#define SPELL_MSTRIKE_BUFF 9347
+#define SPELL_MSTRIKE 24573
+
+#define SPELL_STORM_BUFF 2148
+#define SPELL_STORM 26546
+
+struct aqsentinelAI : public ScriptedAI
+{
+ uint32 ability;
+ int abselected;
+
+ void selectAbility(int asel)
+ {
+ switch (asel)
+ {
+ case 0: ability = SPELL_MENDING_BUFF;break;
+ case 1: ability = SPELL_KNOCK_BUFF;break;
+ case 2: ability = SPELL_MANAB_BUFF;break;
+ case 3: ability = SPELL_REFLECTAF_BUFF;break;
+ case 4: ability = SPELL_REFLECTSFr_BUFF;break;
+ case 5: ability = SPELL_THORNS_BUFF;break;
+ case 6: ability = SPELL_THUNDER_BUFF;break;
+ case 7: ability = SPELL_MSTRIKE_BUFF;break;
+ case 8: ability = SPELL_STORM_BUFF;break;
+ }
+ }
+
+ aqsentinelAI(Creature *c) : ScriptedAI(c)
+ {
+ ClearBuddyList();
+ abselected = 0; // just initialization of variable
+ }
+
+ uint64 NearbyGUID[3];
+
+ void ClearBuddyList()
+ {
+ NearbyGUID[0] = NearbyGUID[1] = NearbyGUID[2] = 0;
+ }
+
+ void AddBuddyToList(uint64 CreatureGUID)
+ {
+ if (CreatureGUID == me->GetGUID())
+ return;
+
+ for (int i=0; i<3; ++i)
+ {
+ if (NearbyGUID[i] == CreatureGUID)
+ return;
+ if (!NearbyGUID[i])
+ {
+ NearbyGUID[i] = CreatureGUID;
+ return;
+ }
+ }
+ }
+
+ void GiveBuddyMyList(Creature *c)
+ {
+ aqsentinelAI *cai = CAST_AI(aqsentinelAI, (c)->AI());
+ for (int i=0; i<3; ++i)
+ if (NearbyGUID[i] && NearbyGUID[i] != c->GetGUID())
+ cai->AddBuddyToList(NearbyGUID[i]);
+ cai->AddBuddyToList(me->GetGUID());
+ }
+
+ void SendMyListToBuddies()
+ {
+ for (int i=0; i<3; ++i)
+ if (Creature *pNearby = Unit::GetCreature(*me, NearbyGUID[i]))
+ GiveBuddyMyList(pNearby);
+ }
+
+ void CallBuddiesToAttack(Unit *who)
+ {
+ for (int i=0; i<3; ++i)
+ {
+ Creature *c = Unit::GetCreature(*me, NearbyGUID[i]);
+ if (c)
+ {
+ if (!c->isInCombat())
+ {
+ c->SetNoCallAssistance(true);
+ if (c->AI())
+ c->AI()->AttackStart(who);
+ }
+ }
+ }
+ }
+
+ void AddSentinelsNear(Unit * /*nears*/)
+ {
+ std::list<Creature*> assistList;
+ me->GetCreatureListWithEntryInGrid(assistList,15264,70.0f);
+
+ if (assistList.empty())
+ return;
+
+ for (std::list<Creature*>::const_iterator iter = assistList.begin(); iter != assistList.end(); ++iter)
+ AddBuddyToList((*iter)->GetGUID());
+ }
+
+ int pickAbilityRandom(bool *chosenAbilities)
+ {
+ for (int t = 0; t < 2; ++t)
+ {
+ for (int i = !t ? (rand()%9) : 0; i < 9; ++i)
+ {
+ if (!chosenAbilities[i])
+ {
+ chosenAbilities[i] = true;
+ return i;
+ }
+ }
+ }
+ return 0; // should never happen
+ }
+
+ void GetOtherSentinels(Unit *who)
+ {
+ bool *chosenAbilities = new bool[9];
+ memset(chosenAbilities, 0, 9*sizeof(bool));
+ selectAbility(pickAbilityRandom(chosenAbilities));
+
+ ClearBuddyList();
+ AddSentinelsNear(me);
+ int bli;
+ for (bli = 0; bli < 3; ++bli)
+ {
+ if (!NearbyGUID[bli])
+ break;
+
+ Creature *pNearby = Unit::GetCreature(*me, NearbyGUID[bli]);
+ if (!pNearby)
+ break;
+
+ AddSentinelsNear(pNearby);
+ CAST_AI(aqsentinelAI, pNearby->AI())->gatherOthersWhenAggro = false;
+ CAST_AI(aqsentinelAI, pNearby->AI())->selectAbility(pickAbilityRandom(chosenAbilities));
+ }
+ /*if (bli < 3)
+ DoYell("I dont have enough buddies.", LANG_NEUTRAL, 0);*/
+ SendMyListToBuddies();
+ CallBuddiesToAttack(who);
+
+ delete[] chosenAbilities;
+ }
+
+ bool gatherOthersWhenAggro;
+
+ void Reset()
+ {
+ if (!me->isDead())
+ {
+ for (int i=0; i<3; ++i)
+ {
+ if (!NearbyGUID[i])
+ continue;
+ if (Creature *pNearby = Unit::GetCreature(*me, NearbyGUID[i]))
+ {
+ if (pNearby->isDead())
+ pNearby->Respawn();
+ }
+ }
+ }
+ ClearBuddyList();
+ gatherOthersWhenAggro = true;
+ }
+
+ void GainSentinelAbility(uint32 id)
+ {
+ me->AddAura(id, me);
+ }
+
+ void EnterCombat(Unit * who)
+ {
+ if (gatherOthersWhenAggro)
+ GetOtherSentinels(who);
+
+ GainSentinelAbility(ability);
+ DoZoneInCombat();
+ }
+
+ void JustDied(Unit* /*who*/)
+ {
+ for (int ni=0; ni<3; ++ni)
+ {
+ Creature *sent = Unit::GetCreature(*me, NearbyGUID[ni]);
+ if (!sent)
+ continue;
+ if (sent->isDead())
+ continue;
+ int h = sent->GetHealth() + (sent->GetMaxHealth() / 2);
+ if (h > sent->GetMaxHealth())
+ h = sent->GetMaxHealth();
+ sent->SetHealth(h);
+ CAST_AI(aqsentinelAI, sent->AI())->GainSentinelAbility(ability);
+ }
+ }
+
+ Unit *GetHatedManaUser() const
+ {
+ std::list<HostileReference*>::const_iterator i;
+ for (i = me->getThreatManager().getThreatList().begin(); i != me->getThreatManager().getThreatList().end(); ++i)
+ {
+ Unit* pUnit = Unit::GetUnit((*me), (*i)->getUnitGuid());
+ if (pUnit->getPowerType() == POWER_MANA)
+ return pUnit;
+ }
+ return NULL;
+ }
+
+ Unit* GetAuraEffectTriggerTarget(uint32 spellId, uint8 /*effIndex*/) const
+ {
+ switch (spellId)
+ {
+ case SPELL_KNOCK_BUFF:
+ case SPELL_THUNDER_BUFF:
+ case SPELL_MSTRIKE_BUFF:
+ case SPELL_STORM_BUFF:
+ return me->getVictim();
+
+ case SPELL_MANAB_BUFF:
+ return GetHatedManaUser();
+
+ case SPELL_MENDING_BUFF:
+ case SPELL_REFLECTAF_BUFF:
+ case SPELL_REFLECTSFr_BUFF:
+ case SPELL_THORNS_BUFF:
+ default:
+ return me;
+ }
+ }
+};
+CreatureAI* GetAI_mob_anubisath_sentinelAI(Creature* pCreature)
+{
+ return new aqsentinelAI (pCreature);
+}
+
+void AddSC_mob_anubisath_sentinel()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "mob_anubisath_sentinel";
+ newscript->GetAI = &GetAI_mob_anubisath_sentinelAI;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/temple_of_ahnqiraj/temple_of_ahnqiraj.h b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/temple_of_ahnqiraj.h
new file mode 100644
index 00000000000..5d545ed7c74
--- /dev/null
+++ b/src/server/scripts/Kalimdor/temple_of_ahnqiraj/temple_of_ahnqiraj.h
@@ -0,0 +1,23 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software licensed under GPL version 2
+ * Please see the included DOCS/LICENSE.TXT for more information */
+
+#ifndef DEF_TEMPLE_OF_AHNQIRAJ_H
+#define DEF_TEMPLE_OF_AHNQIRAJ_H
+
+#define DATA_SKERAM 1
+#define DATA_KRI 2
+#define DATA_VEM 3
+#define DATA_VEMISDEAD 4
+#define DATA_VEM_DEATH 5
+#define DATA_VEKLOR 6
+#define DATA_VEKLORISDEAD 7
+#define DATA_VEKLOR_DEATH 8
+#define DATA_VEKNILASH 9
+#define DATA_VEKNILASHISDEAD 10
+#define DATA_VEKNILASH_DEATH 11
+#define DATA_BUG_TRIO_DEATH 14
+
+#define DATA_CTHUN_PHASE 20
+#endif
+
diff --git a/src/server/scripts/Kalimdor/the_barrens.cpp b/src/server/scripts/Kalimdor/the_barrens.cpp
new file mode 100644
index 00000000000..04daac96877
--- /dev/null
+++ b/src/server/scripts/Kalimdor/the_barrens.cpp
@@ -0,0 +1,701 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: The_Barrens
+SD%Complete: 90
+SDComment: Quest support: 863, 898, 1719, 2458, 4921, 6981,
+SDCategory: Barrens
+EndScriptData */
+
+/* ContentData
+npc_beaten_corpse
+npc_gilthares
+npc_sputtervalve
+npc_taskmaster_fizzule
+npc_twiggy_flathead
+npc_wizzlecrank_shredder
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+
+/*######
+## npc_beaten_corpse
+######*/
+
+#define GOSSIP_CORPSE "Examine corpse in detail..."
+
+enum eQuests
+{
+ QUEST_LOST_IN_BATTLE = 4921
+};
+
+bool GossipHello_npc_beaten_corpse(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->GetQuestStatus(QUEST_LOST_IN_BATTLE) == QUEST_STATUS_INCOMPLETE || pPlayer->GetQuestStatus(QUEST_LOST_IN_BATTLE) == QUEST_STATUS_COMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_CORPSE, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+
+ pPlayer->SEND_GOSSIP_MENU(3557, pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_beaten_corpse(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF +1)
+ {
+ pPlayer->SEND_GOSSIP_MENU(3558, pCreature->GetGUID());
+ pPlayer->TalkedToCreature(pCreature->GetEntry(), pCreature->GetGUID());
+ }
+ return true;
+}
+
+/*######
+# npc_gilthares
+######*/
+
+enum eGilthares
+{
+ SAY_GIL_START = -1000370,
+ SAY_GIL_AT_LAST = -1000371,
+ SAY_GIL_PROCEED = -1000372,
+ SAY_GIL_FREEBOOTERS = -1000373,
+ SAY_GIL_AGGRO_1 = -1000374,
+ SAY_GIL_AGGRO_2 = -1000375,
+ SAY_GIL_AGGRO_3 = -1000376,
+ SAY_GIL_AGGRO_4 = -1000377,
+ SAY_GIL_ALMOST = -1000378,
+ SAY_GIL_SWEET = -1000379,
+ SAY_GIL_FREED = -1000380,
+
+ QUEST_FREE_FROM_HOLD = 898,
+ AREA_MERCHANT_COAST = 391,
+ FACTION_ESCORTEE = 232 //guessed, possible not needed for this quest
+};
+
+struct npc_giltharesAI : public npc_escortAI
+{
+ npc_giltharesAI(Creature* pCreature) : npc_escortAI(pCreature) { }
+
+ void Reset() { }
+
+ void WaypointReached(uint32 uiPointId)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch(uiPointId)
+ {
+ case 16:
+ DoScriptText(SAY_GIL_AT_LAST, me, pPlayer);
+ break;
+ case 17:
+ DoScriptText(SAY_GIL_PROCEED, me, pPlayer);
+ break;
+ case 18:
+ DoScriptText(SAY_GIL_FREEBOOTERS, me, pPlayer);
+ break;
+ case 37:
+ DoScriptText(SAY_GIL_ALMOST, me, pPlayer);
+ break;
+ case 47:
+ DoScriptText(SAY_GIL_SWEET, me, pPlayer);
+ break;
+ case 53:
+ DoScriptText(SAY_GIL_FREED, me, pPlayer);
+ pPlayer->GroupEventHappens(QUEST_FREE_FROM_HOLD, me);
+ break;
+ }
+ }
+
+ void Aggro(Unit* pWho)
+ {
+ //not always use
+ if (rand()%4)
+ return;
+
+ //only aggro text if not player and only in this area
+ if (pWho->GetTypeId() != TYPEID_PLAYER && me->GetAreaId() == AREA_MERCHANT_COAST)
+ {
+ //appears to be pretty much random (possible only if escorter not in combat with pWho yet?)
+ DoScriptText(RAND(SAY_GIL_AGGRO_1, SAY_GIL_AGGRO_2, SAY_GIL_AGGRO_3, SAY_GIL_AGGRO_4), me, pWho);
+ }
+ }
+};
+
+CreatureAI* GetAI_npc_gilthares(Creature* pCreature)
+{
+ return new npc_giltharesAI(pCreature);
+}
+
+bool QuestAccept_npc_gilthares(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_FREE_FROM_HOLD)
+ {
+ pCreature->setFaction(FACTION_ESCORTEE);
+ pCreature->SetStandState(UNIT_STAND_STATE_STAND);
+
+ DoScriptText(SAY_GIL_START, pCreature, pPlayer);
+
+ if (npc_giltharesAI* pEscortAI = CAST_AI(npc_giltharesAI, pCreature->AI()))
+ pEscortAI->Start(false, false, pPlayer->GetGUID(), pQuest);
+ }
+ return true;
+}
+
+/*######
+## npc_sputtervalve
+######*/
+
+#define GOSSIP_SPUTTERVALVE "Can you tell me about this shard?"
+
+bool GossipHello_npc_sputtervalve(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(6981) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SPUTTERVALVE, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+ return true;
+}
+
+bool GossipSelect_npc_sputtervalve(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF)
+ {
+ pPlayer->SEND_GOSSIP_MENU(2013, pCreature->GetGUID());
+ pPlayer->AreaExploredOrEventHappens(6981);
+ }
+ return true;
+}
+
+/*######
+## npc_taskmaster_fizzule
+######*/
+
+enum eEnums
+{
+ FACTION_FRIENDLY_F = 35,
+ SPELL_FLARE = 10113,
+ SPELL_FOLLY = 10137,
+};
+
+struct npc_taskmaster_fizzuleAI : public ScriptedAI
+{
+ npc_taskmaster_fizzuleAI(Creature* c) : ScriptedAI(c)
+ {
+ factionNorm = c->getFaction();
+ }
+
+ uint32 factionNorm;
+ bool IsFriend;
+ uint32 Reset_Timer;
+ uint8 FlareCount;
+
+ void Reset()
+ {
+ IsFriend = false;
+ Reset_Timer = 120000;
+ FlareCount = 0;
+ me->setFaction(factionNorm);
+ }
+
+ void DoFriend()
+ {
+ me->RemoveAllAuras();
+ me->DeleteThreatList();
+ me->CombatStop(true);
+
+ me->StopMoving();
+ me->GetMotionMaster()->MoveIdle();
+
+ me->setFaction(FACTION_FRIENDLY_F);
+ me->HandleEmoteCommand(EMOTE_ONESHOT_SALUTE);
+ }
+
+ void SpellHit(Unit * /*caster*/, const SpellEntry *spell)
+ {
+ if (spell->Id == SPELL_FLARE || spell->Id == SPELL_FOLLY)
+ {
+ ++FlareCount;
+
+ if (FlareCount >= 2)
+ IsFriend = true;
+ }
+ }
+
+ void EnterCombat(Unit* /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (IsFriend)
+ {
+ if (Reset_Timer <= diff)
+ {
+ EnterEvadeMode();
+ return;
+ } else Reset_Timer -= diff;
+ }
+
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+
+ void ReceiveEmote(Player* /*pPlayer*/, uint32 emote)
+ {
+ if (emote == TEXTEMOTE_SALUTE)
+ {
+ if (FlareCount >= 2)
+ {
+ if (me->getFaction() == FACTION_FRIENDLY_F)
+ return;
+
+ DoFriend();
+ }
+ }
+ }
+};
+
+CreatureAI* GetAI_npc_taskmaster_fizzule(Creature* pCreature)
+{
+ return new npc_taskmaster_fizzuleAI(pCreature);
+}
+
+/*#####
+## npc_twiggy_flathead
+#####*/
+
+enum eTwiggyFlathead
+{
+ NPC_BIG_WILL = 6238,
+ NPC_AFFRAY_CHALLENGER = 6240,
+
+ SAY_BIG_WILL_READY = -1000123,
+ SAY_TWIGGY_FLATHEAD_BEGIN = -1000124,
+ SAY_TWIGGY_FLATHEAD_FRAY = -1000125,
+ SAY_TWIGGY_FLATHEAD_DOWN = -1000126,
+ SAY_TWIGGY_FLATHEAD_OVER = -1000127,
+};
+
+float AffrayChallengerLoc[6][4]=
+{
+ {-1683, -4326, 2.79, 0},
+ {-1682, -4329, 2.79, 0},
+ {-1683, -4330, 2.79, 0},
+ {-1680, -4334, 2.79, 1.49},
+ {-1674, -4326, 2.79, 3.49},
+ {-1677, -4334, 2.79, 1.66}
+};
+
+struct npc_twiggy_flatheadAI : public ScriptedAI
+{
+ npc_twiggy_flatheadAI(Creature *c) : ScriptedAI(c) {}
+
+ bool EventInProgress;
+ bool EventGrate;
+ bool EventBigWill;
+ bool Challenger_down[6];
+ uint32 Wave;
+ uint32 Wave_Timer;
+ uint32 Challenger_checker;
+ uint64 PlayerGUID;
+ uint64 AffrayChallenger[6];
+ uint64 BigWill;
+
+ void Reset()
+ {
+ EventInProgress = false;
+ EventGrate = false;
+ EventBigWill = false;
+ Wave_Timer = 600000;
+ Challenger_checker = 0;
+ Wave = 0;
+ PlayerGUID = 0;
+
+ for (uint8 i = 0; i < 6; ++i)
+ {
+ AffrayChallenger[i] = 0;
+ Challenger_down[i] = false;
+ }
+ BigWill = 0;
+ }
+
+ void EnterCombat(Unit * /*who*/) { }
+
+ void MoveInLineOfSight(Unit *who)
+ {
+ if (!who || (!who->isAlive())) return;
+
+ if (me->IsWithinDistInMap(who, 10.0f) && (who->GetTypeId() == TYPEID_PLAYER) && CAST_PLR(who)->GetQuestStatus(1719) == QUEST_STATUS_INCOMPLETE && !EventInProgress)
+ {
+ PlayerGUID = who->GetGUID();
+ EventInProgress = true;
+ }
+ }
+
+ void KilledUnit(Unit * /*victim*/) { }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (EventInProgress) {
+ Player* pWarrior = NULL;
+
+ if (PlayerGUID)
+ pWarrior = Unit::GetPlayer(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* pCreature = Unit::GetCreature((*me), AffrayChallenger[i]);
+ if (pCreature) {
+ if (pCreature->isAlive())
+ {
+ pCreature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_IN_COMBAT);
+ pCreature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ pCreature->setDeathState(JUST_DIED);
+ }
+ }
+ }
+ AffrayChallenger[i] = 0;
+ Challenger_down[i] = false;
+ }
+
+ if (BigWill)
+ {
+ Creature* pCreature = Unit::GetCreature((*me), BigWill);
+ if (pCreature) {
+ if (pCreature->isAlive()) {
+ pCreature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_IN_COMBAT);
+ pCreature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ pCreature->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* pCreature = me->SummonCreature(NPC_AFFRAY_CHALLENGER, AffrayChallengerLoc[i][0], AffrayChallengerLoc[i][1], AffrayChallengerLoc[i][2], AffrayChallengerLoc[i][3], TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 600000);
+ if (!pCreature)
+ continue;
+ pCreature->setFaction(35);
+ pCreature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ pCreature->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ pCreature->HandleEmoteCommand(EMOTE_ONESHOT_ROAR);
+ AffrayChallenger[i] = pCreature->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* pCreature = Unit::GetCreature((*me), AffrayChallenger[i]);
+ if ((!pCreature || (!pCreature->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 (AffrayChallenger[Wave] && Wave < 6 && !EventBigWill)
+ {
+ DoScriptText(SAY_TWIGGY_FLATHEAD_FRAY, me);
+ Creature* pCreature = Unit::GetCreature((*me), AffrayChallenger[Wave]);
+ if (pCreature && (pCreature->isAlive()))
+ {
+ pCreature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE);
+ pCreature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ pCreature->HandleEmoteCommand(EMOTE_ONESHOT_ROAR);
+ pCreature->setFaction(14);
+ pCreature->AI()->AttackStart(pWarrior);
+ ++Wave;
+ Wave_Timer = 20000;
+ }
+ }
+ else if (Wave >= 6 && !EventBigWill) {
+ if (Creature* pCreature = me->SummonCreature(NPC_BIG_WILL, -1722, -4341, 6.12, 6.26, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 480000))
+ {
+ BigWill = pCreature->GetGUID();
+ //pCreature->GetMotionMaster()->MovePoint(0, -1693, -4343, 4.32);
+ //pCreature->GetMotionMaster()->MovePoint(1, -1684, -4333, 2.78);
+ pCreature->GetMotionMaster()->MovePoint(2, -1682, -4329, 2.79);
+ pCreature->HandleEmoteCommand(EMOTE_STATE_READYUNARMED);
+ EventBigWill = true;
+ Wave_Timer = 1000;
+ }
+ }
+ else if (Wave >= 6 && EventBigWill && BigWill)
+ {
+ Creature* pCreature = Unit::GetCreature((*me), BigWill);
+ if (!pCreature || !pCreature->isAlive())
+ {
+ DoScriptText(SAY_TWIGGY_FLATHEAD_OVER, me);
+ EventInProgress = false;
+ EventBigWill = false;
+ EventGrate = false;
+ PlayerGUID = 0;
+ Wave = 0;
+ }
+ }
+ } else Wave_Timer -= diff;
+ }
+ }
+ }
+};
+
+CreatureAI* GetAI_npc_twiggy_flathead(Creature* pCreature)
+{
+ return new npc_twiggy_flatheadAI (pCreature);
+}
+
+/*#####
+## npc_wizzlecrank_shredder
+#####*/
+
+enum eEnums_Wizzlecrank
+{
+ SAY_START = -1000298,
+ SAY_STARTUP1 = -1000299,
+ SAY_STARTUP2 = -1000300,
+ SAY_MERCENARY = -1000301,
+ SAY_PROGRESS_1 = -1000302,
+ SAY_PROGRESS_2 = -1000303,
+ SAY_PROGRESS_3 = -1000304,
+ SAY_END = -1000305,
+
+ QUEST_ESCAPE = 863,
+ FACTION_RATCHET = 637,
+ NPC_PILOT_WIZZ = 3451,
+ NPC_MERCENARY = 3282,
+};
+
+struct npc_wizzlecrank_shredderAI : public npc_escortAI
+{
+ npc_wizzlecrank_shredderAI(Creature* pCreature) : npc_escortAI(pCreature)
+ {
+ m_bIsPostEvent = false;
+ m_uiPostEventTimer = 1000;
+ m_uiPostEventCount = 0;
+ }
+
+ bool m_bIsPostEvent;
+ uint32 m_uiPostEventTimer;
+ uint32 m_uiPostEventCount;
+
+ void Reset()
+ {
+ if (!HasEscortState(STATE_ESCORT_ESCORTING))
+ {
+ if (me->getStandState() == UNIT_STAND_STATE_DEAD)
+ me->SetStandState(UNIT_STAND_STATE_STAND);
+
+ m_bIsPostEvent = false;
+ m_uiPostEventTimer = 1000;
+ m_uiPostEventCount = 0;
+ }
+ }
+
+ void WaypointReached(uint32 uiPointId)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch(uiPointId)
+ {
+ case 0:
+ DoScriptText(SAY_STARTUP1, me);
+ break;
+ case 9:
+ SetRun(false);
+ break;
+ case 17:
+ if (Creature* pTemp = me->SummonCreature(NPC_MERCENARY, 1128.489f, -3037.611f, 92.701f, 1.472f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 120000))
+ {
+ DoScriptText(SAY_MERCENARY, pTemp);
+ me->SummonCreature(NPC_MERCENARY, 1160.172f, -2980.168f, 97.313f, 3.690f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 120000);
+ }
+ break;
+ case 24:
+ m_bIsPostEvent = true;
+ break;
+ }
+ }
+
+ void WaypointStart(uint32 uiPointId)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch(uiPointId)
+ {
+ case 9:
+ DoScriptText(SAY_STARTUP2, me, pPlayer);
+ break;
+ case 18:
+ DoScriptText(SAY_PROGRESS_1, me, pPlayer);
+ SetRun();
+ break;
+ }
+ }
+
+ void JustSummoned(Creature* pSummoned)
+ {
+ if (pSummoned->GetEntry() == NPC_PILOT_WIZZ)
+ me->SetStandState(UNIT_STAND_STATE_DEAD);
+
+ if (pSummoned->GetEntry() == NPC_MERCENARY)
+ pSummoned->AI()->AttackStart(me);
+ }
+
+ void UpdateEscortAI(const uint32 uiDiff)
+ {
+ if (!UpdateVictim())
+ {
+ if (m_bIsPostEvent)
+ {
+ if (m_uiPostEventTimer <= uiDiff)
+ {
+ switch(m_uiPostEventCount)
+ {
+ case 0:
+ DoScriptText(SAY_PROGRESS_2, me);
+ break;
+ case 1:
+ DoScriptText(SAY_PROGRESS_3, me);
+ break;
+ case 2:
+ DoScriptText(SAY_END, me);
+ break;
+ case 3:
+ if (Player* pPlayer = GetPlayerForEscort())
+ {
+ pPlayer->GroupEventHappens(QUEST_ESCAPE, me);
+ me->SummonCreature(NPC_PILOT_WIZZ, 0.0f, 0.0f, 0.0f, 0.0f, TEMPSUMMON_TIMED_DESPAWN, 180000);
+ }
+ break;
+ }
+
+ ++m_uiPostEventCount;
+ m_uiPostEventTimer = 5000;
+ }
+ else
+ m_uiPostEventTimer -= uiDiff;
+ }
+
+ return;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+bool QuestAccept_npc_wizzlecrank_shredder(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_ESCAPE)
+ {
+ pCreature->setFaction(FACTION_RATCHET);
+ if (npc_escortAI* pEscortAI = CAST_AI(npc_wizzlecrank_shredderAI, pCreature->AI()))
+ pEscortAI->Start(true, false, pPlayer->GetGUID());
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_wizzlecrank_shredderAI(Creature* pCreature)
+{
+ return new npc_wizzlecrank_shredderAI(pCreature);
+}
+
+void AddSC_the_barrens()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_beaten_corpse";
+ newscript->pGossipHello = &GossipHello_npc_beaten_corpse;
+ newscript->pGossipSelect = &GossipSelect_npc_beaten_corpse;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_gilthares";
+ newscript->GetAI = &GetAI_npc_gilthares;
+ newscript->pQuestAccept = &QuestAccept_npc_gilthares;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_sputtervalve";
+ newscript->pGossipHello = &GossipHello_npc_sputtervalve;
+ newscript->pGossipSelect = &GossipSelect_npc_sputtervalve;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_taskmaster_fizzule";
+ newscript->GetAI = &GetAI_npc_taskmaster_fizzule;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_twiggy_flathead";
+ newscript->GetAI = &GetAI_npc_twiggy_flathead;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_wizzlecrank_shredder";
+ newscript->GetAI = &GetAI_npc_wizzlecrank_shredderAI;
+ newscript->pQuestAccept = &QuestAccept_npc_wizzlecrank_shredder;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/thousand_needles.cpp b/src/server/scripts/Kalimdor/thousand_needles.cpp
new file mode 100644
index 00000000000..3f54a62dd0b
--- /dev/null
+++ b/src/server/scripts/Kalimdor/thousand_needles.cpp
@@ -0,0 +1,454 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Thousand Needles
+SD%Complete: 100
+SDComment: Support for Quest: 1950, 4770, 4904, 4966, 5151.
+SDCategory: Thousand Needles
+EndScriptData */
+
+/* ContentData
+npc_kanati
+npc_lakota_windsong
+npc_swiftmountain
+npc_plucky
+go_panther_cage
+npc_enraged_panther
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+
+/*#####
+# npc_kanati
+######*/
+
+enum eKanati
+{
+ SAY_KAN_START = -1000410,
+
+ QUEST_PROTECT_KANATI = 4966,
+ NPC_GALAK_ASS = 10720
+};
+
+const float m_afGalakLoc[]= {-4867.387695, -1357.353760, -48.226 };
+
+struct npc_kanatiAI : public npc_escortAI
+{
+ npc_kanatiAI(Creature* pCreature) : npc_escortAI(pCreature) { }
+
+ void Reset() { }
+
+ void WaypointReached(uint32 uiPointId)
+ {
+ switch(uiPointId)
+ {
+ case 0:
+ DoScriptText(SAY_KAN_START, me);
+ DoSpawnGalak();
+ break;
+ case 1:
+ if (Player* pPlayer = GetPlayerForEscort())
+ pPlayer->GroupEventHappens(QUEST_PROTECT_KANATI, me);
+ break;
+ }
+ }
+
+ void DoSpawnGalak()
+ {
+ for (int i = 0; i < 3; ++i)
+ me->SummonCreature(NPC_GALAK_ASS,
+ m_afGalakLoc[0], m_afGalakLoc[1], m_afGalakLoc[2], 0.0f,
+ TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ }
+
+ void JustSummoned(Creature* pSummoned)
+ {
+ pSummoned->AI()->AttackStart(me);
+ }
+};
+
+CreatureAI* GetAI_npc_kanati(Creature* pCreature)
+{
+ return new npc_kanatiAI(pCreature);
+}
+
+bool QuestAccept_npc_kanati(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_PROTECT_KANATI)
+ {
+ if (npc_kanatiAI* pEscortAI = CAST_AI(npc_kanatiAI, pCreature->AI()))
+ pEscortAI->Start(false, false, pPlayer->GetGUID(), pQuest, true);
+ }
+ return true;
+}
+
+/*######
+# npc_lakota_windsong
+######*/
+
+enum eLakota
+{
+ SAY_LAKO_START = -1000365,
+ SAY_LAKO_LOOK_OUT = -1000366,
+ SAY_LAKO_HERE_COME = -1000367,
+ SAY_LAKO_MORE = -1000368,
+ SAY_LAKO_END = -1000369,
+
+ QUEST_FREE_AT_LAST = 4904,
+ NPC_GRIM_BANDIT = 10758,
+ FACTION_ESCORTEE_LAKO = 232, //guessed
+
+ ID_AMBUSH_1 = 0,
+ ID_AMBUSH_2 = 2,
+ ID_AMBUSH_3 = 4
+};
+
+float m_afBanditLoc[6][6]=
+{
+ {-4905.479492, -2062.732666, 84.352},
+ {-4915.201172, -2073.528320, 84.733},
+ {-4878.883301, -1986.947876, 91.966},
+ {-4877.503906, -1966.113403, 91.859},
+ {-4767.985352, -1873.169189, 90.192},
+ {-4788.861328, -1888.007813, 89.888}
+};
+
+struct npc_lakota_windsongAI : public npc_escortAI
+{
+ npc_lakota_windsongAI(Creature* pCreature) : npc_escortAI(pCreature) { }
+
+ void Reset() { }
+
+ void WaypointReached(uint32 uiPointId)
+ {
+ switch(uiPointId)
+ {
+ case 8:
+ DoScriptText(SAY_LAKO_LOOK_OUT, me);
+ DoSpawnBandits(ID_AMBUSH_1);
+ break;
+ case 14:
+ DoScriptText(SAY_LAKO_HERE_COME, me);
+ DoSpawnBandits(ID_AMBUSH_2);
+ break;
+ case 21:
+ DoScriptText(SAY_LAKO_MORE, me);
+ DoSpawnBandits(ID_AMBUSH_3);
+ break;
+ case 45:
+ if (Player* pPlayer = GetPlayerForEscort())
+ pPlayer->GroupEventHappens(QUEST_FREE_AT_LAST, me);
+ break;
+ }
+ }
+
+ void DoSpawnBandits(int uiAmbushId)
+ {
+ for (int i = 0; i < 2; ++i)
+ me->SummonCreature(NPC_GRIM_BANDIT,
+ m_afBanditLoc[i+uiAmbushId][0], m_afBanditLoc[i+uiAmbushId][1], m_afBanditLoc[i+uiAmbushId][2], 0.0f,
+ TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 60000);
+ }
+};
+
+CreatureAI* GetAI_npc_lakota_windsong(Creature* pCreature)
+{
+ return new npc_lakota_windsongAI(pCreature);
+}
+
+bool QuestAccept_npc_lakota_windsong(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_FREE_AT_LAST)
+ {
+ DoScriptText(SAY_LAKO_START, pCreature, pPlayer);
+ pCreature->setFaction(FACTION_ESCORTEE_LAKO);
+
+ if (npc_lakota_windsongAI* pEscortAI = CAST_AI(npc_lakota_windsongAI, pCreature->AI()))
+ pEscortAI->Start(false, false, pPlayer->GetGUID(), pQuest);
+ }
+ return true;
+}
+
+/*######
+# npc_paoka_swiftmountain
+######*/
+
+enum ePacka
+{
+ SAY_START = -1000362,
+ SAY_WYVERN = -1000363,
+ SAY_COMPLETE = -1000364,
+
+ QUEST_HOMEWARD = 4770,
+ NPC_WYVERN = 4107,
+ FACTION_ESCORTEE = 232 //guessed
+};
+
+float m_afWyvernLoc[3][3]=
+{
+ {-4990.606, -906.057, -5.343},
+ {-4970.241, -927.378, -4.951},
+ {-4985.364, -952.528, -5.199}
+};
+
+struct npc_paoka_swiftmountainAI : public npc_escortAI
+{
+ npc_paoka_swiftmountainAI(Creature* pCreature) : npc_escortAI(pCreature) { }
+
+ void Reset() { }
+
+ void WaypointReached(uint32 uiPointId)
+ {
+ switch(uiPointId)
+ {
+ case 15:
+ DoScriptText(SAY_WYVERN, me);
+ DoSpawnWyvern();
+ break;
+ case 26:
+ DoScriptText(SAY_COMPLETE, me);
+ break;
+ case 27:
+ if (Player* pPlayer = GetPlayerForEscort())
+ pPlayer->GroupEventHappens(QUEST_HOMEWARD, me);
+ break;
+ }
+ }
+
+ void DoSpawnWyvern()
+ {
+ for (int i = 0; i < 3; ++i)
+ me->SummonCreature(NPC_WYVERN,
+ m_afWyvernLoc[i][0], m_afWyvernLoc[i][1], m_afWyvernLoc[i][2], 0.0f,
+ TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 60000);
+ }
+};
+
+CreatureAI* GetAI_npc_paoka_swiftmountain(Creature* pCreature)
+{
+ return new npc_paoka_swiftmountainAI(pCreature);
+}
+
+bool QuestAccept_npc_paoka_swiftmountain(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_HOMEWARD)
+ {
+ DoScriptText(SAY_START, pCreature, pPlayer);
+ pCreature->setFaction(FACTION_ESCORTEE);
+
+ if (npc_paoka_swiftmountainAI* pEscortAI = CAST_AI(npc_paoka_swiftmountainAI,pCreature->AI()))
+ pEscortAI->Start(false, false, pPlayer->GetGUID(), pQuest);
+ }
+ return true;
+}
+
+/*#####
+# npc_plucky
+######*/
+
+#define GOSSIP_P "Please tell me the Phrase.."
+
+enum ePlucky
+{
+ FACTION_FRIENDLY = 35,
+ QUEST_SCOOP = 1950,
+ SPELL_PLUCKY_HUMAN = 9192,
+ SPELL_PLUCKY_CHICKEN = 9220
+};
+
+struct npc_pluckyAI : public ScriptedAI
+{
+ npc_pluckyAI(Creature *c) : ScriptedAI(c) { m_uiNormFaction = c->getFaction(); }
+
+ uint32 m_uiNormFaction;
+ uint32 m_uiResetTimer;
+
+ void Reset()
+ {
+ m_uiResetTimer = 120000;
+
+ if (me->getFaction() != m_uiNormFaction)
+ me->setFaction(m_uiNormFaction);
+
+ if (me->HasFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP))
+ me->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+
+ DoCast(me, SPELL_PLUCKY_CHICKEN, false);
+ }
+
+ void ReceiveEmote(Player* pPlayer, uint32 uiTextEmote)
+ {
+ if (pPlayer->GetQuestStatus(QUEST_SCOOP) == QUEST_STATUS_INCOMPLETE)
+ {
+ if (uiTextEmote == TEXTEMOTE_BECKON)
+ {
+ me->setFaction(FACTION_FRIENDLY);
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ DoCast(me, SPELL_PLUCKY_HUMAN, false);
+ }
+ }
+
+ if (uiTextEmote == TEXTEMOTE_CHICKEN)
+ {
+ if (me->HasFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP))
+ return;
+ else
+ {
+ me->setFaction(FACTION_FRIENDLY);
+ me->SetFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+ DoCast(me, SPELL_PLUCKY_HUMAN, false);
+ me->HandleEmoteCommand(EMOTE_ONESHOT_WAVE);
+ }
+ }
+ }
+
+ void UpdateAI(const uint32 uiDiff)
+ {
+ if (me->HasFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP))
+ {
+ if (m_uiResetTimer <= uiDiff)
+ {
+ if (!me->getVictim())
+ EnterEvadeMode();
+ else
+ me->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP);
+
+ return;
+ }
+ else
+ m_uiResetTimer -= uiDiff;
+ }
+
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+bool GossipHello_npc_plucky(Player* pPlayer, Creature* pCreature)
+{
+ if (pPlayer->GetQuestStatus(QUEST_SCOOP) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_P, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(738, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_plucky(Player* pPlayer, Creature* /*pCreature*/, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch(uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pPlayer->CompleteQuest(QUEST_SCOOP);
+ break;
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_plucky(Creature* pCreature)
+{
+ return new npc_pluckyAI(pCreature);
+}
+
+enum ePantherCage
+{
+ ENRAGED_PANTHER = 10992
+};
+
+bool go_panther_cage(Player* pPlayer, GameObject* pGo)
+{
+
+ if (pPlayer->GetQuestStatus(5151) == QUEST_STATUS_INCOMPLETE)
+ {
+ if (Creature* panther = pGo->FindNearestCreature(ENRAGED_PANTHER, 5, true))
+ {
+ panther->RemoveFlag(UNIT_FIELD_FLAGS,UNIT_FLAG_NON_ATTACKABLE);
+ panther->SetReactState(REACT_AGGRESSIVE);
+ panther->AI()->AttackStart(pPlayer);
+ }
+ }
+
+ return true ;
+}
+
+struct npc_enraged_pantherAI : public ScriptedAI
+{
+ npc_enraged_pantherAI(Creature *c) : ScriptedAI(c) {}
+
+ void Reset()
+ {
+ me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE);
+ me->SetReactState(REACT_PASSIVE);
+ }
+
+ void UpdateAI(const uint32 /*diff*/)
+ {
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_enraged_panther(Creature* pCreature)
+{
+ return new npc_enraged_pantherAI(pCreature);
+}
+
+void AddSC_thousand_needles()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_kanati";
+ newscript->GetAI = &GetAI_npc_kanati;
+ newscript->pQuestAccept = &QuestAccept_npc_kanati;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_lakota_windsong";
+ newscript->GetAI = &GetAI_npc_lakota_windsong;
+ newscript->pQuestAccept = &QuestAccept_npc_lakota_windsong;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_paoka_swiftmountain";
+ newscript->GetAI = &GetAI_npc_paoka_swiftmountain;
+ newscript->pQuestAccept = &QuestAccept_npc_paoka_swiftmountain;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_plucky";
+ newscript->GetAI = &GetAI_npc_plucky;
+ newscript->pGossipHello = &GossipHello_npc_plucky;
+ newscript->pGossipSelect = &GossipSelect_npc_plucky;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name="npc_enraged_panther";
+ newscript->GetAI = &GetAI_npc_enraged_panther;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name="go_panther_cage";
+ newscript->pGOHello = &go_panther_cage;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/thunder_bluff.cpp b/src/server/scripts/Kalimdor/thunder_bluff.cpp
new file mode 100644
index 00000000000..288f00946f0
--- /dev/null
+++ b/src/server/scripts/Kalimdor/thunder_bluff.cpp
@@ -0,0 +1,138 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Thunder_Bluff
+SD%Complete: 100
+SDComment: Quest support: 925
+SDCategory: Thunder Bluff
+EndScriptData */
+
+#include "ScriptedPch.h"
+
+/*#####
+# npc_cairne_bloodhoof
+######*/
+
+#define SPELL_BERSERKER_CHARGE 16636
+#define SPELL_CLEAVE 16044
+#define SPELL_MORTAL_STRIKE 16856
+#define SPELL_THUNDERCLAP 23931
+#define SPELL_UPPERCUT 22916
+
+#define GOSSIP_HCB "I know this is rather silly but a young ward who is a bit shy would like your hoofprint."
+//TODO: verify abilities/timers
+struct npc_cairne_bloodhoofAI : public ScriptedAI
+{
+ npc_cairne_bloodhoofAI(Creature* c) : ScriptedAI(c) {}
+
+ uint32 BerserkerCharge_Timer;
+ uint32 Cleave_Timer;
+ uint32 MortalStrike_Timer;
+ uint32 Thunderclap_Timer;
+ uint32 Uppercut_Timer;
+
+ void Reset()
+ {
+ BerserkerCharge_Timer = 30000;
+ Cleave_Timer = 5000;
+ MortalStrike_Timer = 10000;
+ Thunderclap_Timer = 15000;
+ Uppercut_Timer = 10000;
+ }
+
+ void EnterCombat(Unit * /*who*/) {}
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ if (BerserkerCharge_Timer <= diff)
+ {
+ Unit *pTarget = SelectUnit(SELECT_TARGET_RANDOM,0);
+ if (pTarget)
+ DoCast(pTarget, SPELL_BERSERKER_CHARGE);
+ BerserkerCharge_Timer = 25000;
+ } else BerserkerCharge_Timer -= diff;
+
+ if (Uppercut_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_UPPERCUT);
+ Uppercut_Timer = 20000;
+ } else Uppercut_Timer -= diff;
+
+ if (Thunderclap_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_THUNDERCLAP);
+ Thunderclap_Timer = 15000;
+ } else Thunderclap_Timer -= diff;
+
+ if (MortalStrike_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_MORTAL_STRIKE);
+ MortalStrike_Timer = 15000;
+ } else MortalStrike_Timer -= diff;
+
+ if (Cleave_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_CLEAVE);
+ Cleave_Timer = 7000;
+ } else Cleave_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_npc_cairne_bloodhoof(Creature* pCreature)
+{
+ return new npc_cairne_bloodhoofAI (pCreature);
+}
+
+bool GossipHello_npc_cairne_bloodhoof(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(925) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HCB, GOSSIP_SENDER_MAIN, GOSSIP_SENDER_INFO);
+
+ pPlayer->SEND_GOSSIP_MENU(7013, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_cairne_bloodhoof(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_SENDER_INFO)
+ {
+ pPlayer->CastSpell(pPlayer, 23123, false);
+ pPlayer->SEND_GOSSIP_MENU(7014, pCreature->GetGUID());
+ }
+ return true;
+}
+
+void AddSC_thunder_bluff()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_cairne_bloodhoof";
+ newscript->GetAI = &GetAI_npc_cairne_bloodhoof;
+ newscript->pGossipHello = &GossipHello_npc_cairne_bloodhoof;
+ newscript->pGossipSelect = &GossipSelect_npc_cairne_bloodhoof;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/ungoro_crater.cpp b/src/server/scripts/Kalimdor/ungoro_crater.cpp
new file mode 100644
index 00000000000..2be4a95eb4b
--- /dev/null
+++ b/src/server/scripts/Kalimdor/ungoro_crater.cpp
@@ -0,0 +1,356 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+/* ScriptData
+SDName: Ungoro Crater
+SD%Complete: 100
+SDComment: Support for Quest: 4245, 4491
+SDCategory: Ungoro Crater
+EndScriptData */
+
+/* ContentData
+npc_a-me
+npc_ringo
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+#include "ScriptedFollowerAI.h"
+
+#define SAY_READY -1100200
+#define SAY_AGGRO1 -1100201
+#define SAY_SEARCH -1100202
+#define SAY_AGGRO2 -1100203
+#define SAY_AGGRO3 -1100204
+#define SAY_FINISH -1100205
+
+#define SPELL_DEMORALIZINGSHOUT 13730
+
+#define QUEST_CHASING_AME 4245
+#define ENTRY_TARLORD 6519
+#define ENTRY_TARLORD1 6519
+#define ENTRY_STOMPER 6513
+
+struct npc_ameAI : public npc_escortAI
+{
+ npc_ameAI(Creature *c) : npc_escortAI(c) {}
+
+ uint32 DEMORALIZINGSHOUT_Timer;
+
+ void WaypointReached(uint32 i)
+ {
+ Player* pPlayer = GetPlayerForEscort();
+
+ if (!pPlayer)
+ return;
+
+ switch (i)
+ {
+
+ case 19:
+ me->SummonCreature(ENTRY_STOMPER, -6391.69, -1730.49, -272.83, 4.96, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ DoScriptText(SAY_AGGRO1, me, pPlayer);
+ break;
+ case 28:
+ DoScriptText(SAY_SEARCH, me, pPlayer);
+ break;
+ case 38:
+ me->SummonCreature(ENTRY_TARLORD, -6370.75, -1382.84, -270.51, 6.06, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ DoScriptText(SAY_AGGRO2, me, pPlayer);
+ break;
+ case 49:
+ me->SummonCreature(ENTRY_TARLORD1, -6324.44, -1181.05, -270.17, 4.34, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 25000);
+ DoScriptText(SAY_AGGRO3, me, pPlayer);
+ break;
+ case 55:
+ DoScriptText(SAY_FINISH, me, pPlayer);
+ if (pPlayer)
+ pPlayer->GroupEventHappens(QUEST_CHASING_AME,me);
+ break;
+
+ }
+ }
+
+ void Reset()
+ {
+ DEMORALIZINGSHOUT_Timer = 5000;
+ }
+
+ void JustSummoned(Creature* summoned)
+ {
+ summoned->AI()->AttackStart(me);
+ }
+
+ void JustDied(Unit* /*killer*/)
+ {
+ if (Player* pPlayer = GetPlayerForEscort())
+ pPlayer->FailQuest(QUEST_CHASING_AME);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ npc_escortAI::UpdateAI(diff);
+ if (!UpdateVictim())
+ return;
+
+ if (DEMORALIZINGSHOUT_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_DEMORALIZINGSHOUT);
+ DEMORALIZINGSHOUT_Timer = 70000;
+ } else DEMORALIZINGSHOUT_Timer -= diff;
+
+ }
+};
+
+bool QuestAccept_npc_ame(Player* pPlayer, Creature* pCreature, Quest const* quest)
+{
+ if (quest->GetQuestId() == QUEST_CHASING_AME)
+ {
+ CAST_AI(npc_escortAI, (pCreature->AI()))->Start(false, false, pPlayer->GetGUID());
+ DoScriptText(SAY_READY, pCreature, pPlayer);
+ pCreature->SetUInt32Value(UNIT_FIELD_BYTES_1,0);
+ // Change faction so mobs attack
+ pCreature->setFaction(113);
+ }
+ return true;
+}
+
+CreatureAI* GetAI_npc_ame(Creature* pCreature)
+{
+ return new npc_ameAI(pCreature);
+}
+
+/*####
+# npc_ringo
+####*/
+
+enum eRingo
+{
+ SAY_RIN_START_1 = -1000416,
+ SAY_RIN_START_2 = -1000417,
+
+ SAY_FAINT_1 = -1000418,
+ SAY_FAINT_2 = -1000419,
+ SAY_FAINT_3 = -1000420,
+ SAY_FAINT_4 = -1000421,
+
+ SAY_WAKE_1 = -1000422,
+ SAY_WAKE_2 = -1000423,
+ SAY_WAKE_3 = -1000424,
+ SAY_WAKE_4 = -1000425,
+
+ SAY_RIN_END_1 = -1000426,
+ SAY_SPR_END_2 = -1000427,
+ SAY_RIN_END_3 = -1000428,
+ EMOTE_RIN_END_4 = -1000429,
+ EMOTE_RIN_END_5 = -1000430,
+ SAY_RIN_END_6 = -1000431, // signed for 6784
+ SAY_SPR_END_7 = -1000432,
+ EMOTE_RIN_END_8 = -1000433,
+
+ SPELL_REVIVE_RINGO = 15591,
+ QUEST_A_LITTLE_HELP = 4491,
+ NPC_SPRAGGLE = 9997,
+ FACTION_ESCORTEE = 113
+};
+
+struct npc_ringoAI : public FollowerAI
+{
+ npc_ringoAI(Creature* pCreature) : FollowerAI(pCreature) { }
+
+ uint32 m_uiFaintTimer;
+ uint32 m_uiEndEventProgress;
+ uint32 m_uiEndEventTimer;
+
+ uint64 SpraggleGUID;
+
+ void Reset()
+ {
+ m_uiFaintTimer = urand(30000, 60000);
+ m_uiEndEventProgress = 0;
+ m_uiEndEventTimer = 1000;
+ SpraggleGUID = 0;
+ }
+
+ void MoveInLineOfSight(Unit *pWho)
+ {
+ FollowerAI::MoveInLineOfSight(pWho);
+
+ if (!me->getVictim() && !HasFollowState(STATE_FOLLOW_COMPLETE) && pWho->GetEntry() == NPC_SPRAGGLE)
+ {
+ if (me->IsWithinDistInMap(pWho, INTERACTION_DISTANCE))
+ {
+ if (Player* pPlayer = GetLeaderForFollower())
+ {
+ if (pPlayer->GetQuestStatus(QUEST_A_LITTLE_HELP) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->GroupEventHappens(QUEST_A_LITTLE_HELP, me);
+ }
+
+ SpraggleGUID = pWho->GetGUID();
+ SetFollowComplete(true);
+ }
+ }
+ }
+
+ void SpellHit(Unit* /*pCaster*/, const SpellEntry* pSpell)
+ {
+ if (HasFollowState(STATE_FOLLOW_INPROGRESS | STATE_FOLLOW_PAUSED) && pSpell->Id == SPELL_REVIVE_RINGO)
+ ClearFaint();
+ }
+
+ void SetFaint()
+ {
+ if (!HasFollowState(STATE_FOLLOW_POSTEVENT))
+ {
+ SetFollowPaused(true);
+
+ DoScriptText(RAND(SAY_FAINT_1,SAY_FAINT_2,SAY_FAINT_3,SAY_FAINT_4), me);
+ }
+
+ //what does actually happen here? Emote? Aura?
+ me->SetStandState(UNIT_STAND_STATE_SLEEP);
+ }
+
+ void ClearFaint()
+ {
+ me->SetStandState(UNIT_STAND_STATE_STAND);
+
+ if (HasFollowState(STATE_FOLLOW_POSTEVENT))
+ return;
+
+ DoScriptText(RAND(SAY_WAKE_1,SAY_WAKE_2,SAY_WAKE_3,SAY_WAKE_4), me);
+
+ SetFollowPaused(false);
+ }
+
+ void UpdateFollowerAI(const uint32 uiDiff)
+ {
+ if (!UpdateVictim())
+ {
+ if (HasFollowState(STATE_FOLLOW_POSTEVENT))
+ {
+ if (m_uiEndEventTimer <= uiDiff)
+ {
+ Unit *pSpraggle = Unit::GetUnit(*me, SpraggleGUID);
+ if (!pSpraggle || !pSpraggle->isAlive())
+ {
+ SetFollowComplete();
+ return;
+ }
+
+ switch(m_uiEndEventProgress)
+ {
+ case 1:
+ DoScriptText(SAY_RIN_END_1, me);
+ m_uiEndEventTimer = 3000;
+ break;
+ case 2:
+ DoScriptText(SAY_SPR_END_2, pSpraggle);
+ m_uiEndEventTimer = 5000;
+ break;
+ case 3:
+ DoScriptText(SAY_RIN_END_3, me);
+ m_uiEndEventTimer = 1000;
+ break;
+ case 4:
+ DoScriptText(EMOTE_RIN_END_4, me);
+ SetFaint();
+ m_uiEndEventTimer = 9000;
+ break;
+ case 5:
+ DoScriptText(EMOTE_RIN_END_5, me);
+ ClearFaint();
+ m_uiEndEventTimer = 1000;
+ break;
+ case 6:
+ DoScriptText(SAY_RIN_END_6, me);
+ m_uiEndEventTimer = 3000;
+ break;
+ case 7:
+ DoScriptText(SAY_SPR_END_7, pSpraggle);
+ m_uiEndEventTimer = 10000;
+ break;
+ case 8:
+ DoScriptText(EMOTE_RIN_END_8, me);
+ m_uiEndEventTimer = 5000;
+ break;
+ case 9:
+ SetFollowComplete();
+ break;
+ }
+
+ ++m_uiEndEventProgress;
+ }
+ else
+ m_uiEndEventTimer -= uiDiff;
+ }
+ else if (HasFollowState(STATE_FOLLOW_INPROGRESS))
+ {
+ if (!HasFollowState(STATE_FOLLOW_PAUSED))
+ {
+ if (m_uiFaintTimer <= uiDiff)
+ {
+ SetFaint();
+ m_uiFaintTimer = urand(60000, 120000);
+ }
+ else
+ m_uiFaintTimer -= uiDiff;
+ }
+ }
+
+ return;
+ }
+
+ DoMeleeAttackIfReady();
+ }
+};
+
+CreatureAI* GetAI_npc_ringo(Creature* pCreature)
+{
+ return new npc_ringoAI(pCreature);
+}
+
+bool QuestAccept_npc_ringo(Player* pPlayer, Creature* pCreature, const Quest* pQuest)
+{
+ if (pQuest->GetQuestId() == QUEST_A_LITTLE_HELP)
+ {
+ if (npc_ringoAI* pRingoAI = CAST_AI(npc_ringoAI, pCreature->AI()))
+ {
+ pCreature->SetStandState(UNIT_STAND_STATE_STAND);
+ pRingoAI->StartFollow(pPlayer, FACTION_ESCORTEE, pQuest);
+ }
+ }
+
+ return true;
+}
+
+void AddSC_ungoro_crater()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_ame";
+ newscript->GetAI = &GetAI_npc_ame;
+ newscript->pQuestAccept = &QuestAccept_npc_ame;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_ringo";
+ newscript->GetAI = &GetAI_npc_ringo;
+ newscript->pQuestAccept = &QuestAccept_npc_ringo;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/wailing_caverns/instance_wailing_caverns.cpp b/src/server/scripts/Kalimdor/wailing_caverns/instance_wailing_caverns.cpp
new file mode 100644
index 00000000000..287b5db6d57
--- /dev/null
+++ b/src/server/scripts/Kalimdor/wailing_caverns/instance_wailing_caverns.cpp
@@ -0,0 +1,142 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Instance_Wailing_Caverns
+SD%Complete: 99
+SDComment: Everything seems to work, still need some checking
+SDCategory: Wailing Caverns
+EndScriptData */
+
+#include "ScriptedPch.h"
+#include "wailing_caverns.h"
+
+#define MAX_ENCOUNTER 9
+
+struct instance_wailing_caverns : public ScriptedInstance
+{
+ instance_wailing_caverns(Map* pMap) : ScriptedInstance(pMap) {Initialize();};
+
+ uint32 m_auiEncounter[MAX_ENCOUNTER];
+
+ bool yelled;
+ uint64 NaralexGUID;
+
+ void Initialize()
+ {
+ memset(&m_auiEncounter, 0, sizeof(m_auiEncounter));
+
+ yelled = false;
+ NaralexGUID = 0;
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool /*add*/)
+ {
+ if (pCreature->GetEntry() == DATA_NARALEX)
+ NaralexGUID = pCreature->GetGUID();
+ }
+
+ void SetData(uint32 type, uint32 data)
+ {
+ switch (type)
+ {
+ case TYPE_LORD_COBRAHN: m_auiEncounter[0] = data;break;
+ case TYPE_LORD_PYTHAS: m_auiEncounter[1] = data;break;
+ case TYPE_LADY_ANACONDRA: m_auiEncounter[2] = data;break;
+ case TYPE_LORD_SERPENTIS: m_auiEncounter[3] = data;break;
+ case TYPE_NARALEX_EVENT: m_auiEncounter[4] = data;break;
+ case TYPE_NARALEX_PART1: m_auiEncounter[5] = data;break;
+ case TYPE_NARALEX_PART2: m_auiEncounter[6] = data;break;
+ case TYPE_NARALEX_PART3: m_auiEncounter[7] = data;break;
+ case TYPE_MUTANUS_THE_DEVOURER: m_auiEncounter[8] = data;break;
+ case TYPE_NARALEX_YELLED: yelled = true; break;
+ }
+ if (data == DONE)SaveToDB();
+ }
+
+ uint32 GetData(uint32 type)
+ {
+ switch (type)
+ {
+ case TYPE_LORD_COBRAHN: return m_auiEncounter[0];
+ case TYPE_LORD_PYTHAS: return m_auiEncounter[1];
+ case TYPE_LADY_ANACONDRA: return m_auiEncounter[2];
+ case TYPE_LORD_SERPENTIS: return m_auiEncounter[3];
+ case TYPE_NARALEX_EVENT: return m_auiEncounter[4];
+ case TYPE_NARALEX_PART1: return m_auiEncounter[5];
+ case TYPE_NARALEX_PART2: return m_auiEncounter[6];
+ case TYPE_NARALEX_PART3: return m_auiEncounter[7];
+ case TYPE_MUTANUS_THE_DEVOURER: return m_auiEncounter[8];
+ case TYPE_NARALEX_YELLED: return yelled;
+ }
+ return 0;
+ }
+
+ uint64 GetData64(uint32 data)
+ {
+ if (data == DATA_NARALEX)return NaralexGUID;
+ return 0;
+ }
+
+ std::string GetSaveData()
+ {
+ 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];
+
+ OUT_SAVE_INST_DATA_COMPLETE;
+ return saveStream.str();
+ }
+
+ void Load(const char* in)
+ {
+ if (!in)
+ {
+ OUT_LOAD_INST_DATA_FAIL;
+ return;
+ }
+
+ OUT_LOAD_INST_DATA(in);
+
+ std::istringstream loadStream(in);
+ loadStream >> 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];
+
+ for (uint8 i = 0; i < MAX_ENCOUNTER; ++i)
+ if (m_auiEncounter[i] != DONE)
+ m_auiEncounter[i] = NOT_STARTED;
+
+ OUT_LOAD_INST_DATA_COMPLETE;
+ }
+
+};
+
+InstanceData* GetInstanceData_instance_wailing_caverns(Map* pMap)
+{
+ return new instance_wailing_caverns(pMap);
+}
+
+void AddSC_instance_wailing_caverns()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_wailing_caverns";
+ newscript->GetInstanceData = &GetInstanceData_instance_wailing_caverns;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.cpp b/src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.cpp
new file mode 100644
index 00000000000..544c119fc93
--- /dev/null
+++ b/src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.cpp
@@ -0,0 +1,396 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+* This program is free software; you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation; either version 2 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+/* ScriptData
+SDName: Wailing Caverns
+SD%Complete: 95
+SDComment: Need to add skill usage for Disciple of Naralex
+SDCategory: Wailing Caverns
+EndScriptData */
+
+/* ContentData
+EndContentData */
+
+#include "ScriptedPch.h"
+#include "ScriptedEscortAI.h"
+#include "wailing_caverns.h"
+
+/*######
+## npc_disciple_of_naralex
+######*/
+
+enum eEnums
+{
+ //say
+ SAY_MAKE_PREPARATIONS = -1043001,
+ SAY_TEMPLE_OF_PROMISE = -1043002,
+ SAY_MUST_CONTINUE = -1043003,
+ SAY_BANISH_THE_SPIRITS = -1043004,
+ SAY_CAVERNS_PURIFIED = -1043005,
+ SAY_BEYOND_THIS_CORRIDOR = -1043006,
+ SAY_EMERALD_DREAM = -1043007,
+ SAY_MUTANUS_THE_DEVOURER = -1043012,
+ SAY_NARALEX_AWAKES = -1043014,
+ SAY_THANK_YOU = -1043015,
+ SAY_FAREWELL = -1043016,
+ SAY_ATTACKED = -1043017,
+ //yell
+ SAY_AT_LAST = -1043000,
+ SAY_I_AM_AWAKE = -1043013,
+ //emote
+ EMOTE_AWAKENING_RITUAL = -1043008,
+ EMOTE_TROUBLED_SLEEP = -1043009,
+ EMOTE_WRITHE_IN_AGONY = -1043010,
+ EMOTE_HORRENDOUS_VISION = -1043011,
+ //spell
+ SPELL_MARK_OF_THE_WILD_RANK_2 = 5232,
+ SPELL_SERPENTINE_CLEANSING = 6270,
+ SPELL_NARALEXS_AWAKENING = 6271,
+ SPELL_FLIGHT_FORM = 33943,
+ //npc entry
+ NPC_DEVIATE_RAVAGER = 3636,
+ NPC_DEVIATE_VIPER = 5755,
+ NPC_DEVIATE_MOCCASIN = 5762,
+ NPC_NIGHTMARE_ECTOPLASM = 5763,
+ NPC_MUTANUS_THE_DEVOURER = 3654,
+};
+
+#define GOSSIP_ID_START_1 698 //Naralex sleeps again!
+#define GOSSIP_ID_START_2 699 //The fanglords are dead!
+#define GOSSIP_ITEM_NARALEX "Let the event begin!"
+#define ACHIEVEMENT_WAILING_CAVERNS 630
+
+struct npc_disciple_of_naralexAI : public npc_escortAI
+{
+ npc_disciple_of_naralexAI(Creature *c) : npc_escortAI(c)
+ {
+ pInstance = c->GetInstanceData();
+ eventTimer = 0;
+ currentEvent = 0;
+ eventProgress = 0;
+ me->setActive(true);
+ me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE);
+ }
+
+ uint32 eventTimer;
+ uint32 currentEvent;
+ uint32 eventProgress;
+ ScriptedInstance *pInstance;
+
+ void WaypointReached(uint32 i)
+ {
+ if (!pInstance)
+ return;
+
+ switch (i)
+ {
+ case 4:
+ eventProgress = 1;
+ currentEvent = TYPE_NARALEX_PART1;
+ pInstance->SetData(TYPE_NARALEX_PART1, IN_PROGRESS);
+ break;
+ case 5:
+ DoScriptText(SAY_MUST_CONTINUE, me);
+ pInstance->SetData(TYPE_NARALEX_PART1, DONE);
+ break;
+ case 11:
+ eventProgress = 1;
+ currentEvent = TYPE_NARALEX_PART2;
+ pInstance->SetData(TYPE_NARALEX_PART2, IN_PROGRESS);
+ break;
+ case 19:
+ DoScriptText(SAY_BEYOND_THIS_CORRIDOR, me);
+ break;
+ case 24:
+ eventProgress = 1;
+ currentEvent = TYPE_NARALEX_PART3;
+ pInstance->SetData(TYPE_NARALEX_PART3, IN_PROGRESS);
+ break;
+ }
+ }
+
+ void Reset()
+ {
+
+ }
+
+ void EnterCombat(Unit* who)
+ {
+ DoScriptText(SAY_ATTACKED, me, who);
+ }
+
+ void JustDied(Unit * /*slayer*/)
+ {
+ if (pInstance)
+ {
+ pInstance->SetData(TYPE_NARALEX_EVENT, FAIL);
+ pInstance->SetData(TYPE_NARALEX_PART1, FAIL);
+ pInstance->SetData(TYPE_NARALEX_PART2, FAIL);
+ pInstance->SetData(TYPE_NARALEX_PART3, FAIL);
+ }
+ }
+
+ void JustSummoned(Creature* summoned)
+ {
+ summoned->AI()->AttackStart(me);
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (currentEvent != TYPE_NARALEX_PART3)
+ npc_escortAI::UpdateAI(diff);
+
+ if (!pInstance)
+ return;
+ if (eventTimer <= diff)
+ {
+ eventTimer = 0;
+ if (pInstance->GetData(currentEvent) == IN_PROGRESS)
+ {
+ switch (currentEvent)
+ {
+ case TYPE_NARALEX_PART1:
+ if (eventProgress == 1)
+ {
+ ++eventProgress;
+ DoScriptText(SAY_TEMPLE_OF_PROMISE, me);
+ me->SummonCreature(NPC_DEVIATE_RAVAGER, -82.1763, 227.874, -93.3233, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 5000);
+ me->SummonCreature(NPC_DEVIATE_RAVAGER, -72.9506, 216.645, -93.6756, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 5000);
+ }
+ break;
+ case TYPE_NARALEX_PART2:
+ if (eventProgress == 1)
+ {
+ ++eventProgress;
+ DoScriptText(SAY_BANISH_THE_SPIRITS, me);
+ DoCast(me, SPELL_SERPENTINE_CLEANSING);
+ //CAST_AI(npc_escortAI, me->AI())->SetCanDefend(false);
+ eventTimer = 30000;
+ me->SummonCreature(NPC_DEVIATE_VIPER, -61.5261, 273.676, -92.8442, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 5000);
+ me->SummonCreature(NPC_DEVIATE_VIPER, -58.4658, 280.799, -92.8393, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 5000);
+ me->SummonCreature(NPC_DEVIATE_VIPER, -50.002, 278.578, -92.8442, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 5000);
+ }
+ else
+ if (eventProgress == 2)
+ {
+ //CAST_AI(npc_escortAI, me->AI())->SetCanDefend(true);
+ DoScriptText(SAY_CAVERNS_PURIFIED, me);
+ pInstance->SetData(TYPE_NARALEX_PART2, DONE);
+ if (me->HasAura(SPELL_SERPENTINE_CLEANSING))
+ me->RemoveAura(SPELL_SERPENTINE_CLEANSING);
+ }
+ break;
+ case TYPE_NARALEX_PART3:
+ if (eventProgress == 1)
+ {
+ ++eventProgress;
+ eventTimer = 4000;
+ me->SetStandState(UNIT_STAND_STATE_KNEEL);
+ DoScriptText(SAY_EMERALD_DREAM, me);
+ }
+ else
+ if (eventProgress == 2)
+ {
+ ++eventProgress;
+ eventTimer = 15000;
+ //CAST_AI(npc_escortAI, me->AI())->SetCanDefend(false);
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ DoCast(naralex, SPELL_NARALEXS_AWAKENING, true);
+ DoScriptText(EMOTE_AWAKENING_RITUAL, me);
+ }
+ else
+ if (eventProgress == 3)
+ {
+ ++eventProgress;
+ eventTimer = 15000;
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ DoScriptText(EMOTE_TROUBLED_SLEEP, naralex);
+ me->SummonCreature(NPC_DEVIATE_MOCCASIN, 135.943, 199.701, -103.529, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ me->SummonCreature(NPC_DEVIATE_MOCCASIN, 151.08, 221.13, -103.609, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ me->SummonCreature(NPC_DEVIATE_MOCCASIN, 128.007, 227.428, -97.421, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ }
+ else
+ if (eventProgress == 4)
+ {
+ ++eventProgress;
+ eventTimer = 30000;
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ DoScriptText(EMOTE_WRITHE_IN_AGONY, naralex);
+ me->SummonCreature(NPC_NIGHTMARE_ECTOPLASM, 133.413, 207.188, -102.469, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ me->SummonCreature(NPC_NIGHTMARE_ECTOPLASM, 142.857, 218.645, -102.905, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ me->SummonCreature(NPC_NIGHTMARE_ECTOPLASM, 105.102, 227.211, -102.752, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ me->SummonCreature(NPC_NIGHTMARE_ECTOPLASM, 153.372, 235.149, -102.826, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ me->SummonCreature(NPC_NIGHTMARE_ECTOPLASM, 149.524, 251.113, -102.558, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ me->SummonCreature(NPC_NIGHTMARE_ECTOPLASM, 136.208, 266.466, -102.977, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ me->SummonCreature(NPC_NIGHTMARE_ECTOPLASM, 126.167, 274.759, -102.962, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 15000);
+ }
+ else
+ if (eventProgress == 5)
+ {
+ ++eventProgress;
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ DoScriptText(EMOTE_HORRENDOUS_VISION, naralex);
+ me->SummonCreature(NPC_MUTANUS_THE_DEVOURER, 150.872, 262.905, -103.503, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 300000);
+ DoScriptText(SAY_MUTANUS_THE_DEVOURER, me);
+ pInstance->SetData(TYPE_MUTANUS_THE_DEVOURER, IN_PROGRESS);
+ }
+ else
+ if (eventProgress == 6 && pInstance->GetData(TYPE_MUTANUS_THE_DEVOURER) == DONE)
+ {
+ ++eventProgress;
+ eventTimer = 3000;
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ {
+ AchievementEntry const *AchievWC = GetAchievementStore()->LookupEntry(ACHIEVEMENT_WAILING_CAVERNS);
+ if (AchievWC)
+ {
+ Map* pMap = me->GetMap();
+ if (pMap && pMap->IsDungeon())
+ {
+ Map::PlayerList const &players = pMap->GetPlayers();
+ for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr)
+ itr->getSource()->CompletedAchievement(AchievWC);
+ }
+ }
+ if (me->HasAura(SPELL_NARALEXS_AWAKENING))
+ me->RemoveAura(SPELL_NARALEXS_AWAKENING);
+ naralex->SetStandState(UNIT_STAND_STATE_STAND);
+ DoScriptText(SAY_I_AM_AWAKE, naralex);
+ }
+ DoScriptText(SAY_NARALEX_AWAKES, me);
+ }
+ else
+ if (eventProgress == 7)
+ {
+ ++eventProgress;
+ eventTimer = 6000;
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ DoScriptText(SAY_THANK_YOU, naralex);
+ }
+ else
+ if (eventProgress == 8)
+ {
+ ++eventProgress;
+ eventTimer = 8000;
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ {
+ DoScriptText(SAY_FAREWELL, naralex);
+ naralex->AddAura(SPELL_FLIGHT_FORM, naralex);
+ }
+ SetRun();
+ me->SetStandState(UNIT_STAND_STATE_STAND);
+ me->AddAura(SPELL_FLIGHT_FORM, me);
+ }
+ else
+ if (eventProgress == 9)
+ {
+ ++eventProgress;
+ eventTimer = 1500;
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ naralex->GetMotionMaster()->MovePoint(25, naralex->GetPositionX(), naralex->GetPositionY(), naralex->GetPositionZ());
+ }
+ else
+ if (eventProgress == 10)
+ {
+ ++eventProgress;
+ eventTimer = 2500;
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ {
+ naralex->GetMotionMaster()->MovePoint(0, 117.095512, 247.107971, -96.167870);
+ naralex->GetMotionMaster()->MovePoint(1, 90.388809, 276.135406, -83.389801);
+ }
+ me->GetMotionMaster()->MovePoint(26, 117.095512, 247.107971, -96.167870);
+ me->GetMotionMaster()->MovePoint(27, 144.375443, 281.045837, -82.477135);
+ }
+ else
+ if (eventProgress == 11)
+ {
+ if (Creature* naralex = pInstance->instance->GetCreature(pInstance->GetData64(DATA_NARALEX)))
+ naralex->SetVisibility(VISIBILITY_OFF);
+ me->SetVisibility(VISIBILITY_OFF);
+ pInstance->SetData(TYPE_NARALEX_PART3, DONE);
+ }
+ break;
+ }
+ }
+ } else eventTimer -= diff;
+ }
+};
+
+CreatureAI* GetAI_npc_disciple_of_naralex(Creature* pCreature)
+{
+ return new npc_disciple_of_naralexAI(pCreature);
+}
+
+bool GossipHello_npc_disciple_of_naralex(Player* pPlayer, Creature* pCreature)
+{
+ ScriptedInstance *pInstance = pCreature->GetInstanceData();
+
+ if (pInstance)
+ {
+ pCreature->CastSpell(pPlayer, SPELL_MARK_OF_THE_WILD_RANK_2, true);
+ if ((pInstance->GetData(TYPE_LORD_COBRAHN) == DONE) && (pInstance->GetData(TYPE_LORD_PYTHAS) == DONE) &&
+ (pInstance->GetData(TYPE_LADY_ANACONDRA) == DONE) && (pInstance->GetData(TYPE_LORD_SERPENTIS) == DONE))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_ITEM_NARALEX, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_ID_START_2, pCreature->GetGUID());
+
+ if (!pInstance->GetData(TYPE_NARALEX_YELLED))
+ {
+ DoScriptText(SAY_AT_LAST, pCreature);
+ pInstance->SetData(TYPE_NARALEX_YELLED, 1);
+ }
+ }
+ else
+ {
+ pPlayer->SEND_GOSSIP_MENU(GOSSIP_ID_START_1, pCreature->GetGUID());
+ }
+ }
+ return true;
+}
+
+bool GossipSelect_npc_disciple_of_naralex(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ ScriptedInstance *pInstance = pCreature->GetInstanceData();
+ if (uiAction == GOSSIP_ACTION_INFO_DEF + 1)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ if (pInstance)
+ pInstance->SetData(TYPE_NARALEX_EVENT, IN_PROGRESS);
+
+ DoScriptText(SAY_MAKE_PREPARATIONS, pCreature);
+
+ pCreature->setFaction(250);
+ pCreature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE);
+
+ CAST_AI(npc_escortAI, (pCreature->AI()))->Start(false, false, pPlayer->GetGUID());
+ CAST_AI(npc_escortAI, (pCreature->AI()))->SetDespawnAtFar(false);
+ CAST_AI(npc_escortAI, (pCreature->AI()))->SetDespawnAtEnd(false);
+ }
+ return true;
+}
+
+void AddSC_wailing_caverns()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_disciple_of_naralex";
+ newscript->pGossipHello = &GossipHello_npc_disciple_of_naralex;
+ newscript->pGossipSelect = &GossipSelect_npc_disciple_of_naralex;
+ newscript->GetAI = &GetAI_npc_disciple_of_naralex;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.h b/src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.h
new file mode 100644
index 00000000000..6ef1a673c59
--- /dev/null
+++ b/src/server/scripts/Kalimdor/wailing_caverns/wailing_caverns.h
@@ -0,0 +1,24 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software licensed under GPL version 2
+ * Please see the included DOCS/LICENSE.TXT for more information */
+
+#ifndef DEF_WAILING_CAVERNS_H
+#define DEF_WAILING_CAVERNS_H
+
+enum eTypes
+{
+ TYPE_LORD_COBRAHN = 1,
+ TYPE_LORD_PYTHAS = 2,
+ TYPE_LADY_ANACONDRA = 3,
+ TYPE_LORD_SERPENTIS = 4,
+ TYPE_NARALEX_EVENT = 5,
+ TYPE_NARALEX_PART1 = 6,
+ TYPE_NARALEX_PART2 = 7,
+ TYPE_NARALEX_PART3 = 8,
+ TYPE_MUTANUS_THE_DEVOURER = 9,
+ TYPE_NARALEX_YELLED = 10,
+
+ DATA_NARALEX = 3679,
+};
+
+#endif
diff --git a/src/server/scripts/Kalimdor/winterspring.cpp b/src/server/scripts/Kalimdor/winterspring.cpp
new file mode 100644
index 00000000000..a284f32aeaa
--- /dev/null
+++ b/src/server/scripts/Kalimdor/winterspring.cpp
@@ -0,0 +1,168 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Winterspring
+SD%Complete: 90
+SDComment: Quest support: 5126 (Loraxs' tale missing proper gossip items text). Vendor Rivern Frostwind. Obtain Cache of Mau'ari
+SDCategory: Winterspring
+EndScriptData */
+
+/* ContentData
+npc_lorax
+npc_rivern_frostwind
+npc_witch_doctor_mauari
+EndContentData */
+
+#include "ScriptedPch.h"
+
+/*######
+## npc_lorax
+######*/
+
+#define GOSSIP_HL "Talk to me"
+
+#define GOSSIP_SL1 "What do you do here?"
+#define GOSSIP_SL2 "I can help you"
+#define GOSSIP_SL3 "What deal?"
+#define GOSSIP_SL4 "Then what happened?"
+#define GOSSIP_SL5 "He is not safe, i'll make sure of that."
+
+bool GossipHello_npc_lorax(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestStatus(5126) == QUEST_STATUS_INCOMPLETE)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HL, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_lorax(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ switch (uiAction)
+ {
+ case GOSSIP_ACTION_INFO_DEF:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SL1, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
+ pPlayer->SEND_GOSSIP_MENU(3759, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+1:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SL2, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
+ pPlayer->SEND_GOSSIP_MENU(3760, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+2:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SL3, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 3);
+ pPlayer->SEND_GOSSIP_MENU(3761, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+3:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SL4, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 4);
+ pPlayer->SEND_GOSSIP_MENU(3762, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+4:
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_SL5, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 5);
+ pPlayer->SEND_GOSSIP_MENU(3763, pCreature->GetGUID());
+ break;
+ case GOSSIP_ACTION_INFO_DEF+5:
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pPlayer->AreaExploredOrEventHappens(5126);
+ break;
+ }
+ return true;
+}
+
+/*######
+## npc_rivern_frostwind
+######*/
+
+bool GossipHello_npc_rivern_frostwind(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pCreature->isVendor() && pPlayer->GetReputationRank(589) == REP_EXALTED)
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_VENDOR, GOSSIP_TEXT_BROWSE_GOODS, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_TRADE);
+
+ pPlayer->SEND_GOSSIP_MENU(pPlayer->GetGossipTextId(pCreature), pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_rivern_frostwind(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_TRADE)
+ pPlayer->SEND_VENDORLIST(pCreature->GetGUID());
+
+ return true;
+}
+
+/*######
+## npc_witch_doctor_mauari
+######*/
+
+#define GOSSIP_HWDM "I'd like you to make me a new Cache of Mau'ari please."
+
+bool GossipHello_npc_witch_doctor_mauari(Player* pPlayer, Creature* pCreature)
+{
+ if (pCreature->isQuestGiver())
+ pPlayer->PrepareQuestMenu(pCreature->GetGUID());
+
+ if (pPlayer->GetQuestRewardStatus(975))
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_HWDM, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(3377, pCreature->GetGUID());
+ }else
+ pPlayer->SEND_GOSSIP_MENU(3375, pCreature->GetGUID());
+
+ return true;
+}
+
+bool GossipSelect_npc_witch_doctor_mauari(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pCreature->CastSpell(pPlayer, 16351, false);
+ }
+
+ return true;
+}
+
+void AddSC_winterspring()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_lorax";
+ newscript->pGossipHello = &GossipHello_npc_lorax;
+ newscript->pGossipSelect = &GossipSelect_npc_lorax;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_rivern_frostwind";
+ newscript->pGossipHello = &GossipHello_npc_rivern_frostwind;
+ newscript->pGossipSelect = &GossipSelect_npc_rivern_frostwind;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_witch_doctor_mauari";
+ newscript->pGossipHello = &GossipHello_npc_witch_doctor_mauari;
+ newscript->pGossipSelect = &GossipSelect_npc_witch_doctor_mauari;
+ newscript->RegisterSelf();
+}
+
diff --git a/src/server/scripts/Kalimdor/zulfarrak/instance_zulfarrak.cpp b/src/server/scripts/Kalimdor/zulfarrak/instance_zulfarrak.cpp
new file mode 100644
index 00000000000..530ef30f44c
--- /dev/null
+++ b/src/server/scripts/Kalimdor/zulfarrak/instance_zulfarrak.cpp
@@ -0,0 +1,58 @@
+ /*
+ * Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#include "ScriptedPch.h"
+
+#define NPC_GAHZRILLA 7273
+
+struct instance_zulfarrak : public ScriptedInstance
+{
+ instance_zulfarrak(Map* pMap) : ScriptedInstance(pMap) {Initialize();}
+
+ uint32 GahzRillaEncounter;
+
+ void Initialize()
+ {
+ GahzRillaEncounter = NOT_STARTED;
+ }
+
+ void OnCreatureCreate(Creature* pCreature, bool /*add*/)
+ {
+ if (pCreature->GetEntry() == NPC_GAHZRILLA)
+ {
+ if (GahzRillaEncounter >= IN_PROGRESS)
+ pCreature->DisappearAndDie();
+ else
+ GahzRillaEncounter = IN_PROGRESS;
+ }
+ }
+};
+
+InstanceData* GetInstanceData_instance_zulfarrak(Map* pMap)
+{
+ return new instance_zulfarrak(pMap);
+}
+
+void AddSC_instance_zulfarrak()
+{
+ Script *newscript;
+ newscript = new Script;
+ newscript->Name = "instance_zulfarrak";
+ newscript->GetInstanceData = &GetInstanceData_instance_zulfarrak;
+ newscript->RegisterSelf();
+}
diff --git a/src/server/scripts/Kalimdor/zulfarrak/zulfarrak.cpp b/src/server/scripts/Kalimdor/zulfarrak/zulfarrak.cpp
new file mode 100644
index 00000000000..2ca053c23b6
--- /dev/null
+++ b/src/server/scripts/Kalimdor/zulfarrak/zulfarrak.cpp
@@ -0,0 +1,280 @@
+/* Copyright (C) 2006 - 2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/* ScriptData
+SDName: Zulfarrak
+SD%Complete: 50
+SDComment: Consider it temporary, no instance script made for this instance yet.
+SDCategory: Zul'Farrak
+EndScriptData */
+
+/* ContentData
+npc_sergeant_bly
+npc_weegli_blastfuse
+EndContentData */
+
+#include "ScriptedPch.h"
+
+/*######
+## npc_sergeant_bly
+######*/
+
+#define FACTION_HOSTILE 14
+#define FACTION_FRIENDLY 35
+
+#define SPELL_SHIELD_BASH 11972
+#define SPELL_REVENGE 12170
+
+#define GOSSIP_BLY "[PH] In that case, I will take my reward!"
+
+struct npc_sergeant_blyAI : public ScriptedAI
+{
+ npc_sergeant_blyAI(Creature *c) : ScriptedAI(c)
+ {
+ //pInstance = c->GetInstanceData();
+ }
+
+ //ScriptedInstance* pInstance;
+
+ uint32 ShieldBash_Timer;
+ uint32 Revenge_Timer; //this is wrong, spell should never be used unless me->getVictim() dodge, parry or block attack. Trinity support required.
+
+ void Reset()
+ {
+ ShieldBash_Timer = 5000;
+ Revenge_Timer = 8000;
+
+ me->setFaction(FACTION_FRIENDLY);
+
+ /*if (pInstance)
+ pInstance->SetData(0, NOT_STARTED);*/
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ /*if (pInstance)
+ pInstance->SetData(0, IN_PROGRESS);*/
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ /*if (pInstance)
+ pInstance->SetData(0, DONE);*/
+ }
+
+ void UpdateAI(const uint32 diff)
+ {
+ if (!UpdateVictim())
+ return;
+
+ if (ShieldBash_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_SHIELD_BASH);
+ ShieldBash_Timer = 15000;
+ } else ShieldBash_Timer -= diff;
+
+ if (Revenge_Timer <= diff)
+ {
+ DoCast(me->getVictim(), SPELL_REVENGE);
+ Revenge_Timer = 10000;
+ } else Revenge_Timer -= diff;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_npc_sergeant_bly(Creature* pCreature)
+{
+ return new npc_sergeant_blyAI (pCreature);
+}
+
+bool GossipHello_npc_sergeant_bly(Player* pPlayer, Creature* pCreature)
+{
+ /*if (pInstance->GetData(0) == DONE)
+ {*/
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_BLY, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(1517, pCreature->GetGUID());
+ /*}
+ else if (pInstance->GetData(0) == IN_PROGRESS)
+ pPlayer->SEND_GOSSIP_MENU(1516, pCreature->GetGUID());
+ else
+ pPlayer->SEND_GOSSIP_MENU(1515, pCreature->GetGUID());*/
+
+ return true;
+}
+
+bool GossipSelect_npc_sergeant_bly(Player* pPlayer, Creature* pCreature, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ pCreature->setFaction(FACTION_HOSTILE);
+ CAST_AI(npc_sergeant_blyAI, pCreature->AI())->AttackStart(pPlayer);
+ }
+ return true;
+}
+
+/*######
+## npc_weegli_blastfuse
+######*/
+
+#define SPELL_BOMB 8858
+#define SPELL_GOBLIN_LAND_MINE 21688
+#define SPELL_SHOOT 6660
+#define SPELL_WEEGLIS_BARREL 10772
+
+#define GOSSIP_WEEGLI "[PH] Please blow up the door."
+
+struct npc_weegli_blastfuseAI : public ScriptedAI
+{
+ npc_weegli_blastfuseAI(Creature *c) : ScriptedAI(c)
+ {
+ //pInstance = c->GetInstanceData();
+ }
+
+ //ScriptedInstance* pInstance;
+
+ void Reset()
+ {
+ /*if (pInstance)
+ pInstance->SetData(0, NOT_STARTED);*/
+ }
+
+ void EnterCombat(Unit * /*who*/)
+ {
+ /*if (pInstance)
+ pInstance->SetData(0, IN_PROGRESS);*/
+ }
+
+ void JustDied(Unit * /*victim*/)
+ {
+ /*if (pInstance)
+ pInstance->SetData(0, DONE);*/
+ }
+
+ void UpdateAI(const uint32 /*diff*/)
+ {
+ if (!UpdateVictim())
+ return;
+
+ DoMeleeAttackIfReady();
+ }
+};
+CreatureAI* GetAI_npc_weegli_blastfuse(Creature* pCreature)
+{
+ return new npc_weegli_blastfuseAI (pCreature);
+}
+
+bool GossipHello_npc_weegli_blastfuse(Player* pPlayer, Creature* pCreature)
+{
+ //event not implemented yet, this is only placeholder for future developement
+ /*if (pInstance->GetData(0) == DONE)
+ {
+ pPlayer->ADD_GOSSIP_ITEM(GOSSIP_ICON_CHAT, GOSSIP_WEEGLI, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF+1);
+ pPlayer->SEND_GOSSIP_MENU(1514, pCreature->GetGUID());//if event can proceed to end
+ }
+ else if (pInstance->GetData(0) == IN_PROGRESS)
+ pPlayer->SEND_GOSSIP_MENU(1513, pCreature->GetGUID());//if event are in progress
+ else*/
+ pPlayer->SEND_GOSSIP_MENU(1511, pCreature->GetGUID()); //if event not started
+ return true;
+}
+
+bool GossipSelect_npc_weegli_blastfuse(Player* pPlayer, Creature* /*pCreature*/, uint32 /*uiSender*/, uint32 uiAction)
+{
+ if (uiAction == GOSSIP_ACTION_INFO_DEF+1)
+ {
+ pPlayer->CLOSE_GOSSIP_MENU();
+ //here we make him run to door, set the charge and run away off to nowhere
+ }
+ return true;
+}
+
+/*######
+## go_shallow_grave
+######*/
+
+enum {
+ ZOMBIE = 7286,
+ DEAD_HERO = 7276,
+ ZOMBIE_CHANCE = 65,
+ DEAD_HERO_CHANCE = 10
+};
+
+bool GOHello_go_shallow_grave(Player* /*pPlayer*/, GameObject* pGo)
+{
+ // randomly summon a zombie or dead hero the first time a grave is used
+ if (pGo->GetUseCount() == 0)
+ {
+ uint32 randomchance = urand(0,100);
+ if (randomchance < ZOMBIE_CHANCE)
+ pGo->SummonCreature(ZOMBIE, pGo->GetPositionX(), pGo->GetPositionY(), pGo->GetPositionZ(), 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 30000);
+ else if ((randomchance-ZOMBIE_CHANCE) < DEAD_HERO_CHANCE)
+ pGo->SummonCreature(DEAD_HERO, pGo->GetPositionX(), pGo->GetPositionY(), pGo->GetPositionZ(), 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 30000);
+ }
+ pGo->AddUse();
+ return false;
+}
+
+/*######
+## at_zumrah
+######*/
+
+enum {
+ ZUMRAH_ID = 7271,
+ ZUMRAH_HOSTILE_FACTION = 37
+};
+
+bool AreaTrigger_at_zumrah(Player* pPlayer, const AreaTriggerEntry * /*at*/)
+{
+ Creature* Zumrah = pPlayer->FindNearestCreature(ZUMRAH_ID, 30.0f);
+
+ if (!Zumrah)
+ return false;
+
+ Zumrah->setFaction(ZUMRAH_HOSTILE_FACTION);
+ Zumrah->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_OOC_NOT_ATTACKABLE);
+ return true;
+}
+
+void AddSC_zulfarrak()
+{
+ Script *newscript;
+
+ newscript = new Script;
+ newscript->Name = "npc_sergeant_bly";
+ newscript->GetAI = &GetAI_npc_sergeant_bly;
+ newscript->pGossipHello = &GossipHello_npc_sergeant_bly;
+ newscript->pGossipSelect = &GossipSelect_npc_sergeant_bly;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "npc_weegli_blastfuse";
+ newscript->GetAI = &GetAI_npc_weegli_blastfuse;
+ newscript->pGossipHello = &GossipHello_npc_weegli_blastfuse;
+ newscript->pGossipSelect = &GossipSelect_npc_weegli_blastfuse;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "go_shallow_grave";
+ newscript->pGOHello = &GOHello_go_shallow_grave;
+ newscript->RegisterSelf();
+
+ newscript = new Script;
+ newscript->Name = "at_zumrah";
+ newscript->pAreaTrigger = &AreaTrigger_at_zumrah;
+ newscript->RegisterSelf();
+
+}