mirror of
https://github.com/mangosfour/server.git
synced 2025-12-14 07:37:01 +00:00
Merge 'master' into 310
Please enter the commit message for your changes. Lines starting
This commit is contained in:
parent
3423b5dbb2
commit
66f554f74d
26 changed files with 513 additions and 395 deletions
|
|
@ -235,15 +235,6 @@ bool AreaTrigger ( Player *player, AreaTriggerEntry* atEntry )
|
||||||
return tmpscript->pAreaTrigger(player, atEntry);
|
return tmpscript->pAreaTrigger(player, atEntry);
|
||||||
}
|
}
|
||||||
|
|
||||||
MANGOS_DLL_EXPORT
|
|
||||||
bool ReceiveEmote ( Player *player, Creature *_Creature, uint32 emote )
|
|
||||||
{
|
|
||||||
Script *tmpscript = m_scripts[_Creature->GetScriptId()];
|
|
||||||
if(!tmpscript || !tmpscript->pReceiveEmote) return false;
|
|
||||||
|
|
||||||
return tmpscript->pReceiveEmote(player,_Creature, emote);
|
|
||||||
}
|
|
||||||
|
|
||||||
MANGOS_DLL_EXPORT
|
MANGOS_DLL_EXPORT
|
||||||
bool ItemUse( Player *player, Item* _Item, SpellCastTargets const& targets)
|
bool ItemUse( Player *player, Item* _Item, SpellCastTargets const& targets)
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -41,7 +41,7 @@ struct Script
|
||||||
pGossipHello(NULL), pQuestAccept(NULL), pGossipSelect(NULL), pGossipSelectWithCode(NULL),
|
pGossipHello(NULL), pQuestAccept(NULL), pGossipSelect(NULL), pGossipSelectWithCode(NULL),
|
||||||
pQuestSelect(NULL), pQuestComplete(NULL), pNPCDialogStatus(NULL), pGODialogStatus(NULL), pChooseReward(NULL),
|
pQuestSelect(NULL), pQuestComplete(NULL), pNPCDialogStatus(NULL), pGODialogStatus(NULL), pChooseReward(NULL),
|
||||||
pItemHello(NULL), pGOHello(NULL), pAreaTrigger(NULL), pItemQuestAccept(NULL), pGOQuestAccept(NULL),
|
pItemHello(NULL), pGOHello(NULL), pAreaTrigger(NULL), pItemQuestAccept(NULL), pGOQuestAccept(NULL),
|
||||||
pGOChooseReward(NULL), pReceiveEmote(NULL), pItemUse(NULL), pEffectDummyGameObj(NULL), pEffectDummyCreature(NULL),
|
pGOChooseReward(NULL), pItemUse(NULL), pEffectDummyGameObj(NULL), pEffectDummyCreature(NULL),
|
||||||
pEffectDummyItem(NULL), GetAI(NULL)
|
pEffectDummyItem(NULL), GetAI(NULL)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
|
@ -63,7 +63,6 @@ struct Script
|
||||||
bool (*pItemQuestAccept )(Player *player, Item *_Item, Quest const*_Quest );
|
bool (*pItemQuestAccept )(Player *player, Item *_Item, Quest const*_Quest );
|
||||||
bool (*pGOQuestAccept )(Player *player, GameObject *_GO, Quest const*_Quest );
|
bool (*pGOQuestAccept )(Player *player, GameObject *_GO, Quest const*_Quest );
|
||||||
bool (*pGOChooseReward )(Player *player, GameObject *_GO, Quest const*_Quest, uint32 opt );
|
bool (*pGOChooseReward )(Player *player, GameObject *_GO, Quest const*_Quest, uint32 opt );
|
||||||
bool (*pReceiveEmote )(Player *player, Creature *_Creature, uint32 emote );
|
|
||||||
bool (*pItemUse )(Player *player, Item* _Item, SpellCastTargets const& targets);
|
bool (*pItemUse )(Player *player, Item* _Item, SpellCastTargets const& targets);
|
||||||
bool (*pEffectDummyGameObj )(Unit*, uint32, uint32, GameObject* );
|
bool (*pEffectDummyGameObj )(Unit*, uint32, uint32, GameObject* );
|
||||||
bool (*pEffectDummyCreature )(Unit*, uint32, uint32, Creature* );
|
bool (*pEffectDummyCreature )(Unit*, uint32, uint32, Creature* );
|
||||||
|
|
|
||||||
|
|
@ -789,8 +789,18 @@ void AchievementMgr::UpdateAchievementCriteria(AchievementCriteriaTypes type, ui
|
||||||
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_ACCUMULATE);
|
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_ACCUMULATE);
|
||||||
break;
|
break;
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUEST:
|
case ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUEST:
|
||||||
if(GetPlayer()->GetQuestRewardStatus(achievementCriteria->complete_quest.questID))
|
// if miscvalues != 0, it contains the questID.
|
||||||
SetCriteriaProgress(achievementCriteria, 1);
|
if (miscvalue1)
|
||||||
|
{
|
||||||
|
if (miscvalue1 == achievementCriteria->complete_quest.questID)
|
||||||
|
SetCriteriaProgress(achievementCriteria, 1);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// login case.
|
||||||
|
if(GetPlayer()->GetQuestRewardStatus(achievementCriteria->complete_quest.questID))
|
||||||
|
SetCriteriaProgress(achievementCriteria, 1);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_BE_SPELL_TARGET:
|
case ACHIEVEMENT_CRITERIA_TYPE_BE_SPELL_TARGET:
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_BE_SPELL_TARGET2:
|
case ACHIEVEMENT_CRITERIA_TYPE_BE_SPELL_TARGET2:
|
||||||
|
|
@ -943,6 +953,14 @@ void AchievementMgr::UpdateAchievementCriteria(AchievementCriteriaTypes type, ui
|
||||||
if(miscvalue1 != achievementCriteria->use_gameobject.goEntry)
|
if(miscvalue1 != achievementCriteria->use_gameobject.goEntry)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_ACCUMULATE);
|
||||||
|
break;
|
||||||
|
case ACHIEVEMENT_CRITERIA_TYPE_FISH_IN_GAMEOBJECT:
|
||||||
|
if (!miscvalue1)
|
||||||
|
continue;
|
||||||
|
if (miscvalue1 != achievementCriteria->fish_in_gameobject.goEntry)
|
||||||
|
continue;
|
||||||
|
|
||||||
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_ACCUMULATE);
|
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_ACCUMULATE);
|
||||||
break;
|
break;
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_LEARN_SKILLLINE_SPELLS:
|
case ACHIEVEMENT_CRITERIA_TYPE_LEARN_SKILLLINE_SPELLS:
|
||||||
|
|
@ -1031,7 +1049,6 @@ void AchievementMgr::UpdateAchievementCriteria(AchievementCriteriaTypes type, ui
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_MONEY_FROM_VENDORS:
|
case ACHIEVEMENT_CRITERIA_TYPE_MONEY_FROM_VENDORS:
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_NUMBER_OF_TALENT_RESETS:
|
case ACHIEVEMENT_CRITERIA_TYPE_NUMBER_OF_TALENT_RESETS:
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_SPECIAL_PVP_KILL:
|
case ACHIEVEMENT_CRITERIA_TYPE_SPECIAL_PVP_KILL:
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_FISH_IN_GAMEOBJECT:
|
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_EARNED_PVP_TITLE:
|
case ACHIEVEMENT_CRITERIA_TYPE_EARNED_PVP_TITLE:
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_LOSE_DUEL:
|
case ACHIEVEMENT_CRITERIA_TYPE_LOSE_DUEL:
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_KILL_CREATURE_TYPE:
|
case ACHIEVEMENT_CRITERIA_TYPE_KILL_CREATURE_TYPE:
|
||||||
|
|
@ -1172,6 +1189,8 @@ bool AchievementMgr::IsCompletedCriteria(AchievementCriteriaEntry const* achieve
|
||||||
return progress->counter >= achievementCriteria->loot_money.goldInCopper;
|
return progress->counter >= achievementCriteria->loot_money.goldInCopper;
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_USE_GAMEOBJECT:
|
case ACHIEVEMENT_CRITERIA_TYPE_USE_GAMEOBJECT:
|
||||||
return progress->counter >= achievementCriteria->use_gameobject.useCount;
|
return progress->counter >= achievementCriteria->use_gameobject.useCount;
|
||||||
|
case ACHIEVEMENT_CRITERIA_TYPE_FISH_IN_GAMEOBJECT:
|
||||||
|
return progress->counter >= achievementCriteria->fish_in_gameobject.lootCount;
|
||||||
case ACHIEVEMENT_CRITERIA_TYPE_LEARN_SKILLLINE_SPELLS:
|
case ACHIEVEMENT_CRITERIA_TYPE_LEARN_SKILLLINE_SPELLS:
|
||||||
return progress->counter >= achievementCriteria->learn_skilline_spell.spellCount;
|
return progress->counter >= achievementCriteria->learn_skilline_spell.spellCount;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -587,8 +587,8 @@ void WorldSession::HandleTextEmoteOpcode( WorldPacket & recv_data )
|
||||||
GetPlayer()->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_DO_EMOTE, text_emote, 0, unit);
|
GetPlayer()->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_DO_EMOTE, text_emote, 0, unit);
|
||||||
|
|
||||||
//Send scripted event call
|
//Send scripted event call
|
||||||
if (unit && unit->GetTypeId()==TYPEID_UNIT && Script)
|
if (unit && unit->GetTypeId()==TYPEID_UNIT && ((Creature*)unit)->AI())
|
||||||
Script->ReceiveEmote(GetPlayer(),(Creature*)unit,text_emote);
|
((Creature*)unit)->AI()->ReceiveEmote(GetPlayer(),text_emote);
|
||||||
}
|
}
|
||||||
|
|
||||||
void WorldSession::HandleChatIgnoredOpcode(WorldPacket& recv_data )
|
void WorldSession::HandleChatIgnoredOpcode(WorldPacket& recv_data )
|
||||||
|
|
|
||||||
|
|
@ -25,9 +25,10 @@
|
||||||
#include "Dynamic/ObjectRegistry.h"
|
#include "Dynamic/ObjectRegistry.h"
|
||||||
#include "Dynamic/FactoryHolder.h"
|
#include "Dynamic/FactoryHolder.h"
|
||||||
|
|
||||||
|
class WorldObject;
|
||||||
class Unit;
|
class Unit;
|
||||||
class Creature;
|
class Creature;
|
||||||
class WorldObject;
|
class Player;
|
||||||
struct SpellEntry;
|
struct SpellEntry;
|
||||||
|
|
||||||
#define TIME_INTERVAL_LOOK 5000
|
#define TIME_INTERVAL_LOOK 5000
|
||||||
|
|
@ -88,6 +89,9 @@ class MANGOS_DLL_SPEC CreatureAI
|
||||||
// Called at waypoint reached or point movement finished
|
// Called at waypoint reached or point movement finished
|
||||||
virtual void MovementInform(uint32 /*MovementType*/, uint32 /*Data*/) {}
|
virtual void MovementInform(uint32 /*MovementType*/, uint32 /*Data*/) {}
|
||||||
|
|
||||||
|
// Called at text emote receive from player
|
||||||
|
virtual void ReceiveEmote(Player* pPlayer, uint32 text_emote) {}
|
||||||
|
|
||||||
///== Triggered Actions Requested ==================
|
///== Triggered Actions Requested ==================
|
||||||
|
|
||||||
// Called when creature attack expected (if creature can and no have current victim)
|
// Called when creature attack expected (if creature can and no have current victim)
|
||||||
|
|
|
||||||
|
|
@ -47,7 +47,7 @@ CreatureEventAI::CreatureEventAI(Creature *c ) : CreatureAI(c), InCombat(false)
|
||||||
{
|
{
|
||||||
|
|
||||||
//Debug check
|
//Debug check
|
||||||
#ifndef _DEBUG
|
#ifndef MANGOS_DEBUG
|
||||||
if ((*i).event_flags & EFLAG_DEBUG_ONLY)
|
if ((*i).event_flags & EFLAG_DEBUG_ONLY)
|
||||||
continue;
|
continue;
|
||||||
#endif
|
#endif
|
||||||
|
|
@ -1629,19 +1629,17 @@ bool CreatureEventAI::CanCast(Unit* Target, SpellEntry const *Spell, bool Trigge
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool CreatureEventAI::ReceiveEmote(Player* pPlayer, Creature* pCreature, uint32 uiEmote)
|
void CreatureEventAI::ReceiveEmote(Player* pPlayer, uint32 text_emote)
|
||||||
{
|
{
|
||||||
CreatureEventAI* pTmpCreature = (CreatureEventAI*)(pCreature->AI());
|
if (bEmptyList)
|
||||||
|
return;
|
||||||
|
|
||||||
if (pTmpCreature->bEmptyList)
|
for (std::list<CreatureEventAIHolder>::iterator itr = CreatureEventAIList.begin(); itr != CreatureEventAIList.end(); ++itr)
|
||||||
return true;
|
|
||||||
|
|
||||||
for (std::list<CreatureEventAIHolder>::iterator itr = pTmpCreature->CreatureEventAIList.begin(); itr != pTmpCreature->CreatureEventAIList.end(); ++itr)
|
|
||||||
{
|
{
|
||||||
if ((*itr).Event.event_type == EVENT_T_RECEIVE_EMOTE)
|
if ((*itr).Event.event_type == EVENT_T_RECEIVE_EMOTE)
|
||||||
{
|
{
|
||||||
if ((*itr).Event.event_param1 != uiEmote)
|
if ((*itr).Event.event_param1 != text_emote)
|
||||||
return true;
|
return;
|
||||||
|
|
||||||
bool bProcess = false;
|
bool bProcess = false;
|
||||||
|
|
||||||
|
|
@ -1696,10 +1694,8 @@ bool CreatureEventAI::ReceiveEmote(Player* pPlayer, Creature* pCreature, uint32
|
||||||
if (bProcess)
|
if (bProcess)
|
||||||
{
|
{
|
||||||
sLog.outDebug("CreatureEventAI: ReceiveEmote CreatureEventAI: Condition ok, processing");
|
sLog.outDebug("CreatureEventAI: ReceiveEmote CreatureEventAI: Condition ok, processing");
|
||||||
pTmpCreature->ProcessEvent(*itr, pPlayer);
|
ProcessEvent(*itr, pPlayer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -32,74 +32,74 @@ class WorldObject;
|
||||||
#define MAX_ACTIONS 3
|
#define MAX_ACTIONS 3
|
||||||
#define TEXT_SOURCE_RANGE -1000000 //the amount of entries each text source has available
|
#define TEXT_SOURCE_RANGE -1000000 //the amount of entries each text source has available
|
||||||
|
|
||||||
enum Event_Types
|
enum EventAI_Type
|
||||||
{
|
{
|
||||||
EVENT_T_TIMER = 0, //InitialMin, InitialMax, RepeatMin, RepeatMax
|
EVENT_T_TIMER = 0, // InitialMin, InitialMax, RepeatMin, RepeatMax
|
||||||
EVENT_T_TIMER_OOC = 1, //InitialMin, InitialMax, RepeatMin, RepeatMax
|
EVENT_T_TIMER_OOC = 1, // InitialMin, InitialMax, RepeatMin, RepeatMax
|
||||||
EVENT_T_HP = 2, //HPMax%, HPMin%, RepeatMin, RepeatMax
|
EVENT_T_HP = 2, // HPMax%, HPMin%, RepeatMin, RepeatMax
|
||||||
EVENT_T_MANA = 3, //ManaMax%,ManaMin% RepeatMin, RepeatMax
|
EVENT_T_MANA = 3, // ManaMax%,ManaMin% RepeatMin, RepeatMax
|
||||||
EVENT_T_AGGRO = 4, //NONE
|
EVENT_T_AGGRO = 4, // NONE
|
||||||
EVENT_T_KILL = 5, //RepeatMin, RepeatMax
|
EVENT_T_KILL = 5, // RepeatMin, RepeatMax
|
||||||
EVENT_T_DEATH = 6, //NONE
|
EVENT_T_DEATH = 6, // NONE
|
||||||
EVENT_T_EVADE = 7, //NONE
|
EVENT_T_EVADE = 7, // NONE
|
||||||
EVENT_T_SPELLHIT = 8, //SpellID, School, RepeatMin, RepeatMax
|
EVENT_T_SPELLHIT = 8, // SpellID, School, RepeatMin, RepeatMax
|
||||||
EVENT_T_RANGE = 9, //MinDist, MaxDist, RepeatMin, RepeatMax
|
EVENT_T_RANGE = 9, // MinDist, MaxDist, RepeatMin, RepeatMax
|
||||||
EVENT_T_OOC_LOS = 10, //NoHostile, NoFriendly, RepeatMin, RepeatMax
|
EVENT_T_OOC_LOS = 10, // NoHostile, NoFriendly, RepeatMin, RepeatMax
|
||||||
EVENT_T_SPAWNED = 11, //NONE
|
EVENT_T_SPAWNED = 11, // NONE
|
||||||
EVENT_T_TARGET_HP = 12, //HPMax%, HPMin%, RepeatMin, RepeatMax
|
EVENT_T_TARGET_HP = 12, // HPMax%, HPMin%, RepeatMin, RepeatMax
|
||||||
EVENT_T_TARGET_CASTING = 13, //RepeatMin, RepeatMax
|
EVENT_T_TARGET_CASTING = 13, // RepeatMin, RepeatMax
|
||||||
EVENT_T_FRIENDLY_HP = 14, //HPDeficit, Radius, RepeatMin, RepeatMax
|
EVENT_T_FRIENDLY_HP = 14, // HPDeficit, Radius, RepeatMin, RepeatMax
|
||||||
EVENT_T_FRIENDLY_IS_CC = 15, //DispelType, Radius, RepeatMin, RepeatMax
|
EVENT_T_FRIENDLY_IS_CC = 15, // DispelType, Radius, RepeatMin, RepeatMax
|
||||||
EVENT_T_FRIENDLY_MISSING_BUFF = 16, //SpellId, Radius, RepeatMin, RepeatMax
|
EVENT_T_FRIENDLY_MISSING_BUFF = 16, // SpellId, Radius, RepeatMin, RepeatMax
|
||||||
EVENT_T_SUMMONED_UNIT = 17, //CreatureId, RepeatMin, RepeatMax
|
EVENT_T_SUMMONED_UNIT = 17, // CreatureId, RepeatMin, RepeatMax
|
||||||
EVENT_T_TARGET_MANA = 18, //ManaMax%, ManaMin%, RepeatMin, RepeatMax
|
EVENT_T_TARGET_MANA = 18, // ManaMax%, ManaMin%, RepeatMin, RepeatMax
|
||||||
EVENT_T_QUEST_ACCEPT = 19, //QuestID
|
EVENT_T_QUEST_ACCEPT = 19, // QuestID
|
||||||
EVENT_T_QUEST_COMPLETE = 20, //
|
EVENT_T_QUEST_COMPLETE = 20, //
|
||||||
EVENT_T_REACHED_HOME = 21, //NONE
|
EVENT_T_REACHED_HOME = 21, // NONE
|
||||||
EVENT_T_RECEIVE_EMOTE = 22, //EmoteId, Condition, CondValue1, CondValue2
|
EVENT_T_RECEIVE_EMOTE = 22, // EmoteId, Condition, CondValue1, CondValue2
|
||||||
|
|
||||||
EVENT_T_END,
|
EVENT_T_END,
|
||||||
};
|
};
|
||||||
|
|
||||||
enum Action_Types
|
enum EventAI_ActionType
|
||||||
{
|
{
|
||||||
ACTION_T_NONE = 0, //No action
|
ACTION_T_NONE = 0, //*No action
|
||||||
ACTION_T_TEXT = 1, //-TextId1, optionally -TextId2, optionally -TextId3(if -TextId2 exist). If more than just -TextId1 is defined, randomize. Negative values.
|
ACTION_T_TEXT = 1, //*-TextId1, optionally -TextId2, optionally -TextId3(if -TextId2 exist). If more than just -TextId1 is defined, randomize. Negative values.
|
||||||
ACTION_T_SET_FACTION = 2, //FactionId (or 0 for default)
|
ACTION_T_SET_FACTION = 2, //*FactionId (or 0 for default)
|
||||||
ACTION_T_MORPH_TO_ENTRY_OR_MODEL = 3, //Creature_template entry(param1) OR ModelId (param2) (or 0 for both to demorph)
|
ACTION_T_MORPH_TO_ENTRY_OR_MODEL = 3, //*Creature_template entry(param1) OR ModelId (param2) (or 0 for both to demorph)
|
||||||
ACTION_T_SOUND = 4, //SoundId
|
ACTION_T_SOUND = 4, //*SoundId
|
||||||
ACTION_T_EMOTE = 5, //EmoteId
|
ACTION_T_EMOTE = 5, //*EmoteId
|
||||||
ACTION_T_RANDOM_SAY = 6, //UNUSED
|
ACTION_T_RANDOM_SAY = 6, //*UNUSED
|
||||||
ACTION_T_RANDOM_YELL = 7, //UNUSED
|
ACTION_T_RANDOM_YELL = 7, //*UNUSED
|
||||||
ACTION_T_RANDOM_TEXTEMOTE = 8, //UNUSED
|
ACTION_T_RANDOM_TEXTEMOTE = 8, //*UNUSED
|
||||||
ACTION_T_RANDOM_SOUND = 9, //SoundId1, SoundId2, SoundId3 (-1 in any field means no output if randomed that field)
|
ACTION_T_RANDOM_SOUND = 9, //SoundId1, SoundId2, SoundId3 (-1 in any field means no output if randomed that field)
|
||||||
ACTION_T_RANDOM_EMOTE = 10, //EmoteId1, EmoteId2, EmoteId3 (-1 in any field means no output if randomed that field)
|
ACTION_T_RANDOM_EMOTE = 10, //*EmoteId1, EmoteId2, EmoteId3 (-1 in any field means no output if randomed that field)
|
||||||
ACTION_T_CAST = 11, //SpellId, Target, CastFlags
|
ACTION_T_CAST = 11, //*SpellId, Target, CastFlags
|
||||||
ACTION_T_SUMMON = 12, //CreatureID, Target, Duration in ms
|
ACTION_T_SUMMON = 12, //*CreatureID, Target, Duration in ms
|
||||||
ACTION_T_THREAT_SINGLE_PCT = 13, //Threat%, Target
|
ACTION_T_THREAT_SINGLE_PCT = 13, //*Threat%, Target
|
||||||
ACTION_T_THREAT_ALL_PCT = 14, //Threat%
|
ACTION_T_THREAT_ALL_PCT = 14, //Threat%
|
||||||
ACTION_T_QUEST_EVENT = 15, //QuestID, Target
|
ACTION_T_QUEST_EVENT = 15, //*QuestID, Target
|
||||||
ACTION_T_CASTCREATUREGO = 16, //QuestID, SpellId, Target
|
ACTION_T_CASTCREATUREGO = 16, //*QuestID, SpellId, Target
|
||||||
ACTION_T_SET_UNIT_FIELD = 17, //Field_Number, Value, Target
|
ACTION_T_SET_UNIT_FIELD = 17, //*Field_Number, Value, Target
|
||||||
ACTION_T_SET_UNIT_FLAG = 18, //Flags (may be more than one field OR'd together), Target
|
ACTION_T_SET_UNIT_FLAG = 18, //*Flags (may be more than one field OR'd together), Target
|
||||||
ACTION_T_REMOVE_UNIT_FLAG = 19, //Flags (may be more than one field OR'd together), Target
|
ACTION_T_REMOVE_UNIT_FLAG = 19, //*Flags (may be more than one field OR'd together), Target
|
||||||
ACTION_T_AUTO_ATTACK = 20, //AllowAttackState (0 = stop attack, anything else means continue attacking)
|
ACTION_T_AUTO_ATTACK = 20, //AllowAttackState (0 = stop attack, anything else means continue attacking)
|
||||||
ACTION_T_COMBAT_MOVEMENT = 21, //AllowCombatMovement (0 = stop combat based movement, anything else continue attacking)
|
ACTION_T_COMBAT_MOVEMENT = 21, //AllowCombatMovement (0 = stop combat based movement, anything else continue attacking)
|
||||||
ACTION_T_SET_PHASE = 22, //Phase
|
ACTION_T_SET_PHASE = 22, //*Phase
|
||||||
ACTION_T_INC_PHASE = 23, //Value (may be negative to decrement phase, should not be 0)
|
ACTION_T_INC_PHASE = 23, //*Value (may be negative to decrement phase, should not be 0)
|
||||||
ACTION_T_EVADE = 24, //No Params
|
ACTION_T_EVADE = 24, //No Params
|
||||||
ACTION_T_FLEE = 25, //No Params
|
ACTION_T_FLEE = 25, //No Params
|
||||||
ACTION_T_QUEST_EVENT_ALL = 26, //QuestID
|
ACTION_T_QUEST_EVENT_ALL = 26, //*QuestID
|
||||||
ACTION_T_CASTCREATUREGO_ALL = 27, //QuestId, SpellId
|
ACTION_T_CASTCREATUREGO_ALL = 27, //*QuestId, SpellId
|
||||||
ACTION_T_REMOVEAURASFROMSPELL = 28, //Target, Spellid
|
ACTION_T_REMOVEAURASFROMSPELL = 28, //*Target, Spellid
|
||||||
ACTION_T_RANGED_MOVEMENT = 29, //Distance, Angle
|
ACTION_T_RANGED_MOVEMENT = 29, //Distance, Angle
|
||||||
ACTION_T_RANDOM_PHASE = 30, //PhaseId1, PhaseId2, PhaseId3
|
ACTION_T_RANDOM_PHASE = 30, //PhaseId1, PhaseId2, PhaseId3
|
||||||
ACTION_T_RANDOM_PHASE_RANGE = 31, //PhaseMin, PhaseMax
|
ACTION_T_RANDOM_PHASE_RANGE = 31, //PhaseMin, PhaseMax
|
||||||
ACTION_T_SUMMON_ID = 32, //CreatureId, Target, SpawnId
|
ACTION_T_SUMMON_ID = 32, //*CreatureId, Target, SpawnId
|
||||||
ACTION_T_KILLED_MONSTER = 33, //CreatureId, Target
|
ACTION_T_KILLED_MONSTER = 33, //*CreatureId, Target
|
||||||
ACTION_T_SET_INST_DATA = 34, //Field, Data
|
ACTION_T_SET_INST_DATA = 34, //*Field, Data
|
||||||
ACTION_T_SET_INST_DATA64 = 35, //Field, Target
|
ACTION_T_SET_INST_DATA64 = 35, //*Field, Target
|
||||||
ACTION_T_UPDATE_TEMPLATE = 36, //Entry, Team
|
ACTION_T_UPDATE_TEMPLATE = 36, //*Entry, Team
|
||||||
ACTION_T_DIE = 37, //No Params
|
ACTION_T_DIE = 37, //No Params
|
||||||
ACTION_T_ZONE_COMBAT_PULSE = 38, //No Params
|
ACTION_T_ZONE_COMBAT_PULSE = 38, //No Params
|
||||||
|
|
||||||
|
|
@ -152,7 +152,7 @@ enum EventFlags
|
||||||
EFLAG_RESERVED_4 = 0x10,
|
EFLAG_RESERVED_4 = 0x10,
|
||||||
EFLAG_RESERVED_5 = 0x20,
|
EFLAG_RESERVED_5 = 0x20,
|
||||||
EFLAG_RESERVED_6 = 0x40,
|
EFLAG_RESERVED_6 = 0x40,
|
||||||
EFLAG_DEBUG_ONLY = 0x80, //Event only occurs in debug build of SD2 only
|
EFLAG_DEBUG_ONLY = 0x80, //Event only occurs in debug build
|
||||||
};
|
};
|
||||||
|
|
||||||
// String text additional data, used in (CreatureEventAI)
|
// String text additional data, used in (CreatureEventAI)
|
||||||
|
|
@ -172,10 +172,12 @@ struct CreatureEventAI_Event
|
||||||
|
|
||||||
uint32 creature_id;
|
uint32 creature_id;
|
||||||
|
|
||||||
uint16 event_type;
|
|
||||||
uint32 event_inverse_phase_mask;
|
uint32 event_inverse_phase_mask;
|
||||||
uint8 event_chance;
|
|
||||||
uint8 event_flags;
|
EventAI_Type event_type : 16;
|
||||||
|
uint8 event_chance : 8;
|
||||||
|
uint8 event_flags : 8;
|
||||||
|
|
||||||
union
|
union
|
||||||
{
|
{
|
||||||
uint32 event_param1;
|
uint32 event_param1;
|
||||||
|
|
@ -199,7 +201,7 @@ struct CreatureEventAI_Event
|
||||||
|
|
||||||
struct _action
|
struct _action
|
||||||
{
|
{
|
||||||
uint16 type;
|
EventAI_ActionType type: 16;
|
||||||
union
|
union
|
||||||
{
|
{
|
||||||
uint32 param1;
|
uint32 param1;
|
||||||
|
|
@ -265,6 +267,7 @@ class MANGOS_DLL_SPEC CreatureEventAI : public CreatureAI
|
||||||
void SpellHit(Unit* pUnit, const SpellEntry* pSpell);
|
void SpellHit(Unit* pUnit, const SpellEntry* pSpell);
|
||||||
void UpdateAI(const uint32 diff);
|
void UpdateAI(const uint32 diff);
|
||||||
bool IsVisible(Unit *) const;
|
bool IsVisible(Unit *) const;
|
||||||
|
void ReceiveEmote(Player* pPlayer, uint32 text_emote);
|
||||||
static int Permissible(const Creature *);
|
static int Permissible(const Creature *);
|
||||||
|
|
||||||
bool ProcessEvent(CreatureEventAIHolder& pHolder, Unit* pActionInvoker = NULL);
|
bool ProcessEvent(CreatureEventAIHolder& pHolder, Unit* pActionInvoker = NULL);
|
||||||
|
|
@ -277,7 +280,6 @@ class MANGOS_DLL_SPEC CreatureEventAI : public CreatureAI
|
||||||
void DoZoneInCombat(Unit* pUnit);
|
void DoZoneInCombat(Unit* pUnit);
|
||||||
void DoMeleeAttackIfReady();
|
void DoMeleeAttackIfReady();
|
||||||
bool CanCast(Unit* Target, SpellEntry const *Spell, bool Triggered);
|
bool CanCast(Unit* Target, SpellEntry const *Spell, bool Triggered);
|
||||||
bool ReceiveEmote(Player* pPlayer, Creature* pCreature, uint32 uiEmote);
|
|
||||||
|
|
||||||
Unit* DoSelectLowestHpFriendly(float range, uint32 MinHPDiff);
|
Unit* DoSelectLowestHpFriendly(float range, uint32 MinHPDiff);
|
||||||
void DoFindFriendlyMissingBuff(std::list<Creature*>& _list, float range, uint32 spellid);
|
void DoFindFriendlyMissingBuff(std::list<Creature*>& _list, float range, uint32 spellid);
|
||||||
|
|
|
||||||
|
|
@ -171,38 +171,41 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
Field *fields = result->Fetch();
|
Field *fields = result->Fetch();
|
||||||
|
|
||||||
CreatureEventAI_Event temp;
|
CreatureEventAI_Event temp;
|
||||||
|
temp.event_id = EventAI_Type(fields[0].GetUInt32());
|
||||||
temp.event_id = fields[0].GetUInt32();
|
|
||||||
uint32 i = temp.event_id;
|
uint32 i = temp.event_id;
|
||||||
|
|
||||||
temp.creature_id = fields[1].GetUInt32();
|
temp.creature_id = fields[1].GetUInt32();
|
||||||
uint32 creature_id = temp.creature_id;
|
uint32 creature_id = temp.creature_id;
|
||||||
temp.event_type = fields[2].GetUInt16();
|
|
||||||
|
uint32 e_type = fields[2].GetUInt32();
|
||||||
|
//Report any errors in event
|
||||||
|
if (e_type >= EVENT_T_END)
|
||||||
|
{
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Event %u have wrong type (%u), skipping.", i,e_type);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
temp.event_type = EventAI_Type(e_type);
|
||||||
|
|
||||||
temp.event_inverse_phase_mask = fields[3].GetUInt32();
|
temp.event_inverse_phase_mask = fields[3].GetUInt32();
|
||||||
temp.event_chance = fields[4].GetUInt8();
|
temp.event_chance = fields[4].GetUInt8();
|
||||||
temp.event_flags = fields[5].GetUInt8();
|
temp.event_flags = fields[5].GetUInt8();
|
||||||
temp.event_param1 = fields[6].GetUInt32();
|
temp.event_param1 = fields[6].GetUInt32();
|
||||||
temp.event_param2 = fields[7].GetUInt32();
|
temp.event_param2 = fields[7].GetUInt32();
|
||||||
temp.event_param3 = fields[8].GetUInt32();
|
temp.event_param3 = fields[8].GetUInt32();
|
||||||
temp.event_param4 = fields[9].GetUInt32();
|
temp.event_param4 = fields[9].GetUInt32();
|
||||||
|
|
||||||
CreatureInfo const* cInfo = sCreatureStorage.LookupEntry<CreatureInfo>(temp.creature_id);
|
|
||||||
//Creature does not exist in database
|
//Creature does not exist in database
|
||||||
if (!cInfo)
|
if (!sCreatureStorage.LookupEntry<CreatureInfo>(temp.creature_id))
|
||||||
{
|
{
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u has script for non-existing creature.", i);
|
sLog.outErrorDb("CreatureEventAI: Event %u has script for non-existing creature entry (%u), skipping.", i, temp.creature_id);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
//Report any errors in event
|
|
||||||
if (temp.event_type >= EVENT_T_END)
|
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u has incorrect event type. Maybe DB requires updated version of SD2.", i);
|
|
||||||
|
|
||||||
//No chance of this event occuring
|
//No chance of this event occuring
|
||||||
if (temp.event_chance == 0)
|
if (temp.event_chance == 0)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u has 0 percent chance. Event will never trigger!", i);
|
sLog.outErrorDb("CreatureEventAI: Event %u has 0 percent chance. Event will never trigger!", i);
|
||||||
|
|
||||||
//Chance above 100, force it to be 100
|
//Chance above 100, force it to be 100
|
||||||
if (temp.event_chance > 100)
|
else if (temp.event_chance > 100)
|
||||||
{
|
{
|
||||||
sLog.outErrorDb("CreatureEventAI: Creature %u are using event %u with more than 100 percent chance. Adjusting to 100 percent.", temp.creature_id, i);
|
sLog.outErrorDb("CreatureEventAI: Creature %u are using event %u with more than 100 percent chance. Adjusting to 100 percent.", temp.creature_id, i);
|
||||||
temp.event_chance = 100;
|
temp.event_chance = 100;
|
||||||
|
|
@ -211,6 +214,18 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
//Individual event checks
|
//Individual event checks
|
||||||
switch (temp.event_type)
|
switch (temp.event_type)
|
||||||
{
|
{
|
||||||
|
case EVENT_T_TIMER:
|
||||||
|
case EVENT_T_TIMER_OOC:
|
||||||
|
{
|
||||||
|
if (temp.event_param2 < temp.event_param1)
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u are using timed event(%u) with param2 < param1 (InitialMax < InitialMin). Event will never repeat.", temp.creature_id, i);
|
||||||
|
|
||||||
|
if (temp.event_param4 < temp.event_param3)
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u are using repeatable event(%u) with param4 < param3 (RepeatMax < RepeatMin). Event will never repeat.", temp.creature_id, i);
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
case EVENT_T_HP:
|
case EVENT_T_HP:
|
||||||
case EVENT_T_MANA:
|
case EVENT_T_MANA:
|
||||||
case EVENT_T_TARGET_HP:
|
case EVENT_T_TARGET_HP:
|
||||||
|
|
@ -226,14 +241,14 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
sLog.outErrorDb("CreatureEventAI: Creature %u has param3 and param4=0 (RepeatMin/RepeatMax) but cannot be repeatable without timers. Removing EFLAG_REPEATABLE for event %u.", temp.creature_id, i);
|
sLog.outErrorDb("CreatureEventAI: Creature %u has param3 and param4=0 (RepeatMin/RepeatMax) but cannot be repeatable without timers. Removing EFLAG_REPEATABLE for event %u.", temp.creature_id, i);
|
||||||
temp.event_flags &= ~EFLAG_REPEATABLE;
|
temp.event_flags &= ~EFLAG_REPEATABLE;
|
||||||
}
|
}
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case EVENT_T_SPELLHIT:
|
case EVENT_T_SPELLHIT:
|
||||||
{
|
{
|
||||||
if (temp.event_param1)
|
if (temp.event_param1)
|
||||||
{
|
{
|
||||||
SpellEntry const* pSpell = GetSpellStore()->LookupEntry(temp.event_param1);
|
SpellEntry const* pSpell = sSpellStore.LookupEntry(temp.event_param1);
|
||||||
if (!pSpell)
|
if (!pSpell)
|
||||||
{
|
{
|
||||||
sLog.outErrorDb("CreatureEventAI: Creature %u has non-existant SpellID(%u) defined in event %u.", temp.creature_id, temp.event_param1, i);
|
sLog.outErrorDb("CreatureEventAI: Creature %u has non-existant SpellID(%u) defined in event %u.", temp.creature_id, temp.event_param1, i);
|
||||||
|
|
@ -251,8 +266,8 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
|
|
||||||
if (temp.event_param4 < temp.event_param3)
|
if (temp.event_param4 < temp.event_param3)
|
||||||
sLog.outErrorDb("CreatureEventAI: Creature %u are using repeatable event(%u) with param4 < param3 (RepeatMax < RepeatMin). Event will never repeat.", temp.creature_id, i);
|
sLog.outErrorDb("CreatureEventAI: Creature %u are using repeatable event(%u) with param4 < param3 (RepeatMax < RepeatMin). Event will never repeat.", temp.creature_id, i);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case EVENT_T_RANGE:
|
case EVENT_T_RANGE:
|
||||||
case EVENT_T_OOC_LOS:
|
case EVENT_T_OOC_LOS:
|
||||||
|
|
@ -260,29 +275,28 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
case EVENT_T_FRIENDLY_IS_CC:
|
case EVENT_T_FRIENDLY_IS_CC:
|
||||||
case EVENT_T_FRIENDLY_MISSING_BUFF:
|
case EVENT_T_FRIENDLY_MISSING_BUFF:
|
||||||
{
|
{
|
||||||
if (temp.event_param4 < temp.event_param3)
|
//Disabled check for now. Check code related to events and adjust accordingly before enable.
|
||||||
sLog.outErrorDb("CreatureEventAI: Creature %u are using repeatable event(%u) with param4 < param3 (RepeatMax < RepeatMin). Event will never repeat.", temp.creature_id, i);
|
//Events should have min/max or alternative set to a static value.
|
||||||
}
|
/*if (!temp.event_param3 && !temp.event_param4)
|
||||||
break;
|
{
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u are using repeatable event(%u) without param3/param4 (RepeatMin/RepeatMax). Using minimum values.", temp.creature_id, i);
|
||||||
case EVENT_T_TIMER:
|
temp.event_param3 = 2500;
|
||||||
case EVENT_T_TIMER_OOC:
|
temp.event_param4 = 2500;
|
||||||
{
|
}*/
|
||||||
if (temp.event_param2 < temp.event_param1)
|
|
||||||
sLog.outErrorDb("CreatureEventAI: Creature %u are using timed event(%u) with param2 < param1 (InitialMax < InitialMin). Event will never repeat.", temp.creature_id, i);
|
|
||||||
|
|
||||||
if (temp.event_param4 < temp.event_param3)
|
if (temp.event_param4 < temp.event_param3)
|
||||||
sLog.outErrorDb("CreatureEventAI: Creature %u are using repeatable event(%u) with param4 < param3 (RepeatMax < RepeatMin). Event will never repeat.", temp.creature_id, i);
|
sLog.outErrorDb("CreatureEventAI: Creature %u are using repeatable event(%u) with param4 < param3 (RepeatMax < RepeatMin). Event will never repeat.", temp.creature_id, i);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case EVENT_T_KILL:
|
case EVENT_T_KILL:
|
||||||
case EVENT_T_TARGET_CASTING:
|
case EVENT_T_TARGET_CASTING:
|
||||||
{
|
{
|
||||||
if (temp.event_param2 < temp.event_param1)
|
if (temp.event_param2 < temp.event_param1)
|
||||||
sLog.outErrorDb("CreatureEventAI: Creature %u are using event(%u) with param2 < param1 (RepeatMax < RepeatMin). Event will never repeat.", temp.creature_id, i);
|
sLog.outErrorDb("CreatureEventAI: Creature %u are using event(%u) with param2 < param1 (RepeatMax < RepeatMin). Event will never repeat.", temp.creature_id, i);
|
||||||
|
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case EVENT_T_AGGRO:
|
case EVENT_T_AGGRO:
|
||||||
case EVENT_T_DEATH:
|
case EVENT_T_DEATH:
|
||||||
|
|
@ -295,13 +309,70 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
sLog.outErrorDb("CreatureEventAI: Creature %u has EFLAG_REPEATABLE set. Event can never be repeatable. Removing flag for event %u.", temp.creature_id, i);
|
sLog.outErrorDb("CreatureEventAI: Creature %u has EFLAG_REPEATABLE set. Event can never be repeatable. Removing flag for event %u.", temp.creature_id, i);
|
||||||
temp.event_flags &= ~EFLAG_REPEATABLE;
|
temp.event_flags &= ~EFLAG_REPEATABLE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
case EVENT_T_RECEIVE_EMOTE:
|
||||||
|
{
|
||||||
|
if (!sEmotesTextStore.LookupEntry(temp.event_param1))
|
||||||
|
{
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u using event %u: param1 (EmoteTextId: %u) are not valid.",temp.creature_id, i, temp.event_param1);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (temp.event_param2 == CONDITION_AD_COMMISSION_AURA || temp.event_param2 == CONDITION_NO_AURA)
|
||||||
|
{
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u using event %u: param2 (Condition: %u) are not implemented for EventAI.",temp.creature_id, i, temp.event_param2);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!PlayerCondition::IsValid(ConditionType(temp.event_param2), temp.event_param3, temp.event_param4))
|
||||||
|
{
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u using event %u: param2 (Condition: %u) are not valid.",temp.creature_id, i, temp.event_param2);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(temp.event_flags & EFLAG_REPEATABLE))
|
||||||
|
{
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u using event %u: EFLAG_REPEATABLE not set. Event must always be repeatable. Flag applied.", temp.creature_id, i);
|
||||||
|
temp.event_flags |= EFLAG_REPEATABLE;
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
case EVENT_T_SUMMONED_UNIT:
|
||||||
|
{
|
||||||
|
if (!sCreatureStorage.LookupEntry<CreatureInfo>(temp.event_param1))
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u are using event(%u) with not existed creature template id (%u) in param1, skipped.", temp.creature_id, i, temp.event_param1);
|
||||||
|
|
||||||
|
if (temp.event_param3 < temp.event_param2)
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u are using repeatable event(%u) with param3 < param2 (RepeatMax < RepeatMin). Event will never repeat.", temp.creature_id, i);
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
case EVENT_T_QUEST_ACCEPT:
|
||||||
|
case EVENT_T_QUEST_COMPLETE:
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u using not implemented event (%u) in event %u.", temp.creature_id, temp.event_id, i);
|
||||||
|
continue;
|
||||||
|
default:
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Creature %u using not checked at load event (%u) in event %u. Need check code update?", temp.creature_id, temp.event_id, i);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
for (uint32 j = 0; j < MAX_ACTIONS; j++)
|
for (uint32 j = 0; j < MAX_ACTIONS; j++)
|
||||||
{
|
{
|
||||||
temp.action[j].type = fields[10+(j*4)].GetUInt16();
|
uint16 action_type = fields[10+(j*4)].GetUInt16();
|
||||||
|
if (action_type >= ACTION_T_END)
|
||||||
|
{
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u has incorrect action type (%u), replace by ACTION_T_NONE.", i, j+1, action_type);
|
||||||
|
temp.action[j].type = ACTION_T_NONE;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
temp.action[j].type = EventAI_ActionType(action_type);
|
||||||
temp.action[j].param1 = fields[11+(j*4)].GetUInt32();
|
temp.action[j].param1 = fields[11+(j*4)].GetUInt32();
|
||||||
temp.action[j].param2 = fields[12+(j*4)].GetUInt32();
|
temp.action[j].param2 = fields[12+(j*4)].GetUInt32();
|
||||||
temp.action[j].param3 = fields[13+(j*4)].GetUInt32();
|
temp.action[j].param3 = fields[13+(j*4)].GetUInt32();
|
||||||
|
|
@ -309,6 +380,8 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
//Report any errors in actions
|
//Report any errors in actions
|
||||||
switch (temp.action[j].type)
|
switch (temp.action[j].type)
|
||||||
{
|
{
|
||||||
|
case ACTION_T_NONE:
|
||||||
|
break;
|
||||||
case ACTION_T_TEXT:
|
case ACTION_T_TEXT:
|
||||||
{
|
{
|
||||||
if (temp.action[j].param1_s < 0)
|
if (temp.action[j].param1_s < 0)
|
||||||
|
|
@ -332,10 +405,10 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
if (!temp.action[j].param1_s || !temp.action[j].param2_s)
|
if (!temp.action[j].param1_s || !temp.action[j].param2_s)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u has param3, but param1 and/or param2 is not set. Required for randomized text.", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u has param3, but param1 and/or param2 is not set. Required for randomized text.", i, j+1);
|
||||||
}
|
}
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_SET_FACTION:
|
case ACTION_T_SET_FACTION:
|
||||||
if (temp.action[j].param1 !=0 && !GetFactionStore()->LookupEntry(temp.action[j].param1))
|
if (temp.action[j].param1 !=0 && !sFactionStore.LookupEntry(temp.action[j].param1))
|
||||||
{
|
{
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant FactionId %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant FactionId %u.", i, j+1, temp.action[j].param1);
|
||||||
temp.action[j].param1 = 0;
|
temp.action[j].param1 = 0;
|
||||||
|
|
@ -344,13 +417,13 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
case ACTION_T_MORPH_TO_ENTRY_OR_MODEL:
|
case ACTION_T_MORPH_TO_ENTRY_OR_MODEL:
|
||||||
if (temp.action[j].param1 !=0 || temp.action[j].param2 !=0)
|
if (temp.action[j].param1 !=0 || temp.action[j].param2 !=0)
|
||||||
{
|
{
|
||||||
if (temp.action[j].param1 && !GetCreatureTemplateStore(temp.action[j].param1))
|
if (temp.action[j].param1 && !sCreatureStorage.LookupEntry<CreatureInfo>(temp.action[j].param1))
|
||||||
{
|
{
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant Creature entry %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant Creature entry %u.", i, j+1, temp.action[j].param1);
|
||||||
temp.action[j].param1 = 0;
|
temp.action[j].param1 = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (temp.action[j].param2 && !GetCreatureDisplayStore()->LookupEntry(temp.action[j].param2))
|
if (temp.action[j].param2 && !sCreatureDisplayInfoStore.LookupEntry(temp.action[j].param2))
|
||||||
{
|
{
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant ModelId %u.", i, j+1, temp.action[j].param2);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant ModelId %u.", i, j+1, temp.action[j].param2);
|
||||||
temp.action[j].param2 = 0;
|
temp.action[j].param2 = 0;
|
||||||
|
|
@ -358,24 +431,38 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ACTION_T_SOUND:
|
case ACTION_T_SOUND:
|
||||||
if (!GetSoundEntriesStore()->LookupEntry(temp.action[j].param1))
|
if (!sSoundEntriesStore.LookupEntry(temp.action[j].param1))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SoundID %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SoundID %u.", i, j+1, temp.action[j].param1);
|
||||||
break;
|
break;
|
||||||
/*
|
|
||||||
case ACTION_T_RANDOM_SOUND:
|
case ACTION_T_RANDOM_SOUND:
|
||||||
{
|
if (!sSoundEntriesStore.LookupEntry(temp.action[j].param1))
|
||||||
if(!GetSoundEntriesStore()->LookupEntry(temp.action[j].param1))
|
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param1 uses non-existant SoundID %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param1 uses non-existant SoundID %u.", i, j+1, temp.action[j].param1);
|
||||||
if(!GetSoundEntriesStore()->LookupEntry(temp.action[j].param2))
|
if (temp.action[j].param2_s >= 0 && !sSoundEntriesStore.LookupEntry(temp.action[j].param2))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param2 uses non-existant SoundID %u.", i, j+1, temp.action[j].param2);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param2 uses non-existant SoundID %u.", i, j+1, temp.action[j].param2);
|
||||||
if(!GetSoundEntriesStore()->LookupEntry(temp.action[j].param3))
|
if (temp.action[j].param3_s >= 0 && !sSoundEntriesStore.LookupEntry(temp.action[j].param3))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param3 uses non-existant SoundID %u.", i, j+1, temp.action[j].param3);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param3 uses non-existant SoundID %u.", i, j+1, temp.action[j].param3);
|
||||||
}
|
break;
|
||||||
break;
|
case ACTION_T_EMOTE:
|
||||||
*/
|
//TODO: load emotes and check it's store for existing
|
||||||
|
/*
|
||||||
|
if (!sEmotesStore.LookupEntry(temp.action[j].param1))
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param1 (EmoteId: %u) are not valid.", i, j+1, temp.action[j].param1);
|
||||||
|
*/
|
||||||
|
break;
|
||||||
|
case ACTION_T_RANDOM_EMOTE:
|
||||||
|
//TODO: load emotes and check it's store for existing
|
||||||
|
/*
|
||||||
|
if (!sEmotesStore.LookupEntry(temp.action[j].param1))
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param1 (EmoteId: %u) are not valid.", i, j+1, temp.action[j].param1);
|
||||||
|
if (temp.action[j].param2_s >= 0 && !sEmotesStore.LookupEntry(temp.action[j].param2))
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param2 (EmoteId: %u) are not valid.", i, j+1, temp.action[j].param2);
|
||||||
|
if (temp.action[j].param3_s >= 0 && !sEmotesStore.LookupEntry(temp.action[j].param3))
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param3 (EmoteId: %u) are not valid.", i, j+1, temp.action[j].param3);
|
||||||
|
*/
|
||||||
|
break;
|
||||||
case ACTION_T_CAST:
|
case ACTION_T_CAST:
|
||||||
{
|
{
|
||||||
const SpellEntry *spell = GetSpellStore()->LookupEntry(temp.action[j].param1);
|
const SpellEntry *spell = sSpellStore.LookupEntry(temp.action[j].param1);
|
||||||
if (!spell)
|
if (!spell)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SpellID %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SpellID %u.", i, j+1, temp.action[j].param1);
|
||||||
else
|
else
|
||||||
|
|
@ -384,26 +471,26 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
{
|
{
|
||||||
//output as debug for now, also because there's no general rule all spells have RecoveryTime
|
//output as debug for now, also because there's no general rule all spells have RecoveryTime
|
||||||
if (temp.event_param3 < spell->RecoveryTime)
|
if (temp.event_param3 < spell->RecoveryTime)
|
||||||
debug_log("CreatureEventAI: Event %u Action %u uses SpellID %u but cooldown is longer(%u) than minumum defined in event param3(%u).", i, j+1,temp.action[j].param1, spell->RecoveryTime, temp.event_param3);
|
sLog.outDebug("CreatureEventAI: Event %u Action %u uses SpellID %u but cooldown is longer(%u) than minumum defined in event param3(%u).", i, j+1,temp.action[j].param1, spell->RecoveryTime, temp.event_param3);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (temp.action[j].param2 >= TARGET_T_END)
|
if (temp.action[j].param2 >= TARGET_T_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_REMOVEAURASFROMSPELL:
|
case ACTION_T_REMOVEAURASFROMSPELL:
|
||||||
{
|
{
|
||||||
if (!GetSpellStore()->LookupEntry(temp.action[j].param2))
|
if (!sSpellStore.LookupEntry(temp.action[j].param2))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SpellID %u.", i, j+1, temp.action[j].param2);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SpellID %u.", i, j+1, temp.action[j].param2);
|
||||||
|
|
||||||
if (temp.action[j].param1 >= TARGET_T_END)
|
if (temp.action[j].param1 >= TARGET_T_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_QUEST_EVENT:
|
case ACTION_T_QUEST_EVENT:
|
||||||
{
|
{
|
||||||
if (Quest const* qid = GetQuestTemplateStore(temp.action[j].param1))
|
if (Quest const* qid = objmgr.GetQuestTemplate(temp.action[j].param1))
|
||||||
{
|
{
|
||||||
if (!qid->HasFlag(QUEST_MANGOS_FLAGS_EXPLORATION_OR_EVENT))
|
if (!qid->HasFlag(QUEST_MANGOS_FLAGS_EXPLORATION_OR_EVENT))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u. SpecialFlags for quest entry %u does not include |2, Action will not have any effect.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u. SpecialFlags for quest entry %u does not include |2, Action will not have any effect.", i, j+1, temp.action[j].param1);
|
||||||
|
|
@ -413,45 +500,46 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
|
|
||||||
if (temp.action[j].param2 >= TARGET_T_END)
|
if (temp.action[j].param2 >= TARGET_T_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
||||||
|
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_QUEST_EVENT_ALL:
|
case ACTION_T_QUEST_EVENT_ALL:
|
||||||
{
|
{
|
||||||
if (Quest const* qid = GetQuestTemplateStore(temp.action[j].param1))
|
if (Quest const* qid = objmgr.GetQuestTemplate(temp.action[j].param1))
|
||||||
{
|
{
|
||||||
if (!qid->HasFlag(QUEST_MANGOS_FLAGS_EXPLORATION_OR_EVENT))
|
if (!qid->HasFlag(QUEST_MANGOS_FLAGS_EXPLORATION_OR_EVENT))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u. SpecialFlags for quest entry %u does not include |2, Action will not have any effect.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u. SpecialFlags for quest entry %u does not include |2, Action will not have any effect.", i, j+1, temp.action[j].param1);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant Quest entry %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant Quest entry %u.", i, j+1, temp.action[j].param1);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_CASTCREATUREGO:
|
case ACTION_T_CASTCREATUREGO:
|
||||||
{
|
{
|
||||||
if (!GetCreatureTemplateStore(temp.action[j].param1))
|
if (!sCreatureStorage.LookupEntry<CreatureInfo>(temp.action[j].param1))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
||||||
|
|
||||||
if (!GetSpellStore()->LookupEntry(temp.action[j].param2))
|
if (!sSpellStore.LookupEntry(temp.action[j].param2))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SpellID %u.", i, j+1, temp.action[j].param2);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SpellID %u.", i, j+1, temp.action[j].param2);
|
||||||
|
|
||||||
if (temp.action[j].param3 >= TARGET_T_END)
|
if (temp.action[j].param3 >= TARGET_T_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_CASTCREATUREGO_ALL:
|
case ACTION_T_CASTCREATUREGO_ALL:
|
||||||
{
|
{
|
||||||
if (!GetQuestTemplateStore(temp.action[j].param1))
|
if (!objmgr.GetQuestTemplate(temp.action[j].param1))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant Quest entry %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant Quest entry %u.", i, j+1, temp.action[j].param1);
|
||||||
|
|
||||||
if (!GetSpellStore()->LookupEntry(temp.action[j].param2))
|
if (!sSpellStore.LookupEntry(temp.action[j].param2))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SpellID %u.", i, j+1, temp.action[j].param2);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant SpellID %u.", i, j+1, temp.action[j].param2);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
//2nd param target
|
//2nd param target
|
||||||
case ACTION_T_SUMMON_ID:
|
case ACTION_T_SUMMON_ID:
|
||||||
{
|
{
|
||||||
if (!GetCreatureTemplateStore(temp.action[j].param1))
|
if (!sCreatureStorage.LookupEntry<CreatureInfo>(temp.action[j].param1))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
||||||
|
|
||||||
if (m_CreatureEventAI_Summon_Map.find(temp.action[j].param3) == m_CreatureEventAI_Summon_Map.end())
|
if (m_CreatureEventAI_Summon_Map.find(temp.action[j].param3) == m_CreatureEventAI_Summon_Map.end())
|
||||||
|
|
@ -459,34 +547,33 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
|
|
||||||
if (temp.action[j].param2 >= TARGET_T_END)
|
if (temp.action[j].param2 >= TARGET_T_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_KILLED_MONSTER:
|
case ACTION_T_KILLED_MONSTER:
|
||||||
{
|
{
|
||||||
if (!GetCreatureTemplateStore(temp.action[j].param1))
|
if (!sCreatureStorage.LookupEntry<CreatureInfo>(temp.action[j].param1))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
||||||
|
|
||||||
if (temp.action[j].param2 >= TARGET_T_END)
|
if (temp.action[j].param2 >= TARGET_T_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_SUMMON:
|
case ACTION_T_SUMMON:
|
||||||
{
|
{
|
||||||
if (!GetCreatureTemplateStore(temp.action[j].param1))
|
if (!sCreatureStorage.LookupEntry<CreatureInfo>(temp.action[j].param1))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
||||||
|
|
||||||
if (temp.action[j].param2 >= TARGET_T_END)
|
if (temp.action[j].param2 >= TARGET_T_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_THREAT_SINGLE_PCT:
|
case ACTION_T_THREAT_SINGLE_PCT:
|
||||||
case ACTION_T_SET_UNIT_FLAG:
|
case ACTION_T_SET_UNIT_FLAG:
|
||||||
case ACTION_T_REMOVE_UNIT_FLAG:
|
case ACTION_T_REMOVE_UNIT_FLAG:
|
||||||
if (temp.action[j].param2 >= TARGET_T_END)
|
if (temp.action[j].param2 >= TARGET_T_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
||||||
break;
|
break;
|
||||||
|
//3rd param target
|
||||||
//3rd param target
|
|
||||||
case ACTION_T_SET_UNIT_FIELD:
|
case ACTION_T_SET_UNIT_FIELD:
|
||||||
if (temp.action[j].param1 < OBJECT_END || temp.action[j].param1 >= UNIT_END)
|
if (temp.action[j].param1 < OBJECT_END || temp.action[j].param1 >= UNIT_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param1 (UNIT_FIELD*). Index out of range for intended use.", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u param1 (UNIT_FIELD*). Index out of range for intended use.", i, j+1);
|
||||||
|
|
@ -511,8 +598,9 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
|
|
||||||
if (temp.action[j].param2 > 4/*SPECIAL*/)
|
if (temp.action[j].param2 > 4/*SPECIAL*/)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u attempts to set instance data above encounter state 4. Custom case?", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u attempts to set instance data above encounter state 4. Custom case?", i, j+1);
|
||||||
|
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_SET_INST_DATA64:
|
case ACTION_T_SET_INST_DATA64:
|
||||||
{
|
{
|
||||||
if (!(temp.event_flags & EFLAG_NORMAL) && !(temp.event_flags & EFLAG_HEROIC))
|
if (!(temp.event_flags & EFLAG_NORMAL) && !(temp.event_flags & EFLAG_HEROIC))
|
||||||
|
|
@ -520,23 +608,42 @@ void CreatureEventAIMgr::LoadCreatureEventAI_Scripts()
|
||||||
|
|
||||||
if (temp.action[j].param2 >= TARGET_T_END)
|
if (temp.action[j].param2 >= TARGET_T_END)
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses incorrect Target type", i, j+1);
|
||||||
|
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ACTION_T_UPDATE_TEMPLATE:
|
case ACTION_T_UPDATE_TEMPLATE:
|
||||||
{
|
{
|
||||||
if (!GetCreatureTemplateStore(temp.action[j].param1))
|
if (!sCreatureStorage.LookupEntry<CreatureInfo>(temp.action[j].param1))
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses non-existant creature entry %u.", i, j+1, temp.action[j].param1);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
case ACTION_T_THREAT_ALL_PCT:
|
||||||
|
if (abs(temp.action[j].param1_s) > 100)
|
||||||
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u uses invalid percent value %u.", i, j+1, temp.action[j].param1);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case ACTION_T_EVADE: //No Params
|
||||||
|
case ACTION_T_FLEE: //No Params
|
||||||
|
case ACTION_T_DIE: //No Params
|
||||||
|
case ACTION_T_ZONE_COMBAT_PULSE: //No Params
|
||||||
|
case ACTION_T_AUTO_ATTACK: //AllowAttackState (0 = stop attack, anything else means continue attacking)
|
||||||
|
case ACTION_T_COMBAT_MOVEMENT: //AllowCombatMovement (0 = stop combat based movement, anything else continue attacking)
|
||||||
|
case ACTION_T_RANGED_MOVEMENT: //Distance, Angle
|
||||||
|
break;
|
||||||
|
|
||||||
|
case ACTION_T_RANDOM_PHASE: //PhaseId1, PhaseId2, PhaseId3
|
||||||
|
case ACTION_T_RANDOM_PHASE_RANGE: //PhaseMin, PhaseMax
|
||||||
|
// check not implemented
|
||||||
|
break;
|
||||||
|
|
||||||
case ACTION_T_RANDOM_SAY:
|
case ACTION_T_RANDOM_SAY:
|
||||||
case ACTION_T_RANDOM_YELL:
|
case ACTION_T_RANDOM_YELL:
|
||||||
case ACTION_T_RANDOM_TEXTEMOTE:
|
case ACTION_T_RANDOM_TEXTEMOTE:
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u currently unused ACTION type. Did you forget to update database?", i, j+1);
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u currently unused ACTION type. Did you forget to update database?", i, j+1);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
if (temp.action[j].type >= ACTION_T_END)
|
sLog.outErrorDb("CreatureEventAI: Event %u Action %u have currently not checked at load action type (%u). Need check code update?", i, j+1, temp.action[j].type);
|
||||||
sLog.outErrorDb("CreatureEventAI: Event %u Action %u has incorrect action type. Maybe DB requires updated version of SD2.", i, j+1);
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -281,50 +281,50 @@ enum TotemCategoryType
|
||||||
};
|
};
|
||||||
|
|
||||||
// SummonProperties.dbc, col 1
|
// SummonProperties.dbc, col 1
|
||||||
/*enum SummonGroup
|
enum SummonPropGroup
|
||||||
{
|
{
|
||||||
SUMMON_GROUP_UNKNOWN1 = 0, // 1160 spells in 3.0.3
|
SUMMON_PROP_GROUP_UNKNOWN1 = 0, // 1160 spells in 3.0.3
|
||||||
SUMMON_GROUP_UNKNOWN2 = 1, // 861 spells in 3.0.3
|
SUMMON_PROP_GROUP_UNKNOWN2 = 1, // 861 spells in 3.0.3
|
||||||
SUMMON_GROUP_PETS = 2, // 52 spells in 3.0.3, pets mostly
|
SUMMON_PROP_GROUP_PETS = 2, // 52 spells in 3.0.3, pets mostly
|
||||||
SUMMON_GROUP_CONTROLLABLE = 3, // 13 spells in 3.0.3, mostly controllable
|
SUMMON_PROP_GROUP_CONTROLLABLE = 3, // 13 spells in 3.0.3, mostly controllable
|
||||||
SUMMON_GROUP_UNKNOWN3 = 4 // 86 spells in 3.0.3, taxi/mounts
|
SUMMON_PROP_GROUP_UNKNOWN3 = 4 // 86 spells in 3.0.3, taxi/mounts
|
||||||
};
|
};
|
||||||
|
|
||||||
// SummonProperties.dbc, col 3
|
// SummonProperties.dbc, col 3
|
||||||
enum SummonType
|
enum SummonPropType
|
||||||
{
|
{
|
||||||
SUMMON_TYPE_UNKNOWN = 0, // different summons, 1330 spells in 3.0.3
|
SUMMON_PROP_TYPE_UNKNOWN = 0, // different summons, 1330 spells in 3.0.3
|
||||||
SUMMON_TYPE_SUMMON = 1, // generic summons, 49 spells in 3.0.3
|
SUMMON_PROP_TYPE_SUMMON = 1, // generic summons, 49 spells in 3.0.3
|
||||||
SUMMON_TYPE_GUARDIAN = 2, // summon guardian, 393 spells in 3.0.3
|
SUMMON_PROP_TYPE_GUARDIAN = 2, // summon guardian, 393 spells in 3.0.3
|
||||||
SUMMON_TYPE_ARMY = 3, // summon army, 5 spells in 3.0.3
|
SUMMON_PROP_TYPE_ARMY = 3, // summon army, 5 spells in 3.0.3
|
||||||
SUMMON_TYPE_TOTEM = 4, // summon totem, 169 spells in 3.0.3
|
SUMMON_PROP_TYPE_TOTEM = 4, // summon totem, 169 spells in 3.0.3
|
||||||
SUMMON_TYPE_CRITTER = 5, // critter/minipet, 195 spells in 3.0.3
|
SUMMON_PROP_TYPE_CRITTER = 5, // critter/minipet, 195 spells in 3.0.3
|
||||||
SUMMON_TYPE_DK = 6, // summon DRW/Ghoul, 2 spells in 3.0.3
|
SUMMON_PROP_TYPE_DK = 6, // summon DRW/Ghoul, 2 spells in 3.0.3
|
||||||
SUMMON_TYPE_BOMB = 7, // summon bot/bomb, 4 spells in 3.0.3
|
SUMMON_PROP_TYPE_BOMB = 7, // summon bot/bomb, 4 spells in 3.0.3
|
||||||
SUMMON_TYPE_PHASING = 8, // something todo with DK prequest line, 2 spells in 3.0.3
|
SUMMON_PROP_TYPE_PHASING = 8, // something todo with DK prequest line, 2 spells in 3.0.3
|
||||||
SUMMON_TYPE_SIEGE_VEH = 9, // summon different vehicles, 14 spells in 3.0.3
|
SUMMON_PROP_TYPE_SIEGE_VEH = 9, // summon different vehicles, 14 spells in 3.0.3
|
||||||
SUMMON_TYPE_DRAKE_VEH = 10, // summon drake (vehicle), 3 spells
|
SUMMON_PROP_TYPE_DRAKE_VEH = 10, // summon drake (vehicle), 3 spells
|
||||||
SUMMON_TYPE_LIGHTWELL = 11 // summon lightwell, 6 spells in 3.0.3
|
SUMMON_PROP_TYPE_LIGHTWELL = 11 // summon lightwell, 6 spells in 3.0.3
|
||||||
};
|
};
|
||||||
|
|
||||||
// SummonProperties.dbc, col 5
|
// SummonProperties.dbc, col 5
|
||||||
enum SummonFlags
|
enum SummonPropFlags
|
||||||
{
|
{
|
||||||
SUMMON_FLAG_NONE = 0x0000, // 1342 spells in 3.0.3
|
SUMMON_PROP_FLAG_NONE = 0x0000, // 1342 spells in 3.0.3
|
||||||
SUMMON_FLAG_UNK1 = 0x0001, // 75 spells in 3.0.3, something unfriendly
|
SUMMON_PROP_FLAG_UNK1 = 0x0001, // 75 spells in 3.0.3, something unfriendly
|
||||||
SUMMON_FLAG_UNK2 = 0x0002, // 616 spells in 3.0.3, something friendly
|
SUMMON_PROP_FLAG_UNK2 = 0x0002, // 616 spells in 3.0.3, something friendly
|
||||||
SUMMON_FLAG_UNK3 = 0x0004, // 22 spells in 3.0.3, no idea...
|
SUMMON_PROP_FLAG_UNK3 = 0x0004, // 22 spells in 3.0.3, no idea...
|
||||||
SUMMON_FLAG_UNK4 = 0x0008, // 49 spells in 3.0.3, some mounts
|
SUMMON_PROP_FLAG_UNK4 = 0x0008, // 49 spells in 3.0.3, some mounts
|
||||||
SUMMON_FLAG_UNK5 = 0x0010, // 25 spells in 3.0.3, quest related?
|
SUMMON_PROP_FLAG_UNK5 = 0x0010, // 25 spells in 3.0.3, quest related?
|
||||||
SUMMON_FLAG_UNK6 = 0x0020, // 0 spells in 3.0.3, unused
|
SUMMON_PROP_FLAG_UNK6 = 0x0020, // 0 spells in 3.0.3, unused
|
||||||
SUMMON_FLAG_UNK7 = 0x0040, // 12 spells in 3.0.3, no idea
|
SUMMON_PROP_FLAG_UNK7 = 0x0040, // 12 spells in 3.0.3, no idea
|
||||||
SUMMON_FLAG_UNK8 = 0x0080, // 4 spells in 3.0.3, no idea
|
SUMMON_PROP_FLAG_UNK8 = 0x0080, // 4 spells in 3.0.3, no idea
|
||||||
SUMMON_FLAG_UNK9 = 0x0100, // 51 spells in 3.0.3, no idea, many quest related
|
SUMMON_PROP_FLAG_UNK9 = 0x0100, // 51 spells in 3.0.3, no idea, many quest related
|
||||||
SUMMON_FLAG_UNK10 = 0x0200, // 51 spells in 3.0.3, something defensive
|
SUMMON_PROP_FLAG_UNK10 = 0x0200, // 51 spells in 3.0.3, something defensive
|
||||||
SUMMON_FLAG_UNK11 = 0x0400, // 3 spells, requires something near?
|
SUMMON_PROP_FLAG_UNK11 = 0x0400, // 3 spells, requires something near?
|
||||||
SUMMON_FLAG_UNK12 = 0x0800, // 30 spells in 3.0.3, no idea
|
SUMMON_PROP_FLAG_UNK12 = 0x0800, // 30 spells in 3.0.3, no idea
|
||||||
SUMMON_FLAG_UNK13 = 0x1000, // 8 spells in 3.0.3, siege vehicle
|
SUMMON_PROP_FLAG_UNK13 = 0x1000, // 8 spells in 3.0.3, siege vehicle
|
||||||
SUMMON_FLAG_UNK14 = 0x2000, // 2 spells in 3.0.3, escort?
|
SUMMON_PROP_FLAG_UNK14 = 0x2000, // 2 spells in 3.0.3, escort?
|
||||||
};
|
};
|
||||||
*/
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
||||||
|
|
@ -56,7 +56,8 @@ DBCStorage <CurrencyTypesEntry> sCurrencyTypesStore(CurrencyTypesfmt);
|
||||||
DBCStorage <DurabilityQualityEntry> sDurabilityQualityStore(DurabilityQualityfmt);
|
DBCStorage <DurabilityQualityEntry> sDurabilityQualityStore(DurabilityQualityfmt);
|
||||||
DBCStorage <DurabilityCostsEntry> sDurabilityCostsStore(DurabilityCostsfmt);
|
DBCStorage <DurabilityCostsEntry> sDurabilityCostsStore(DurabilityCostsfmt);
|
||||||
|
|
||||||
DBCStorage <EmotesTextEntry> sEmotesTextStore(EmoteEntryfmt);
|
DBCStorage <EmotesEntry> sEmotesStore(EmotesEntryfmt);
|
||||||
|
DBCStorage <EmotesTextEntry> sEmotesTextStore(EmotesTextEntryfmt);
|
||||||
|
|
||||||
typedef std::map<uint32,SimpleFactionsList> FactionTeamMap;
|
typedef std::map<uint32,SimpleFactionsList> FactionTeamMap;
|
||||||
static FactionTeamMap sFactionTeamMap;
|
static FactionTeamMap sFactionTeamMap;
|
||||||
|
|
@ -198,7 +199,7 @@ void LoadDBCStores(const std::string& dataPath)
|
||||||
{
|
{
|
||||||
std::string dbcPath = dataPath+"dbc/";
|
std::string dbcPath = dataPath+"dbc/";
|
||||||
|
|
||||||
const uint32 DBCFilesCount = 77;
|
const uint32 DBCFilesCount = 78;
|
||||||
|
|
||||||
barGoLink bar( DBCFilesCount );
|
barGoLink bar( DBCFilesCount );
|
||||||
|
|
||||||
|
|
@ -243,6 +244,7 @@ void LoadDBCStores(const std::string& dataPath)
|
||||||
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sCurrencyTypesStore, dbcPath,"CurrencyTypes.dbc");
|
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sCurrencyTypesStore, dbcPath,"CurrencyTypes.dbc");
|
||||||
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sDurabilityCostsStore, dbcPath,"DurabilityCosts.dbc");
|
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sDurabilityCostsStore, dbcPath,"DurabilityCosts.dbc");
|
||||||
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sDurabilityQualityStore, dbcPath,"DurabilityQuality.dbc");
|
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sDurabilityQualityStore, dbcPath,"DurabilityQuality.dbc");
|
||||||
|
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sEmotesStore, dbcPath,"Emotes.dbc");
|
||||||
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sEmotesTextStore, dbcPath,"EmotesText.dbc");
|
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sEmotesTextStore, dbcPath,"EmotesText.dbc");
|
||||||
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sFactionStore, dbcPath,"Faction.dbc");
|
LoadDBC(availableDbcLocales,bar,bad_dbc_files,sFactionStore, dbcPath,"Faction.dbc");
|
||||||
for (uint32 i=0;i<sFactionStore.GetNumRows(); ++i)
|
for (uint32 i=0;i<sFactionStore.GetNumRows(); ++i)
|
||||||
|
|
@ -667,3 +669,5 @@ MANGOS_DLL_SPEC DBCStorage <SpellRangeEntry> const* GetSpellRangeStore()
|
||||||
MANGOS_DLL_SPEC DBCStorage <FactionEntry> const* GetFactionStore() { return &sFactionStore; }
|
MANGOS_DLL_SPEC DBCStorage <FactionEntry> const* GetFactionStore() { return &sFactionStore; }
|
||||||
MANGOS_DLL_SPEC DBCStorage <ItemEntry> const* GetItemDisplayStore() { return &sItemStore; }
|
MANGOS_DLL_SPEC DBCStorage <ItemEntry> const* GetItemDisplayStore() { return &sItemStore; }
|
||||||
MANGOS_DLL_SPEC DBCStorage <CreatureDisplayInfoEntry> const* GetCreatureDisplayStore() { return &sCreatureDisplayInfoStore; }
|
MANGOS_DLL_SPEC DBCStorage <CreatureDisplayInfoEntry> const* GetCreatureDisplayStore() { return &sCreatureDisplayInfoStore; }
|
||||||
|
MANGOS_DLL_SPEC DBCStorage <EmotesEntry> const* GetEmotesStore() { return &sEmotesStore; }
|
||||||
|
MANGOS_DLL_SPEC DBCStorage <EmotesTextEntry> const* GetEmotesTextStore() { return &sEmotesTextStore; }
|
||||||
|
|
|
||||||
|
|
@ -78,6 +78,7 @@ extern DBCStorage <CreatureTypeEntry> sCreatureTypeStore;
|
||||||
extern DBCStorage <CurrencyTypesEntry> sCurrencyTypesStore;
|
extern DBCStorage <CurrencyTypesEntry> sCurrencyTypesStore;
|
||||||
extern DBCStorage <DurabilityCostsEntry> sDurabilityCostsStore;
|
extern DBCStorage <DurabilityCostsEntry> sDurabilityCostsStore;
|
||||||
extern DBCStorage <DurabilityQualityEntry> sDurabilityQualityStore;
|
extern DBCStorage <DurabilityQualityEntry> sDurabilityQualityStore;
|
||||||
|
extern DBCStorage <EmotesEntry> sEmotesStore;
|
||||||
extern DBCStorage <EmotesTextEntry> sEmotesTextStore;
|
extern DBCStorage <EmotesTextEntry> sEmotesTextStore;
|
||||||
extern DBCStorage <FactionEntry> sFactionStore;
|
extern DBCStorage <FactionEntry> sFactionStore;
|
||||||
extern DBCStorage <FactionTemplateEntry> sFactionTemplateStore;
|
extern DBCStorage <FactionTemplateEntry> sFactionTemplateStore;
|
||||||
|
|
@ -153,4 +154,6 @@ MANGOS_DLL_SPEC DBCStorage <SpellRangeEntry> const* GetSpellRangeStor
|
||||||
MANGOS_DLL_SPEC DBCStorage <FactionEntry> const* GetFactionStore();
|
MANGOS_DLL_SPEC DBCStorage <FactionEntry> const* GetFactionStore();
|
||||||
MANGOS_DLL_SPEC DBCStorage <ItemEntry> const* GetItemDisplayStore();
|
MANGOS_DLL_SPEC DBCStorage <ItemEntry> const* GetItemDisplayStore();
|
||||||
MANGOS_DLL_SPEC DBCStorage <CreatureDisplayInfoEntry> const* GetCreatureDisplayStore();
|
MANGOS_DLL_SPEC DBCStorage <CreatureDisplayInfoEntry> const* GetCreatureDisplayStore();
|
||||||
|
MANGOS_DLL_SPEC DBCStorage <EmotesEntry> const* GetEmotesStore();
|
||||||
|
MANGOS_DLL_SPEC DBCStorage <EmotesTextEntry> const* GetEmotesTextStore();
|
||||||
#endif
|
#endif
|
||||||
|
|
|
||||||
|
|
@ -749,6 +749,17 @@ struct DurabilityQualityEntry
|
||||||
float quality_mod; // 1
|
float quality_mod; // 1
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct EmotesEntry
|
||||||
|
{
|
||||||
|
uint32 Id; // 0
|
||||||
|
//char* Name; // 1, internal name
|
||||||
|
//uint32 AnimationId; // 2, ref to animationData
|
||||||
|
uint32 Flags; // 3, bitmask, may be unit_flags
|
||||||
|
uint32 EmoteType; // 4, Can be 0, 1 or 2 (determine how emote are shown)
|
||||||
|
uint32 UnitStandState; // 5, uncomfirmed, may be enum UnitStandStateType
|
||||||
|
//uint32 SoundId; // 6, ref to soundEntries
|
||||||
|
};
|
||||||
|
|
||||||
struct EmotesTextEntry
|
struct EmotesTextEntry
|
||||||
{
|
{
|
||||||
uint32 Id;
|
uint32 Id;
|
||||||
|
|
@ -1446,15 +1457,17 @@ struct StableSlotPricesEntry
|
||||||
uint32 Price;
|
uint32 Price;
|
||||||
};
|
};
|
||||||
|
|
||||||
/*struct SummonPropertiesEntry
|
/* unused currently
|
||||||
|
struct SummonPropertiesEntry
|
||||||
{
|
{
|
||||||
uint32 Id; // 0
|
uint32 Id; // 0
|
||||||
uint32 Group; // 1, 0 - can't be controlled?, 1 - something guardian?, 2 - pet?, 3 - something controllable?, 4 - taxi/mount?
|
uint32 Group; // 1, enum SummonPropGroup, 0 - can't be controlled?, 1 - something guardian?, 2 - pet?, 3 - something controllable?, 4 - taxi/mount?
|
||||||
uint32 FactionId; // 2, 14 rows > 0
|
uint32 FactionId; // 2, 14 rows > 0
|
||||||
uint32 Type; // 3, see enum
|
uint32 Type; // 3, enum SummonPropType
|
||||||
uint32 Slot; // 4, 0-6
|
uint32 Slot; // 4, 0-6
|
||||||
uint32 Flags; // 5
|
uint32 Flags; // 5, enum SummonPropFlags
|
||||||
};*/
|
};
|
||||||
|
*/
|
||||||
|
|
||||||
#define MAX_TALENT_RANK 5
|
#define MAX_TALENT_RANK 5
|
||||||
#define MAX_PET_TALENT_RANK 3 // use in calculations, expected <= MAX_TALENT_RANK
|
#define MAX_PET_TALENT_RANK 3 // use in calculations, expected <= MAX_TALENT_RANK
|
||||||
|
|
|
||||||
|
|
@ -42,7 +42,8 @@ const char CreatureTypefmt[]="nxxxxxxxxxxxxxxxxxx";
|
||||||
const char CurrencyTypesfmt[]="xnxi";
|
const char CurrencyTypesfmt[]="xnxi";
|
||||||
const char DurabilityCostsfmt[]="niiiiiiiiiiiiiiiiiiiiiiiiiiiii";
|
const char DurabilityCostsfmt[]="niiiiiiiiiiiiiiiiiiiiiiiiiiiii";
|
||||||
const char DurabilityQualityfmt[]="nf";
|
const char DurabilityQualityfmt[]="nf";
|
||||||
const char EmoteEntryfmt[]="nxixxxxxxxxxxxxxxxx";
|
const char EmotesEntryfmt[]="nxxiiix";
|
||||||
|
const char EmotesTextEntryfmt[]="nxixxxxxxxxxxxxxxxx";
|
||||||
const char FactionEntryfmt[]="niiiiiiiiiiiiiiiiiissssssssssssssssxxxxxxxxxxxxxxxxxx";
|
const char FactionEntryfmt[]="niiiiiiiiiiiiiiiiiissssssssssssssssxxxxxxxxxxxxxxxxxx";
|
||||||
const char FactionTemplateEntryfmt[]="niiiiiiiiiiiii";
|
const char FactionTemplateEntryfmt[]="niiiiiiiiiiiii";
|
||||||
const char GemPropertiesEntryfmt[]="nixxi";
|
const char GemPropertiesEntryfmt[]="nixxi";
|
||||||
|
|
|
||||||
|
|
@ -1024,6 +1024,7 @@ void GameObject::Use(Unit* user)
|
||||||
if (ok)
|
if (ok)
|
||||||
{
|
{
|
||||||
player->SendLoot(ok->GetGUID(),LOOT_FISHINGHOLE);
|
player->SendLoot(ok->GetGUID(),LOOT_FISHINGHOLE);
|
||||||
|
player->UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_FISH_IN_GAMEOBJECT, ok->GetGOInfo()->id);
|
||||||
SetLootState(GO_JUST_DEACTIVATED);
|
SetLootState(GO_JUST_DEACTIVATED);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
|
|
||||||
|
|
@ -7416,13 +7416,16 @@ void ObjectMgr::CheckScripts(ScriptMapMap const& scripts,std::set<int32>& ids)
|
||||||
{
|
{
|
||||||
for(ScriptMap::const_iterator itrM = itrMM->second.begin(); itrM != itrMM->second.end(); ++itrM)
|
for(ScriptMap::const_iterator itrM = itrMM->second.begin(); itrM != itrMM->second.end(); ++itrM)
|
||||||
{
|
{
|
||||||
if(itrM->second.dataint)
|
switch(itrM->second.command)
|
||||||
{
|
{
|
||||||
if(!GetMangosStringLocale (itrM->second.dataint))
|
case SCRIPT_COMMAND_TALK:
|
||||||
sLog.outErrorDb( "Table `db_script_string` has not existed string id %u", itrM->first);
|
{
|
||||||
|
if(!GetMangosStringLocale (itrM->second.dataint))
|
||||||
|
sLog.outErrorDb( "Table `db_script_string` not has string id %u used db script (ID: %u)", itrM->second.dataint, itrMM->first);
|
||||||
|
|
||||||
if(ids.count(itrM->second.dataint))
|
if(ids.count(itrM->second.dataint))
|
||||||
ids.erase(itrM->second.dataint);
|
ids.erase(itrM->second.dataint);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -63,7 +63,7 @@ void PetAI::MoveInLineOfSight(Unit *u)
|
||||||
|
|
||||||
void PetAI::AttackStart(Unit *u)
|
void PetAI::AttackStart(Unit *u)
|
||||||
{
|
{
|
||||||
if( inCombat || !u || (m_creature->isPet() && ((Pet&)m_creature).getPetType() == MINI_PET) )
|
if( inCombat || !u || (m_creature->isPet() && ((Pet*)m_creature)->getPetType() == MINI_PET) )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if(m_creature->Attack(u,true))
|
if(m_creature->Attack(u,true))
|
||||||
|
|
@ -274,7 +274,7 @@ void PetAI::UpdateAI(const uint32 diff)
|
||||||
|
|
||||||
m_creature->AddCreatureSpellCooldown(spell->m_spellInfo->Id);
|
m_creature->AddCreatureSpellCooldown(spell->m_spellInfo->Id);
|
||||||
if (m_creature->isPet())
|
if (m_creature->isPet())
|
||||||
((Pet&)m_creature).CheckLearning(spell->m_spellInfo->Id);
|
((Pet*)m_creature)->CheckLearning(spell->m_spellInfo->Id);
|
||||||
|
|
||||||
spell->prepare(&targets);
|
spell->prepare(&targets);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -12371,7 +12371,7 @@ void Player::RewardQuest( Quest const *pQuest, uint32 reward, Object* questGiver
|
||||||
if (pQuest->GetZoneOrSort() > 0)
|
if (pQuest->GetZoneOrSort() > 0)
|
||||||
GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUESTS_IN_ZONE, pQuest->GetZoneOrSort());
|
GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUESTS_IN_ZONE, pQuest->GetZoneOrSort());
|
||||||
GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUEST_COUNT);
|
GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUEST_COUNT);
|
||||||
GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUEST);
|
GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUEST, pQuest->GetQuestId());
|
||||||
|
|
||||||
uint32 zone = 0;
|
uint32 zone = 0;
|
||||||
uint32 area = 0;
|
uint32 area = 0;
|
||||||
|
|
@ -16205,28 +16205,22 @@ void Player::PetSpellInitialize()
|
||||||
|
|
||||||
for(CreatureSpellCooldowns::const_iterator itr = pet->m_CreatureSpellCooldowns.begin(); itr != pet->m_CreatureSpellCooldowns.end(); ++itr)
|
for(CreatureSpellCooldowns::const_iterator itr = pet->m_CreatureSpellCooldowns.begin(); itr != pet->m_CreatureSpellCooldowns.end(); ++itr)
|
||||||
{
|
{
|
||||||
time_t cooldown = 0;
|
time_t cooldown = (itr->second > curTime) ? (itr->second - curTime) * IN_MILISECONDS : 0;
|
||||||
|
|
||||||
if(itr->second > curTime)
|
|
||||||
cooldown = (itr->second - curTime) * IN_MILISECONDS;
|
|
||||||
|
|
||||||
data << uint32(itr->first); // spellid
|
data << uint32(itr->first); // spellid
|
||||||
data << uint16(0); // spell category?
|
data << uint16(0); // spell category?
|
||||||
data << uint32(itr->second); // cooldown
|
data << uint32(cooldown); // cooldown
|
||||||
data << uint32(0); // category cooldown
|
data << uint32(0); // category cooldown
|
||||||
}
|
}
|
||||||
|
|
||||||
for(CreatureSpellCooldowns::const_iterator itr = pet->m_CreatureCategoryCooldowns.begin(); itr != pet->m_CreatureCategoryCooldowns.end(); ++itr)
|
for(CreatureSpellCooldowns::const_iterator itr = pet->m_CreatureCategoryCooldowns.begin(); itr != pet->m_CreatureCategoryCooldowns.end(); ++itr)
|
||||||
{
|
{
|
||||||
time_t cooldown = 0;
|
time_t cooldown = (itr->second > curTime) ? (itr->second - curTime) * IN_MILISECONDS : 0;
|
||||||
|
|
||||||
if(itr->second > curTime)
|
|
||||||
cooldown = (itr->second - curTime) * IN_MILISECONDS;
|
|
||||||
|
|
||||||
data << uint32(itr->first); // spellid
|
data << uint32(itr->first); // spellid
|
||||||
data << uint16(0); // spell category?
|
data << uint16(0); // spell category?
|
||||||
data << uint32(0); // cooldown
|
data << uint32(0); // cooldown
|
||||||
data << uint32(itr->second); // category cooldown
|
data << uint32(cooldown); // category cooldown
|
||||||
}
|
}
|
||||||
|
|
||||||
GetSession()->SendPacket(&data);
|
GetSession()->SendPacket(&data);
|
||||||
|
|
@ -19378,7 +19372,7 @@ void Player::HandleFall(MovementInfo const& movementInfo)
|
||||||
sLog.outDebug("zDiff = %f", z_diff);
|
sLog.outDebug("zDiff = %f", z_diff);
|
||||||
|
|
||||||
//Players with low fall distance, Feather Fall or physical immunity (charges used) are ignored
|
//Players with low fall distance, Feather Fall or physical immunity (charges used) are ignored
|
||||||
// 14.57 can be calculated by resolving damageperc formular below to 0
|
// 14.57 can be calculated by resolving damageperc formula below to 0
|
||||||
if (z_diff >= 14.57f && !isDead() && !isGameMaster() &&
|
if (z_diff >= 14.57f && !isDead() && !isGameMaster() &&
|
||||||
!HasAuraType(SPELL_AURA_HOVER) && !HasAuraType(SPELL_AURA_FEATHER_FALL) &&
|
!HasAuraType(SPELL_AURA_HOVER) && !HasAuraType(SPELL_AURA_FEATHER_FALL) &&
|
||||||
!HasAuraType(SPELL_AURA_FLY) && !IsImmunedToDamage(SPELL_SCHOOL_MASK_NORMAL) )
|
!HasAuraType(SPELL_AURA_FLY) && !IsImmunedToDamage(SPELL_SCHOOL_MASK_NORMAL) )
|
||||||
|
|
|
||||||
|
|
@ -72,7 +72,6 @@ bool LoadScriptingModule(char const* libName)
|
||||||
||!(testScript->scriptAreaTrigger =(scriptCallAreaTrigger )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"AreaTrigger" ))
|
||!(testScript->scriptAreaTrigger =(scriptCallAreaTrigger )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"AreaTrigger" ))
|
||||||
||!(testScript->ItemQuestAccept =(scriptCallItemQuestAccept )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"ItemQuestAccept" ))
|
||!(testScript->ItemQuestAccept =(scriptCallItemQuestAccept )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"ItemQuestAccept" ))
|
||||||
||!(testScript->GOQuestAccept =(scriptCallGOQuestAccept )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"GOQuestAccept" ))
|
||!(testScript->GOQuestAccept =(scriptCallGOQuestAccept )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"GOQuestAccept" ))
|
||||||
||!(testScript->ReceiveEmote =(scriptCallReceiveEmote )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"ReceiveEmote" ))
|
|
||||||
||!(testScript->ItemUse =(scriptCallItemUse )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"ItemUse" ))
|
||!(testScript->ItemUse =(scriptCallItemUse )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"ItemUse" ))
|
||||||
||!(testScript->EffectDummyGameObj =(scriptCallEffectDummyGameObj )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"EffectDummyGameObj" ))
|
||!(testScript->EffectDummyGameObj =(scriptCallEffectDummyGameObj )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"EffectDummyGameObj" ))
|
||||||
||!(testScript->EffectDummyCreature =(scriptCallEffectDummyCreature )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"EffectDummyCreature" ))
|
||!(testScript->EffectDummyCreature =(scriptCallEffectDummyCreature )MANGOS_GET_PROC_ADDR(testScript->hScriptsLib,"EffectDummyCreature" ))
|
||||||
|
|
|
||||||
|
|
@ -54,7 +54,6 @@ typedef bool(MANGOS_IMPORT * scriptCallAreaTrigger)( Player *player, AreaTrigger
|
||||||
typedef bool(MANGOS_IMPORT * scriptCallItemQuestAccept)(Player *player, Item *, Quest const*);
|
typedef bool(MANGOS_IMPORT * scriptCallItemQuestAccept)(Player *player, Item *, Quest const*);
|
||||||
typedef bool(MANGOS_IMPORT * scriptCallGOQuestAccept)(Player *player, GameObject *, Quest const*);
|
typedef bool(MANGOS_IMPORT * scriptCallGOQuestAccept)(Player *player, GameObject *, Quest const*);
|
||||||
typedef bool(MANGOS_IMPORT * scriptCallGOChooseReward)(Player *player, GameObject *, Quest const*, uint32 opt );
|
typedef bool(MANGOS_IMPORT * scriptCallGOChooseReward)(Player *player, GameObject *, Quest const*, uint32 opt );
|
||||||
typedef bool(MANGOS_IMPORT * scriptCallReceiveEmote) ( Player *player, Creature *_Creature, uint32 emote );
|
|
||||||
typedef bool(MANGOS_IMPORT * scriptCallItemUse) (Player *player, Item *_Item, SpellCastTargets const& targets);
|
typedef bool(MANGOS_IMPORT * scriptCallItemUse) (Player *player, Item *_Item, SpellCastTargets const& targets);
|
||||||
typedef bool(MANGOS_IMPORT * scriptCallEffectDummyGameObj) (Unit *caster, uint32 spellId, uint32 effIndex, GameObject *gameObjTarget);
|
typedef bool(MANGOS_IMPORT * scriptCallEffectDummyGameObj) (Unit *caster, uint32 spellId, uint32 effIndex, GameObject *gameObjTarget);
|
||||||
typedef bool(MANGOS_IMPORT * scriptCallEffectDummyCreature) (Unit *caster, uint32 spellId, uint32 effIndex, Creature *crTarget);
|
typedef bool(MANGOS_IMPORT * scriptCallEffectDummyCreature) (Unit *caster, uint32 spellId, uint32 effIndex, Creature *crTarget);
|
||||||
|
|
@ -83,7 +82,6 @@ typedef struct
|
||||||
scriptCallAreaTrigger scriptAreaTrigger;
|
scriptCallAreaTrigger scriptAreaTrigger;
|
||||||
scriptCallItemQuestAccept ItemQuestAccept;
|
scriptCallItemQuestAccept ItemQuestAccept;
|
||||||
scriptCallGOQuestAccept GOQuestAccept;
|
scriptCallGOQuestAccept GOQuestAccept;
|
||||||
scriptCallReceiveEmote ReceiveEmote;
|
|
||||||
scriptCallItemUse ItemUse;
|
scriptCallItemUse ItemUse;
|
||||||
scriptCallEffectDummyGameObj EffectDummyGameObj;
|
scriptCallEffectDummyGameObj EffectDummyGameObj;
|
||||||
scriptCallEffectDummyCreature EffectDummyCreature;
|
scriptCallEffectDummyCreature EffectDummyCreature;
|
||||||
|
|
|
||||||
|
|
@ -991,6 +991,7 @@ enum Targets
|
||||||
TARGET_RANDOM_FRIEND_CHAIN_IN_AREA = 3,
|
TARGET_RANDOM_FRIEND_CHAIN_IN_AREA = 3,
|
||||||
TARGET_PET = 5,
|
TARGET_PET = 5,
|
||||||
TARGET_CHAIN_DAMAGE = 6,
|
TARGET_CHAIN_DAMAGE = 6,
|
||||||
|
TARGET_AREAEFFECT_INSTANT = 7, // targets around provided destination point
|
||||||
TARGET_AREAEFFECT_CUSTOM = 8,
|
TARGET_AREAEFFECT_CUSTOM = 8,
|
||||||
TARGET_INNKEEPER_COORDINATES = 9, // uses in teleport to innkeeper spells
|
TARGET_INNKEEPER_COORDINATES = 9, // uses in teleport to innkeeper spells
|
||||||
TARGET_ALL_ENEMY_IN_AREA = 15,
|
TARGET_ALL_ENEMY_IN_AREA = 15,
|
||||||
|
|
@ -1336,7 +1337,7 @@ enum Emote
|
||||||
EMOTE_ONESHOT_POINT = 25,
|
EMOTE_ONESHOT_POINT = 25,
|
||||||
EMOTE_STATE_STAND = 26,
|
EMOTE_STATE_STAND = 26,
|
||||||
EMOTE_STATE_READYUNARMED = 27,
|
EMOTE_STATE_READYUNARMED = 27,
|
||||||
EMOTE_STATE_WORK = 28,
|
EMOTE_STATE_WORK_SHEATHED = 28,
|
||||||
EMOTE_STATE_POINT = 29,
|
EMOTE_STATE_POINT = 29,
|
||||||
EMOTE_STATE_NONE = 30,
|
EMOTE_STATE_NONE = 30,
|
||||||
EMOTE_ONESHOT_WOUND = 33,
|
EMOTE_ONESHOT_WOUND = 33,
|
||||||
|
|
@ -1369,13 +1370,13 @@ enum Emote
|
||||||
EMOTE_ONESHOT_SALUTE_NOSHEATH = 113,
|
EMOTE_ONESHOT_SALUTE_NOSHEATH = 113,
|
||||||
EMOTE_STATE_USESTANDING_NOSHEATHE = 133,
|
EMOTE_STATE_USESTANDING_NOSHEATHE = 133,
|
||||||
EMOTE_ONESHOT_LAUGH_NOSHEATHE = 153,
|
EMOTE_ONESHOT_LAUGH_NOSHEATHE = 153,
|
||||||
EMOTE_STATE_WORK_NOSHEATHE = 173,
|
EMOTE_STATE_WORK = 173,
|
||||||
EMOTE_STATE_SPELLPRECAST = 193,
|
EMOTE_STATE_SPELLPRECAST = 193,
|
||||||
EMOTE_ONESHOT_READYRIFLE = 213,
|
EMOTE_ONESHOT_READYRIFLE = 213,
|
||||||
EMOTE_STATE_READYRIFLE = 214,
|
EMOTE_STATE_READYRIFLE = 214,
|
||||||
EMOTE_STATE_WORK_NOSHEATHE_MINING = 233,
|
EMOTE_STATE_WORK_MINING = 233,
|
||||||
EMOTE_STATE_WORK_NOSHEATHE_CHOPWOOD= 234,
|
EMOTE_STATE_WORK_CHOPWOOD = 234,
|
||||||
EMOTE_zzOLDONESHOT_LIFTOFF = 253,
|
EMOTE_STATE_APPLAUD = 253,
|
||||||
EMOTE_ONESHOT_LIFTOFF = 254,
|
EMOTE_ONESHOT_LIFTOFF = 254,
|
||||||
EMOTE_ONESHOT_YES = 273,
|
EMOTE_ONESHOT_YES = 273,
|
||||||
EMOTE_ONESHOT_NO = 274,
|
EMOTE_ONESHOT_NO = 274,
|
||||||
|
|
@ -1424,8 +1425,57 @@ enum Emote
|
||||||
EMOTE_ONESHOT_CUSTOMSPELL09 = 410,
|
EMOTE_ONESHOT_CUSTOMSPELL09 = 410,
|
||||||
EMOTE_ONESHOT_CUSTOMSPELL10 = 411,
|
EMOTE_ONESHOT_CUSTOMSPELL10 = 411,
|
||||||
EMOTE_STATE_EXCLAIM = 412,
|
EMOTE_STATE_EXCLAIM = 412,
|
||||||
|
EMOTE_STATE_DANCE_CUSTOM = 413,
|
||||||
EMOTE_STATE_SIT_CHAIR_MED = 415,
|
EMOTE_STATE_SIT_CHAIR_MED = 415,
|
||||||
EMOTE_STATE_SPELLEFFECT_HOLD = 422
|
EMOTE_STATE_CUSTOM_SPELL_01 = 416,
|
||||||
|
EMOTE_STATE_CUSTOM_SPELL_02 = 417,
|
||||||
|
EMOTE_STATE_EAT = 418,
|
||||||
|
EMOTE_STATE_CUSTOM_SPELL_04 = 419,
|
||||||
|
EMOTE_STATE_CUSTOM_SPELL_03 = 420,
|
||||||
|
EMOTE_STATE_CUSTOM_SPELL_05 = 421,
|
||||||
|
EMOTE_STATE_SPELLEFFECT_HOLD = 422,
|
||||||
|
EMOTE_STATE_EAT_NO_SHEATHE = 423,
|
||||||
|
EMOTE_STATE_MOUNT = 424,
|
||||||
|
EMOTE_STATE_READY2HL = 425,
|
||||||
|
EMOTE_STATE_SIT_CHAIR_HIGH = 426,
|
||||||
|
EMOTE_STATE_FALL = 427,
|
||||||
|
EMOTE_STATE_LOOT = 428,
|
||||||
|
EMOTE_STATE_SUBMERGED_NEW = 429,
|
||||||
|
EMOTE_ONESHOT_COWER = 430,
|
||||||
|
EMOTE_STATE_COWER = 431,
|
||||||
|
EMOTE_ONESHOT_USESTANDING = 432,
|
||||||
|
EMOTE_STATE_STEALTH_STAND = 433,
|
||||||
|
EMOTE_ONESHOT_OMNICAST_GHOUL = 434,
|
||||||
|
EMOTE_ONESHOT_ATTACKBOW = 435,
|
||||||
|
EMOTE_ONESHOT_ATTACKRIFLE = 436,
|
||||||
|
EMOTE_STATE_SWIM_IDLE = 437,
|
||||||
|
EMOTE_STATE_ATTACK_UNARMED = 438,
|
||||||
|
EMOTE_ONESHOT_SPELLCAST_W_SOUND = 439,
|
||||||
|
EMOTE_ONESHOT_DODGE = 440,
|
||||||
|
EMOTE_ONESHOT_PARRY1H = 441,
|
||||||
|
EMOTE_ONESHOT_PARRY2H = 442,
|
||||||
|
EMOTE_ONESHOT_PARRY2HL = 443,
|
||||||
|
EMOTE_STATE_FLYFALL = 444,
|
||||||
|
EMOTE_ONESHOT_FLYDEATH = 445,
|
||||||
|
EMOTE_STATE_FLY_FALL = 446,
|
||||||
|
EMOTE_ONESHOT_FLY_SIT_GROUND_DOWN = 447,
|
||||||
|
EMOTE_ONESHOT_FLY_SIT_GROUND_UP = 448,
|
||||||
|
EMOTE_ONESHOT_EMERGE = 449,
|
||||||
|
EMOTE_ONESHOT_DRAGONSPIT = 450,
|
||||||
|
EMOTE_STATE_SPECIALUNARMED = 451,
|
||||||
|
EMOTE_ONESHOT_FLYGRAB = 452,
|
||||||
|
EMOTE_STATE_FLYGRABCLOSED = 453,
|
||||||
|
EMOTE_ONESHOT_FLYGRABTHROWN = 454,
|
||||||
|
EMOTE_STATE_FLY_SIT_GROUND = 455,
|
||||||
|
EMOTE_STATE_WALKBACKWARDS = 456,
|
||||||
|
EMOTE_ONESHOT_FLYTALK = 457,
|
||||||
|
EMOTE_ONESHOT_FLYATTACK1H = 458,
|
||||||
|
EMOTE_STATE_CUSTOMSPELL08 = 459,
|
||||||
|
EMOTE_ONESHOT_FLY_DRAGONSPIT = 460,
|
||||||
|
EMOTE_STATE_SIT_CHAIR_LOW = 461,
|
||||||
|
EMOTE_ONE_SHOT_STUN = 462,
|
||||||
|
EMOTE_ONESHOT_SPELLCAST_OMNI = 463,
|
||||||
|
EMOTE_STATE_READYTHROWN = 464
|
||||||
};
|
};
|
||||||
|
|
||||||
enum Anim
|
enum Anim
|
||||||
|
|
|
||||||
|
|
@ -457,6 +457,11 @@ void Spell::FillTargetMap()
|
||||||
case 0:
|
case 0:
|
||||||
SetTargetMap(i,m_spellInfo->EffectImplicitTargetA[i],tmpUnitMap);
|
SetTargetMap(i,m_spellInfo->EffectImplicitTargetA[i],tmpUnitMap);
|
||||||
break;
|
break;
|
||||||
|
case TARGET_AREAEFFECT_INSTANT: // use B case that not dependent from from A in fact
|
||||||
|
if((m_targets.m_targetMask & TARGET_FLAG_DEST_LOCATION)==0)
|
||||||
|
m_targets.setDestination(m_caster->GetPositionX(),m_caster->GetPositionY(),m_caster->GetPositionZ());
|
||||||
|
SetTargetMap(i,m_spellInfo->EffectImplicitTargetB[i],tmpUnitMap);
|
||||||
|
break;
|
||||||
case TARGET_BEHIND_VICTIM: // use B case that not dependent from from A in fact
|
case TARGET_BEHIND_VICTIM: // use B case that not dependent from from A in fact
|
||||||
SetTargetMap(i,m_spellInfo->EffectImplicitTargetB[i],tmpUnitMap);
|
SetTargetMap(i,m_spellInfo->EffectImplicitTargetB[i],tmpUnitMap);
|
||||||
break;
|
break;
|
||||||
|
|
@ -482,8 +487,25 @@ void Spell::FillTargetMap()
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case TARGET_TABLE_X_Y_Z_COORDINATES:
|
case TARGET_TABLE_X_Y_Z_COORDINATES:
|
||||||
// Only if target A, for target B (used in teleports) dest select in effect
|
switch(m_spellInfo->EffectImplicitTargetB[i])
|
||||||
SetTargetMap(i,m_spellInfo->EffectImplicitTargetA[i],tmpUnitMap);
|
{
|
||||||
|
case 0:
|
||||||
|
SetTargetMap(i,m_spellInfo->EffectImplicitTargetA[i],tmpUnitMap);
|
||||||
|
|
||||||
|
// need some target for proccesing
|
||||||
|
if(m_targets.getUnitTarget())
|
||||||
|
tmpUnitMap.push_back(m_targets.getUnitTarget());
|
||||||
|
else
|
||||||
|
tmpUnitMap.push_back(m_caster);
|
||||||
|
break;
|
||||||
|
case TARGET_AREAEFFECT_INSTANT: // All 17/7 pairs used for dest teleportation, A processed in effect code
|
||||||
|
SetTargetMap(i,m_spellInfo->EffectImplicitTargetB[i],tmpUnitMap);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
SetTargetMap(i,m_spellInfo->EffectImplicitTargetA[i],tmpUnitMap);
|
||||||
|
SetTargetMap(i,m_spellInfo->EffectImplicitTargetB[i],tmpUnitMap);
|
||||||
|
break;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
switch(m_spellInfo->EffectImplicitTargetB[i])
|
switch(m_spellInfo->EffectImplicitTargetB[i])
|
||||||
|
|
@ -1314,7 +1336,7 @@ struct TargetDistanceOrder : public std::binary_function<const Unit, const Unit,
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
void Spell::SetTargetMap(uint32 i,uint32 cur,UnitList& TagUnitMap)
|
||||||
{
|
{
|
||||||
float radius;
|
float radius;
|
||||||
if (m_spellInfo->EffectRadiusIndex[i])
|
if (m_spellInfo->EffectRadiusIndex[i])
|
||||||
|
|
@ -1598,38 +1620,27 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
}break;
|
}break;
|
||||||
case TARGET_ALL_ENEMY_IN_AREA:
|
case TARGET_ALL_ENEMY_IN_AREA:
|
||||||
{
|
{
|
||||||
CellPair p(MaNGOS::ComputeCellPair(m_targets.m_destX, m_targets.m_destY));
|
FillAreaTargets(TagUnitMap,m_targets.m_destX, m_targets.m_destY,radius,PUSH_DEST_CENTER,SPELL_TARGETS_AOE_DAMAGE);
|
||||||
Cell cell(p);
|
break;
|
||||||
cell.data.Part.reserved = ALL_DISTRICT;
|
}
|
||||||
cell.SetNoCreate();
|
case TARGET_AREAEFFECT_INSTANT:
|
||||||
|
{
|
||||||
|
SpellTargets targetB = SPELL_TARGETS_AOE_DAMAGE;
|
||||||
|
// Select friendly targets for positive effect
|
||||||
|
if (IsPositiveEffect(m_spellInfo->Id, i))
|
||||||
|
targetB = SPELL_TARGETS_FRIENDLY;
|
||||||
|
|
||||||
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius, PUSH_DEST_CENTER,SPELL_TARGETS_AOE_DAMAGE);
|
FillAreaTargets(TagUnitMap,m_caster->GetPositionX(), m_caster->GetPositionY(),radius, PUSH_DEST_CENTER, targetB);
|
||||||
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_object_notifier(notifier);
|
// exclude caster
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_object_notifier(notifier);
|
TagUnitMap.remove(m_caster);
|
||||||
|
}
|
||||||
CellLock<GridReadGuard> cell_lock(cell, p);
|
|
||||||
cell_lock->Visit(cell_lock, world_object_notifier, *m_caster->GetMap());
|
|
||||||
cell_lock->Visit(cell_lock, grid_object_notifier, *m_caster->GetMap());
|
|
||||||
}break;
|
|
||||||
case TARGET_ALL_ENEMY_IN_AREA_INSTANT:
|
case TARGET_ALL_ENEMY_IN_AREA_INSTANT:
|
||||||
{
|
{
|
||||||
// targets the ground, not the units in the area
|
// targets the ground, not the units in the area
|
||||||
if (m_spellInfo->Effect[i]!=SPELL_EFFECT_PERSISTENT_AREA_AURA)
|
if (m_spellInfo->Effect[i]!=SPELL_EFFECT_PERSISTENT_AREA_AURA)
|
||||||
{
|
{
|
||||||
CellPair p(MaNGOS::ComputeCellPair(m_targets.m_destX, m_targets.m_destY));
|
FillAreaTargets(TagUnitMap,m_targets.m_destX, m_targets.m_destY,radius,PUSH_DEST_CENTER,SPELL_TARGETS_AOE_DAMAGE);
|
||||||
Cell cell(p);
|
|
||||||
cell.data.Part.reserved = ALL_DISTRICT;
|
|
||||||
cell.SetNoCreate();
|
|
||||||
|
|
||||||
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius, PUSH_DEST_CENTER,SPELL_TARGETS_AOE_DAMAGE);
|
|
||||||
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_object_notifier(notifier);
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_object_notifier(notifier);
|
|
||||||
|
|
||||||
CellLock<GridReadGuard> cell_lock(cell, p);
|
|
||||||
cell_lock->Visit(cell_lock, world_object_notifier, *m_caster->GetMap());
|
|
||||||
cell_lock->Visit(cell_lock, grid_object_notifier, *m_caster->GetMap());
|
|
||||||
|
|
||||||
// exclude caster (this can be important if this not original caster)
|
// exclude caster (this can be important if this not original caster)
|
||||||
TagUnitMap.remove(m_caster);
|
TagUnitMap.remove(m_caster);
|
||||||
|
|
@ -1770,7 +1781,7 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
{
|
{
|
||||||
// Check original caster is GO - set its coordinates as dst cast
|
// Check original caster is GO - set its coordinates as dst cast
|
||||||
WorldObject *caster = NULL;
|
WorldObject *caster = NULL;
|
||||||
if (m_originalCasterGUID)
|
if (IS_GAMEOBJECT_GUID(m_originalCasterGUID))
|
||||||
caster = ObjectAccessor::GetGameObject(*m_caster, m_originalCasterGUID);
|
caster = ObjectAccessor::GetGameObject(*m_caster, m_originalCasterGUID);
|
||||||
if (!caster)
|
if (!caster)
|
||||||
caster = m_caster;
|
caster = m_caster;
|
||||||
|
|
@ -1778,37 +1789,11 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
m_targets.setDestination(caster->GetPositionX(), caster->GetPositionY(), caster->GetPositionZ());
|
m_targets.setDestination(caster->GetPositionX(), caster->GetPositionY(), caster->GetPositionZ());
|
||||||
}break;
|
}break;
|
||||||
case TARGET_ALL_FRIENDLY_UNITS_AROUND_CASTER:
|
case TARGET_ALL_FRIENDLY_UNITS_AROUND_CASTER:
|
||||||
{
|
FillAreaTargets(TagUnitMap,m_targets.m_destX, m_targets.m_destY,radius,PUSH_SELF_CENTER,SPELL_TARGETS_FRIENDLY);
|
||||||
CellPair p(MaNGOS::ComputeCellPair(m_targets.m_destX, m_targets.m_destY));
|
break;
|
||||||
Cell cell(p);
|
|
||||||
cell.data.Part.reserved = ALL_DISTRICT;
|
|
||||||
cell.SetNoCreate();
|
|
||||||
|
|
||||||
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius, PUSH_SELF_CENTER,SPELL_TARGETS_FRIENDLY);
|
|
||||||
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_object_notifier(notifier);
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_object_notifier(notifier);
|
|
||||||
|
|
||||||
CellLock<GridReadGuard> cell_lock(cell, p);
|
|
||||||
cell_lock->Visit(cell_lock, world_object_notifier, *m_caster->GetMap());
|
|
||||||
cell_lock->Visit(cell_lock, grid_object_notifier, *m_caster->GetMap());
|
|
||||||
}break;
|
|
||||||
case TARGET_ALL_FRIENDLY_UNITS_IN_AREA:
|
case TARGET_ALL_FRIENDLY_UNITS_IN_AREA:
|
||||||
{
|
FillAreaTargets(TagUnitMap,m_targets.m_destX, m_targets.m_destY,radius,PUSH_DEST_CENTER,SPELL_TARGETS_FRIENDLY);
|
||||||
CellPair p(MaNGOS::ComputeCellPair(m_targets.m_destX, m_targets.m_destY));
|
break;
|
||||||
Cell cell(p);
|
|
||||||
cell.data.Part.reserved = ALL_DISTRICT;
|
|
||||||
cell.SetNoCreate();
|
|
||||||
|
|
||||||
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius, PUSH_DEST_CENTER,SPELL_TARGETS_FRIENDLY);
|
|
||||||
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_object_notifier(notifier);
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_object_notifier(notifier);
|
|
||||||
|
|
||||||
CellLock<GridReadGuard> cell_lock(cell, p);
|
|
||||||
cell_lock->Visit(cell_lock, world_object_notifier, *m_caster->GetMap());
|
|
||||||
cell_lock->Visit(cell_lock, grid_object_notifier, *m_caster->GetMap());
|
|
||||||
}break;
|
|
||||||
// TARGET_SINGLE_PARTY means that the spells can only be casted on a party member and not on the caster (some seals, fire shield from imp, etc..)
|
// TARGET_SINGLE_PARTY means that the spells can only be casted on a party member and not on the caster (some seals, fire shield from imp, etc..)
|
||||||
case TARGET_SINGLE_PARTY:
|
case TARGET_SINGLE_PARTY:
|
||||||
{
|
{
|
||||||
|
|
@ -1871,21 +1856,10 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
}break;
|
}break;
|
||||||
case TARGET_IN_FRONT_OF_CASTER:
|
case TARGET_IN_FRONT_OF_CASTER:
|
||||||
{
|
{
|
||||||
CellPair p(MaNGOS::ComputeCellPair(m_caster->GetPositionX(), m_caster->GetPositionY()));
|
|
||||||
Cell cell(p);
|
|
||||||
cell.data.Part.reserved = ALL_DISTRICT;
|
|
||||||
cell.SetNoCreate();
|
|
||||||
|
|
||||||
bool inFront = m_spellInfo->SpellVisual[0] != 3879;
|
bool inFront = m_spellInfo->SpellVisual[0] != 3879;
|
||||||
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius, inFront ? PUSH_IN_FRONT : PUSH_IN_BACK,SPELL_TARGETS_AOE_DAMAGE);
|
FillAreaTargets(TagUnitMap,m_caster->GetPositionX(), m_caster->GetPositionY(),radius,inFront ? PUSH_IN_FRONT : PUSH_IN_BACK,SPELL_TARGETS_AOE_DAMAGE);
|
||||||
|
break;
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_object_notifier(notifier);
|
}
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_object_notifier(notifier);
|
|
||||||
|
|
||||||
CellLock<GridReadGuard> cell_lock(cell, p);
|
|
||||||
cell_lock->Visit(cell_lock, world_object_notifier, *m_caster->GetMap());
|
|
||||||
cell_lock->Visit(cell_lock, grid_object_notifier, *m_caster->GetMap());
|
|
||||||
}break;
|
|
||||||
case TARGET_DUELVSPLAYER:
|
case TARGET_DUELVSPLAYER:
|
||||||
{
|
{
|
||||||
Unit *target = m_targets.getUnitTarget();
|
Unit *target = m_targets.getUnitTarget();
|
||||||
|
|
@ -1921,22 +1895,9 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
{
|
{
|
||||||
// targets the ground, not the units in the area
|
// targets the ground, not the units in the area
|
||||||
if (m_spellInfo->Effect[i]!=SPELL_EFFECT_PERSISTENT_AREA_AURA)
|
if (m_spellInfo->Effect[i]!=SPELL_EFFECT_PERSISTENT_AREA_AURA)
|
||||||
{
|
FillAreaTargets(TagUnitMap,m_targets.m_destX, m_targets.m_destY,radius,PUSH_DEST_CENTER,SPELL_TARGETS_AOE_DAMAGE);
|
||||||
CellPair p(MaNGOS::ComputeCellPair(m_targets.m_destX, m_targets.m_destY));
|
break;
|
||||||
Cell cell(p);
|
}
|
||||||
cell.data.Part.reserved = ALL_DISTRICT;
|
|
||||||
cell.SetNoCreate();
|
|
||||||
|
|
||||||
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius, PUSH_DEST_CENTER,SPELL_TARGETS_AOE_DAMAGE);
|
|
||||||
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_object_notifier(notifier);
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_object_notifier(notifier);
|
|
||||||
|
|
||||||
CellLock<GridReadGuard> cell_lock(cell, p);
|
|
||||||
cell_lock->Visit(cell_lock, world_object_notifier, *m_caster->GetMap());
|
|
||||||
cell_lock->Visit(cell_lock, grid_object_notifier, *m_caster->GetMap());
|
|
||||||
}
|
|
||||||
}break;
|
|
||||||
case TARGET_MINION:
|
case TARGET_MINION:
|
||||||
{
|
{
|
||||||
if(m_spellInfo->Effect[i] != SPELL_EFFECT_DUEL)
|
if(m_spellInfo->Effect[i] != SPELL_EFFECT_DUEL)
|
||||||
|
|
@ -2038,24 +1999,9 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
unMaxTargets = EffectChainTarget;
|
unMaxTargets = EffectChainTarget;
|
||||||
float max_range = radius + unMaxTargets * CHAIN_SPELL_JUMP_RADIUS;
|
float max_range = radius + unMaxTargets * CHAIN_SPELL_JUMP_RADIUS;
|
||||||
|
|
||||||
std::list<Unit *> tempUnitMap;
|
UnitList tempUnitMap;
|
||||||
|
|
||||||
{
|
FillAreaTargets(tempUnitMap,m_caster->GetPositionX(), m_caster->GetPositionY(),max_range,PUSH_SELF_CENTER, SPELL_TARGETS_FRIENDLY);
|
||||||
CellPair p(MaNGOS::ComputeCellPair(m_caster->GetPositionX(), m_caster->GetPositionY()));
|
|
||||||
Cell cell(p);
|
|
||||||
cell.data.Part.reserved = ALL_DISTRICT;
|
|
||||||
cell.SetNoCreate();
|
|
||||||
|
|
||||||
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, tempUnitMap, max_range, PUSH_SELF_CENTER, SPELL_TARGETS_FRIENDLY);
|
|
||||||
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_object_notifier(notifier);
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_object_notifier(notifier);
|
|
||||||
|
|
||||||
CellLock<GridReadGuard> cell_lock(cell, p);
|
|
||||||
cell_lock->Visit(cell_lock, world_object_notifier, *m_caster->GetMap());
|
|
||||||
cell_lock->Visit(cell_lock, grid_object_notifier, *m_caster->GetMap());
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
if(m_caster != pUnitTarget && std::find(tempUnitMap.begin(),tempUnitMap.end(),m_caster) == tempUnitMap.end() )
|
if(m_caster != pUnitTarget && std::find(tempUnitMap.begin(),tempUnitMap.end(),m_caster) == tempUnitMap.end() )
|
||||||
tempUnitMap.push_front(m_caster);
|
tempUnitMap.push_front(m_caster);
|
||||||
|
|
@ -2108,20 +2054,10 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
TagUnitMap.push_back(currentTarget);
|
TagUnitMap.push_back(currentTarget);
|
||||||
m_targets.setDestination(currentTarget->GetPositionX(), currentTarget->GetPositionY(), currentTarget->GetPositionZ());
|
m_targets.setDestination(currentTarget->GetPositionX(), currentTarget->GetPositionY(), currentTarget->GetPositionZ());
|
||||||
if(m_spellInfo->EffectImplicitTargetB[i]==TARGET_ALL_ENEMY_IN_AREA_INSTANT)
|
if(m_spellInfo->EffectImplicitTargetB[i]==TARGET_ALL_ENEMY_IN_AREA_INSTANT)
|
||||||
{
|
FillAreaTargets(TagUnitMap, currentTarget->GetPositionX(), currentTarget->GetPositionY(), radius, PUSH_TARGET_CENTER, SPELL_TARGETS_AOE_DAMAGE);
|
||||||
CellPair p(MaNGOS::ComputeCellPair(currentTarget->GetPositionX(), currentTarget->GetPositionY()));
|
|
||||||
Cell cell(p);
|
|
||||||
cell.data.Part.reserved = ALL_DISTRICT;
|
|
||||||
cell.SetNoCreate();
|
|
||||||
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius,PUSH_TARGET_CENTER, SPELL_TARGETS_AOE_DAMAGE);
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_notifier(notifier);
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_notifier(notifier);
|
|
||||||
CellLock<GridReadGuard> cell_lock(cell, p);
|
|
||||||
cell_lock->Visit(cell_lock, world_notifier, *m_caster->GetMap());
|
|
||||||
cell_lock->Visit(cell_lock, grid_notifier, *m_caster->GetMap());
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}break;
|
break;
|
||||||
|
}
|
||||||
case TARGET_AREAEFFECT_PARTY_AND_CLASS:
|
case TARGET_AREAEFFECT_PARTY_AND_CLASS:
|
||||||
{
|
{
|
||||||
Player* targetPlayer = m_targets.getUnitTarget() && m_targets.getUnitTarget()->GetTypeId() == TYPEID_PLAYER
|
Player* targetPlayer = m_targets.getUnitTarget() && m_targets.getUnitTarget()->GetTypeId() == TYPEID_PLAYER
|
||||||
|
|
@ -2154,29 +2090,8 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
{
|
{
|
||||||
if (st->target_mapId == m_caster->GetMapId())
|
if (st->target_mapId == m_caster->GetMapId())
|
||||||
m_targets.setDestination(st->target_X, st->target_Y, st->target_Z);
|
m_targets.setDestination(st->target_X, st->target_Y, st->target_Z);
|
||||||
|
else
|
||||||
// if B==TARGET_TABLE_X_Y_Z_COORDINATES then A already fill all required targets
|
sLog.outError( "SPELL: wrong map (%u instead %u) target coordinates for spell ID %u", st->target_mapId, m_caster->GetMapId(), m_spellInfo->Id );
|
||||||
if (m_spellInfo->EffectImplicitTargetB[i] && m_spellInfo->EffectImplicitTargetB[i]!=TARGET_TABLE_X_Y_Z_COORDINATES)
|
|
||||||
{
|
|
||||||
CellPair p(MaNGOS::ComputeCellPair(m_caster->GetPositionX(), m_caster->GetPositionY()));
|
|
||||||
Cell cell(p);
|
|
||||||
cell.data.Part.reserved = ALL_DISTRICT;
|
|
||||||
cell.SetNoCreate();
|
|
||||||
|
|
||||||
SpellTargets targetB = SPELL_TARGETS_AOE_DAMAGE;
|
|
||||||
// Select friendly targets for positive effect
|
|
||||||
if (IsPositiveEffect(m_spellInfo->Id, i))
|
|
||||||
targetB = SPELL_TARGETS_FRIENDLY;
|
|
||||||
|
|
||||||
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius,PUSH_DEST_CENTER, targetB);
|
|
||||||
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_notifier(notifier);
|
|
||||||
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_notifier(notifier);
|
|
||||||
|
|
||||||
CellLock<GridReadGuard> cell_lock(cell, p);
|
|
||||||
cell_lock->Visit(cell_lock, world_notifier, *m_caster->GetMap());
|
|
||||||
cell_lock->Visit(cell_lock, grid_notifier, *m_caster->GetMap());
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
sLog.outError( "SPELL: unknown target coordinates for spell ID %u", m_spellInfo->Id );
|
sLog.outError( "SPELL: unknown target coordinates for spell ID %u", m_spellInfo->Id );
|
||||||
|
|
@ -2238,7 +2153,7 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
{
|
{
|
||||||
// make sure one unit is always removed per iteration
|
// make sure one unit is always removed per iteration
|
||||||
uint32 removed_utarget = 0;
|
uint32 removed_utarget = 0;
|
||||||
for (std::list<Unit*>::iterator itr = TagUnitMap.begin(), next; itr != TagUnitMap.end(); itr = next)
|
for (UnitList::iterator itr = TagUnitMap.begin(), next; itr != TagUnitMap.end(); itr = next)
|
||||||
{
|
{
|
||||||
next = itr;
|
next = itr;
|
||||||
++next;
|
++next;
|
||||||
|
|
@ -2254,9 +2169,10 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
while (TagUnitMap.size() > unMaxTargets - removed_utarget)
|
while (TagUnitMap.size() > unMaxTargets - removed_utarget)
|
||||||
{
|
{
|
||||||
uint32 poz = urand(0, TagUnitMap.size()-1);
|
uint32 poz = urand(0, TagUnitMap.size()-1);
|
||||||
for (std::list<Unit*>::iterator itr = TagUnitMap.begin(); itr != TagUnitMap.end(); ++itr, --poz)
|
for (UnitList::iterator itr = TagUnitMap.begin(); itr != TagUnitMap.end(); ++itr, --poz)
|
||||||
{
|
{
|
||||||
if (!*itr) continue;
|
if (!*itr) continue;
|
||||||
|
|
||||||
if (!poz)
|
if (!poz)
|
||||||
{
|
{
|
||||||
TagUnitMap.erase(itr);
|
TagUnitMap.erase(itr);
|
||||||
|
|
@ -5490,7 +5406,7 @@ bool Spell::CheckTarget( Unit* target, uint32 eff )
|
||||||
default: // normal case
|
default: // normal case
|
||||||
// Get GO cast coordinates if original caster -> GO
|
// Get GO cast coordinates if original caster -> GO
|
||||||
WorldObject *caster = NULL;
|
WorldObject *caster = NULL;
|
||||||
if (m_originalCasterGUID)
|
if (IS_GAMEOBJECT_GUID(m_originalCasterGUID))
|
||||||
caster = ObjectAccessor::GetGameObject(*m_caster, m_originalCasterGUID);
|
caster = ObjectAccessor::GetGameObject(*m_caster, m_originalCasterGUID);
|
||||||
if (!caster)
|
if (!caster)
|
||||||
caster = m_caster;
|
caster = m_caster;
|
||||||
|
|
@ -5730,3 +5646,17 @@ SpellCastResult Spell::CanOpenLock(uint32 effIndex, uint32 lockId, SkillType& sk
|
||||||
|
|
||||||
return SPELL_CAST_OK;
|
return SPELL_CAST_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Spell::FillAreaTargets( UnitList& TagUnitMap, float x, float y, float radius, SpellNotifyPushType pushType, SpellTargets spellTargets )
|
||||||
|
{
|
||||||
|
CellPair p(MaNGOS::ComputeCellPair(x, y));
|
||||||
|
Cell cell(p);
|
||||||
|
cell.data.Part.reserved = ALL_DISTRICT;
|
||||||
|
cell.SetNoCreate();
|
||||||
|
MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, TagUnitMap, radius, pushType, spellTargets);
|
||||||
|
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, WorldTypeMapContainer > world_notifier(notifier);
|
||||||
|
TypeContainerVisitor<MaNGOS::SpellNotifierCreatureAndPlayer, GridTypeMapContainer > grid_notifier(notifier);
|
||||||
|
CellLock<GridReadGuard> cell_lock(cell, p);
|
||||||
|
cell_lock->Visit(cell_lock, world_notifier, *m_caster->GetMap());
|
||||||
|
cell_lock->Visit(cell_lock, grid_notifier, *m_caster->GetMap());
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -205,6 +205,15 @@ enum SpellState
|
||||||
SPELL_STATE_DELAYED = 5
|
SPELL_STATE_DELAYED = 5
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum SpellTargets
|
||||||
|
{
|
||||||
|
SPELL_TARGETS_HOSTILE,
|
||||||
|
SPELL_TARGETS_NOT_FRIENDLY,
|
||||||
|
SPELL_TARGETS_NOT_HOSTILE,
|
||||||
|
SPELL_TARGETS_FRIENDLY,
|
||||||
|
SPELL_TARGETS_AOE_DAMAGE
|
||||||
|
};
|
||||||
|
|
||||||
#define SPELL_SPELL_CHANNEL_UPDATE_INTERVAL (1*IN_MILISECONDS)
|
#define SPELL_SPELL_CHANNEL_UPDATE_INTERVAL (1*IN_MILISECONDS)
|
||||||
|
|
||||||
typedef std::multimap<uint64, uint64> SpellTargetTimeMap;
|
typedef std::multimap<uint64, uint64> SpellTargetTimeMap;
|
||||||
|
|
@ -366,9 +375,11 @@ class Spell
|
||||||
void DoCreateItem(uint32 i, uint32 itemtype);
|
void DoCreateItem(uint32 i, uint32 itemtype);
|
||||||
void WriteSpellGoTargets( WorldPacket * data );
|
void WriteSpellGoTargets( WorldPacket * data );
|
||||||
void WriteAmmoToPacket( WorldPacket * data );
|
void WriteAmmoToPacket( WorldPacket * data );
|
||||||
void FillTargetMap();
|
|
||||||
|
|
||||||
void SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap);
|
typedef std::list<Unit*> UnitList;
|
||||||
|
void FillTargetMap();
|
||||||
|
void SetTargetMap(uint32 i,uint32 cur,UnitList& TagUnitMap);
|
||||||
|
void FillAreaTargets( UnitList& TagUnitMap, float x, float y, float radius, SpellNotifyPushType pushType, SpellTargets spellTargets );
|
||||||
|
|
||||||
Unit* SelectMagnetTarget();
|
Unit* SelectMagnetTarget();
|
||||||
bool CheckTarget( Unit* target, uint32 eff );
|
bool CheckTarget( Unit* target, uint32 eff );
|
||||||
|
|
@ -579,15 +590,6 @@ enum ReplenishType
|
||||||
REPLENISH_RAGE = 22
|
REPLENISH_RAGE = 22
|
||||||
};
|
};
|
||||||
|
|
||||||
enum SpellTargets
|
|
||||||
{
|
|
||||||
SPELL_TARGETS_HOSTILE,
|
|
||||||
SPELL_TARGETS_NOT_FRIENDLY,
|
|
||||||
SPELL_TARGETS_NOT_HOSTILE,
|
|
||||||
SPELL_TARGETS_FRIENDLY,
|
|
||||||
SPELL_TARGETS_AOE_DAMAGE
|
|
||||||
};
|
|
||||||
|
|
||||||
namespace MaNGOS
|
namespace MaNGOS
|
||||||
{
|
{
|
||||||
struct MANGOS_DLL_DECL SpellNotifierPlayer
|
struct MANGOS_DLL_DECL SpellNotifierPlayer
|
||||||
|
|
|
||||||
|
|
@ -468,12 +468,12 @@ Unit *caster, Item* castItem) : Aura(spellproto, eff, currentBasePoints, target,
|
||||||
{
|
{
|
||||||
case SPELL_EFFECT_APPLY_AREA_AURA_PARTY:
|
case SPELL_EFFECT_APPLY_AREA_AURA_PARTY:
|
||||||
m_areaAuraType = AREA_AURA_PARTY;
|
m_areaAuraType = AREA_AURA_PARTY;
|
||||||
if(target->GetTypeId() == TYPEID_UNIT && ((Creature*)target)->isTotem())
|
if (target->GetTypeId() == TYPEID_UNIT && ((Creature*)target)->isTotem())
|
||||||
m_modifier.m_auraname = SPELL_AURA_NONE;
|
m_modifier.m_auraname = SPELL_AURA_NONE;
|
||||||
break;
|
break;
|
||||||
case SPELL_EFFECT_APPLY_AREA_AURA_RAID:
|
case SPELL_EFFECT_APPLY_AREA_AURA_RAID:
|
||||||
m_areaAuraType = AREA_AURA_RAID;
|
m_areaAuraType = AREA_AURA_RAID;
|
||||||
if(target->GetTypeId() == TYPEID_UNIT && ((Creature*)target)->isTotem())
|
if (target->GetTypeId() == TYPEID_UNIT && ((Creature*)target)->isTotem())
|
||||||
m_modifier.m_auraname = SPELL_AURA_NONE;
|
m_modifier.m_auraname = SPELL_AURA_NONE;
|
||||||
break;
|
break;
|
||||||
case SPELL_EFFECT_APPLY_AREA_AURA_FRIEND:
|
case SPELL_EFFECT_APPLY_AREA_AURA_FRIEND:
|
||||||
|
|
@ -481,7 +481,7 @@ Unit *caster, Item* castItem) : Aura(spellproto, eff, currentBasePoints, target,
|
||||||
break;
|
break;
|
||||||
case SPELL_EFFECT_APPLY_AREA_AURA_ENEMY:
|
case SPELL_EFFECT_APPLY_AREA_AURA_ENEMY:
|
||||||
m_areaAuraType = AREA_AURA_ENEMY;
|
m_areaAuraType = AREA_AURA_ENEMY;
|
||||||
if(target == caster_ptr)
|
if (target == caster_ptr)
|
||||||
m_modifier.m_auraname = SPELL_AURA_NONE; // Do not do any effect on self
|
m_modifier.m_auraname = SPELL_AURA_NONE; // Do not do any effect on self
|
||||||
break;
|
break;
|
||||||
case SPELL_EFFECT_APPLY_AREA_AURA_PET:
|
case SPELL_EFFECT_APPLY_AREA_AURA_PET:
|
||||||
|
|
@ -489,7 +489,7 @@ Unit *caster, Item* castItem) : Aura(spellproto, eff, currentBasePoints, target,
|
||||||
break;
|
break;
|
||||||
case SPELL_EFFECT_APPLY_AREA_AURA_OWNER:
|
case SPELL_EFFECT_APPLY_AREA_AURA_OWNER:
|
||||||
m_areaAuraType = AREA_AURA_OWNER;
|
m_areaAuraType = AREA_AURA_OWNER;
|
||||||
if(target == caster_ptr)
|
if (target == caster_ptr)
|
||||||
m_modifier.m_auraname = SPELL_AURA_NONE;
|
m_modifier.m_auraname = SPELL_AURA_NONE;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
|
|
||||||
|
|
@ -2100,6 +2100,7 @@ void Spell::EffectTeleportUnits(uint32 i)
|
||||||
((Player*)unitTarget)->TeleportTo(((Player*)unitTarget)->m_homebindMapId,((Player*)unitTarget)->m_homebindX,((Player*)unitTarget)->m_homebindY,((Player*)unitTarget)->m_homebindZ,unitTarget->GetOrientation(),unitTarget==m_caster ? TELE_TO_SPELL : 0);
|
((Player*)unitTarget)->TeleportTo(((Player*)unitTarget)->m_homebindMapId,((Player*)unitTarget)->m_homebindX,((Player*)unitTarget)->m_homebindY,((Player*)unitTarget)->m_homebindZ,unitTarget->GetOrientation(),unitTarget==m_caster ? TELE_TO_SPELL : 0);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
case TARGET_AREAEFFECT_INSTANT: // in all cases first TARGET_TABLE_X_Y_Z_COORDINATES
|
||||||
case TARGET_TABLE_X_Y_Z_COORDINATES:
|
case TARGET_TABLE_X_Y_Z_COORDINATES:
|
||||||
{
|
{
|
||||||
SpellTargetPosition const* st = spellmgr.GetSpellTargetPosition(m_spellInfo->Id);
|
SpellTargetPosition const* st = spellmgr.GetSpellTargetPosition(m_spellInfo->Id);
|
||||||
|
|
|
||||||
|
|
@ -181,6 +181,7 @@ inline bool IsAreaEffectTarget( Targets target )
|
||||||
{
|
{
|
||||||
switch (target )
|
switch (target )
|
||||||
{
|
{
|
||||||
|
case TARGET_AREAEFFECT_INSTANT:
|
||||||
case TARGET_AREAEFFECT_CUSTOM:
|
case TARGET_AREAEFFECT_CUSTOM:
|
||||||
case TARGET_ALL_ENEMY_IN_AREA:
|
case TARGET_ALL_ENEMY_IN_AREA:
|
||||||
case TARGET_ALL_ENEMY_IN_AREA_INSTANT:
|
case TARGET_ALL_ENEMY_IN_AREA_INSTANT:
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,4 @@
|
||||||
#ifndef __REVISION_NR_H__
|
#ifndef __REVISION_NR_H__
|
||||||
#define __REVISION_NR_H__
|
#define __REVISION_NR_H__
|
||||||
#define REVISION_NR "7670"
|
#define REVISION_NR "7685"
|
||||||
#endif // __REVISION_NR_H__
|
#endif // __REVISION_NR_H__
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue