fix(wob): aggregate unique materials across ALL groups in toWMOModel

Previously only group[0]'s materials were emitted. Buildings with
group-specific materials (e.g., the indoor groups using a different
texture set than outdoor) lost those materials, leaving batches in
later groups pointing to materialIndex out of range. Now dedupes by
(texture, blend, flags) across every group.
This commit is contained in:
Kelsi 2026-05-06 02:37:10 -07:00
parent b7d9d54b29
commit a49b35e41b

View file

@ -5,6 +5,7 @@
#include <fstream>
#include <filesystem>
#include <cstring>
#include <unordered_map>
namespace wowee {
namespace pipeline {
@ -224,8 +225,17 @@ bool WoweeBuildingLoader::toWMOModel(const WoweeBuilding& building, WMOModel& ou
return static_cast<uint32_t>(outModel.textures.size() - 1);
};
if (!building.groups.empty()) {
for (const auto& mat : building.groups[0].materials) {
// Collect unique materials across all groups. WMO has a single global
// materials array shared by every group's batches; pulling only from
// group[0] dropped per-group materials. Dedupe by (texture, blend, flags).
auto materialKey = [](const WoweeBuilding::Material& m) {
return m.texturePath + "|" + std::to_string(m.flags) + "|" + std::to_string(m.blendMode);
};
std::unordered_map<std::string, uint32_t> materialIndex;
for (const auto& grp : building.groups) {
for (const auto& mat : grp.materials) {
std::string key = materialKey(mat);
if (materialIndex.count(key)) continue;
WMOMaterial wm{};
wm.flags = mat.flags;
wm.shader = mat.shader;
@ -236,6 +246,7 @@ bool WoweeBuildingLoader::toWMOModel(const WoweeBuilding& building, WMOModel& ou
wm.color2 = 0;
wm.texture3 = 0;
wm.color3 = 0;
materialIndex[key] = static_cast<uint32_t>(outModel.materials.size());
outModel.materials.push_back(wm);
}
}