From a0e52dc5506981b2b7b78acab1698702ac50b2ec Mon Sep 17 00:00:00 2001 From: momo5502 Date: Fri, 10 Jun 2016 00:08:07 +0200 Subject: [PATCH] Fix looped anims and add the long-awaited support for model-tags and quick and ugly fix for textures --- .../Modules/AssetInterfaces/IMaterial.cpp | 73 ++++++++++++++----- .../Modules/AssetInterfaces/IXModel.cpp | 25 +------ src/Game/Structs.hpp | 8 +- 3 files changed, 63 insertions(+), 43 deletions(-) diff --git a/src/Components/Modules/AssetInterfaces/IMaterial.cpp b/src/Components/Modules/AssetInterfaces/IMaterial.cpp index 9b96529d..aaa016d1 100644 --- a/src/Components/Modules/AssetInterfaces/IMaterial.cpp +++ b/src/Components/Modules/AssetInterfaces/IMaterial.cpp @@ -45,8 +45,8 @@ namespace Assets memcpy(material, baseMaterial, sizeof(Game::Material)); material->name = builder->GetAllocator()->DuplicateString(name); - material->textureAtlasRowCount = 0; - material->textureAtlasColumnCount = 0; + material->textureAtlasRowCount = 1; + material->textureAtlasColumnCount = 1; // Load animation frames auto anims = infoData["anims"]; @@ -71,6 +71,16 @@ namespace Assets } } + // Model surface textures are special, they need a special order and whatnot + bool replaceTexture = Utils::StartsWith(name, "mc/"); + if (replaceTexture) + { + Game::MaterialTextureDef* textureTable = builder->GetAllocator()->AllocateArray(baseMaterial->textureCount); + std::memcpy(textureTable, baseMaterial->textureTable, sizeof(Game::MaterialTextureDef) * baseMaterial->textureCount); + material->textureTable = textureTable; + material->textureCount = baseMaterial->textureCount; + } + // Load referenced textures auto textures = infoData["textures"]; if (textures.is_array()) @@ -87,7 +97,7 @@ namespace Assets auto map = textureInfo[0]; auto image = textureInfo[1]; - if(!map.is_string() || !image.is_string()) continue; + if (!map.is_string() || !image.is_string()) continue; Game::MaterialTextureDef textureDef; @@ -99,29 +109,54 @@ namespace Assets textureDef.info.image = Components::AssetHandler::FindAssetForZone(Game::XAssetType::ASSET_TYPE_IMAGE, image.string_value(), builder).image; - textureList.push_back(textureDef); + if (replaceTexture) + { + bool applied = false; + + for (char i = 0; i < baseMaterial->textureCount; ++i) + { + if (material->textureTable[i].nameHash == textureDef.nameHash) + { + applied = true; + material->textureTable[i].info.image = textureDef.info.image; + break; + } + } + + if (!applied) + { + Components::Logger::Error(0, "Unable to find texture for map '%s' in %s!", map.string_value().data(), baseMaterial->name); + } + } + else + { + textureList.push_back(textureDef); + } } - if (!textureList.empty()) + if(!replaceTexture) { - Game::MaterialTextureDef* textureTable = builder->GetAllocator()->AllocateArray(textureList.size()); - - if (!textureTable) + if (!textureList.empty()) { - Components::Logger::Error("Failed to allocate texture table!"); - return; + Game::MaterialTextureDef* textureTable = builder->GetAllocator()->AllocateArray(textureList.size()); + + if (!textureTable) + { + Components::Logger::Error("Failed to allocate texture table!"); + return; + } + + std::memcpy(textureTable, textureList.data(), sizeof(Game::MaterialTextureDef) * textureList.size()); + + material->textureTable = textureTable; + } + else + { + material->textureTable = 0; } - memcpy(textureTable, textureList.data(), sizeof(Game::MaterialTextureDef) * textureList.size()); - - material->textureTable = textureTable; + material->textureCount = static_cast(textureList.size()) & 0xFF; } - else - { - material->textureTable = 0; - } - - material->textureCount = static_cast(textureList.size()) & 0xFF; } header->material = material; diff --git a/src/Components/Modules/AssetInterfaces/IXModel.cpp b/src/Components/Modules/AssetInterfaces/IXModel.cpp index ef76afe4..28e23702 100644 --- a/src/Components/Modules/AssetInterfaces/IXModel.cpp +++ b/src/Components/Modules/AssetInterfaces/IXModel.cpp @@ -64,6 +64,10 @@ namespace Assets Game::XSurface* surface = &surf->surfaces[i]; std::memcpy(surface, baseSurface, sizeof(Game::XSurface)); + surface->streamHandle = reader.Read(); + surface->something = reader.Read(); + surface->something2 = reader.Read(); + surface->numVertices = reader.Read(); surface->numPrimitives = reader.Read(); surface->numCT = reader.Read(); @@ -103,15 +107,6 @@ namespace Assets for (char i = 0; i < model->numSurfaces; ++i) { model->materials[i] = Components::AssetHandler::FindAssetForZone(Game::XAssetType::ASSET_TYPE_MATERIAL, reader.ReadString(), builder).material; - - //if (i < 9) - { - model->materials[i] = baseModel->materials[0]; - } -// else -// { -// OutputDebugStringA(model->materials[i]->name); -// } } // Read collision surfaces @@ -207,18 +202,6 @@ namespace Assets buffer->PushBlock(Game::XFILE_BLOCK_VIRTUAL); -// if (!strcmp(asset->name, "viewmodel_m40a3")) -// { -// for (char i = 0; i < asset->numBones; ++i) -// { -// OutputDebugStringA(Utils::VA("Bounds[%d][0]: %f - %X\n", i, asset->boneInfo[i].bounds[0], *(DWORD*)&asset->boneInfo[i].bounds[0])); -// OutputDebugStringA(Utils::VA("Bounds[%d][1]: %f - %X\n", i, asset->boneInfo[i].bounds[1], *(DWORD*)&asset->boneInfo[i].bounds[1])); -// OutputDebugStringA(Utils::VA("Bounds[%d][2]: %f - %X\n\n", i, asset->boneInfo[i].bounds[2], *(DWORD*)&asset->boneInfo[i].bounds[2])); -// } -// -// __debugbreak(); -// } - if (asset->name) { buffer->SaveString(builder->GetAssetName(this->GetType(), asset->name)); diff --git a/src/Game/Structs.hpp b/src/Game/Structs.hpp index 4b8b6062..737e617e 100644 --- a/src/Game/Structs.hpp +++ b/src/Game/Structs.hpp @@ -1355,7 +1355,9 @@ namespace Game GfxPackedVertex* vertexBuffer; // +28 int numCT; // +32 XRigidVertList* ct; // +36 - char pad5[24]; // +40 + int something; + int something2; + char pad5[16]; // +40 // pad5 matches XModelSurfaces pad // total size, 64 }; @@ -1660,10 +1662,10 @@ namespace Game unsigned short randomDataByteCount; // 10 - 0xA unsigned short randomDataIntCount;// 12 - 0xC unsigned short framecount; // 14 - 0xE - char pad1; // 16 + char bLoop; // 16 char boneCount[10]; // 17 char notetrackCount; // 27 - bool bLoop; // 28 + bool pad1; // 28 bool bDelta; // 29 char assetType; // 30 char pad2; // 31