Skip to content

Commit 6b6fdad

Browse files
authored
Merge c3f069d into b5d14f3
2 parents b5d14f3 + c3f069d commit 6b6fdad

7 files changed

Lines changed: 61 additions & 0 deletions

File tree

src/game/Object/Player.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7492,6 +7492,10 @@ void Player::UpdateZone(uint32 newZone, uint32 newArea)
74927492
sOutdoorPvPMgr.HandlePlayerLeaveZone(this, m_zoneUpdateId);
74937493
sOutdoorPvPMgr.HandlePlayerEnterZone(this, newZone);
74947494

7495+
#ifdef ENABLE_PLAYERBOTS
7496+
sRandomPlayerbotMgr.OnPlayerZoneChange(this, newZone);
7497+
#endif
7498+
74957499
SendInitWorldStates(newZone); // only if really enters to new zone, not just area change, works strange...
74967500

74977501
if (sWorld.getConfig(CONFIG_BOOL_WEATHER))

src/modules/Bots/playerbot/PlayerbotAI.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -305,6 +305,13 @@ void PlayerbotAI::UpdateAI(uint32 elapsed)
305305
return;
306306
}
307307

308+
if (sPlayerbotAIConfig.randomBotActiveZoneOnly && !bot->GetGroup() && sRandomPlayerbotMgr.IsRandomBot(bot) &&
309+
!sRandomPlayerbotMgr.HasRealPlayerInZone(bot->GetZoneId()))
310+
{
311+
SetNextCheckDelay(5000);
312+
return;
313+
}
314+
308315
if (nextAICheckDelay > sPlayerbotAIConfig.globalCoolDown &&
309316
bot->IsNonMeleeSpellCasted(true, true, false) &&
310317
*GetAiObjectContext()->GetValue<bool>("invalid target", "current target"))

src/modules/Bots/playerbot/PlayerbotAIConfig.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ PlayerbotAIConfig::PlayerbotAIConfig()
6464
randomBotJoinLfg(false),
6565
randomBotLoginAtStartup(false),
6666
randomBotKeepGroups(false),
67+
randomBotActiveZoneOnly(false),
6768
randomBotTeleLevel(0),
6869
logInGroupOnly(false),
6970
logValuesPerTick(false),
@@ -190,6 +191,7 @@ bool PlayerbotAIConfig::Initialize()
190191
randomBotMaxLevel = config.GetIntDefault("AiPlayerbot.RandomBotMaxLevel", 255);
191192
randomBotLoginAtStartup = config.GetBoolDefault("AiPlayerbot.RandomBotLoginAtStartup", true);
192193
randomBotKeepGroups = config.GetBoolDefault("AiPlayerbot.RandomBotKeepGroups", false);
194+
randomBotActiveZoneOnly = config.GetBoolDefault("AiPlayerbot.RandomBotActiveZoneOnly", false);
193195
randomBotTeleLevel = config.GetIntDefault("AiPlayerbot.RandomBotTeleLevel", 3);
194196

195197
randomChangeMultiplier = config.GetFloatDefault("AiPlayerbot.RandomChangeMultiplier", 1.0);

src/modules/Bots/playerbot/PlayerbotAIConfig.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,7 @@ class PlayerbotAIConfig
6969
bool randomBotJoinLfg; ///< Indicates if random bots should join Looking For Group.
7070
bool randomBotLoginAtStartup; ///< Indicates if random bots should login at startup.
7171
bool randomBotKeepGroups; ///< Indicates if random bots should preserve groups across restarts.
72+
bool randomBotActiveZoneOnly; ///< If true, ungrouped random bots only tick when a real player is in their zone.
7273
uint32 randomBotTeleLevel; ///< The teleport level for random bots.
7374
bool logInGroupOnly, logValuesPerTick;
7475
bool fleeingEnabled; ///< Indicates if fleeing is enabled for bots.

