diff --git a/Data/expansions/classic/dbc_layouts.json b/Data/expansions/classic/dbc_layouts.json index bcbcd27b..0aa17c74 100644 --- a/Data/expansions/classic/dbc_layouts.json +++ b/Data/expansions/classic/dbc_layouts.json @@ -6,9 +6,9 @@ "ItemDisplayInfo": { "ID": 0, "LeftModel": 1, "LeftModelTexture": 3, "InventoryIcon": 5, "GeosetGroup1": 7, "GeosetGroup3": 9, - "TextureArmUpper": 15, "TextureArmLower": 16, "TextureHand": 17, - "TextureTorsoUpper": 18, "TextureTorsoLower": 19, - "TextureLegUpper": 20, "TextureLegLower": 21, "TextureFoot": 22 + "TextureArmUpper": 14, "TextureArmLower": 15, "TextureHand": 16, + "TextureTorsoUpper": 17, "TextureTorsoLower": 18, + "TextureLegUpper": 19, "TextureLegLower": 20, "TextureFoot": 21 }, "CharSections": { "RaceID": 1, "SexID": 2, "BaseSection": 3, diff --git a/Data/expansions/tbc/dbc_layouts.json b/Data/expansions/tbc/dbc_layouts.json index 2d0ff1ae..a49d1c7a 100644 --- a/Data/expansions/tbc/dbc_layouts.json +++ b/Data/expansions/tbc/dbc_layouts.json @@ -6,9 +6,9 @@ "ItemDisplayInfo": { "ID": 0, "LeftModel": 1, "LeftModelTexture": 3, "InventoryIcon": 5, "GeosetGroup1": 7, "GeosetGroup3": 9, - "TextureArmUpper": 15, "TextureArmLower": 16, "TextureHand": 17, - "TextureTorsoUpper": 18, "TextureTorsoLower": 19, - "TextureLegUpper": 20, "TextureLegLower": 21, "TextureFoot": 22 + "TextureArmUpper": 14, "TextureArmLower": 15, "TextureHand": 16, + "TextureTorsoUpper": 17, "TextureTorsoLower": 18, + "TextureLegUpper": 19, "TextureLegLower": 20, "TextureFoot": 21 }, "CharSections": { "RaceID": 1, "SexID": 2, "BaseSection": 3, diff --git a/Data/expansions/turtle/dbc_layouts.json b/Data/expansions/turtle/dbc_layouts.json index bcbcd27b..0aa17c74 100644 --- a/Data/expansions/turtle/dbc_layouts.json +++ b/Data/expansions/turtle/dbc_layouts.json @@ -6,9 +6,9 @@ "ItemDisplayInfo": { "ID": 0, "LeftModel": 1, "LeftModelTexture": 3, "InventoryIcon": 5, "GeosetGroup1": 7, "GeosetGroup3": 9, - "TextureArmUpper": 15, "TextureArmLower": 16, "TextureHand": 17, - "TextureTorsoUpper": 18, "TextureTorsoLower": 19, - "TextureLegUpper": 20, "TextureLegLower": 21, "TextureFoot": 22 + "TextureArmUpper": 14, "TextureArmLower": 15, "TextureHand": 16, + "TextureTorsoUpper": 17, "TextureTorsoLower": 18, + "TextureLegUpper": 19, "TextureLegLower": 20, "TextureFoot": 21 }, "CharSections": { "RaceID": 1, "SexID": 2, "BaseSection": 3, diff --git a/Data/expansions/wotlk/dbc_layouts.json b/Data/expansions/wotlk/dbc_layouts.json index 4f8bc338..7a5271a3 100644 --- a/Data/expansions/wotlk/dbc_layouts.json +++ b/Data/expansions/wotlk/dbc_layouts.json @@ -6,9 +6,9 @@ "ItemDisplayInfo": { "ID": 0, "LeftModel": 1, "LeftModelTexture": 3, "InventoryIcon": 5, "GeosetGroup1": 7, "GeosetGroup3": 9, - "TextureArmUpper": 15, "TextureArmLower": 16, "TextureHand": 17, - "TextureTorsoUpper": 18, "TextureTorsoLower": 19, - "TextureLegUpper": 20, "TextureLegLower": 21, "TextureFoot": 22 + "TextureArmUpper": 14, "TextureArmLower": 15, "TextureHand": 16, + "TextureTorsoUpper": 17, "TextureTorsoLower": 18, + "TextureLegUpper": 19, "TextureLegLower": 20, "TextureFoot": 21 }, "CharSections": { "RaceID": 1, "SexID": 2, "BaseSection": 3, diff --git a/include/game/game_handler.hpp b/include/game/game_handler.hpp index 8d4d7ff0..a846aa35 100644 --- a/include/game/game_handler.hpp +++ b/include/game/game_handler.hpp @@ -1134,6 +1134,7 @@ private: int packSlotBase_ = -1; std::map lastPlayerFields_; bool onlineEquipDirty_ = false; + std::array lastEquipDisplayIds_{}; // Visible equipment for other players: detect the update-field layout (base + stride) // using the local player's own equipped items, then decode other players by index. diff --git a/src/core/application.cpp b/src/core/application.cpp index 58f2927a..9fea8d99 100644 --- a/src/core/application.cpp +++ b/src/core/application.cpp @@ -3130,16 +3130,16 @@ void Application::spawnOnlineCreature(uint64_t guid, uint32_t displayId, float x const auto* idiL = pipeline::getActiveDBCLayout() ? pipeline::getActiveDBCLayout()->getLayout("ItemDisplayInfo") : nullptr; // Texture component region fields (8 regions: ArmUpper..Foot) - // Fields 15-22 in WotLK ItemDisplayInfo.dbc (field 14 = HelmetGeosetVis[1]) + // Binary DBC (23 fields) has textures at 14+ const uint32_t texRegionFields[8] = { - idiL ? (*idiL)["TextureArmUpper"] : 15u, - idiL ? (*idiL)["TextureArmLower"] : 16u, - idiL ? (*idiL)["TextureHand"] : 17u, - idiL ? (*idiL)["TextureTorsoUpper"]: 18u, - idiL ? (*idiL)["TextureTorsoLower"]: 19u, - idiL ? (*idiL)["TextureLegUpper"] : 20u, - idiL ? (*idiL)["TextureLegLower"] : 21u, - idiL ? (*idiL)["TextureFoot"] : 22u, + idiL ? (*idiL)["TextureArmUpper"] : 14u, + idiL ? (*idiL)["TextureArmLower"] : 15u, + idiL ? (*idiL)["TextureHand"] : 16u, + idiL ? (*idiL)["TextureTorsoUpper"]: 17u, + idiL ? (*idiL)["TextureTorsoLower"]: 18u, + idiL ? (*idiL)["TextureLegUpper"] : 19u, + idiL ? (*idiL)["TextureLegLower"] : 20u, + idiL ? (*idiL)["TextureFoot"] : 21u, }; const bool npcIsFemale = (extra.sexId == 1); @@ -3970,16 +3970,16 @@ void Application::setOnlinePlayerEquipment(uint64_t guid, }; // Texture component region fields from DBC layout - // Fields 15-22 in WotLK ItemDisplayInfo.dbc (field 14 = HelmetGeosetVis[1]) + // Binary DBC (23 fields) has textures at 14+ const uint32_t texRegionFields[8] = { - idiL ? (*idiL)["TextureArmUpper"] : 15u, - idiL ? (*idiL)["TextureArmLower"] : 16u, - idiL ? (*idiL)["TextureHand"] : 17u, - idiL ? (*idiL)["TextureTorsoUpper"]: 18u, - idiL ? (*idiL)["TextureTorsoLower"]: 19u, - idiL ? (*idiL)["TextureLegUpper"] : 20u, - idiL ? (*idiL)["TextureLegLower"] : 21u, - idiL ? (*idiL)["TextureFoot"] : 22u, + idiL ? (*idiL)["TextureArmUpper"] : 14u, + idiL ? (*idiL)["TextureArmLower"] : 15u, + idiL ? (*idiL)["TextureHand"] : 16u, + idiL ? (*idiL)["TextureTorsoUpper"]: 17u, + idiL ? (*idiL)["TextureTorsoLower"]: 18u, + idiL ? (*idiL)["TextureLegUpper"] : 19u, + idiL ? (*idiL)["TextureLegLower"] : 20u, + idiL ? (*idiL)["TextureFoot"] : 21u, }; std::vector> regionLayers; diff --git a/src/game/game_handler.cpp b/src/game/game_handler.cpp index 03436c40..b5926d7e 100644 --- a/src/game/game_handler.cpp +++ b/src/game/game_handler.cpp @@ -5686,7 +5686,16 @@ void GameHandler::rebuildOnlineInventory() { } } - onlineEquipDirty_ = true; + // Only mark equipment dirty if equipped item displayInfoIds actually changed + std::array currentEquipDisplayIds{}; + for (int i = 0; i < 19; i++) { + const auto& slot = inventory.getEquipSlot(static_cast(i)); + if (!slot.empty()) currentEquipDisplayIds[i] = slot.item.displayInfoId; + } + if (currentEquipDisplayIds != lastEquipDisplayIds_) { + lastEquipDisplayIds_ = currentEquipDisplayIds; + onlineEquipDirty_ = true; + } LOG_DEBUG("Rebuilt online inventory: equip=", [&](){ int c = 0; for (auto g : equipSlotGuids_) if (g) c++; return c; diff --git a/src/ui/game_screen.cpp b/src/ui/game_screen.cpp index 4a80a6a6..109d1f12 100644 --- a/src/ui/game_screen.cpp +++ b/src/ui/game_screen.cpp @@ -2639,6 +2639,20 @@ void GameScreen::updateCharacterTextures(game::Inventory& inventory) { // Load ItemDisplayInfo.dbc auto displayInfoDbc = assetManager->loadDBC("ItemDisplayInfo.dbc"); if (!displayInfoDbc) return; + const auto* idiL = pipeline::getActiveDBCLayout() + ? pipeline::getActiveDBCLayout()->getLayout("ItemDisplayInfo") : nullptr; + // Texture component region fields (8 regions: ArmUpper..Foot) + // Binary DBC (23 fields) has textures at 14+ + const uint32_t texRegionFields[8] = { + idiL ? (*idiL)["TextureArmUpper"] : 14u, + idiL ? (*idiL)["TextureArmLower"] : 15u, + idiL ? (*idiL)["TextureHand"] : 16u, + idiL ? (*idiL)["TextureTorsoUpper"]: 17u, + idiL ? (*idiL)["TextureTorsoLower"]: 18u, + idiL ? (*idiL)["TextureLegUpper"] : 19u, + idiL ? (*idiL)["TextureLegLower"] : 20u, + idiL ? (*idiL)["TextureFoot"] : 21u, + }; // Collect equipment texture regions from all equipped items std::vector> regionLayers; @@ -2650,11 +2664,9 @@ void GameScreen::updateCharacterTextures(game::Inventory& inventory) { int32_t recIdx = displayInfoDbc->findRecordById(slot.item.displayInfoId); if (recIdx < 0) continue; - // DBC fields 14-21 = texture_1 through texture_8 (regions 0-7) - // Binary DBC (23 fields) has textures at 14+; some CSVs (25 fields) have them at 15+. for (int region = 0; region < 8; region++) { - uint32_t fieldIdx = 14 + region; - std::string texName = displayInfoDbc->getString(static_cast(recIdx), fieldIdx); + std::string texName = displayInfoDbc->getString( + static_cast(recIdx), texRegionFields[region]); if (texName.empty()) continue; // Actual MPQ files have a gender suffix: _M (male), _F (female), _U (unisex)