Loot filter on the options window's Beute page
Per category (Gold, Tränke, white/blue/yellow/brown/green items) one of Löschen (loot deleted at once), Ignorieren (pickup key leaves it), Standard, Immer anzeigen (label without the labels key). Replaces the game's PICKUPAUTO choice; settings in [loot] of sacredK.ini. docs/loot-filter.md. Also ignore MSYS *.stackdump files. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
This commit is contained in:
1 parent
ce3d46a568
commit
198c21dbfa
12 files changed
+709
-25
No files matched your search
@@ -60,6 +60,61 @@ inline uint32_t ItemType(const void* item) {
|
||||
return *reinterpret_cast<const uint32_t*>(static_cast<const uint8_t*>(item) + kItemType);
|
||||
}
|
||||
|
||||
// 0x43ae20 (thiscall on the type table, (type), ret 4): the type is a gold
|
||||
// pile (one of the four types at 0x947920; labels show its amount, the loot
|
||||
// drop sets it, the collect mode takes it without inventory space).
|
||||
inline bool ItemIsGold(uint32_t type) {
|
||||
using Fn = bool(__fastcall*)(void* table, void* edx, uint32_t type);
|
||||
void* table = *reinterpret_cast<void**>(kItemTypeTable);
|
||||
return table && reinterpret_cast<Fn>(0x0043ae20)(table, nullptr, type);
|
||||
}
|
||||
|
||||
// 0x433f00 (thiscall on the type table, (type), ret 4): the type's group
|
||||
// record (0x102 bytes), null if none. +0x23 set: a set item (the item colour
|
||||
// 0x5c1330 shows it green).
|
||||
inline bool ItemIsSetItem(uint32_t type) {
|
||||
using Fn = const uint8_t*(__fastcall*)(void* table, void* edx, uint32_t type);
|
||||
void* table = *reinterpret_cast<void**>(kItemTypeTable);
|
||||
const uint8_t* group = table ? reinterpret_cast<Fn>(0x00433f00)(table, nullptr, type) : nullptr;
|
||||
return group && group[0x23] != 0;
|
||||
}
|
||||
|
||||
// 0x428550 (thiscall on the type table, (type), ret 4): cCreature::
|
||||
// CanCollectItem takes items of such types whatever the pickup setting (type
|
||||
// flag 0x1000000 with +0x61 / +0x62 / +0x1c set; quest items, presumably).
|
||||
inline bool ItemAlwaysCollected(uint32_t type) {
|
||||
using Fn = bool(__fastcall*)(void* table, void* edx, uint32_t type);
|
||||
void* table = *reinterpret_cast<void**>(kItemTypeTable);
|
||||
return table && reinterpret_cast<Fn>(0x00428550)(table, nullptr, type);
|
||||
}
|
||||
|
||||
// The item's quality block (+0x118, cArmor3D::vf24 case 2 hands it to the
|
||||
// item colour 0x5c1330): flags at +4, bits 16..19 the quality tier. With the
|
||||
// game's UNIQUE_COLOR option (on by default) the colour follows the tier:
|
||||
// up to 4 white, 5..11 blue, 12..14 yellow, 15 brown; set items green.
|
||||
constexpr size_t kItemQualityFlags = 0x118 + 4;
|
||||
inline unsigned ItemQualityTier(const void* item) {
|
||||
const uint32_t flags =
|
||||
*reinterpret_cast<const uint32_t*>(static_cast<const uint8_t*>(item) + kItemQualityFlags);
|
||||
return (flags >> 16) & 0xf;
|
||||
}
|
||||
constexpr unsigned kTierBlue = 5;
|
||||
constexpr unsigned kTierYellow = 12;
|
||||
constexpr unsigned kTierBrown = 15;
|
||||
|
||||
// The item colours of 0x5c1330 (ARGB).
|
||||
constexpr uint32_t kItemColourWhite = 0xffefefef;
|
||||
constexpr uint32_t kItemColourBlue = 0xffa0a0ff;
|
||||
constexpr uint32_t kItemColourYellow = 0xfff0e040;
|
||||
constexpr uint32_t kItemColourBrown = 0xffc19a33;
|
||||
constexpr uint32_t kItemColourGreen = 0xff15ff25;
|
||||
|
||||
// The item colour the game shows (vf24(2, 0): 0x5c1330).
|
||||
inline uint32_t ItemColour(void* item) {
|
||||
using Fn = uint32_t(__fastcall*)(void*, void*, int, int);
|
||||
return reinterpret_cast<Fn>((*static_cast<void***>(item))[0x24 / 4])(item, nullptr, 2, 0);
|
||||
}
|
||||
|
||||
// The potion kind of object `id`, 0 if it is no potion (or gone).
|
||||
inline int PotionKindOf(uint32_t id) {
|
||||
const void* item = id ? GetObjectById(id) : nullptr;
|
||||
|
||||
@@ -16,6 +16,10 @@ inline bool IsPlayerHeroId(uint32_t id) {
|
||||
// manager (saving marks effect objects dead, cObjectManager::Place refuses them).
|
||||
constexpr size_t kObjectFlags = 0x14;
|
||||
constexpr uint32_t kObjectDead = 0x10;
|
||||
// Set while an item is carried (in an inventory), not on the map:
|
||||
// cCreature::CanCollectItem refuses it, cEngine::dropItem (0x6116c0) only
|
||||
// takes it off the map without it.
|
||||
constexpr uint32_t kObjectCarried = 0x2;
|
||||
|
||||
// The creatures near the player (g_nearbyCreatures 0xad1c60: {object id, ?}
|
||||
// x g_nearbyCreatureCount 0xad1b48), as the game uses them for aura targets.
|
||||
@@ -31,6 +35,7 @@ constexpr uint32_t kTypeObject = 0x008e9648;
|
||||
constexpr uint32_t kTypeCreature = 0x008e9660;
|
||||
constexpr uint32_t kTypeControl = 0x009de168;
|
||||
constexpr uint32_t kTypeEditControl = 0x009e3608;
|
||||
constexpr uint32_t kTypeItemBase = 0x0094cbc0;
|
||||
|
||||
// __RTDynamicCast (0x849701).
|
||||
inline void* DynamicCast(void* object, uint32_t sourceType, uint32_t targetType) {
|
||||
@@ -51,11 +56,22 @@ inline void* GetObjectById(uint32_t id) {
|
||||
}
|
||||
|
||||
// cObjectManager::DestroyObject (0x5fbe10), with the arguments cCreature::UseItem
|
||||
// destroys a drunk potion with (id, 1, 0, 0).
|
||||
inline void DestroyObject(uint32_t id) {
|
||||
// destroys a drunk potion with (id, 1, 0, 0); the loot drop (0x559a30) an
|
||||
// item it replaces with (id, 0, 0, 0), after RemoveFromMap.
|
||||
inline void DestroyObject(uint32_t id, uint32_t a = 1) {
|
||||
using Fn = uint32_t(__fastcall*)(void* manager, void* edx, uint32_t, uint32_t, uint32_t, uint32_t);
|
||||
if (void* manager = ObjectManager()) {
|
||||
reinterpret_cast<Fn>(0x005fbe10)(manager, nullptr, id, 1, 0, 0);
|
||||
reinterpret_cast<Fn>(0x005fbe10)(manager, nullptr, id, a, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
// cObjectManager 0x5fc910 (thiscall (id), ret 4): takes object `id` off the
|
||||
// map. The loot drop (0x559a30) replaces an item it made with this and
|
||||
// DestroyObject.
|
||||
inline void RemoveFromMap(uint32_t id) {
|
||||
using Fn = void(__fastcall*)(void* manager, void* edx, uint32_t);
|
||||
if (void* manager = ObjectManager()) {
|
||||
reinterpret_cast<Fn>(0x005fc910)(manager, nullptr, id);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in new issue
Block a user