diff --git a/Content/Editor/MaterialTemplates/Features/ForwardShading.hlsl b/Content/Editor/MaterialTemplates/Features/ForwardShading.hlsl index dc866c1ea..bbc06f15d 100644 --- a/Content/Editor/MaterialTemplates/Features/ForwardShading.hlsl +++ b/Content/Editor/MaterialTemplates/Features/ForwardShading.hlsl @@ -67,7 +67,6 @@ void PS_Forward( gBuffer.Color = material.Color; gBuffer.Specular = material.Specular; gBuffer.AO = material.AO; - // gBuffer.ViewPos is the view space position of the pixel gBuffer.ViewPos = mul(float4(materialInput.WorldPosition, 1), ViewMatrix).xyz; #if MATERIAL_SHADING_MODEL == SHADING_MODEL_SUBSURFACE gBuffer.CustomData = float4(material.SubsurfaceColor, material.Opacity); @@ -126,23 +125,19 @@ void PS_Forward( float3 screenColor = sceneColorTexture.SampleLevel(SamplerPointClamp, hit.xy, 0).rgb; reflections = lerp(reflections, screenColor, hit.z); } - + // Fallback to software tracing if possible #if USE_GLOBAL_SURFACE_ATLAS && CAN_USE_GLOBAL_SURFACE_ATLAS - - // If hit.z >= 0.9f then skip sdf tracing - if (hit.z < 0.9f) + if (hit.z < REFLECTIONS_HIT_THRESHOLD) { - // Don't use temporal effect in forward pass float3 reflectWS = ScreenSpaceReflectionDirection(screenUV, gBuffer, ViewPos); float4 surfaceAtlas; - - if(TraceSDFSoftwareReflections(gBuffer, reflectWS, surfaceAtlas)){ + if (TraceSDFSoftwareReflections(gBuffer, reflectWS, surfaceAtlas)) + { float3 screenColor = sceneColorTexture.SampleLevel(SamplerPointClamp, hit.xy, 0).rgb; reflections = lerp(surfaceAtlas, float4(screenColor, 1), hit.z); } } - #endif #endif diff --git a/Content/Editor/MaterialTemplates/Features/SDFReflections.hlsl b/Content/Editor/MaterialTemplates/Features/SDFReflections.hlsl index a7177e686..34201f546 100644 --- a/Content/Editor/MaterialTemplates/Features/SDFReflections.hlsl +++ b/Content/Editor/MaterialTemplates/Features/SDFReflections.hlsl @@ -29,10 +29,8 @@ bool TraceSDFSoftwareReflections(GBufferSample gBuffer, float3 reflectWS, out fl float3 hitPosition = sdfHit.GetHitPosition(sdfTrace); float surfaceThreshold = GetGlobalSurfaceAtlasThreshold(GlobalSDF, sdfHit); surfaceAtlas = SampleGlobalSurfaceAtlas(GlobalSurfaceAtlas, GlobalSurfaceAtlasChunks, RWGlobalSurfaceAtlasCulledObjects, GlobalSurfaceAtlasObjects, GlobalSurfaceAtlasDepth, GlobalSurfaceAtlasTex, hitPosition, -reflectWS, surfaceThreshold); - return true; } - return false; } diff --git a/Source/Engine/Graphics/Materials/ForwardMaterialShader.cpp b/Source/Engine/Graphics/Materials/ForwardMaterialShader.cpp index fd9568bcf..7aa662d43 100644 --- a/Source/Engine/Graphics/Materials/ForwardMaterialShader.cpp +++ b/Source/Engine/Graphics/Materials/ForwardMaterialShader.cpp @@ -51,7 +51,8 @@ void ForwardMaterialShader::Bind(BindParameters& params) int32 srv = 2; // Setup features - if ((_info.FeaturesFlags & MaterialFeaturesFlags::GlobalIllumination) != MaterialFeaturesFlags::None) { + if ((_info.FeaturesFlags & MaterialFeaturesFlags::GlobalIllumination) != MaterialFeaturesFlags::None) + { GlobalIlluminationFeature::Bind(params, cb, srv); if ((_info.FeaturesFlags & MaterialFeaturesFlags::ScreenSpaceReflections) != MaterialFeaturesFlags::None) SDFReflectionsFeature::Bind(params, cb, srv); @@ -181,7 +182,6 @@ bool ForwardMaterialShader::Load() psDesc.VS = _shader->GetVS("VS"); if (psDesc.VS == nullptr) return true; - psDesc.PS = _shader->GetPS("PS_Forward"); psDesc.DepthWriteEnable = false; psDesc.BlendMode = BlendingMode::AlphaBlend; diff --git a/Source/Engine/Graphics/Materials/MaterialShader.h b/Source/Engine/Graphics/Materials/MaterialShader.h index 7a5b842e2..5a4cec20c 100644 --- a/Source/Engine/Graphics/Materials/MaterialShader.h +++ b/Source/Engine/Graphics/Materials/MaterialShader.h @@ -10,7 +10,7 @@ /// /// Current materials shader version. /// -#define MATERIAL_GRAPH_VERSION 162 +#define MATERIAL_GRAPH_VERSION 163 class Material; class GPUShader; diff --git a/Source/Engine/Graphics/Materials/MaterialShaderFeatures.cpp b/Source/Engine/Graphics/Materials/MaterialShaderFeatures.cpp index 94c963b74..697176763 100644 --- a/Source/Engine/Graphics/Materials/MaterialShaderFeatures.cpp +++ b/Source/Engine/Graphics/Materials/MaterialShaderFeatures.cpp @@ -132,13 +132,13 @@ bool LightmapFeature::Bind(MaterialShader::BindParameters& params, Span& c const bool useLightmap = EnumHasAnyFlags(params.RenderContext.View.Flags, ViewFlags::GI) #if USE_EDITOR - && EnableLightmapsUsage + && EnableLightmapsUsage #endif - && drawCall.Surface.Lightmap != nullptr; + && drawCall.Surface.Lightmap != nullptr; if (useLightmap) { // Bind lightmap textures - GPUTexture* lightmap0, * lightmap1, * lightmap2; + GPUTexture *lightmap0, *lightmap1, *lightmap2; drawCall.Features.Lightmap->GetTextures(&lightmap0, &lightmap1, &lightmap2); params.GPUContext->BindSR(srv + 0, lightmap0); params.GPUContext->BindSR(srv + 1, lightmap1); @@ -210,16 +210,14 @@ bool SDFReflectionsFeature::Bind(MaterialShader::BindParameters& params, SpanGet(params.RenderContext.Buffers, bindingDataSDF) && !GlobalSurfaceAtlasPass::Instance()->Get(params.RenderContext.Buffers, bindingDataSurfaceAtlas)) { useSDFReflections = true; - // Bind DDGI data + // Bind SDF and Surface Atlas data data.GlobalSDF = bindingDataSDF.Constants; data.GlobalSurfaceAtlas = bindingDataSurfaceAtlas.Constants; - params.GPUContext->BindSR(srv + 0, bindingDataSDF.Texture ? bindingDataSDF.Texture->ViewVolume() : nullptr); params.GPUContext->BindSR(srv + 1, bindingDataSDF.TextureMip ? bindingDataSDF.TextureMip->ViewVolume() : nullptr); params.GPUContext->BindSR(srv + 2, bindingDataSurfaceAtlas.Chunks ? bindingDataSurfaceAtlas.Chunks->View() : nullptr); @@ -232,11 +230,10 @@ bool SDFReflectionsFeature::Bind(MaterialShader::BindParameters& params, SpanUnBindSR(srv + 0); params.GPUContext->UnBindSR(srv + 1); params.GPUContext->UnBindSR(srv + 2); diff --git a/Source/Engine/Tools/MaterialGenerator/MaterialGenerator.cpp b/Source/Engine/Tools/MaterialGenerator/MaterialGenerator.cpp index bff70e709..f9ca26705 100644 --- a/Source/Engine/Tools/MaterialGenerator/MaterialGenerator.cpp +++ b/Source/Engine/Tools/MaterialGenerator/MaterialGenerator.cpp @@ -188,45 +188,46 @@ bool MaterialGenerator::Generate(WriteStream& source, MaterialInfo& materialInfo { case MaterialDomain::Surface: if (materialInfo.TessellationMode != TessellationMethod::None) - ADD_FEATURE(TessellationFeature); + ADD_FEATURE(TessellationFeature); if (materialInfo.BlendMode == MaterialBlendMode::Opaque) - ADD_FEATURE(MotionVectorsFeature); + ADD_FEATURE(MotionVectorsFeature); if (materialInfo.BlendMode == MaterialBlendMode::Opaque) - ADD_FEATURE(LightmapFeature); + ADD_FEATURE(LightmapFeature); if (materialInfo.BlendMode == MaterialBlendMode::Opaque) - ADD_FEATURE(DeferredShadingFeature); + ADD_FEATURE(DeferredShadingFeature); if (materialInfo.BlendMode != MaterialBlendMode::Opaque && (materialInfo.FeaturesFlags & MaterialFeaturesFlags::DisableDistortion) == MaterialFeaturesFlags::None) - ADD_FEATURE(DistortionFeature); - if (materialInfo.BlendMode != MaterialBlendMode::Opaque && EnumHasAnyFlags(materialInfo.FeaturesFlags, MaterialFeaturesFlags::GlobalIllumination)) { + ADD_FEATURE(DistortionFeature); + if (materialInfo.BlendMode != MaterialBlendMode::Opaque && EnumHasAnyFlags(materialInfo.FeaturesFlags, MaterialFeaturesFlags::GlobalIllumination)) + { ADD_FEATURE(GlobalIlluminationFeature); // SDF Reflections is only valid when both GI and SSR is enabled if (materialInfo.BlendMode != MaterialBlendMode::Opaque && EnumHasAnyFlags(materialInfo.FeaturesFlags, MaterialFeaturesFlags::ScreenSpaceReflections)) - ADD_FEATURE(SDFReflectionsFeature); + ADD_FEATURE(SDFReflectionsFeature); } if (materialInfo.BlendMode != MaterialBlendMode::Opaque) - ADD_FEATURE(ForwardShadingFeature); + ADD_FEATURE(ForwardShadingFeature); break; case MaterialDomain::Terrain: if (materialInfo.TessellationMode != TessellationMethod::None) - ADD_FEATURE(TessellationFeature); + ADD_FEATURE(TessellationFeature); ADD_FEATURE(LightmapFeature); ADD_FEATURE(DeferredShadingFeature); break; case MaterialDomain::Particle: if (materialInfo.BlendMode != MaterialBlendMode::Opaque && (materialInfo.FeaturesFlags & MaterialFeaturesFlags::DisableDistortion) == MaterialFeaturesFlags::None) - ADD_FEATURE(DistortionFeature); + ADD_FEATURE(DistortionFeature); if (materialInfo.BlendMode != MaterialBlendMode::Opaque && EnumHasAnyFlags(materialInfo.FeaturesFlags, MaterialFeaturesFlags::GlobalIllumination)) - ADD_FEATURE(GlobalIlluminationFeature); + ADD_FEATURE(GlobalIlluminationFeature); ADD_FEATURE(ForwardShadingFeature); break; case MaterialDomain::Deformable: if (materialInfo.TessellationMode != TessellationMethod::None) - ADD_FEATURE(TessellationFeature); + ADD_FEATURE(TessellationFeature); if (materialInfo.BlendMode == MaterialBlendMode::Opaque) - ADD_FEATURE(DeferredShadingFeature); + ADD_FEATURE(DeferredShadingFeature); if (materialInfo.BlendMode != MaterialBlendMode::Opaque) - ADD_FEATURE(ForwardShadingFeature); + ADD_FEATURE(ForwardShadingFeature); break; default: break; @@ -713,7 +714,7 @@ void MaterialGenerator::ProcessGroupMath(Box* box, Node* node, Value& value) { switch (node->TypeID) { - // Vector Transform + // Vector Transform case 30: { // Get input vector diff --git a/Source/Shaders/GBufferCommon.hlsl b/Source/Shaders/GBufferCommon.hlsl index 27095f000..88a6c3688 100644 --- a/Source/Shaders/GBufferCommon.hlsl +++ b/Source/Shaders/GBufferCommon.hlsl @@ -14,7 +14,6 @@ struct GBufferSample float Metalness; float3 Color; float Specular; - // View space position of pixel, DIFFERENT FROM GBufferData.ViewPos float3 ViewPos; float AO; int ShadingModel; diff --git a/Source/Shaders/ReflectionsCommon.hlsl b/Source/Shaders/ReflectionsCommon.hlsl index f571abc47..0af6e39c1 100644 --- a/Source/Shaders/ReflectionsCommon.hlsl +++ b/Source/Shaders/ReflectionsCommon.hlsl @@ -5,6 +5,9 @@ #include "./Flax/GBufferCommon.hlsl" +// Hit depth (view space) threshold to detect if sky was hit (value above it where 1.0f is default) +#define REFLECTIONS_HIT_THRESHOLD 0.9f + float GetSpecularOcclusion(float NoV, float roughnessSq, float ao) { return saturate(pow(NoV + ao, roughnessSq) - 1 + ao); diff --git a/Source/Shaders/SSR.shader b/Source/Shaders/SSR.shader index 3aa3cbc60..a9cdbe57d 100644 --- a/Source/Shaders/SSR.shader +++ b/Source/Shaders/SSR.shader @@ -129,13 +129,12 @@ float4 PS_RayTracePass(Quad_VS2PS input) : SV_Target0 float mip = clamp(log2(intersectionCircleRadius * TraceSizeMax), 0.0, MaxColorMiplevel); float3 sampleColor = Texture0.SampleLevel(SamplerLinearClamp, screenHit.xy, mip).rgb; result = float4(sampleColor, screenHit.z); - if (screenHit.z >= 0.9f) + if (screenHit.z >= REFLECTIONS_HIT_THRESHOLD) return result; } // Fallback to Global SDF and Global Surface Atlas tracing #if USE_GLOBAL_SURFACE_ATLAS && CAN_USE_GLOBAL_SURFACE_ATLAS - // Calculate reflection direction (the same TraceScreenSpaceReflection) float3 reflectWS = ScreenSpaceReflectionDirection(input.TexCoord, gBuffer, gBufferData.ViewPos, TemporalEffect, TemporalTime, BRDFBias); @@ -149,9 +148,7 @@ float4 PS_RayTracePass(Quad_VS2PS input) : SV_Target0 float3 hitPosition = sdfHit.GetHitPosition(sdfTrace); float surfaceThreshold = GetGlobalSurfaceAtlasThreshold(GlobalSDF, sdfHit); float4 surfaceAtlas = SampleGlobalSurfaceAtlas(GlobalSurfaceAtlas, GlobalSurfaceAtlasChunks, RWGlobalSurfaceAtlasCulledObjects, GlobalSurfaceAtlasObjects, GlobalSurfaceAtlasDepth, GlobalSurfaceAtlasTex, hitPosition, -reflectWS, surfaceThreshold); - // Now the sdf reflection part is significantly darker than the screen space part - // TODO: Maybe multiply surfaceAtlas by a constant to make it brighter, adding 2* looks fine - result = lerp(surfaceAtlas, float4(result.rgb, 1), result.a); + result = lerp(surfaceAtlas, float4(result.rgb, 1), result.a); } #endif