summaryrefslogtreecommitdiff
path: root/src/game/AI/ScriptedAI/ScriptedFollowerAI.cpp
diff options
context:
space:
mode:
authorYehonal <yehonal.azeroth@gmail.com>2017-12-20 20:48:35 +0100
committerYehonal <yehonal.azeroth@gmail.com>2017-12-21 00:20:29 +0100
commit17332304fdf129076d0196010602350d5750c808 (patch)
treed161f8845df9e5c8ec0b149bd846646c2b112d49 /src/game/AI/ScriptedAI/ScriptedFollowerAI.cpp
parent0fc4a6a153ca3a09ccb6e1311131b12a59c6cba3 (diff)
Using TC structure allowing easier patches importing
Diffstat (limited to 'src/game/AI/ScriptedAI/ScriptedFollowerAI.cpp')
-rw-r--r--src/game/AI/ScriptedAI/ScriptedFollowerAI.cpp381
1 files changed, 0 insertions, 381 deletions
diff --git a/src/game/AI/ScriptedAI/ScriptedFollowerAI.cpp b/src/game/AI/ScriptedAI/ScriptedFollowerAI.cpp
deleted file mode 100644
index b44ec3ca0f..0000000000
--- a/src/game/AI/ScriptedAI/ScriptedFollowerAI.cpp
+++ /dev/null
@@ -1,381 +0,0 @@
-/*
- * Copyright (C) 2016+ AzerothCore <www.azerothcore.org>, released under GNU GPL v2 license: http://github.com/azerothcore/azerothcore-wotlk/LICENSE-GPL2
- * Copyright (C) 2006-2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/>
- */
-
-/* ScriptData
-SDName: FollowerAI
-SD%Complete: 50
-SDComment: This AI is under development
-SDCategory: Npc
-EndScriptData */
-
-#include "ScriptedCreature.h"
-#include "ScriptedFollowerAI.h"
-#include "Group.h"
-#include "Player.h"
-
-const float MAX_PLAYER_DISTANCE = 100.0f;
-
-enum ePoints
-{
- POINT_COMBAT_START = 0xFFFFFF
-};
-
-FollowerAI::FollowerAI(Creature* creature) : ScriptedAI(creature),
- m_uiLeaderGUID(0),
- m_uiUpdateFollowTimer(2500),
- m_uiFollowState(STATE_FOLLOW_NONE),
- m_pQuestForFollow(NULL)
-{}
-
-void FollowerAI::AttackStart(Unit* who)
-{
- if (!who)
- return;
-
- if (me->Attack(who, true))
- {
- // This is done in Unit::Attack function which wont bug npcs by not adding threat upon combat start...
- //me->AddThreat(who, 0.0f);
- //me->SetInCombatWith(who);
- //who->SetInCombatWith(me);
-
- if (me->HasUnitState(UNIT_STATE_FOLLOW))
- me->ClearUnitState(UNIT_STATE_FOLLOW);
-
- if (IsCombatMovementAllowed())
- me->GetMotionMaster()->MoveChase(who);
- }
-}
-
-//This part provides assistance to a player that are attacked by who, even if out of normal aggro range
-//It will cause me to attack who that are attacking _any_ player (which has been confirmed may happen also on offi)
-//The flag (type_flag) is unconfirmed, but used here for further research and is a good candidate.
-bool FollowerAI::AssistPlayerInCombat(Unit* who)
-{
- if (!who || !who->GetVictim())
- return false;
-
- //experimental (unknown) flag not present
- if (!(me->GetCreatureTemplate()->type_flags & CREATURE_TYPEFLAGS_AID_PLAYERS))
- return false;
-
- //not a player
- if (!who->GetVictim()->GetCharmerOrOwnerPlayerOrPlayerItself())
- return false;
-
- //never attack friendly
- if (me->IsFriendlyTo(who))
- return false;
-
- //too far away and no free sight?
- if (me->IsWithinDistInMap(who, MAX_PLAYER_DISTANCE) && me->IsWithinLOSInMap(who))
- {
- AttackStart(who);
- return true;
- }
-
- return false;
-}
-
-void FollowerAI::MoveInLineOfSight(Unit* who)
-{
- if (me->GetVictim())
- return;
-
- if (!me->HasUnitState(UNIT_STATE_STUNNED) && who->isTargetableForAttack(true, me) && who->isInAccessiblePlaceFor(me))
- if (HasFollowState(STATE_FOLLOW_INPROGRESS) && AssistPlayerInCombat(who))
- return;
-
- if (me->CanStartAttack(who))
- AttackStart(who);
-}
-
-void FollowerAI::JustDied(Unit* /*pKiller*/)
-{
- if (!HasFollowState(STATE_FOLLOW_INPROGRESS) || !m_uiLeaderGUID || !m_pQuestForFollow)
- return;
-
- //TODO: need a better check for quests with time limit.
- if (Player* player = GetLeaderForFollower())
- {
- if (Group* group = player->GetGroup())
- {
- for (GroupReference* groupRef = group->GetFirstMember(); groupRef != NULL; groupRef = groupRef->next())
- {
- if (Player* member = groupRef->GetSource())
- {
- if (member->IsInMap(player) && member->GetQuestStatus(m_pQuestForFollow->GetQuestId()) == QUEST_STATUS_INCOMPLETE)
- member->FailQuest(m_pQuestForFollow->GetQuestId());
- }
- }
- }
- else
- {
- if (player->GetQuestStatus(m_pQuestForFollow->GetQuestId()) == QUEST_STATUS_INCOMPLETE)
- player->FailQuest(m_pQuestForFollow->GetQuestId());
- }
- }
-}
-
-void FollowerAI::JustRespawned()
-{
- m_uiFollowState = STATE_FOLLOW_NONE;
-
- if (!IsCombatMovementAllowed())
- SetCombatMovement(true);
-
- if (me->getFaction() != me->GetCreatureTemplate()->faction)
- me->setFaction(me->GetCreatureTemplate()->faction);
-
- Reset();
-}
-
-void FollowerAI::EnterEvadeMode()
-{
- me->RemoveAllAuras();
- me->DeleteThreatList();
- me->CombatStop(true);
- me->SetLootRecipient(NULL);
-
- if (HasFollowState(STATE_FOLLOW_INPROGRESS))
- {
-#if defined(ENABLE_EXTRAS) && defined(ENABLE_EXTRA_LOGS)
- sLog->outDebug(LOG_FILTER_TSCR, "TSCR: FollowerAI left combat, returning to CombatStartPosition.");
-#endif
-
- if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() == CHASE_MOTION_TYPE)
- {
- float fPosX, fPosY, fPosZ;
- me->GetPosition(fPosX, fPosY, fPosZ);
- me->GetMotionMaster()->MovePoint(POINT_COMBAT_START, fPosX, fPosY, fPosZ);
- }
- }
- else
- {
- if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() == CHASE_MOTION_TYPE)
- me->GetMotionMaster()->MoveTargetedHome();
- }
-
- Reset();
-}
-
-void FollowerAI::UpdateAI(uint32 uiDiff)
-{
- if (HasFollowState(STATE_FOLLOW_INPROGRESS) && !me->GetVictim())
- {
- if (m_uiUpdateFollowTimer <= uiDiff)
- {
- if (HasFollowState(STATE_FOLLOW_COMPLETE) && !HasFollowState(STATE_FOLLOW_POSTEVENT))
- {
-#if defined(ENABLE_EXTRAS) && defined(ENABLE_EXTRA_LOGS)
- sLog->outDebug(LOG_FILTER_TSCR, "TSCR: FollowerAI is set completed, despawns.");
-#endif
- me->DespawnOrUnsummon();
- return;
- }
-
- bool bIsMaxRangeExceeded = true;
-
- if (Player* player = GetLeaderForFollower())
- {
- if (HasFollowState(STATE_FOLLOW_RETURNING))
- {
-#if defined(ENABLE_EXTRAS) && defined(ENABLE_EXTRA_LOGS)
- sLog->outDebug(LOG_FILTER_TSCR, "TSCR: FollowerAI is returning to leader.");
-#endif
-
- RemoveFollowState(STATE_FOLLOW_RETURNING);
- me->GetMotionMaster()->MoveFollow(player, PET_FOLLOW_DIST, PET_FOLLOW_ANGLE);
- return;
- }
-
- if (Group* group = player->GetGroup())
- {
- for (GroupReference* groupRef = group->GetFirstMember(); groupRef != NULL; groupRef = groupRef->next())
- {
- Player* member = groupRef->GetSource();
-
- if (member && me->IsWithinDistInMap(member, MAX_PLAYER_DISTANCE))
- {
- bIsMaxRangeExceeded = false;
- break;
- }
- }
- }
- else
- {
- if (me->IsWithinDistInMap(player, MAX_PLAYER_DISTANCE))
- bIsMaxRangeExceeded = false;
- }
- }
-
- if (bIsMaxRangeExceeded)
- {
-#if defined(ENABLE_EXTRAS) && defined(ENABLE_EXTRA_LOGS)
- sLog->outDebug(LOG_FILTER_TSCR, "TSCR: FollowerAI failed because player/group was to far away or not found");
-#endif
- me->DespawnOrUnsummon();
- return;
- }
-
- m_uiUpdateFollowTimer = 1000;
- }
- else
- m_uiUpdateFollowTimer -= uiDiff;
- }
-
- UpdateFollowerAI(uiDiff);
-}
-
-void FollowerAI::UpdateFollowerAI(uint32 /*uiDiff*/)
-{
- if (!UpdateVictim())
- return;
-
- DoMeleeAttackIfReady();
-}
-
-void FollowerAI::MovementInform(uint32 motionType, uint32 pointId)
-{
- if (motionType != POINT_MOTION_TYPE || !HasFollowState(STATE_FOLLOW_INPROGRESS))
- return;
-
- if (pointId == POINT_COMBAT_START)
- {
- if (GetLeaderForFollower())
- {
- if (!HasFollowState(STATE_FOLLOW_PAUSED))
- AddFollowState(STATE_FOLLOW_RETURNING);
- }
- else
- me->DespawnOrUnsummon();
- }
-}
-
-void FollowerAI::StartFollow(Player* player, uint32 factionForFollower, const Quest* quest)
-{
- if (me->GetVictim())
- {
-#if defined(ENABLE_EXTRAS) && defined(ENABLE_EXTRA_LOGS)
- sLog->outDebug(LOG_FILTER_TSCR, "TSCR: FollowerAI attempt to StartFollow while in combat.");
-#endif
- return;
- }
-
- if (HasFollowState(STATE_FOLLOW_INPROGRESS))
- {
- sLog->outError("TSCR: FollowerAI attempt to StartFollow while already following.");
- return;
- }
-
- //set variables
- m_uiLeaderGUID = player->GetGUID();
-
- if (factionForFollower)
- me->setFaction(factionForFollower);
-
- m_pQuestForFollow = quest;
-
- if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() == WAYPOINT_MOTION_TYPE)
- {
- me->GetMotionMaster()->Clear();
- me->GetMotionMaster()->MoveIdle();
-#if defined(ENABLE_EXTRAS) && defined(ENABLE_EXTRA_LOGS)
- sLog->outDebug(LOG_FILTER_TSCR, "TSCR: FollowerAI start with WAYPOINT_MOTION_TYPE, set to MoveIdle.");
-#endif
- }
-
- me->SetUInt32Value(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_NONE);
-
- AddFollowState(STATE_FOLLOW_INPROGRESS);
-
- me->GetMotionMaster()->MoveFollow(player, PET_FOLLOW_DIST, PET_FOLLOW_ANGLE);
-
-#if defined(ENABLE_EXTRAS) && defined(ENABLE_EXTRA_LOGS)
- sLog->outDebug(LOG_FILTER_TSCR, "TSCR: FollowerAI start follow %s (GUID " UI64FMTD ")", player->GetName().c_str(), m_uiLeaderGUID);
-#endif
-}
-
-Player* FollowerAI::GetLeaderForFollower()
-{
- if (Player* player = ObjectAccessor::GetPlayer(*me, m_uiLeaderGUID))
- {
- if (player->IsAlive())
- return player;
- else
- {
- if (Group* group = player->GetGroup())
- {
- for (GroupReference* groupRef = group->GetFirstMember(); groupRef != NULL; groupRef = groupRef->next())
- {
- Player* member = groupRef->GetSource();
-
- if (member && me->IsWithinDistInMap(member, MAX_PLAYER_DISTANCE) && member->IsAlive())
- {
-#if defined(ENABLE_EXTRAS) && defined(ENABLE_EXTRA_LOGS)
- sLog->outDebug(LOG_FILTER_TSCR, "TSCR: FollowerAI GetLeader changed and returned new leader.");
-#endif
- m_uiLeaderGUID = member->GetGUID();
- return member;
- }
- }
- }
- }
- }
-
-#if defined(ENABLE_EXTRAS) && defined(ENABLE_EXTRA_LOGS)
- sLog->outDebug(LOG_FILTER_TSCR, "TSCR: FollowerAI GetLeader can not find suitable leader.");
-#endif
- return NULL;
-}
-
-void FollowerAI::SetFollowComplete(bool bWithEndEvent)
-{
- if (me->HasUnitState(UNIT_STATE_FOLLOW))
- {
- me->ClearUnitState(UNIT_STATE_FOLLOW);
-
- me->StopMoving();
- me->GetMotionMaster()->Clear();
- me->GetMotionMaster()->MoveIdle();
- }
-
- if (bWithEndEvent)
- AddFollowState(STATE_FOLLOW_POSTEVENT);
- else
- {
- if (HasFollowState(STATE_FOLLOW_POSTEVENT))
- RemoveFollowState(STATE_FOLLOW_POSTEVENT);
- }
-
- AddFollowState(STATE_FOLLOW_COMPLETE);
-}
-
-void FollowerAI::SetFollowPaused(bool paused)
-{
- if (!HasFollowState(STATE_FOLLOW_INPROGRESS) || HasFollowState(STATE_FOLLOW_COMPLETE))
- return;
-
- if (paused)
- {
- AddFollowState(STATE_FOLLOW_PAUSED);
-
- if (me->HasUnitState(UNIT_STATE_FOLLOW))
- {
- me->ClearUnitState(UNIT_STATE_FOLLOW);
-
- me->StopMoving();
- me->GetMotionMaster()->Clear();
- me->GetMotionMaster()->MoveIdle();
- }
- }
- else
- {
- RemoveFollowState(STATE_FOLLOW_PAUSED);
-
- if (Player* leader = GetLeaderForFollower())
- me->GetMotionMaster()->MoveFollow(leader, PET_FOLLOW_DIST, PET_FOLLOW_ANGLE);
- }
-}