public bool RenderIndirectDiffuse(HDCamera hdCamera, CommandBuffer cmd, ScriptableRenderContext renderContext, int frameCount) { // Bind the indirect diffuse texture BindIndirectDiffuseTexture(cmd); // First thing to check is: Do we have a valid ray-tracing environment? HDRaytracingEnvironment rtEnvironment = m_RaytracingManager.CurrentEnvironment(); RayTracingShader indirectDiffuseShader = m_PipelineAsset.renderPipelineRayTracingResources.indirectDiffuseRaytracing; ComputeShader indirectDiffuseAccumulation = m_PipelineAsset.renderPipelineRayTracingResources.indirectDiffuseAccumulation; var settings = VolumeManager.instance.stack.GetComponent <GlobalIllumination>(); var lightClusterSettings = VolumeManager.instance.stack.GetComponent <LightCluster>(); bool invalidState = rtEnvironment == null || !settings.enableRayTracing.value || indirectDiffuseShader == null || indirectDiffuseAccumulation == null || m_PipelineResources.textures.owenScrambledTex == null || m_PipelineResources.textures.scramblingTex == null; // If no acceleration structure available, end it now if (invalidState) { return(false); } // Grab the acceleration structures and the light cluster to use RayTracingAccelerationStructure accelerationStructure = m_RaytracingManager.RequestAccelerationStructure(rtEnvironment.indirectDiffuseLayerMask); HDRaytracingLightCluster lightCluster = m_RaytracingManager.RequestLightCluster(rtEnvironment.indirectDiffuseLayerMask); // Compute the actual resolution that is needed base on the quality string targetRayGen = m_RayGenIndirectDiffuseName; // Define the shader pass to use for the indirect diffuse pass cmd.SetRayTracingShaderPass(indirectDiffuseShader, "IndirectDXR"); // Set the acceleration structure for the pass cmd.SetRayTracingAccelerationStructure(indirectDiffuseShader, HDShaderIDs._RaytracingAccelerationStructureName, accelerationStructure); // Inject the ray-tracing sampling data cmd.SetRayTracingTextureParam(indirectDiffuseShader, HDShaderIDs._OwenScrambledTexture, m_PipelineResources.textures.owenScrambledTex); cmd.SetRayTracingTextureParam(indirectDiffuseShader, HDShaderIDs._ScramblingTexture, m_PipelineResources.textures.scramblingTex); // Inject the ray generation data cmd.SetGlobalFloat(HDShaderIDs._RaytracingRayBias, rtEnvironment.rayBias); cmd.SetGlobalFloat(HDShaderIDs._RaytracingRayMaxLength, settings.rayLength.value); cmd.SetRayTracingIntParams(indirectDiffuseShader, HDShaderIDs._RaytracingNumSamples, settings.numSamples.value); int frameIndex = hdCamera.IsTAAEnabled() ? hdCamera.taaFrameIndex : (int)frameCount % 8; cmd.SetGlobalInt(HDShaderIDs._RaytracingFrameIndex, frameIndex); // Set the data for the ray generation cmd.SetRayTracingTextureParam(indirectDiffuseShader, HDShaderIDs._IndirectDiffuseTextureRW, m_IndirectDiffuseTexture); cmd.SetRayTracingTextureParam(indirectDiffuseShader, HDShaderIDs._DepthTexture, m_SharedRTManager.GetDepthStencilBuffer()); cmd.SetRayTracingTextureParam(indirectDiffuseShader, HDShaderIDs._NormalBufferTexture, m_SharedRTManager.GetNormalBuffer()); // Set the indirect diffuse parameters cmd.SetRayTracingFloatParams(indirectDiffuseShader, HDShaderIDs._RaytracingIntensityClamp, settings.clampValue.value); // Set ray count texture cmd.SetRayTracingIntParam(indirectDiffuseShader, HDShaderIDs._RayCountEnabled, m_RaytracingManager.rayCountManager.RayCountIsEnabled()); cmd.SetRayTracingTextureParam(indirectDiffuseShader, HDShaderIDs._RayCountTexture, m_RaytracingManager.rayCountManager.rayCountTexture); // Compute the pixel spread value float pixelSpreadAngle = Mathf.Atan(2.0f * Mathf.Tan(hdCamera.camera.fieldOfView * Mathf.PI / 360.0f) / Mathf.Min(hdCamera.actualWidth, hdCamera.actualHeight)); cmd.SetRayTracingFloatParam(indirectDiffuseShader, HDShaderIDs._RaytracingPixelSpreadAngle, pixelSpreadAngle); // LightLoop data cmd.SetGlobalBuffer(HDShaderIDs._RaytracingLightCluster, lightCluster.GetCluster()); cmd.SetGlobalBuffer(HDShaderIDs._LightDatasRT, lightCluster.GetLightDatas()); cmd.SetGlobalVector(HDShaderIDs._MinClusterPos, lightCluster.GetMinClusterPos()); cmd.SetGlobalVector(HDShaderIDs._MaxClusterPos, lightCluster.GetMaxClusterPos()); cmd.SetGlobalInt(HDShaderIDs._LightPerCellCount, lightClusterSettings.maxNumLightsPercell.value); cmd.SetGlobalInt(HDShaderIDs._PunctualLightCountRT, lightCluster.GetPunctualLightCount()); cmd.SetGlobalInt(HDShaderIDs._AreaLightCountRT, lightCluster.GetAreaLightCount()); // Set the data for the ray miss cmd.SetRayTracingTextureParam(indirectDiffuseShader, HDShaderIDs._SkyTexture, m_SkyManager.skyReflection); // Compute the actual resolution that is needed base on the quality int widthResolution = hdCamera.actualWidth; int heightResolution = hdCamera.actualHeight; // Run the computation CoreUtils.SetKeyword(cmd, "DIFFUSE_LIGHTING_ONLY", true); cmd.DispatchRays(indirectDiffuseShader, targetRayGen, (uint)widthResolution, (uint)heightResolution, 1); CoreUtils.SetKeyword(cmd, "DIFFUSE_LIGHTING_ONLY", false); if (settings.enableFilter.value) { // Grab the history buffer RTHandleSystem.RTHandle indirectDiffuseHistory = hdCamera.GetCurrentFrameRT((int)HDCameraFrameHistoryType.RaytracedIndirectDiffuse) ?? hdCamera.AllocHistoryFrameRT((int)HDCameraFrameHistoryType.RaytracedIndirectDiffuse, IndirectDiffuseHistoryBufferAllocatorFunction, 1); HDSimpleDenoiser simpleDenoiser = m_RaytracingManager.GetSimpleDenoiser(); simpleDenoiser.DenoiseBuffer(cmd, hdCamera, m_IndirectDiffuseTexture, indirectDiffuseHistory, m_DenoiseBuffer0, settings.filterRadius.value, singleChannel: false); HDUtils.BlitCameraTexture(cmd, m_DenoiseBuffer0, m_IndirectDiffuseTexture); } // If we are in deferred mode, we need to make sure to add the indirect diffuse (that we intentionally ignored during the GBuffer pass) // Note that this discards the texture/object ambient occlusion. But we consider that okay given that the ray traced indirect diffuse // is a physically correct evaluation of that quantity if (hdCamera.frameSettings.litShaderMode == LitShaderMode.Deferred) { int indirectDiffuseKernel = indirectDiffuseAccumulation.FindKernel("IndirectDiffuseAccumulation"); // Bind the source texture cmd.SetComputeTextureParam(indirectDiffuseAccumulation, indirectDiffuseKernel, HDShaderIDs._IndirectDiffuseTexture, m_IndirectDiffuseTexture); // Bind the output texture cmd.SetComputeTextureParam(indirectDiffuseAccumulation, indirectDiffuseKernel, HDShaderIDs._GBufferTexture[0], m_GBufferManager.GetBuffer(0)); cmd.SetComputeTextureParam(indirectDiffuseAccumulation, indirectDiffuseKernel, HDShaderIDs._GBufferTexture[3], m_GBufferManager.GetBuffer(3)); // Evaluate the dispatch parameters int areaTileSize = 8; int numTilesX = (widthResolution + (areaTileSize - 1)) / areaTileSize; int numTilesY = (heightResolution + (areaTileSize - 1)) / areaTileSize; // Add the indirect diffuse to the GBuffer cmd.DispatchCompute(indirectDiffuseAccumulation, indirectDiffuseKernel, numTilesX, numTilesY, 1); } (RenderPipelineManager.currentPipeline as HDRenderPipeline).PushFullScreenDebugTexture(hdCamera, cmd, m_IndirectDiffuseTexture, FullScreenDebugMode.IndirectDiffuse); return(true); }
public void RenderAO(HDCamera hdCamera, CommandBuffer cmd, RTHandleSystem.RTHandle outputTexture, ScriptableRenderContext renderContext, int frameCount) { // Let's check all the resources HDRaytracingEnvironment rtEnvironment = m_RaytracingManager.CurrentEnvironment(); RayTracingShader aoShader = m_PipelineRayTracingResources.aoRaytracing; var aoSettings = VolumeManager.instance.stack.GetComponent <AmbientOcclusion>(); // Check if the state is valid for evaluating ambient occlusion bool invalidState = rtEnvironment == null || aoShader == null || m_PipelineResources.textures.owenScrambledTex == null || m_PipelineResources.textures.scramblingTex == null; // If any of the previous requirements is missing, the effect is not requested or no acceleration structure, set the default one and leave right away if (invalidState) { SetDefaultAmbientOcclusionTexture(cmd); return; } // Grab the acceleration structure for the target camera RayTracingAccelerationStructure accelerationStructure = m_RaytracingManager.RequestAccelerationStructure(rtEnvironment.aoLayerMask); // Define the shader pass to use for the reflection pass cmd.SetRayTracingShaderPass(aoShader, "VisibilityDXR"); // Set the acceleration structure for the pass cmd.SetRayTracingAccelerationStructure(aoShader, HDShaderIDs._RaytracingAccelerationStructureName, accelerationStructure); // Inject the ray-tracing sampling data cmd.SetRayTracingTextureParam(aoShader, HDShaderIDs._OwenScrambledTexture, m_PipelineResources.textures.owenScrambledTex); cmd.SetRayTracingTextureParam(aoShader, HDShaderIDs._ScramblingTexture, m_PipelineResources.textures.scramblingTex); // Inject the ray generation data cmd.SetRayTracingFloatParams(aoShader, HDShaderIDs._RaytracingRayBias, rtEnvironment.rayBias); cmd.SetRayTracingFloatParams(aoShader, HDShaderIDs._RaytracingRayMaxLength, aoSettings.rayLength.value); cmd.SetRayTracingIntParams(aoShader, HDShaderIDs._RaytracingNumSamples, aoSettings.numSamples.value); // Set the data for the ray generation cmd.SetRayTracingTextureParam(aoShader, HDShaderIDs._DepthTexture, m_SharedRTManager.GetDepthStencilBuffer()); cmd.SetRayTracingTextureParam(aoShader, HDShaderIDs._NormalBufferTexture, m_SharedRTManager.GetNormalBuffer()); int frameIndex = hdCamera.IsTAAEnabled() ? hdCamera.taaFrameIndex : (int)frameCount % 8; cmd.SetGlobalInt(HDShaderIDs._RaytracingFrameIndex, frameIndex); // Value used to scale the ao intensity cmd.SetRayTracingFloatParam(aoShader, HDShaderIDs._RaytracingAOIntensity, aoSettings.intensity.value); cmd.SetRayTracingIntParam(aoShader, HDShaderIDs._RayCountEnabled, m_RaytracingManager.rayCountManager.RayCountIsEnabled()); cmd.SetRayTracingTextureParam(aoShader, HDShaderIDs._RayCountTexture, m_RaytracingManager.rayCountManager.rayCountTexture); // Set the output textures cmd.SetRayTracingTextureParam(aoShader, HDShaderIDs._AmbientOcclusionTextureRW, m_IntermediateBuffer); cmd.SetRayTracingTextureParam(aoShader, HDShaderIDs._RaytracingVSNormalTexture, m_ViewSpaceNormalBuffer); // Run the computation cmd.DispatchRays(aoShader, m_RayGenShaderName, (uint)hdCamera.actualWidth, (uint)hdCamera.actualHeight, 1); using (new ProfilingSample(cmd, "Filter Reflection", CustomSamplerId.RaytracingAmbientOcclusion.GetSampler())) { if (aoSettings.enableFilter.value) { // Grab the history buffer RTHandleSystem.RTHandle ambientOcclusionHistory = hdCamera.GetCurrentFrameRT((int)HDCameraFrameHistoryType.RaytracedAmbientOcclusion) ?? hdCamera.AllocHistoryFrameRT((int)HDCameraFrameHistoryType.RaytracedAmbientOcclusion, AmbientOcclusionHistoryBufferAllocatorFunction, 1); // Apply the simple denoiser HDSimpleDenoiser simpleDenoiser = m_RaytracingManager.GetSimpleDenoiser(); simpleDenoiser.DenoiseBuffer(cmd, hdCamera, m_IntermediateBuffer, ambientOcclusionHistory, outputTexture, aoSettings.filterRadius.value); } else { HDUtils.BlitCameraTexture(cmd, m_IntermediateBuffer, outputTexture); } } // Bind the textures and the params cmd.SetGlobalTexture(HDShaderIDs._AmbientOcclusionTexture, outputTexture); cmd.SetGlobalVector(HDShaderIDs._AmbientOcclusionParam, new Vector4(0f, 0f, 0f, VolumeManager.instance.stack.GetComponent <AmbientOcclusion>().directLightingStrength.value)); // TODO: All the push-debug stuff should be centralized somewhere (RenderPipelineManager.currentPipeline as HDRenderPipeline).PushFullScreenDebugTexture(hdCamera, cmd, outputTexture, FullScreenDebugMode.SSAO); }