diff --git a/src/araxiaonline/mcp/SpawnTools.cpp b/src/araxiaonline/mcp/SpawnTools.cpp index 1b37269c90..4ce856d3e7 100644 --- a/src/araxiaonline/mcp/SpawnTools.cpp +++ b/src/araxiaonline/mcp/SpawnTools.cpp @@ -25,7 +25,11 @@ #include "DatabaseEnv.h" #include "GameTime.h" #include "DB2Stores.h" +#include "AuctionHouseBot.h" +#include "AuctionHouseMgr.h" +#include "Item.h" #include +#include namespace Araxia { @@ -440,6 +444,168 @@ void RegisterSpawnTools() }; } } + // AHBot commands - useful for managing auction house bot without a player + // These mirror the .ahbot GM commands but work from MCP console + else if (cmd == "ahbot") + { + std::string subcmd; + iss >> subcmd; + + if (subcmd == "status") + { + // Get AHBot status info + std::unordered_map statusInfo; + sAuctionBot->PrepareStatusInfos(statusInfo); + + return { + {"success", true}, + {"command", "ahbot status"}, + {"alliance", { + {"itemCount", statusInfo[AUCTION_HOUSE_ALLIANCE].ItemsCount} + }}, + {"horde", { + {"itemCount", statusInfo[AUCTION_HOUSE_HORDE].ItemsCount} + }}, + {"neutral", { + {"itemCount", statusInfo[AUCTION_HOUSE_NEUTRAL].ItemsCount} + }}, + {"total", statusInfo[AUCTION_HOUSE_ALLIANCE].ItemsCount + + statusInfo[AUCTION_HOUSE_HORDE].ItemsCount + + statusInfo[AUCTION_HOUSE_NEUTRAL].ItemsCount} + }; + } + else if (subcmd == "rebuild") + { + std::string arg; + iss >> arg; + bool all = (arg == "all"); + + sAuctionBot->Rebuild(all); + + return { + {"success", true}, + {"command", "ahbot rebuild"}, + {"all", all}, + {"message", all ? "Rebuilding all auction house items" : "Rebuilding auction house items"} + }; + } + else if (subcmd == "reload") + { + sAuctionBot->ReloadAllConfig(); + return { + {"success", true}, + {"command", "ahbot reload"}, + {"message", "AHBot configuration reloaded"} + }; + } + else if (subcmd == "stats") + { + // Item level statistics - mirrors the new .ahbot stats command + std::string arg; + iss >> arg; + bool equipmentOnly = (arg == "equipment"); + + std::map itemLevelBuckets; + uint32 totalItems = 0; + uint32 equipmentItems = 0; + uint32 minItemLevel = UINT32_MAX; + uint32 maxItemLevel = 0; + uint64 totalItemLevel = 0; + + std::vector auctionHouseIds = { 1, 2, 6, 7 }; + + for (uint32 ahId : auctionHouseIds) + { + AuctionHouseObject* auctionHouse = sAuctionMgr->GetAuctionsById(ahId); + if (!auctionHouse) + continue; + + for (auto itr = auctionHouse->GetAuctionsBegin(); itr != auctionHouse->GetAuctionsEnd(); ++itr) + { + AuctionPosting& auction = itr->second; + for (Item* item : auction.Items) + { + if (!item) + continue; + + ItemTemplate const* proto = item->GetTemplate(); + if (!proto) + continue; + + bool isEquipment = (proto->GetClass() == ITEM_CLASS_WEAPON || proto->GetClass() == ITEM_CLASS_ARMOR); + + if (equipmentOnly && !isEquipment) + continue; + + if (isEquipment) + ++equipmentItems; + + uint32 itemLevel = Item::GetItemLevel(proto, *item->GetBonus(), 90, 0, 0, 0, 0, false, 0); + + ++totalItems; + totalItemLevel += itemLevel; + + if (itemLevel < minItemLevel) + minItemLevel = itemLevel; + if (itemLevel > maxItemLevel) + maxItemLevel = itemLevel; + + uint32 bucket = (itemLevel / 50) * 50; + itemLevelBuckets[bucket]++; + } + } + } + + if (totalItems == 0) + { + return { + {"success", true}, + {"command", "ahbot stats"}, + {"message", "No items found in auction house"}, + {"totalItems", 0} + }; + } + + json distribution = json::array(); + for (auto const& [bucket, count] : itemLevelBuckets) + { + distribution.push_back({ + {"minLevel", bucket}, + {"maxLevel", bucket + 49}, + {"count", count}, + {"percentage", (static_cast(count) / totalItems) * 100.0f} + }); + } + + return { + {"success", true}, + {"command", "ahbot stats"}, + {"equipmentOnly", equipmentOnly}, + {"totalItems", totalItems}, + {"equipmentItems", equipmentItems}, + {"minItemLevel", minItemLevel}, + {"maxItemLevel", maxItemLevel}, + {"avgItemLevel", static_cast(totalItemLevel) / totalItems}, + {"distribution", distribution}, + {"scalingConfig", { + {"enabled", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_ENABLED)}, + {"minTargetLevel", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_MIN_ITEM_LEVEL)}, + {"maxTargetLevel", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_MAX_ITEM_LEVEL)}, + {"chance", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_CHANCE)}, + {"equipmentOnly", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_EQUIPMENT_ONLY)} + }} + }; + } + else + { + return { + {"success", false}, + {"error", "Unknown ahbot subcommand"}, + {"subcommand", subcmd}, + {"supported", {"status", "rebuild [all]", "reload", "stats [equipment]"}} + }; + } + } return { {"success", false}, @@ -448,7 +614,11 @@ void RegisterSpawnTools() {"supported", { "server info", "reload creature [entry]", - "reload creature_spawns (requires restart)" + "reload creature_spawns (requires restart)", + "ahbot status", + "ahbot rebuild [all]", + "ahbot reload", + "ahbot stats [equipment]" }} }; } diff --git a/src/server/game/AuctionHouseBot/AuctionHouseBot.cpp b/src/server/game/AuctionHouseBot/AuctionHouseBot.cpp index 86f5747264..7188e2a6de 100644 --- a/src/server/game/AuctionHouseBot/AuctionHouseBot.cpp +++ b/src/server/game/AuctionHouseBot/AuctionHouseBot.cpp @@ -167,6 +167,11 @@ void AuctionBotConfig::GetConfigFromFile() SetConfig(CONFIG_AHBOT_ITEMS_LOOT, "AuctionHouseBot.Items.Loot", true); SetConfig(CONFIG_AHBOT_ITEMS_MISC, "AuctionHouseBot.Items.Misc", false); + // AHBot Item Level Scaling - applies random item level bonuses to equipment + // Uses ItemBonusMgr::GetItemBonusListForItemLevelDelta() (same system as Timewalking/Remix) + SetConfig(CONFIG_AHBOT_ITEM_SCALING_ENABLED, "AuctionHouseBot.Items.Scaling.Enabled", false); + SetConfig(CONFIG_AHBOT_ITEM_SCALING_EQUIPMENT_ONLY, "AuctionHouseBot.Items.Scaling.EquipmentOnly", true); + SetConfig(CONFIG_AHBOT_BIND_NO, "AuctionHouseBot.Bind.No", true); SetConfig(CONFIG_AHBOT_BIND_PICKUP, "AuctionHouseBot.Bind.Pickup", false); SetConfig(CONFIG_AHBOT_BIND_EQUIP, "AuctionHouseBot.Bind.Equip", true); @@ -181,6 +186,10 @@ void AuctionBotConfig::GetConfigFromFile() SetConfig(CONFIG_AHBOT_ITEM_MIN_ITEM_LEVEL, "AuctionHouseBot.Items.ItemLevel.Min", 0); SetConfig(CONFIG_AHBOT_ITEM_MAX_ITEM_LEVEL, "AuctionHouseBot.Items.ItemLevel.Max", 0); + // Item level scaling range and chance (only used when scaling is enabled) + SetConfig(CONFIG_AHBOT_ITEM_SCALING_MIN_ITEM_LEVEL, "AuctionHouseBot.Items.Scaling.MinItemLevel", 0); + SetConfig(CONFIG_AHBOT_ITEM_SCALING_MAX_ITEM_LEVEL, "AuctionHouseBot.Items.Scaling.MaxItemLevel", 550); + SetConfigMax(CONFIG_AHBOT_ITEM_SCALING_CHANCE, "AuctionHouseBot.Items.Scaling.Chance", 50, 100); SetConfig(CONFIG_AHBOT_ITEM_MIN_REQ_LEVEL, "AuctionHouseBot.Items.ReqLevel.Min", 0); SetConfig(CONFIG_AHBOT_ITEM_MAX_REQ_LEVEL, "AuctionHouseBot.Items.ReqLevel.Max", 0); SetConfig(CONFIG_AHBOT_ITEM_MIN_SKILL_RANK, "AuctionHouseBot.Items.ReqSkill.Min", 0); diff --git a/src/server/game/AuctionHouseBot/AuctionHouseBot.h b/src/server/game/AuctionHouseBot/AuctionHouseBot.h index 11381b38a1..04ab88a326 100644 --- a/src/server/game/AuctionHouseBot/AuctionHouseBot.h +++ b/src/server/game/AuctionHouseBot/AuctionHouseBot.h @@ -64,6 +64,9 @@ enum AuctionBotConfigUInt32Values CONFIG_AHBOT_NEUTRAL_ITEM_AMOUNT_RATIO, CONFIG_AHBOT_ITEM_MIN_ITEM_LEVEL, CONFIG_AHBOT_ITEM_MAX_ITEM_LEVEL, + CONFIG_AHBOT_ITEM_SCALING_MIN_ITEM_LEVEL, + CONFIG_AHBOT_ITEM_SCALING_MAX_ITEM_LEVEL, + CONFIG_AHBOT_ITEM_SCALING_CHANCE, CONFIG_AHBOT_ITEM_MIN_REQ_LEVEL, CONFIG_AHBOT_ITEM_MAX_REQ_LEVEL, CONFIG_AHBOT_ITEM_MIN_SKILL_RANK, @@ -171,6 +174,7 @@ enum AuctionBotConfigBoolValues CONFIG_AHBOT_ITEMS_VENDOR, CONFIG_AHBOT_ITEMS_LOOT, CONFIG_AHBOT_ITEMS_MISC, + CONFIG_AHBOT_ITEM_SCALING_ENABLED, CONFIG_AHBOT_BIND_NO, CONFIG_AHBOT_BIND_PICKUP, CONFIG_AHBOT_BIND_EQUIP, @@ -180,6 +184,7 @@ enum AuctionBotConfigBoolValues CONFIG_AHBOT_SELLER_ENABLED, CONFIG_AHBOT_BUYER_ENABLED, CONFIG_AHBOT_LOCKBOX_ENABLED, + CONFIG_AHBOT_ITEM_SCALING_EQUIPMENT_ONLY, CONFIG_AHBOT_CLASS_CONSUMABLE_ALLOW_ZERO, CONFIG_AHBOT_CLASS_CONTAINER_ALLOW_ZERO, CONFIG_AHBOT_CLASS_WEAPON_ALLOW_ZERO, diff --git a/src/server/game/AuctionHouseBot/AuctionHouseBotSeller.cpp b/src/server/game/AuctionHouseBot/AuctionHouseBotSeller.cpp index 478e7e19b5..5d40472fc7 100644 --- a/src/server/game/AuctionHouseBot/AuctionHouseBotSeller.cpp +++ b/src/server/game/AuctionHouseBot/AuctionHouseBotSeller.cpp @@ -21,6 +21,7 @@ #include "DB2Stores.h" #include "GameTime.h" #include "Item.h" +#include "ItemBonusMgr.h" #include "Log.h" #include "Containers.h" #include "ObjectMgr.h" @@ -586,7 +587,9 @@ bool AuctionBotSeller::GetItemsToSell(SellerConfiguration& config, ItemsToSellAr } // Set items price. All important value are passed by address. -void AuctionBotSeller::SetPricesOfItem(ItemTemplate const* itemProto, SellerConfiguration& config, uint32& buyout, uint32& bid, uint32 stackCount) +// scaledItemLevel: If non-zero, use this item level for price calculation instead of base level +// This ensures scaled items are priced appropriately for their actual power level +void AuctionBotSeller::SetPricesOfItem(ItemTemplate const* itemProto, SellerConfiguration& config, uint32& buyout, uint32& bid, uint32 stackCount, uint32 scaledItemLevel /*= 0*/) { uint32 classRatio = config.GetPriceRatioPerClass(ItemClass(itemProto->GetClass())); uint32 qualityRatio = config.GetPriceRatioPerQuality(AuctionQuality(itemProto->GetQuality())); @@ -595,6 +598,9 @@ void AuctionBotSeller::SetPricesOfItem(ItemTemplate const* itemProto, SellerConf float buyPrice = itemProto->GetBuyPrice(); float sellPrice = itemProto->GetSellPrice(); + // Use scaled item level if provided, otherwise use base item level + float effectiveItemLevel = scaledItemLevel > 0 ? static_cast(scaledItemLevel) : static_cast(itemProto->GetBaseItemLevel()); + if (buyPrice == 0) { if (sellPrice > 0) @@ -602,12 +608,21 @@ void AuctionBotSeller::SetPricesOfItem(ItemTemplate const* itemProto, SellerConf else { float divisor = ((itemProto->GetClass() == ITEM_CLASS_WEAPON || itemProto->GetClass() == ITEM_CLASS_ARMOR) ? 284.0f : 80.0f); - float tempLevel = (itemProto->GetBaseItemLevel() == 0 ? 1.0f : itemProto->GetBaseItemLevel()); + float tempLevel = (effectiveItemLevel == 0 ? 1.0f : effectiveItemLevel); float tempQuality = (itemProto->GetQuality() == 0 ? 1.0f : itemProto->GetQuality()); buyPrice = tempLevel * tempQuality * static_cast(GetBuyModifier(itemProto))* tempLevel / divisor; } } + // If item has a buy price but was scaled, apply a multiplier based on item level increase + else if (scaledItemLevel > 0 && scaledItemLevel > itemProto->GetBaseItemLevel()) + { + // Scale price proportionally: higher ilvl = higher price + // Formula: basePrice * (1 + (deltaLevel * 0.02)) - 2% increase per item level + float deltaLevel = static_cast(scaledItemLevel - itemProto->GetBaseItemLevel()); + float scalingFactor = 1.0f + (deltaLevel * 0.02f); + buyPrice *= scalingFactor; + } if (sellPrice == 0) sellPrice = (buyPrice > 10 ? buyPrice / GetSellModifier(itemProto) : buyPrice); @@ -869,11 +884,47 @@ void AuctionBotSeller::AddNewAuctions(SellerConfiguration& config) // Ex: Notched Shortsword of Stamina will only generate as a Notched Shortsword without this. item->SetItemRandomBonusList(GenerateItemRandomBonusListId(itemId)); + // AHBot Item Level Scaling: Apply random item level bonus to equipment items + // Uses the same ItemBonusMgr system as Timewalking/Remix for item level deltas + // This allows AH to stock gear at varied item levels for players at all progression stages + uint32 scaledItemLevel = prototype->GetBaseItemLevel(); + if (sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_ENABLED)) + { + // Check if we should scale this item (equipment-only filter and chance roll) + bool isEquipment = (prototype->GetClass() == ITEM_CLASS_WEAPON || prototype->GetClass() == ITEM_CLASS_ARMOR); + bool shouldScale = !sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_EQUIPMENT_ONLY) || isEquipment; + + if (shouldScale && urand(0, 99) < sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_CHANCE)) + { + uint32 minLevel = sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_MIN_ITEM_LEVEL); + uint32 maxLevel = sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_MAX_ITEM_LEVEL); + uint32 targetLevel = urand(minLevel, maxLevel); + + // Only scale up, not down - if target is below base level, skip scaling + if (targetLevel > prototype->GetBaseItemLevel()) + { + int16 delta = static_cast(targetLevel - prototype->GetBaseItemLevel()); + if (uint32 bonusListId = ItemBonusMgr::GetItemBonusListForItemLevelDelta(delta)) + { + item->AddBonuses(bonusListId); + scaledItemLevel = targetLevel; + TC_LOG_DEBUG("ahbot", "AHBot: Scaled item {} from ilvl {} to {} (delta: {}, bonus: {})", + itemId, prototype->GetBaseItemLevel(), targetLevel, delta, bonusListId); + } + else + { + TC_LOG_DEBUG("ahbot", "AHBot: No bonus list found for item {} delta {} - keeping base ilvl {}", + itemId, delta, prototype->GetBaseItemLevel()); + } + } + } + } + uint32 buyoutPrice; uint32 bidPrice = 0; - // Price of items are set here - SetPricesOfItem(prototype, config, buyoutPrice, bidPrice, stackCount); + // Price of items are set here - pass scaled item level for price calculation + SetPricesOfItem(prototype, config, buyoutPrice, bidPrice, stackCount, scaledItemLevel); // Deposit time uint32 etime = urand(1, 3); diff --git a/src/server/game/AuctionHouseBot/AuctionHouseBotSeller.h b/src/server/game/AuctionHouseBot/AuctionHouseBotSeller.h index 49f4387291..9b91e11dfb 100644 --- a/src/server/game/AuctionHouseBot/AuctionHouseBotSeller.h +++ b/src/server/game/AuctionHouseBot/AuctionHouseBotSeller.h @@ -142,7 +142,7 @@ private: void LoadSellerValues(SellerConfiguration& config); uint32 SetStat(SellerConfiguration& config); bool GetItemsToSell(SellerConfiguration& config, ItemsToSellArray& itemsToSellArray, AllItemsArray const& addedItem); - void SetPricesOfItem(ItemTemplate const* itemProto, SellerConfiguration& config, uint32& buyout, uint32& bid, uint32 stackcnt); + void SetPricesOfItem(ItemTemplate const* itemProto, SellerConfiguration& config, uint32& buyout, uint32& bid, uint32 stackcnt, uint32 scaledItemLevel = 0); uint32 GetStackSizeForItem(ItemTemplate const* itemProto, SellerConfiguration& config) const; void LoadItemsQuantity(SellerConfiguration& config); static uint32 GetBuyModifier(ItemTemplate const* prototype); diff --git a/src/server/scripts/Commands/cs_ahbot.cpp b/src/server/scripts/Commands/cs_ahbot.cpp index daeb06a7fb..d2a8b99030 100644 --- a/src/server/scripts/Commands/cs_ahbot.cpp +++ b/src/server/scripts/Commands/cs_ahbot.cpp @@ -17,10 +17,13 @@ #include "ScriptMgr.h" #include "AuctionHouseBot.h" +#include "AuctionHouseMgr.h" #include "Chat.h" #include "ChatCommand.h" +#include "Item.h" #include "Language.h" #include "RBAC.h" +#include using namespace Trinity::ChatCommands; @@ -69,6 +72,7 @@ public: { "rebuild", HandleAHBotRebuildCommand, rbac::RBAC_PERM_COMMAND_AHBOT_REBUILD, Console::Yes }, { "reload", HandleAHBotReloadCommand, rbac::RBAC_PERM_COMMAND_AHBOT_RELOAD, Console::Yes }, { "status", HandleAHBotStatusCommand, rbac::RBAC_PERM_COMMAND_AHBOT_STATUS, Console::Yes }, + { "stats", HandleAHBotStatsCommand, rbac::RBAC_PERM_COMMAND_AHBOT_STATUS, Console::Yes }, }; static ChatCommandTable commandTable = @@ -188,6 +192,105 @@ public: return true; } + // AHBot Stats Command - Reports item level distribution for auction house items + // This is useful for analyzing the effectiveness of item level scaling + // Usage: .ahbot stats [equipment] - shows item level distribution + // equipment flag filters to only weapons/armor + static bool HandleAHBotStatsCommand(ChatHandler* handler, Optional equipmentOnly) + { + // Item level buckets for distribution analysis + std::map itemLevelBuckets; // bucket -> count + uint32 totalItems = 0; + uint32 equipmentItems = 0; + uint32 minItemLevel = UINT32_MAX; + uint32 maxItemLevel = 0; + uint64 totalItemLevel = 0; + + // Iterate through all three auction houses + // AuctionHouseIds: 1=Alliance, 2=Neutral (Goblin), 6=Horde, 7=Neutral (Blackwater) + std::vector auctionHouseIds = { 1, 2, 6, 7 }; + + for (uint32 ahId : auctionHouseIds) + { + AuctionHouseObject* auctionHouse = sAuctionMgr->GetAuctionsById(ahId); + if (!auctionHouse) + continue; + + for (auto itr = auctionHouse->GetAuctionsBegin(); itr != auctionHouse->GetAuctionsEnd(); ++itr) + { + AuctionPosting& auction = itr->second; + for (Item* item : auction.Items) + { + if (!item) + continue; + + ItemTemplate const* proto = item->GetTemplate(); + if (!proto) + continue; + + bool isEquipment = (proto->GetClass() == ITEM_CLASS_WEAPON || proto->GetClass() == ITEM_CLASS_ARMOR); + + // Skip non-equipment if filter is active + if (equipmentOnly.has_value() && !isEquipment) + continue; + + if (isEquipment) + ++equipmentItems; + + // Get item level from bonus data (includes any scaling bonuses) + // Use static GetItemLevel with minimal parameters since AHBot items have no owner + uint32 itemLevel = Item::GetItemLevel(proto, *item->GetBonus(), 90, 0, 0, 0, 0, false, 0); + + ++totalItems; + totalItemLevel += itemLevel; + + if (itemLevel < minItemLevel) + minItemLevel = itemLevel; + if (itemLevel > maxItemLevel) + maxItemLevel = itemLevel; + + // Bucket by 50 item levels for readable output + uint32 bucket = (itemLevel / 50) * 50; + itemLevelBuckets[bucket]++; + } + } + } + + if (totalItems == 0) + { + handler->SendSysMessage("AHBot Stats: No items found in auction house."); + return true; + } + + // Output results + handler->PSendSysMessage("=== AHBot Item Level Statistics ==="); + handler->PSendSysMessage("Total items analyzed: %u", totalItems); + if (!equipmentOnly.has_value()) + handler->PSendSysMessage("Equipment items (weapons/armor): %u", equipmentItems); + handler->PSendSysMessage("Item level range: %u - %u", minItemLevel, maxItemLevel); + handler->PSendSysMessage("Average item level: %.1f", static_cast(totalItemLevel) / totalItems); + handler->SendSysMessage("--- Distribution by Item Level ---"); + + for (auto const& [bucket, count] : itemLevelBuckets) + { + float percentage = (static_cast(count) / totalItems) * 100.0f; + handler->PSendSysMessage(" ilvl %u-%u: %u items (%.1f%%)", bucket, bucket + 49, count, percentage); + } + + // Show scaling config status + handler->SendSysMessage("--- Scaling Configuration ---"); + handler->PSendSysMessage("Scaling Enabled: %s", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_ENABLED) ? "Yes" : "No"); + if (sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_ENABLED)) + { + handler->PSendSysMessage(" Min Target ilvl: %u", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_MIN_ITEM_LEVEL)); + handler->PSendSysMessage(" Max Target ilvl: %u", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_MAX_ITEM_LEVEL)); + handler->PSendSysMessage(" Scaling Chance: %u%%", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_CHANCE)); + handler->PSendSysMessage(" Equipment Only: %s", sAuctionBotConfig->GetConfig(CONFIG_AHBOT_ITEM_SCALING_EQUIPMENT_ONLY) ? "Yes" : "No"); + } + + return true; + } + }; template bool ahbot_commandscript::HandleAHBotItemsAmountQualityCommand(ChatHandler* handler, uint32 amount); diff --git a/src/server/worldserver/worldserver.conf.dist b/src/server/worldserver/worldserver.conf.dist index 765403a3df..0d98592e9d 100644 --- a/src/server/worldserver/worldserver.conf.dist +++ b/src/server/worldserver/worldserver.conf.dist @@ -3779,6 +3779,41 @@ AuctionHouseBot.Class.Glyph.Price.Ratio = 100 AuctionHouseBot.Items.ItemLevel.Min = 0 AuctionHouseBot.Items.ItemLevel.Max = 0 +# +# AuctionHouseBot.Items.Scaling.* +# Description: Item level scaling for AHBot items. When enabled, equipment items +# posted by AHBot can receive random item level bonuses, allowing +# the AH to stock gear suitable for all player progression levels. +# Uses the same ItemBonusMgr system as Timewalking/Remix scaling. +# +# AuctionHouseBot.Items.Scaling.Enabled +# Description: Enable item level scaling for AHBot items +# Default: 0 - (Disabled, items use base item level) +# 1 - (Enabled, items may receive random item level bonuses) +# +# AuctionHouseBot.Items.Scaling.MinItemLevel +# Description: Minimum target item level for scaled items +# Default: 0 - (Use item's base level as minimum) +# +# AuctionHouseBot.Items.Scaling.MaxItemLevel +# Description: Maximum target item level for scaled items +# Default: 550 - (MoP raid gear level) +# +# AuctionHouseBot.Items.Scaling.Chance +# Description: Percentage chance (0-100) for each item to be scaled +# Default: 50 - (50% of eligible items get scaled) +# +# AuctionHouseBot.Items.Scaling.EquipmentOnly +# Description: Only scale equipment (weapons/armor), not consumables/materials +# Default: 1 - (Only equipment is scaled) +# 0 - (All item types can be scaled) + +AuctionHouseBot.Items.Scaling.Enabled = 0 +AuctionHouseBot.Items.Scaling.MinItemLevel = 0 +AuctionHouseBot.Items.Scaling.MaxItemLevel = 550 +AuctionHouseBot.Items.Scaling.Chance = 50 +AuctionHouseBot.Items.Scaling.EquipmentOnly = 1 + # # AuctionHouseBot.Items.ReqLevel.* # Description: Prevent seller from listing items below/above this required level