Skip to content

Commit 9fe6f5f

Browse files
RoseHirigoyenEvergreen
authored andcommitted
UUM-69940 URP NRP RG uses more GPU bandwidth than URP non-RG NRP
JIRA: [UUM-69940](https://jira.unity3d.com/browse/UUM-69940) ## Changes: It was determined that URP NRP RG uses more GPU bandwidth than URP non-RG NRP (see JIRA task for documentation + results), which is a bug. This PR removes the gBuffer as a default global, which should reduce the bandwidth usage and is a step towards preventing the resource and texture properties to be out of sync, which is another bug. Considering that this is a breaking change for some users, we also add a sample to show how to re-enable the gBuffer if needed. The main changes are that we use builder.UseTexture(gBuffer[i]) rather than builder.UseAllGlobalTextures(true) to reference the gBuffer in a pass. This means that we need to call material.SetTexture() in passes that use the gBuffer because it cannot be accessed from the globals anymore. Some tests were modified as well to use the non-global gBuffer ## Sample: The sample is a ScriptableRendererFeature that can be added to the rendering asset that will display the contents of the gBuffer and set the gBuffer components as globals after the pass using the builder.SetGlobalTextureAfterPass method. It aims to show (1) how to use the gBuffer as a non-global in a pass and (2) how to set the gBuffer as global (and which names are used internally by URP)
1 parent 2930f0d commit 9fe6f5f

23 files changed

+698
-72
lines changed

Packages/com.unity.render-pipelines.universal/Runtime/2D/Rendergraph/Renderer2DRendergraph.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -624,7 +624,7 @@ private void OnAfterRendering(RenderGraph renderGraph)
624624
if (requireFinalPostProcessPass)
625625
postProcessPass.RenderFinalPassRenderGraph(renderGraph, frameData, in finalColorHandle, commonResourceData.overlayUITexture, in finalBlitTarget, needsColorEncoding);
626626
else
627-
m_FinalBlitPass.Render(renderGraph, cameraData, finalColorHandle, finalBlitTarget, commonResourceData.overlayUITexture);
627+
m_FinalBlitPass.Render(renderGraph, frameData, cameraData, finalColorHandle, finalBlitTarget, commonResourceData.overlayUITexture);
628628

629629
finalColorHandle = finalBlitTarget;
630630
}