src/modules/Bots/playerbot/RandomPlayerbotMgr.cpp

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1004,6 +1004,16 @@ void RandomPlayerbotMgr::OnPlayerLogout(Player* player)
10041004
{
10051005
players.erase(i);
10061006
}
1007+
1008+
uint32 zone = player->GetZoneId();
1009+
std::unordered_map<uint32, uint32>::iterator zi = m_playerZoneCounts.find(zone);
1010+
if (zi != m_playerZoneCounts.end())
1011+
{
1012+
if (zi->second <= 1)
1013+
m_playerZoneCounts.erase(zi);
1014+
else
1015+
zi->second--;
1016+
}
10071017
}
10081018
}
10091019

@@ -1042,7 +1052,35 @@ void RandomPlayerbotMgr::OnPlayerLogin(Player* player)
10421052
{
10431053
players.push_back(player);
10441054
sLog.outDebug("Including non-random bot player %s into random bot update", player->GetName());
1055+
m_playerZoneCounts[player->GetZoneId()]++;
1056+
}
1057+
}
1058+
1059+
void RandomPlayerbotMgr::OnPlayerZoneChange(Player* player, uint32 newZone)
1060+
{
1061+
if (player->GetPlayerbotAI())
1062+
return;
1063+
1064+
uint32 oldZone = player->GetCachedZoneId();
1065+
if (oldZone == newZone)
1066+
return;
1067+
1068+
std::unordered_map<uint32, uint32>::iterator zi = m_playerZoneCounts.find(oldZone);
1069+
if (zi != m_playerZoneCounts.end())
1070+
{
1071+
if (zi->second <= 1)
1072+
m_playerZoneCounts.erase(zi);
1073+
else
1074+
zi->second--;
10451075
}
1076+
1077+
m_playerZoneCounts[newZone]++;
1078+
}
1079+
1080+
bool RandomPlayerbotMgr::HasRealPlayerInZone(uint32 zoneId) const
1081+
{
1082+
std::unordered_map<uint32, uint32>::const_iterator zi = m_playerZoneCounts.find(zoneId);
1083+
return zi != m_playerZoneCounts.end() && zi->second > 0;
10461084
}
10471085

10481086
Player* RandomPlayerbotMgr::GetRandomPlayer()

src/modules/Bots/playerbot/RandomPlayerbotMgr.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
#include "PlayerbotAIBase.h"
66
#include "PlayerbotMgr.h"
77
#include <set>
8+
#include <unordered_map>
89

910
class WorldPacket;
1011
class Player;
@@ -99,6 +100,9 @@ class RandomPlayerbotMgr : public PlayerbotHolder
99100
*/
100101
void OnPlayerLogin(Player* player);
101102

103+
void OnPlayerZoneChange(Player* player, uint32 newZone);
104+
bool HasRealPlayerInZone(uint32 zoneId) const;
105+
102106
/**
103107
* @brief Gets a random player.
104108
* @return Pointer to the random player.
@@ -235,6 +239,7 @@ class RandomPlayerbotMgr : public PlayerbotHolder
235239
set<uint32> m_groupedBots; ///< Cached set of bot GUIDs currently in a group, refreshed each update cycle.
236240
std::map<uint32, AreaCreatureStats> m_areaCreatureStatsMap;
237241
std::map<std::pair<uint32, uint32>, uint32> m_cellToAreaCache;
242+
std::unordered_map<uint32, uint32> m_playerZoneCounts; ///< zone_id -> real player count, for O(1) bot tick gating.
238243
};
239244

240245
#define sRandomPlayerbotMgr MaNGOS::Singleton<RandomPlayerbotMgr>::Instance()

src/modules/Bots/playerbot/aiplayerbot.conf.dist.in

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -164,6 +164,10 @@ AiPlayerbot.RandomBotTeleLevel = 3
164164
# Preserve bot group assignments across server restarts
165165
#AiPlayerbot.RandomBotKeepGroups = 0
166166

167+
# Only tick ungrouped random bots when a real player is in their zone.
168+
# Reduces CPU load on empty zones at the cost of bots being frozen there.
169+
#AiPlayerbot.RandomBotActiveZoneOnly = 0
170+
167171
# How far random bots are teleported after death
168172
#AiPlayerbot.RandomBotTeleportDistance = 1000
169173

0 commit comments

Comments
 (0)