Move GatherSpellTargets and Raid to stored variables.

Missing some in "organize some checks in IsImmuneToBotSpell"
This commit is contained in:
nytmyr
2024-12-22 00:29:15 -06:00
parent 0c0fee1c67
commit f6fa28681b
4 changed files with 91 additions and 36 deletions
+47 -25
View File
@@ -109,6 +109,9 @@ Bot::Bot(NPCType *npcTypeData, Client* botOwner) : NPC(npcTypeData, nullptr, glm
GenerateBaseStats();
bot_timers.clear();
bot_blocked_buffs.clear();
_spellTargetList.clear();
_groupSpellTargetList.clear();
_storedRaid = nullptr;
// Calculate HitPoints Last As It Uses Base Stats
current_hp = GenerateBaseHitPoints();
@@ -258,6 +261,9 @@ Bot::Bot(
database.botdb.LoadBotBlockedBuffs(this);
}
_spellTargetList.clear();
_groupSpellTargetList.clear();
_storedRaid = nullptr;
LoadAAs();
if (database.botdb.LoadBuffs(this)) {
@@ -2095,7 +2101,7 @@ void Bot::AI_Process()
else {
follow_mob = entity_list.GetMob(GetFollowID());
if (!follow_mob || !IsInGroupOrRaid(follow_mob, raid)) {
if (!follow_mob || !IsInGroupOrRaid(follow_mob)) {
follow_mob = leash_owner;
}
}
@@ -2126,6 +2132,12 @@ void Bot::AI_Process()
return;
}
SetStoredRaid(raid);
std::vector<Mob*> spellTargetList = GatherSpellTargets(RuleB(Bots, CrossRaidBuffingAndHealing));
SetSpellTargetList(spellTargetList);
std::vector<Mob*> groupSpellTargetList = GatherSpellTargets();
SetGroupSpellTargetList(groupSpellTargetList);
// HEAL ROTATION CASTING CHECKS
HealRotationChecks();
@@ -2369,7 +2381,7 @@ void Bot::AI_Process()
// AUTO DEFEND
if (TryAutoDefend(bot_owner, leash_distance, raid) ) {
if (TryAutoDefend(bot_owner, leash_distance) ) {
return;
}
@@ -2468,7 +2480,7 @@ bool Bot::TryIdleChecks(float fm_distance) {
// This is as close as I could get without modifying the aggro mechanics and making it an expensive process...
// 'class Client' doesn't make use of hate_list
bool Bot::TryAutoDefend(Client* bot_owner, float leash_distance, Raid* raid) {
bool Bot::TryAutoDefend(Client* bot_owner, float leash_distance) {
if (RuleB(Bots, AllowOwnerOptionAutoDefend) && bot_owner->GetBotOption(Client::booAutoDefend)) {
@@ -2505,6 +2517,7 @@ bool Bot::TryAutoDefend(Client* bot_owner, float leash_distance, Raid* raid) {
bool assisteeFound = false;
if (IsRaidGrouped()) {
Raid* raid = GetStoredRaid();
if (raid) {
for (const auto& m : raid->members) {
if (
@@ -2555,7 +2568,7 @@ bool Bot::TryAutoDefend(Client* bot_owner, float leash_distance, Raid* raid) {
if (bot_owner->GetAssistee()) {
Client* c = entity_list.GetClientByCharID(bot_owner->GetAssistee());
if (bot_owner->IsInGroupOrRaid(c, raid) && c->GetAggroCount()) {
if (bot_owner->IsInGroupOrRaid(c) && c->GetAggroCount()) {
tempHaters = bot_owner->GetXTargetAutoMgr();
if (tempHaters && !tempHaters->empty()) {
@@ -5976,7 +5989,7 @@ bool Bot::DoFinishedSpellSingleTarget(uint16 spell_id, Mob* spellTarget, EQ::spe
if (
spellTarget &&
GetClass() != Class::Bard &&
(IsGrouped() || (IsRaidGrouped() && GetRaid()->GetGroup(GetCleanName()) != RAID_GROUPLESS)) &&
(IsGrouped() || (IsRaidGrouped() && GetStoredRaid()->GetGroup(GetCleanName()) != RAID_GROUPLESS)) &&
(spellTarget->IsBot() || spellTarget->IsClient()) &&
(RuleB(Bots, GroupBuffing) || RuleB(Bots, RaidBuffing))
) {
@@ -6008,7 +6021,12 @@ bool Bot::DoFinishedSpellSingleTarget(uint16 spell_id, Mob* spellTarget, EQ::spe
if (!noGroupSpell) {
std::vector<Mob*> v;
v = GatherSpellTargets(RuleB(Bots, RaidBuffing));
if (RuleB(Bots, RaidBuffing)) {
v = GetSpellTargetList();
}
else {
v = GatherSpellTargets(false, spellTarget);
}
for (Mob* m : v) {
if (IsEffectInSpell(thespell, SE_AbsorbMagicAtt) || IsEffectInSpell(thespell, SE_Rune)) {
@@ -6043,7 +6061,7 @@ bool Bot::DoFinishedSpellSingleTarget(uint16 spell_id, Mob* spellTarget, EQ::spe
bool Bot::DoFinishedSpellGroupTarget(uint16 spell_id, Mob* spellTarget, EQ::spells::CastingSlot slot, bool& stopLogic) {
bool isMainGroupMGB = false;
Raid* raid = entity_list.GetRaidByBot(this);
Raid* raid = GetStoredRaid();
if (isMainGroupMGB && (GetClass() != Class::Bard)) {
BotGroupSay(
@@ -6065,7 +6083,7 @@ bool Bot::DoFinishedSpellGroupTarget(uint16 spell_id, Mob* spellTarget, EQ::spel
std::vector<Mob*> v;
if (RuleB(Bots, RaidBuffing)) {
v = GatherSpellTargets(true);
v = GetSpellTargetList();
}
else {
v = GatherSpellTargets(false, spellTarget);
@@ -7206,11 +7224,11 @@ bool Bot::CheckLoreConflict(const EQ::ItemData* item) {
return (m_inv.HasItemByLoreGroup(item->LoreGroup, invWhereWorn) != INVALID_INDEX);
}
bool Bot::AttemptCloseBeneficialSpells(uint16 spellType, Raid* raid, std::vector<Mob*> targetList) {
bool Bot::AttemptCloseBeneficialSpells(uint16 spellType) {
bool result = false;
Mob* tar = nullptr;
for (Mob* m : targetList) {
for (Mob* m : GetSpellTargetList()) {
tar = m;
if (!tar) {
@@ -7218,12 +7236,13 @@ bool Bot::AttemptCloseBeneficialSpells(uint16 spellType, Raid* raid, std::vector
}
if (IsGroupTargetOnlyBotSpellType(spellType)) {
Raid* raid = GetStoredRaid();
if (raid && (raid->GetGroup(GetName()) == raid->GetGroup(tar->GetName()))) {
continue;
}
}
result = AttemptAICastSpell(spellType, tar, raid);
result = AttemptAICastSpell(spellType, tar);
if (!result) {
if (tar->HasPet() && (!m->GetPet()->IsFamiliar() || RuleB(Bots, AllowBuffingHealingFamiliars))) {
@@ -7237,7 +7256,7 @@ bool Bot::AttemptCloseBeneficialSpells(uint16 spellType, Raid* raid, std::vector
continue;
}
result = AttemptAICastSpell(spellType, tar, raid);
result = AttemptAICastSpell(spellType, tar);
}
}
@@ -7752,7 +7771,7 @@ void Bot::BotGroupSay(Mob* speaker, const char* msg, ...) {
va_end(ap);
if (speaker->IsRaidGrouped()) {
Raid* r = entity_list.GetRaidByBot(speaker->CastToBot());
Raid* r = speaker->CastToBot()->GetStoredRaid();
if (r) {
for (const auto& m : r->members) {
if (m.member && !m.is_bot) {
@@ -9699,16 +9718,21 @@ bool Bot::BotHasEnoughMana(uint16 spell_id) {
return true;
}
bool Bot::IsTargetAlreadyReceivingSpell(Mob* tar, uint16 spell_id) {
bool Bot::IsTargetAlreadyReceivingSpell(Mob* tar, uint16 spell_id) { //TODO bot rewrite - add raid and spell targets
if (!tar || !spell_id) {
return true;
}
std::vector<Mob*> v;
uint16 targetID = tar->GetID();
v = GatherSpellTargets(RuleB(Bots, CrossRaidBuffingAndHealing));
if (RuleB(Bots, CrossRaidBuffingAndHealing)) {
v = GetSpellTargetList();
}
else {
v = GetGroupSpellTargetList();
}
for (Mob* m : v) {
if (
m->IsBot() &&
@@ -9716,7 +9740,7 @@ bool Bot::IsTargetAlreadyReceivingSpell(Mob* tar, uint16 spell_id) {
m->CastToBot()->casting_spell_targetid &&
m->CastingSpellID() == spell_id
) {
if (IsGroupSpell(spell_id)) {
if (RuleB(Bots, CrossRaidBuffingAndHealing) && IsGroupSpell(spell_id)) {
std::vector<Mob*> t = GatherSpellTargets(false, tar);
for (Mob* x : t) {
@@ -9849,9 +9873,7 @@ bool Bot::IsMobEngagedByAnyone(Mob* tar) {
return false;
}
const std::vector<Mob*> v = GatherSpellTargets(true);
for (Mob* m : v) {
for (Mob* m : GetSpellTargetList()) {
if (m->GetTarget() == tar) {
if (
m->IsBot() &&
@@ -10763,7 +10785,7 @@ std::list<BotSpellTypeOrder> Bot::GetSpellTypesPrioritized(uint8 priorityType) {
return castOrder;
}
bool Bot::AttemptAICastSpell(uint16 spellType, Mob* tar, Raid* raid) {
bool Bot::AttemptAICastSpell(uint16 spellType, Mob* tar) {
bool result = false;
if (!tar) {
@@ -10787,12 +10809,12 @@ bool Bot::AttemptAICastSpell(uint16 spellType, Mob* tar, Raid* raid) {
tar = this;
}
if (!PrecastChecks(tar, spellType) || !AICastSpell(tar, GetChanceToCastBySpellType(spellType), spellType, raid)) {
if (!PrecastChecks(tar, spellType) || !AICastSpell(tar, GetChanceToCastBySpellType(spellType), spellType)) {
return result;
}
}
else {
if (!PrecastChecks(tar, spellType) || !AICastSpell(tar, GetChanceToCastBySpellType(spellType), spellType, raid)) {
if (!PrecastChecks(tar, spellType) || !AICastSpell(tar, GetChanceToCastBySpellType(spellType), spellType)) {
return result;
}
}
@@ -10948,7 +10970,7 @@ bool Bot::AttemptForcedCastSpell(Mob* tar, uint16 spell_id) {
!RuleB(Bots, EnableBotTGB) &&
IsGroupSpell(forcedSpellID) &&
!IsTGBCompatibleSpell(forcedSpellID) &&
!IsInGroupOrRaid(tar, nullptr, true)
!IsInGroupOrRaid(tar, true)
) {
LogTestDebug("{} failed TGB for {} [#{}].", GetCleanName(), spell.name, forcedSpellID); //deleteme
return false;
+16 -6
View File
@@ -397,11 +397,11 @@ public:
void AI_Bot_Event_SpellCastFinished(bool iCastSucceeded, uint16 slot);
// AI Methods
bool AICastSpell(Mob* tar, uint8 iChance, uint16 spellType, Raid* raid = nullptr, uint16 subTargetType = UINT16_MAX, uint16 subType = UINT16_MAX);
bool AttemptAICastSpell(uint16 spellType, Mob* tar = nullptr, Raid* raid = nullptr);
bool AICastSpell(Mob* tar, uint8 iChance, uint16 spellType, uint16 subTargetType = UINT16_MAX, uint16 subType = UINT16_MAX);
bool AttemptAICastSpell(uint16 spellType, Mob* tar = nullptr);
bool AttemptAACastSpell(Mob* tar, uint16 spell_id, AA::Rank* rank);
bool AttemptForcedCastSpell(Mob* tar, uint16 spell_id);
bool AttemptCloseBeneficialSpells(uint16 spellType, Raid* raid, std::vector<Mob*> targetList);
bool AttemptCloseBeneficialSpells(uint16 spellType);
bool AI_EngagedCastCheck() override;
bool AI_PursueCastCheck() override;
bool AI_IdleCastCheck() override;
@@ -460,6 +460,12 @@ public:
bool CastChecks(uint16 spell_id, Mob* tar, uint16 spellType, bool doPrechecks = false, bool AECheck = false);
bool CanCastSpellType(uint16 spellType, uint16 spell_id, Mob* tar);
bool BotHasEnoughMana(uint16 spell_id);
std::vector<Mob*> GetSpellTargetList() { return _spellTargetList; }
void SetSpellTargetList(std::vector<Mob*> spellTargetList) { _spellTargetList = spellTargetList; }
std::vector<Mob*> GetGroupSpellTargetList() { return _groupSpellTargetList; }
void SetGroupSpellTargetList(std::vector<Mob*> spellTargetList) { _groupSpellTargetList = spellTargetList; }
Raid* GetStoredRaid() { return _storedRaid; }
void SetStoredRaid(Raid* storedRaid) { _storedRaid = storedRaid; }
bool IsTargetAlreadyReceivingSpell(Mob* tar, uint16 spell_id);
bool DoResistCheck(Mob* target, uint16 spell_id, int32 resist_limit);
bool DoResistCheckBySpellType(Mob* tar, uint16 spell_id, uint16 spellType);
@@ -476,7 +482,6 @@ public:
void SetBotBaseSetting(uint16 botSetting, int settingValue);
void LoadDefaultBotSettings();
void SetBotSpellRecastTimer(uint16 spellType, Mob* spelltar, bool preCast = false);
BotSpell GetSpellByHealType(uint16 spellType, Mob* tar);
uint16 GetSpellByAA(int id, AA::Rank* &rank);
void CleanBotBlockedBuffs();
void ClearBotBlockedBuffs() { bot_blocked_buffs.clear(); }
@@ -598,6 +603,7 @@ public:
static std::vector<BotSpell_wPriority> GetPrioritizedBotSpellsBySpellType(Bot* botCaster, uint16 spellType, Mob* tar, bool AE = false, uint16 subTargetType = UINT16_MAX, uint16 subType = UINT16_MAX);
static BotSpell GetFirstBotSpellBySpellType(Bot* botCaster, uint16 spellType);
BotSpell GetSpellByHealType(uint16 spellType, Mob* tar);
static BotSpell GetBestBotSpellForVeryFastHeal(Bot* botCaster, Mob* tar, uint16 spellType = BotSpellTypes::RegularHeal);
static BotSpell GetBestBotSpellForFastHeal(Bot* botCaster, Mob* tar, uint16 spellType = BotSpellTypes::RegularHeal);
static BotSpell GetBestBotSpellForHealOverTime(Bot* botCaster, Mob* tar, uint16 spellType = BotSpellTypes::RegularHeal);
@@ -608,7 +614,7 @@ public:
static BotSpell GetBestBotSpellForGroupCompleteHeal(Bot* botCaster, Mob* tar, uint16 spellType = BotSpellTypes::RegularHeal);
static BotSpell GetBestBotSpellForGroupHeal(Bot* botCaster, Mob* tar, uint16 spellType = BotSpellTypes::RegularHeal);
static Mob* GetFirstIncomingMobToMez(Bot* botCaster, int16 spell_id, uint16 spellType, bool AE = false);
static Mob* GetFirstIncomingMobToMez(Bot* botCaster, int16 spell_id, uint16 spellType, bool AE);
bool IsValidMezTarget(Mob* owner, Mob* npc, uint16 spell_id);
static BotSpell GetBestBotSpellForMez(Bot* botCaster, uint16 spellType = BotSpellTypes::Mez);
static BotSpell GetBestBotMagicianPetSpell(Bot* botCaster, uint16 spellType = BotSpellTypes::Pet);
@@ -988,7 +994,7 @@ public:
bool TryFacingTarget(Mob* tar);
bool TryPursueTarget(float leash_distance, glm::vec3& Goal);
bool TryMeditate();
bool TryAutoDefend(Client* bot_owner, float leash_distance, Raid* raid = nullptr);
bool TryAutoDefend(Client* bot_owner, float leash_distance);
bool TryIdleChecks(float fm_distance);
bool TryNonCombatMovementChecks(Client* bot_owner, const Mob* follow_mob, glm::vec3& Goal);
bool TryBardMovementCasts();
@@ -1093,6 +1099,10 @@ private:
bool _commandedSpell;
bool _pullingSpell;
std::vector<Mob*> _spellTargetList; // TODO bot rewrite - implement this and raid
std::vector<Mob*> _groupSpellTargetList;
Raid* _storedRaid;
// Private "base stats" Members
int32 _baseMR;
int32 _baseCR;
+1 -1
View File
@@ -588,7 +588,7 @@ void bot_command_cast(Client* c, const Seperator* sep)
LogTestDebug("{}: {} says, 'Attempting {} [{}-{}] on [{}]'", __LINE__, bot_iter->GetCleanName(), c->GetSpellTypeNameByID(spellType), (subType != UINT16_MAX ? c->GetSubTypeNameByID(subType) : "Standard"), (subTargetType != UINT16_MAX ? c->GetSubTypeNameByID(subTargetType) : "Standard"), (newTar ? newTar->GetCleanName() : "NOBODY")); //deleteme
bot_iter->SetCommandedSpell(true);
if (bot_iter->AICastSpell(newTar, 100, spellType, nullptr, subTargetType, subType)) {
if (bot_iter->AICastSpell(newTar, 100, spellType, subTargetType, subType)) {
if (!firstFound) {
firstFound = bot_iter;
}
+27 -4
View File
@@ -9954,7 +9954,7 @@ void Mob::ClearDataBucketCache()
}
}
bool Mob::IsInGroupOrRaid(Mob *other, Raid* raid, bool sameRaidGroup) {
bool Mob::IsInGroupOrRaid(Mob *other, bool sameRaidGroup) {
if (!other || !IsOfClientBotMerc() || !other->IsOfClientBotMerc()) {
return false;
}
@@ -9963,9 +9963,18 @@ bool Mob::IsInGroupOrRaid(Mob *other, Raid* raid, bool sameRaidGroup) {
return true;
}
if (IsRaidGrouped() && !raid) {
raid = GetRaid();
Raid* raid = nullptr;
if (IsBot) {
CastToBot()->GetStoredRaid();
}
else {
if (IsRaidGrouped()) {
raid = GetRaid();
}
}
if (IsRaidGrouped()) {
if (!raid) {
return false;
}
@@ -9975,8 +9984,22 @@ bool Mob::IsInGroupOrRaid(Mob *other, Raid* raid, bool sameRaidGroup) {
if (!other->IsRaidGrouped()) {
return false;
}
Raid* otherRaid = nullptr;
if (other->IsBot()) {
otherRaid = other->CastToBot()->GetStoredRaid();
}
else {
otherRaid = other->GetRaid();
}
if (!otherRaid) {
return false;
}
auto rGroup = raid->GetGroup(GetCleanName());
auto rOGroup = raid->GetGroup(other->GetCleanName());
auto rOGroup = otherRaid->GetGroup(other->GetCleanName());
if (rGroup == RAID_GROUPLESS || rOGroup == RAID_GROUPLESS || (sameRaidGroup && rGroup != rOGroup)) {
return false;