Packages/com.unity.render-pipelines.universal/Runtime/DeferredLights.cs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -623,6 +623,15 @@ internal void ExecuteDeferredPass(RasterCommandBuffer cmd, UniversalCameraData c
623623
// which prevents from resolving correct pass indices.
624624
if (m_StencilDeferredPasses[0] < 0)
625625
InitStencilDeferredMaterial();
626+
627+
if (!UseFramebufferFetch)
628+
{
629+
for (int i = 0; i < GbufferTextureHandles.Length; i++)
630+
{
631+
if (i != GBufferLightingIndex)
632+
m_StencilDeferredMaterial.SetTexture(k_GBufferShaderPropertyIDs[i], GbufferTextureHandles[i]);
633+
}
634+
}
626635

627636
using (new ProfilingScope(cmd, m_ProfilingDeferredPass))
628637
{

Packages/com.unity.render-pipelines.universal/Runtime/Passes/DeferredPass.cs

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -112,10 +112,6 @@ internal void Render(RenderGraph renderGraph, ContextContainer frameData, Textur
112112
}
113113
}
114114

115-
// Without NRP GBuffer textures are set after GBuffer, we only do this here to avoid breaking the pass
116-
if (renderGraph.nativeRenderPassesEnabled)
117-
GBufferPass.SetGlobalGBufferTextures(builder, gbuffer, ref m_DeferredLights);
118-
119115
builder.AllowPassCulling(false);
120116
builder.AllowGlobalStateModification(true);
121117

Packages/com.unity.render-pipelines.universal/Runtime/Passes/DrawScreenSpaceUIPass.cs

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -224,14 +224,6 @@ internal void RenderOverlay(RenderGraph renderGraph, ContextContainer frameData,
224224
// Render uGUI and UIToolkit overlays
225225
using (var builder = renderGraph.AddRasterRenderPass<PassData>("Screen Space UIToolkit/uGUI Pass - Overlay", out var passData, base.profilingSampler))
226226
{
227-
if (cameraData.requiresDepthTexture && renderer != null)
228-
{
229-
if (renderer.renderingModeActual != RenderingMode.Deferred)
230-
builder.UseGlobalTexture(s_CameraDepthTextureID);
231-
else if (renderer.deferredLights.GbufferDepthIndex != -1)
232-
builder.UseGlobalTexture(DeferredLights.k_GBufferShaderPropertyIDs[renderer.deferredLights.GbufferDepthIndex]);
233-
}
234-
235227
if (cameraData.requiresOpaqueTexture && renderer != null)
236228
builder.UseGlobalTexture(s_CameraOpaqueTextureID);
237229

Packages/com.unity.render-pipelines.universal/Runtime/Passes/DrawSkyboxPass.cs

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -123,6 +123,8 @@ private class PassData
123123
{
124124
internal XRPass xr;
125125
internal RendererListHandle skyRendererListHandle;
126+
internal TextureHandle cameraDepthTexture;
127+
internal Material material;
126128
}
127129

128130
private void InitPassData(ref PassData passData, in XRPass xr, in RendererListHandle handle)
@@ -131,7 +133,7 @@ private void InitPassData(ref PassData passData, in XRPass xr, in RendererListHa
131133
passData.skyRendererListHandle = handle;
132134
}
133135

134-
internal void Render(RenderGraph renderGraph, ContextContainer frameData, ScriptableRenderContext context, TextureHandle colorTarget, TextureHandle depthTarget, bool hasDepthCopy = false)
136+
internal void Render(RenderGraph renderGraph, ContextContainer frameData, ScriptableRenderContext context, TextureHandle colorTarget, TextureHandle depthTarget, Material skyboxMaterial, bool hasDepthCopy = false)
135137
{
136138
UniversalCameraData cameraData = frameData.Get<UniversalCameraData>();
137139
UniversalResourceData resourceData = frameData.Get<UniversalResourceData>();
@@ -152,6 +154,7 @@ internal void Render(RenderGraph renderGraph, ContextContainer frameData, Script
152154
{
153155
var skyRendererListHandle = CreateSkyBoxRendererList(renderGraph, cameraData);
154156
InitPassData(ref passData, cameraData.xr, skyRendererListHandle);
157+
passData.material = skyboxMaterial;
155158
builder.UseRendererList(skyRendererListHandle);
156159
builder.SetRenderAttachment(colorTarget, 0, AccessFlags.Write);
157160
builder.SetRenderAttachmentDepth(depthTarget, AccessFlags.Write);
@@ -160,9 +163,16 @@ internal void Render(RenderGraph renderGraph, ContextContainer frameData, Script
160163
if (hasDepthCopy && resourceData.cameraDepthTexture.IsValid())
161164
{
162165
if (renderer.renderingModeActual != RenderingMode.Deferred)
166+
{
163167
builder.UseGlobalTexture(s_CameraDepthTextureID);
168+
passData.cameraDepthTexture = resourceData.cameraDepthTexture;
169+
}
170+
164171
else if (renderer.deferredLights.GbufferDepthIndex != -1)
165-
builder.UseGlobalTexture(DeferredLights.k_GBufferShaderPropertyIDs[renderer.deferredLights.GbufferDepthIndex]);
172+
{
173+
builder.UseTexture(resourceData.gBuffer[renderer.deferredLights.GbufferDepthIndex]);
174+
passData.cameraDepthTexture = resourceData.gBuffer[renderer.deferredLights.GbufferDepthIndex];
175+
}
166176
}
167177

168178
builder.AllowPassCulling(false);
@@ -174,6 +184,8 @@ internal void Render(RenderGraph renderGraph, ContextContainer frameData, Script
174184

175185
builder.SetRenderFunc((PassData data, RasterGraphContext context) =>
176186
{
187+
if(data.cameraDepthTexture.IsValid())
188+
data.material.SetTexture(s_CameraDepthTextureID, data.cameraDepthTexture);
177189
ExecutePass(context.cmd, data.xr, data.skyRendererListHandle);
178190
});
179191
}

Packages/com.unity.render-pipelines.universal/Runtime/Passes/FinalBlitPass.cs

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -243,6 +243,7 @@ private class PassData
243243
{
244244
internal TextureHandle source;
245245
internal TextureHandle destination;
246+
internal TextureHandle depthTexture;
246247
internal int sourceID;
247248
internal Vector4 hdrOutputLuminanceParams;
248249
internal bool requireSrgbConversion;
@@ -264,17 +265,26 @@ private void InitPassData(UniversalCameraData cameraData, ref PassData passData,
264265
passData.blitMaterialData = m_BlitMaterialData[(int)blitType];
265266
}
266267

267-
internal void Render(RenderGraph renderGraph, UniversalCameraData cameraData, in TextureHandle src, in TextureHandle dest, TextureHandle overlayUITexture)
268+
internal void Render(RenderGraph renderGraph, ContextContainer frameData, UniversalCameraData cameraData, in TextureHandle src, in TextureHandle dest, TextureHandle overlayUITexture)
268269
{
269270
using (var builder = renderGraph.AddRasterRenderPass<PassData>("Final Blit", out var passData, base.profilingSampler))
270271
{
272+
UniversalResourceData resourceData = frameData.Get<UniversalResourceData>();
271273
UniversalRenderer renderer = cameraData.renderer as UniversalRenderer;
274+
272275
if (cameraData.requiresDepthTexture && renderer != null)
273276
{
274277
if (renderer.renderingModeActual != RenderingMode.Deferred)
278+
{
275279
builder.UseGlobalTexture(s_CameraDepthTextureID);
280+
passData.depthTexture = resourceData.activeDepthTexture;
281+
}
282+
276283
else if (renderer.deferredLights.GbufferDepthIndex != -1)
277-
builder.UseGlobalTexture(DeferredLights.k_GBufferShaderPropertyIDs[renderer.deferredLights.GbufferDepthIndex]);
284+
{
285+
builder.UseTexture(resourceData.gBuffer[renderer.deferredLights.GbufferDepthIndex]);
286+
passData.depthTexture = resourceData.gBuffer[renderer.deferredLights.GbufferDepthIndex];
287+
}
278288
}
279289

280290
bool outputsToHDR = cameraData.isHDROutputActive;
@@ -315,6 +325,9 @@ internal void Render(RenderGraph renderGraph, UniversalCameraData cameraData, in
315325
context.cmd.SetKeyword(ShaderGlobalKeywords.LinearToSRGBConversion, data.requireSrgbConversion);
316326
data.blitMaterialData.material.SetTexture(data.sourceID, data.source);
317327

328+
if(data.depthTexture.IsValid())
329+
data.blitMaterialData.material.SetTexture(s_CameraDepthTextureID, data.depthTexture);
330+
318331
DebugHandler debugHandler = GetActiveDebugHandler(data.cameraData);
319332
bool resolveToDebugScreen = debugHandler != null && debugHandler.WriteToDebugScreenTexture(data.cameraData.resolveFinalTarget);
320333

Packages/com.unity.render-pipelines.universal/Runtime/Passes/GBufferPass.cs

Lines changed: 0 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -273,10 +273,6 @@ internal void Render(RenderGraph renderGraph, ContextContainer frameData, Textur
273273
builder.UseRendererList(passData.rendererListHdl);
274274
builder.UseRendererList(passData.objectsWithErrorRendererListHdl);
275275

276-
// With NRP GBuffer textures are set after Deferred, we do this to avoid breaking the pass
277-
if (!renderGraph.nativeRenderPassesEnabled)
278-
GBufferPass.SetGlobalGBufferTextures(builder, gbuffer, ref m_DeferredLights);
279-
280276
builder.AllowPassCulling(false);
281277
builder.AllowGlobalStateModification(true);
282278

@@ -286,25 +282,5 @@ internal void Render(RenderGraph renderGraph, ContextContainer frameData, Textur
286282
});
287283
}
288284
}
289-
290-
internal static void SetGlobalGBufferTextures(IRasterRenderGraphBuilder builder, TextureHandle[] gbuffer, ref DeferredLights deferredLights)
291-
{
292-
for (int i = 0; i < gbuffer.Length; i++)
293-
{
294-
if (i != deferredLights.GBufferLightingIndex && gbuffer[i].IsValid())
295-
builder.SetGlobalTextureAfterPass(gbuffer[i], Shader.PropertyToID(DeferredLights.k_GBufferNames[i]));
296-
}
297-
298-
// If any sub-system needs camera normal texture, make it available.
299-
// Input attachments will only be used when this is not needed so safe to skip in that case
300-
if (gbuffer[deferredLights.GBufferNormalSmoothnessIndex].IsValid())
301-
builder.SetGlobalTextureAfterPass(gbuffer[deferredLights.GBufferNormalSmoothnessIndex], s_CameraNormalsTextureID);
302-
303-
if (deferredLights.UseRenderingLayers && gbuffer[deferredLights.GBufferRenderingLayers].IsValid())
304-
{
305-
builder.SetGlobalTextureAfterPass(gbuffer[deferredLights.GBufferRenderingLayers], Shader.PropertyToID(DeferredLights.k_GBufferNames[deferredLights.GBufferRenderingLayers]));
306-
builder.SetGlobalTextureAfterPass(gbuffer[deferredLights.GBufferRenderingLayers], Shader.PropertyToID("_CameraRenderingLayersTexture"));
307-
}
308-
}
309285
}
310286
}

Packages/com.unity.render-pipelines.universal/Runtime/Passes/PostProcessPassRenderGraph.cs

Lines changed: 14 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -637,12 +637,6 @@ public void RenderDoFGaussian(RenderGraph renderGraph, UniversalResourceData res
637637
builder.UseTexture(resourceData.cameraDepthTexture, AccessFlags.Read);
638638
passData.material = m_Materials.gaussianDepthOfFieldCoC;
639639

640-
UniversalRenderer renderer = cameraData.renderer as UniversalRenderer;
641-
if (renderer.renderingModeActual != RenderingMode.Deferred)
642-
builder.UseGlobalTexture(s_CameraDepthTextureID);
643-
else if (renderer.deferredLights.GbufferDepthIndex != -1)
644-
builder.UseGlobalTexture(DeferredLights.k_GBufferShaderPropertyIDs[renderer.deferredLights.GbufferDepthIndex]);
645-
646640
builder.SetRenderFunc(static (DoFGaussianPassData data, RasterGraphContext context) =>
647641
{
648642
var dofmaterial = data.material;
@@ -856,12 +850,6 @@ public void RenderDoFBokeh(RenderGraph renderGraph, UniversalResourceData resour
856850
builder.UseTexture(resourceData.cameraDepthTexture, AccessFlags.Read);
857851
passData.material = m_Materials.bokehDepthOfFieldCoC;
858852

859-
UniversalRenderer renderer = cameraData.renderer as UniversalRenderer;
860-
if (renderer.renderingModeActual != RenderingMode.Deferred)
861-
builder.UseGlobalTexture(s_CameraDepthTextureID);
862-
else if (renderer.deferredLights.GbufferDepthIndex != -1)
863-
builder.UseGlobalTexture(DeferredLights.k_GBufferShaderPropertyIDs[renderer.deferredLights.GbufferDepthIndex]);
864-
865853
builder.SetRenderFunc(static (DoFBokehPassData data, RasterGraphContext context) =>
866854
{
867855
var dofmaterial = data.material;
@@ -1885,6 +1873,7 @@ private class UberPostPassData
18851873
internal TextureHandle destinationTexture;
18861874
internal TextureHandle sourceTexture;
18871875
internal TextureHandle lutTexture;
1876+
internal TextureHandle depthTexture;
18881877
internal Vector4 lutParams;
18891878
internal TextureHandle userLutTexture;
18901879
internal Vector4 userLutParams;
@@ -1896,7 +1885,7 @@ private class UberPostPassData
18961885
internal bool enableAlphaOutput;
18971886
}
18981887

1899-
public void RenderUberPost(RenderGraph renderGraph, UniversalCameraData cameraData, UniversalPostProcessingData postProcessingData, in TextureHandle sourceTexture, in TextureHandle destTexture, in TextureHandle lutTexture, in TextureHandle overlayUITexture, bool requireHDROutput, bool enableAlphaOutput, bool resolveToDebugScreen)
1888+
public void RenderUberPost(RenderGraph renderGraph, ContextContainer frameData, UniversalCameraData cameraData, UniversalPostProcessingData postProcessingData, in TextureHandle sourceTexture, in TextureHandle destTexture, in TextureHandle lutTexture, in TextureHandle overlayUITexture, bool requireHDROutput, bool enableAlphaOutput, bool resolveToDebugScreen)
19001889
{
19011890
var material = m_Materials.uber;
19021891
bool hdrGrading = postProcessingData.gradingMode == ColorGradingMode.HighDynamicRange;
@@ -1919,12 +1908,20 @@ public void RenderUberPost(RenderGraph renderGraph, UniversalCameraData cameraDa
19191908
using (var builder = renderGraph.AddRasterRenderPass<UberPostPassData>("Postprocessing Uber Post Pass", out var passData, ProfilingSampler.Get(URPProfileId.RG_UberPost)))
19201909
{
19211910
UniversalRenderer renderer = cameraData.renderer as UniversalRenderer;
1911+
UniversalResourceData resourceData = frameData.Get<UniversalResourceData>();
1912+
19221913
if (cameraData.requiresDepthTexture && renderer != null)
19231914
{
19241915
if (renderer.renderingModeActual != RenderingMode.Deferred)
1916+
{
19251917
builder.UseGlobalTexture(s_CameraDepthTextureID);
1918+
passData.depthTexture = resourceData.activeDepthTexture;
1919+
}
19261920
else if (renderer.deferredLights.GbufferDepthIndex != -1)
1927-
builder.UseGlobalTexture(DeferredLights.k_GBufferShaderPropertyIDs[renderer.deferredLights.GbufferDepthIndex]);
1921+
{
1922+
builder.UseTexture(resourceData.gBuffer[renderer.deferredLights.GbufferDepthIndex]);
1923+
passData.depthTexture = resourceData.gBuffer[renderer.deferredLights.GbufferDepthIndex];
1924+
}
19281925
}
19291926

19301927
if (cameraData.requiresOpaqueTexture && renderer != null)
@@ -1963,6 +1960,8 @@ public void RenderUberPost(RenderGraph renderGraph, UniversalCameraData cameraDa
19631960
var material = data.material;
19641961
RTHandle sourceTextureHdl = data.sourceTexture;
19651962

1963+
if(data.depthTexture.IsValid())
1964+
material.SetTexture(s_CameraDepthTextureID, data.depthTexture);
19661965
material.SetTexture(ShaderConstants._InternalLut, data.lutTexture);
19671966
material.SetVector(ShaderConstants._Lut_Params, data.lutParams);
19681967
material.SetTexture(ShaderConstants._UserLut, data.userLutTexture);
@@ -2177,7 +2176,7 @@ public void RenderPostProcessingRenderGraph(RenderGraph renderGraph, ContextCont
21772176
DebugHandler debugHandler = GetActiveDebugHandler(cameraData);
21782177
debugHandler?.UpdateShaderGlobalPropertiesForFinalValidationPass(renderGraph, cameraData, !m_HasFinalPass && !resolveToDebugScreen);
21792178

2180-
RenderUberPost(renderGraph, cameraData, postProcessingData, in currentSource, in postProcessingTarget, in lutTexture, in overlayUITexture, requireHDROutput, enableAlphaOutput, resolveToDebugScreen);
2179+
RenderUberPost(renderGraph, frameData, cameraData, postProcessingData, in currentSource, in postProcessingTarget, in lutTexture, in overlayUITexture, requireHDROutput, enableAlphaOutput, resolveToDebugScreen);
21812180
}
21822181
}
21832182
}

Packages/com.unity.render-pipelines.universal/Runtime/ScriptableRendererFeature.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ internal virtual bool SupportsNativeRenderPass()
7171
/// Override this method and return true that renderer would produce rendering layers texture.
7272
/// </summary>
7373
/// <param name="isDeferred">True if renderer is using deferred rendering mode</param>
74-
/// <param name="isDeferred">True if renderer has Accurate G-Buffer Normals enabled</param>
74+
/// <param name="needsGBufferAccurateNormals">True if renderer has Accurate G-Buffer Normals enabled</param>
7575
/// <param name="atEvent">Requeted event at which rendering layers texture will be produced</param>
7676
/// <param name="maskSize">Requested bit size of rendering layers texture</param>
7777
/// <returns></returns>

0 commit comments

Comments
 (0)