Files
mod-playerbots/src/LootObjectStack.h
Type1Error 97f582b9b1 Fix bot chest looting exploits in ICC and Halls of Stone (#1280)
- Prevent bots from looting Gunship Armory chest in ICC before the event ends (#1162)
- Fix bots being able to loot Tribunal Cache in Halls of Stone multiple times (#1200)
- Ensure bots do not attempt to loot Deathbringer's Cache in ICC before it is available

Three chests (Gunship Armory, Tribunal Cache, Deathbringer's Cache) were tested and now behave as expected: bots will not approach or attempt to loot chests while they are unlootable, even if players move close to them.

Closes #1162, #1200
2025-05-10 13:45:58 +02:00

88 lines
1.9 KiB
C++

/*
* Copyright (C) 2016+ AzerothCore <www.azerothcore.org>, released under GNU GPL v2 license, you may redistribute it
* and/or modify it under version 2 of the License, or (at your option), any later version.
*/
#ifndef _PLAYERBOT_LOOTOBJECTSTACK_H
#define _PLAYERBOT_LOOTOBJECTSTACK_H
#include "ObjectGuid.h"
class AiObjectContext;
class Player;
class WorldObject;
struct ItemTemplate;
class LootStrategy
{
public:
LootStrategy() {}
virtual ~LootStrategy(){};
virtual bool CanLoot(ItemTemplate const* proto, AiObjectContext* context) = 0;
virtual std::string const GetName() = 0;
};
class LootObject
{
public:
LootObject() : skillId(0), reqSkillValue(0), reqItem(0) {}
LootObject(Player* bot, ObjectGuid guid);
LootObject(LootObject const& other);
LootObject& operator=(LootObject const& other) = default;
bool IsEmpty() { return !guid; }
bool IsLootPossible(Player* bot);
void Refresh(Player* bot, ObjectGuid guid);
WorldObject* GetWorldObject(Player* bot);
ObjectGuid guid;
uint32 skillId;
uint32 reqSkillValue;
uint32 reqItem;
private:
static bool IsNeededForQuest(Player* bot, uint32 itemId);
};
class LootTarget
{
public:
LootTarget(ObjectGuid guid);
LootTarget(LootTarget const& other);
public:
LootTarget& operator=(LootTarget const& other);
bool operator<(LootTarget const& other) const;
public:
ObjectGuid guid;
time_t asOfTime;
};
class LootTargetList : public std::set<LootTarget>
{
public:
void shrink(time_t fromTime);
};
class LootObjectStack
{
public:
LootObjectStack(Player* bot) : bot(bot) {}
bool Add(ObjectGuid guid);
void Remove(ObjectGuid guid);
void Clear();
bool CanLoot(float maxDistance);
LootObject GetLoot(float maxDistance = 0);
private:
std::vector<LootObject> OrderByDistance(float maxDistance = 0);
Player* bot;
LootTargetList availableLoot;
};
#endif