1
0
mirror of https://github.com/XLabsProject/iw3x-port.git synced 2023-08-02 15:02:11 +02:00

Delay Model Surface and fix Static model flags

This commit is contained in:
Louvenarde 2022-12-15 23:52:49 +01:00
parent 3864d4968d
commit f1e0fe8aec
5 changed files with 82 additions and 4 deletions

View File

@ -946,7 +946,14 @@ namespace Components
map.dpvs.smodelDrawInsts[i].reflectionProbeIndex = world->dpvs.smodelDrawInsts[i].reflectionProbeIndex;
map.dpvs.smodelDrawInsts[i].primaryLightIndex = world->dpvs.smodelDrawInsts[i].primaryLightIndex;
map.dpvs.smodelDrawInsts[i].lightingHandle = world->dpvs.smodelDrawInsts[i].lightingHandle;
map.dpvs.smodelDrawInsts[i].flags = world->dpvs.smodelDrawInsts[i].flags;
map.dpvs.smodelDrawInsts[i].flags = 0;
if (world->dpvs.smodelDrawInsts[i].flags & Game::IW3::STATIC_MODEL_FLAG_NO_SHADOW)
{
// Confirmed to be the same in the rendering functions
// Check R_AddAllStaticModelSurfacesSpotShadow in both iw3 and iw4
map.dpvs.smodelDrawInsts[i].flags |= Game::IW4::STATIC_MODEL_FLAG_NO_CAST_SHADOW;
}
// This has been moved
if (world->dpvs.smodelInsts)
@ -957,7 +964,7 @@ namespace Components
//// Whenever a model needs ground lighting in iw4, it has to specify it
if (map.dpvs.smodelDrawInsts[i].groundLighting.packed > 0)
{
map.dpvs.smodelDrawInsts[i].flags |= 0x20;
map.dpvs.smodelDrawInsts[i].flags |= Game::IW4::STATIC_MODEL_FLAG_GROUND_LIGHTING;
}
}
}

View File

@ -4,6 +4,7 @@
namespace Components
{
std::unordered_map<char, Game::IW4::Material> IMaterial::exampleMaterialForKey{};
std::unordered_map<char, char> IMaterial::sortKeysTable = {
{0, 43}, // Distortion
// Opaque water (never used)
@ -369,6 +370,9 @@ namespace Components
mat.gameFlags.fields.unk8 = material->info.gameFlags.fields.unk7;
mat.gameFlags.fields.unk7 = material->info.gameFlags.fields.unk8;
// Do not delay model surface ever! In iw4 this doesn't even exist
// If this flag is ever set to 1 it usually burns the delayed surface buffer of IW4
mat.gameFlags.fields.delayModelSurface = 0;
// Sort key
#if USE_IW3_SORTKEYS
mat.sortKey = material->info.sortKey; // Using iw3 value directly
@ -458,6 +462,16 @@ namespace Components
Logger::Print("Set statebit %i loadbit 0 to GFXS0_CULL_NONE on material %s (it is glass)\n", index, mat.name);
}
#if not USE_IW3_SORTKEYS
Game::IW4::Material conflict;
if (CheckSortKeyConflict(&mat, conflict))
{
Components::Logger::Print("There is a sort key conflict between %s and %s on the key %i. One of these two (most probably the first one) doesn't have the right sort key! You will need to fix the material JSON manually.\n",
mat.name, conflict.name, mat.sortKey);
assert(false);
}
#endif
IMaterial::SaveConvertedMaterial(&mat);
}
@ -538,6 +552,15 @@ namespace Components
return 34;
}
if (techsetName.contains("effect"))
{
// Really not sure about this! But some posters on some custom maps (mp_nuked_xmas) are on wc_effect tecshet
// and cause a sort crash when put on the decal layer (9)
Logger::Print("Material %s was given sortkey %i from %i (techset name contains 'effect')\n", name.data(), 34, iw3Key);
return 48;
}
/*
- 16 (3 matches)
- mp_crash:mc\ch_bulletinboardpaperdecals_2.json
@ -669,6 +692,51 @@ namespace Components
return iw3Key;
}
bool IMaterial::CheckSortKeyConflict(Game::IW4::Material* material, OUT Game::IW4::Material& conflictingMaterial)
{
if (exampleMaterialForKey.find(material->sortKey) == exampleMaterialForKey.end())
{
exampleMaterialForKey[material->sortKey] = *material;
return false;
}
auto* otherMaterial = &exampleMaterialForKey.at(material->sortKey);
assert(material->techniqueSet);
bool hasLit = material->techniqueSet->techniques[Game::IW4::TECHNIQUE_LIT] != nullptr;
bool otherHasLit = otherMaterial->techniqueSet->techniques[Game::IW4::TECHNIQUE_LIT] != nullptr;
if (otherHasLit != hasLit)
{
conflictingMaterial = *otherMaterial;
return true;
}
if (hasLit)
{
bool hasEmissive = material->techniqueSet->techniques[Game::IW4::TECHNIQUE_EMISSIVE];
bool otherHasEmissive = otherMaterial->techniqueSet->techniques[Game::IW4::TECHNIQUE_EMISSIVE];
if (hasEmissive)
{
conflictingMaterial = *otherMaterial;
return true;
}
if (otherHasEmissive)
{
conflictingMaterial = *otherMaterial;
return true;
}
}
return false;
}
IMaterial::IMaterial()
{

View File

@ -14,6 +14,7 @@ namespace Components
private:
static std::unordered_map<char, char> sortKeysTable;
static std::unordered_map<char, Game::IW4::Material> exampleMaterialForKey;
static void Dump(Game::IW3::Material* material);
@ -21,6 +22,8 @@ namespace Components
static char GetConvertedSortKey(Game::IW3::Material* material);
static bool CheckSortKeyConflict(Game::IW4::Material* material, OUT Game::IW4::Material& conflictingMaterial);
static rapidjson::Value StateBitsToJsonArray(Game::IW3::GfxStateBits* stateBits, unsigned char count, rapidjson::MemoryPoolAllocator<rapidjson::CrtAllocator>& allocator);
};
}

View File

@ -113,7 +113,7 @@ namespace Game
if (entry->entry.asset.type == type)
{
auto assetName = DB_GetXAssetNameHandlers[entry->entry.asset.type](&entry->entry.asset.header);
if (!stricmp(name, assetName))
if (!_stricmp(name, assetName))
break;
}

View File

@ -136,7 +136,7 @@ namespace Game
unsigned char isFoliageRequiresGroundLighting : 1;
unsigned char unk4 : 1;
unsigned char unk5 : 1;
unsigned char unk6 : 1;
unsigned char delayModelSurface : 1;
unsigned char unk7 : 1;
unsigned char unk8 : 1;
};