Tighten builtin pass metadata and remove skybox property fallbacks

This commit is contained in:
2026-04-08 13:13:42 +08:00
parent efdd6bd68f
commit 08c3278e10
9 changed files with 186 additions and 157 deletions

View File

@@ -1076,7 +1076,7 @@ TEST(BuiltinForwardPipeline_Test, BuildsBuiltinPassResourceBindingPlanFromBuilti
ShaderPassTagEntry tag = {};
tag.name = "LightMode";
tag.value = "ForwardBase";
tag.value = "ForwardLit";
pass.tags.PushBack(tag);
AppendDefaultBuiltinPassResources(pass);

View File

@@ -65,6 +65,37 @@ Material* CreateTestMaterial(const char* path, int32_t renderQueue) {
return material;
}
Texture* CreateTestTexture(const char* path, TextureType type) {
auto* texture = new Texture();
IResource::ConstructParams params = {};
params.name = path;
params.path = path;
params.guid = ResourceGUID::Generate(path);
texture->Initialize(params);
const uint32 arraySize =
(type == TextureType::TextureCube || type == TextureType::TextureCubeArray) ? 6u : 1u;
const unsigned char pixels[6 * 4] = {
255, 255, 255, 255,
255, 255, 255, 255,
255, 255, 255, 255,
255, 255, 255, 255,
255, 255, 255, 255,
255, 255, 255, 255
};
EXPECT_TRUE(texture->Create(
1u,
1u,
1u,
1u,
type,
TextureFormat::RGBA8_UNORM,
pixels,
static_cast<size_t>(arraySize) * 4u,
arraySize));
return texture;
}
TEST(RenderSceneExtractor_Test, SelectsHighestDepthPrimaryCameraAndVisibleObjects) {
Scene scene("RenderScene");
@@ -502,6 +533,46 @@ TEST(RenderMaterialUtility_Test, ShaderPassMetadataCanDriveBuiltinPassMatching)
EXPECT_FALSE(MatchesBuiltinPass(&material, BuiltinMaterialPass::Unlit));
}
TEST(RenderMaterialUtility_Test, CanonicalBuiltinPassMetadataMatchesFinalColorAndPostProcessPasses) {
ShaderPass finalColorPass = {};
finalColorPass.name = "FinalColor";
EXPECT_TRUE(ShaderPassMatchesBuiltinPass(finalColorPass, BuiltinMaterialPass::FinalColor));
ShaderPass postProcessPass = {};
postProcessPass.name = "ColorScale";
EXPECT_TRUE(ShaderPassMatchesBuiltinPass(postProcessPass, BuiltinMaterialPass::PostProcess));
}
TEST(RenderMaterialUtility_Test, LegacyBuiltinPassAliasesDoNotMatchCanonicalBuiltinPasses) {
ShaderPass forwardAliasByName = {};
forwardAliasByName.name = "ForwardBase";
EXPECT_FALSE(ShaderPassMatchesBuiltinPass(forwardAliasByName, BuiltinMaterialPass::ForwardLit));
ShaderPassTagEntry forwardAliasTag = {};
forwardAliasTag.name = "LightMode";
forwardAliasTag.value = "ForwardBase";
ShaderPass forwardAliasByTag = {};
forwardAliasByTag.name = "Default";
forwardAliasByTag.tags.PushBack(forwardAliasTag);
EXPECT_FALSE(ShaderPassMatchesBuiltinPass(forwardAliasByTag, BuiltinMaterialPass::ForwardLit));
ShaderPassTagEntry finalColorAliasTag = {};
finalColorAliasTag.name = "LightMode";
finalColorAliasTag.value = "FinalOutput";
ShaderPass finalColorAliasPass = {};
finalColorAliasPass.name = "Default";
finalColorAliasPass.tags.PushBack(finalColorAliasTag);
EXPECT_FALSE(ShaderPassMatchesBuiltinPass(finalColorAliasPass, BuiltinMaterialPass::FinalColor));
ShaderPassTagEntry postProcessAliasTag = {};
postProcessAliasTag.name = "LightMode";
postProcessAliasTag.value = "PostProcess";
ShaderPass postProcessAliasPass = {};
postProcessAliasPass.name = "Default";
postProcessAliasPass.tags.PushBack(postProcessAliasTag);
EXPECT_FALSE(ShaderPassMatchesBuiltinPass(postProcessAliasPass, BuiltinMaterialPass::PostProcess));
}
TEST(RenderMaterialUtility_Test, ExplicitShaderPassMetadataDisablesImplicitForwardFallback) {
Material material;
auto* shader = new Shader();
@@ -651,6 +722,84 @@ TEST(RenderMaterialUtility_Test, ResolvesBuiltinForwardMaterialContractFromShade
EXPECT_EQ(ResolveBuiltinBaseColorTexture(&material), nullptr);
}
TEST(RenderMaterialUtility_Test, ResolvesBuiltinSkyboxMaterialContractFromShaderSemanticMetadata) {
auto* shader = new Shader();
ShaderPropertyDesc tintProperty = {};
tintProperty.name = "SkyTintColor";
tintProperty.type = ShaderPropertyType::Color;
tintProperty.semantic = "Tint";
shader->AddProperty(tintProperty);
ShaderPropertyDesc exposureProperty = {};
exposureProperty.name = "ExposureControl";
exposureProperty.type = ShaderPropertyType::Float;
exposureProperty.semantic = "Exposure";
shader->AddProperty(exposureProperty);
ShaderPropertyDesc rotationProperty = {};
rotationProperty.name = "SkyYawDegrees";
rotationProperty.type = ShaderPropertyType::Float;
rotationProperty.semantic = "Rotation";
shader->AddProperty(rotationProperty);
ShaderPropertyDesc panoramicProperty = {};
panoramicProperty.name = "SkyPanorama";
panoramicProperty.type = ShaderPropertyType::Texture2D;
panoramicProperty.semantic = "SkyboxPanoramicTexture";
shader->AddProperty(panoramicProperty);
Material panoramicMaterial;
panoramicMaterial.SetShader(ResourceHandle<Shader>(shader));
panoramicMaterial.SetFloat4("SkyTintColor", Vector4(0.2f, 0.3f, 0.4f, 1.0f));
panoramicMaterial.SetFloat("ExposureControl", 1.35f);
panoramicMaterial.SetFloat("SkyYawDegrees", 27.0f);
Texture* panoramicTexture = CreateTestTexture("Textures/sky_panorama.texture", TextureType::Texture2D);
panoramicMaterial.SetTexture("SkyPanorama", ResourceHandle<Texture>(panoramicTexture));
EXPECT_EQ(ResolveSkyboxTint(&panoramicMaterial), Vector4(0.2f, 0.3f, 0.4f, 1.0f));
EXPECT_FLOAT_EQ(ResolveSkyboxExposure(&panoramicMaterial), 1.35f);
EXPECT_FLOAT_EQ(ResolveSkyboxRotationDegrees(&panoramicMaterial), 27.0f);
EXPECT_EQ(ResolveSkyboxPanoramicTexture(&panoramicMaterial), panoramicTexture);
EXPECT_EQ(ResolveSkyboxCubemapTexture(&panoramicMaterial), nullptr);
EXPECT_EQ(ResolveSkyboxTextureMode(&panoramicMaterial), BuiltinSkyboxTextureMode::Panoramic);
auto* cubemapShader = new Shader();
ShaderPropertyDesc cubemapProperty = {};
cubemapProperty.name = "EnvironmentCube";
cubemapProperty.type = ShaderPropertyType::TextureCube;
cubemapProperty.semantic = "SkyboxTexture";
cubemapShader->AddProperty(cubemapProperty);
Material cubemapMaterial;
cubemapMaterial.SetShader(ResourceHandle<Shader>(cubemapShader));
Texture* cubemapTexture = CreateTestTexture("Textures/sky_cube.texture", TextureType::TextureCube);
cubemapMaterial.SetTexture("EnvironmentCube", ResourceHandle<Texture>(cubemapTexture));
EXPECT_EQ(ResolveSkyboxPanoramicTexture(&cubemapMaterial), nullptr);
EXPECT_EQ(ResolveSkyboxCubemapTexture(&cubemapMaterial), cubemapTexture);
EXPECT_EQ(ResolveSkyboxTextureMode(&cubemapMaterial), BuiltinSkyboxTextureMode::Cubemap);
}
TEST(RenderMaterialUtility_Test, SkyboxMaterialDoesNotUseLegacyPropertyNameFallbacksWithoutSemanticMetadata) {
Material material;
material.SetFloat4("_Tint", Vector4(0.8f, 0.7f, 0.6f, 1.0f));
material.SetFloat("_Exposure", 2.0f);
material.SetFloat("_Rotation", 45.0f);
Texture* panoramicTexture = CreateTestTexture("Textures/legacy_panorama.texture", TextureType::Texture2D);
Texture* cubemapTexture = CreateTestTexture("Textures/legacy_cube.texture", TextureType::TextureCube);
material.SetTexture("_MainTex", ResourceHandle<Texture>(panoramicTexture));
material.SetTexture("_Tex", ResourceHandle<Texture>(cubemapTexture));
EXPECT_EQ(ResolveSkyboxTint(&material), Vector4::One());
EXPECT_FLOAT_EQ(ResolveSkyboxExposure(&material), 1.0f);
EXPECT_FLOAT_EQ(ResolveSkyboxRotationDegrees(&material), 0.0f);
EXPECT_EQ(ResolveSkyboxPanoramicTexture(&material), nullptr);
EXPECT_EQ(ResolveSkyboxCubemapTexture(&material), nullptr);
EXPECT_EQ(ResolveSkyboxTextureMode(&material), BuiltinSkyboxTextureMode::None);
}
TEST(RenderMaterialUtility_Test, ExposesSchemaDrivenMaterialConstantPayload) {
auto* shader = new Shader();

View File

@@ -355,7 +355,7 @@ TEST(MaterialLoader, LoadMaterialWithAuthoringShaderResolvesShaderPass) {
Pass
{
Name "ForwardLit"
Tags { "LightMode" = "ForwardBase" }
Tags { "LightMode" = "ForwardLit" }
HLSLPROGRAM
#pragma vertex MainVS
#pragma fragment MainPS

View File

@@ -152,7 +152,7 @@ TEST(ShaderLoader, LoadShaderAuthoringBuildsMultiPassGenericVariants) {
Pass
{
Name "ForwardLit"
Tags { "LightMode" = "ForwardBase", "Queue" = "Geometry" }
Tags { "LightMode" = "ForwardLit", "Queue" = "Geometry" }
HLSLPROGRAM
#pragma target 4.5
#pragma vertex MainVS
@@ -228,7 +228,7 @@ TEST(ShaderLoader, LoadShaderAuthoringBuildsMultiPassGenericVariants) {
EXPECT_EQ(forwardLitPass->resources.Size(), 8u);
ASSERT_NE(FindPassTag(forwardLitPass, "LightMode"), nullptr);
ASSERT_NE(FindPassTag(forwardLitPass, "Queue"), nullptr);
EXPECT_EQ(FindPassTag(forwardLitPass, "LightMode")->value, "ForwardBase");
EXPECT_EQ(FindPassTag(forwardLitPass, "LightMode")->value, "ForwardLit");
EXPECT_EQ(FindPassTag(forwardLitPass, "Queue")->value, "Geometry");
const ShaderStageVariant* d3d12Vertex = shader->FindVariant("ForwardLit", ShaderType::Vertex, ShaderBackend::D3D12);
@@ -1631,7 +1631,7 @@ TEST(ShaderLoader, AssetDatabaseCreatesShaderArtifactFromAuthoringAndLoaderReads
Pass
{
Name "ForwardLit"
Tags { "LightMode" = "ForwardBase" }
Tags { "LightMode" = "ForwardLit" }
HLSLPROGRAM
#pragma vertex MainVS
#pragma fragment MainPS
@@ -1720,7 +1720,7 @@ TEST(ShaderLoader, AssetDatabaseReimportsLegacyShaderArtifactHeaderBeforeLoad) {
Pass
{
Name "ForwardLit"
Tags { "LightMode" = "ForwardBase" }
Tags { "LightMode" = "ForwardLit" }
HLSLPROGRAM
#pragma vertex MainVS
#pragma fragment MainPS
@@ -1888,7 +1888,7 @@ TEST(ShaderLoader, AssetDatabaseCreatesShaderArtifactFromAuthoringAndTracksInclu
Pass
{
Name "ForwardLit"
Tags { "LightMode" = "ForwardBase" }
Tags { "LightMode" = "ForwardLit" }
HLSLPROGRAM
#pragma vertex Vert
#pragma fragment Frag
@@ -2031,7 +2031,7 @@ TEST(ShaderLoader, LoadBuiltinForwardLitShaderBuildsAuthoringVariants) {
EXPECT_TRUE(pass->fixedFunctionState.depthWriteEnable);
EXPECT_EQ(pass->fixedFunctionState.depthFunc, MaterialComparisonFunc::LessEqual);
EXPECT_EQ(pass->tags[0].name, "LightMode");
EXPECT_EQ(pass->tags[0].value, "ForwardBase");
EXPECT_EQ(pass->tags[0].value, "ForwardLit");
const ShaderPropertyDesc* baseColorProperty = shader->FindProperty("_BaseColor");
ASSERT_NE(baseColorProperty, nullptr);
@@ -2601,7 +2601,7 @@ TEST(ShaderLoader, LoadBuiltinFinalColorShaderBuildsAuthoringVariants) {
EXPECT_FALSE(pass->fixedFunctionState.depthWriteEnable);
EXPECT_EQ(pass->fixedFunctionState.depthFunc, MaterialComparisonFunc::Always);
EXPECT_EQ(pass->tags[0].name, "LightMode");
EXPECT_EQ(pass->tags[0].value, "FinalOutput");
EXPECT_EQ(pass->tags[0].value, "FinalColor");
const ShaderPropertyDesc* colorScaleProperty = shader->FindProperty("_ColorScale");
ASSERT_NE(colorScaleProperty, nullptr);
@@ -2684,7 +2684,7 @@ TEST(ShaderLoader, LoadBuiltinColorScalePostProcessShaderBuildsAuthoringVariants
EXPECT_FALSE(pass->fixedFunctionState.depthWriteEnable);
EXPECT_EQ(pass->fixedFunctionState.depthFunc, MaterialComparisonFunc::Always);
EXPECT_EQ(pass->tags[0].name, "LightMode");
EXPECT_EQ(pass->tags[0].value, "PostProcess");
EXPECT_EQ(pass->tags[0].value, "ColorScale");
const ShaderPropertyDesc* colorScaleProperty = shader->FindProperty("_ColorScale");
ASSERT_NE(colorScaleProperty, nullptr);