Browse Source

Move decals to its own pass

Panagiotis Christopoulos Charitos 7 years ago
parent
commit
aaad5caa4f

+ 88 - 3
programs/GBufferPost.ankiprog

@@ -9,8 +9,6 @@ http://www.anki3d.org/LICENSE
 		<input name="CLUSTER_COUNT_X" type="uint" const="1"/>
 		<input name="CLUSTER_COUNT_Y" type="uint" const="1"/>
 		<input name="CLUSTER_COUNT_Z" type="uint" const="1"/>
-		<input name="CLUSTER_COUNT" type="uint" const="1"/>
-		<input name="IR_MIPMAP_COUNT" type="uint" const="1"/>
 	</inputs>
 
 	<shaders>
@@ -39,12 +37,99 @@ void main()
 
 		<shader type="frag">
 			<source><![CDATA[
+#include "shaders/Pack.glsl"
+#include "shaders/Clusterer.glsl"
+#include "shaders/Functions.glsl"
 
-// TODO
+#define LIGHT_SET 0
+#define LIGHT_SS_BINDING 0
+#define LIGHT_UBO_BINDING 0
+#define LIGHT_TEX_BINDING 2
+#define LIGHT_DECALS
+#define LIGHT_COMMON_UNIS
+#include "shaders/ClusterLightCommon.glsl"
+
+layout(ANKI_TEX_BINDING(0, 0)) uniform sampler2D u_msDepthRt;
+layout(ANKI_TEX_BINDING(0, 1)) uniform sampler2D u_ssaoTex;
+
+layout(location = 0) in vec2 in_uv;
+layout(location = 1) in vec2 in_clusterIJ;
+
+layout(location = 0) out vec4 out_color0;
+layout(location = 1) out vec4 out_color1;
 
 void main()
 {
+	// This code blends the diffuse and the specular+rougness of the decals with GBuffer render targets.
+	// Normaly the blending is being done ('D' is the decal diffuse and 'f' is decal blend factor):
+	// d=gbuffer.diff
+	// 1st decal: d'=d*(1-f)+D*f
+	// 2nd decal: d''=d'*(1-f')+D'*f' <=> d''=d*(1-f)*(1-f')+D*f*(1-f')+D'*f'
+	// By looking at the trend we will have to multiply the gbuffer.diff with: (1-f)*(1-f') ... (1-f'''')
+
+	vec4 outDiffuse = vec4(0.0, 0.0, 0.0, 1.0);
+	vec4 outSpecular = vec4(0.0, 0.0, 0.0, 1.0);
+
+	// Sample SSAO
+	float ssao = textureLod(u_ssaoTex, in_uv, 0.0).r;
+	outDiffuse.a *= ssao;
+
+	// Get worldPos
+	float depth = textureLod(u_msDepthRt, in_uv, 0.0).r;
+	vec2 ndc = UV_TO_NDC(in_uv);
+	vec4 worldPos4 = u_invViewProjMat * vec4(ndc, depth, 1.0);
+	vec3 worldPos = worldPos4.xyz / worldPos4.w;
+
+	// Get first light index
+	uint idxOffset;
+	{
+		uint k = computeClusterK(u_clustererMagic, worldPos);
+		uint clusterIdx = 
+			k * (CLUSTER_COUNT_X * CLUSTER_COUNT_Y) + uint(in_clusterIJ.y) * CLUSTER_COUNT_X + uint(in_clusterIJ.x);
+
+		idxOffset = u_clusters[clusterIdx];
+	}
+
+	// Process decals
+	uint count = u_lightIndices[idxOffset++];
+	while(count-- != 0)
+	{
+		Decal decal = u_decals[u_lightIndices[idxOffset++]];
+
+		// Project pos to decal space
+		vec4 texCoords4 = decal.texProjectionMat * vec4(worldPos, 1.0);
+		if(texCoords4.w <= 0.7)
+		{
+			// Behind the decal, skip
+			continue;
+		}
+
+		vec2 texCoords2 = texCoords4.xy / texCoords4.w;
+
+		// Clamp the tex coords. Expect a border in the texture atlas
+		texCoords2 = saturate(texCoords2);
+	
+		// Read diffuse
+		vec2 diffUv = mad(texCoords2, decal.diffUv.zw, decal.diffUv.xy);
+		vec4 decalDiff = texture(u_diffDecalTex, diffUv);
+
+		// Read roughness
+		vec2 specUv = mad(texCoords2, decal.normRoughnessUv.zw, decal.normRoughnessUv.xy);
+		vec3 spec = texture(u_specularRoughnessDecalTex, specUv).rgb;
+
+		// Update diffuse
+		float f = decalDiff.a * decal.blendFactors[0];
+		outDiffuse.rgb = outDiffuse.rgb * (1.0 - f) + decalDiff.rgb * f;
+		outDiffuse.a *= (1.0 - f);
+
+		// Update specular
+		f = decalDiff.a * decal.blendFactors[1];
+		outSpecular.rgb = outSpecular.rgb * (1.0 - f) + spec.rgb * f;
+		outSpecular.a *= (1.0 - f);
+	}
 
+	out_color0 = outDiffuse;
+	out_color1 = outSpecular;
 }
 			]]></source>
 		</shader>

+ 7 - 38
programs/LightShading.ankiprog

@@ -46,19 +46,16 @@ void main()
 #define LIGHT_SET 0
 #define LIGHT_SS_BINDING 0
 #define LIGHT_UBO_BINDING 0
-#define LIGHT_TEX_BINDING 0
+#define LIGHT_TEX_BINDING 4
 #define LIGHT_LIGHTS
 #define LIGHT_INDIRECT
-#define LIGHT_DECALS
 #define LIGHT_COMMON_UNIS
 #include "shaders/ClusterLightCommon.glsl"
 
-layout(ANKI_TEX_BINDING(1, 0)) uniform sampler2D u_msRt0;
-layout(ANKI_TEX_BINDING(1, 1)) uniform sampler2D u_msRt1;
-layout(ANKI_TEX_BINDING(1, 2)) uniform sampler2D u_msRt2;
-layout(ANKI_TEX_BINDING(1, 3)) uniform sampler2D u_msDepthRt;
-
-layout(ANKI_TEX_BINDING(1, 4)) uniform sampler2D u_ssaoTex;
+layout(ANKI_TEX_BINDING(0, 0)) uniform sampler2D u_msRt0;
+layout(ANKI_TEX_BINDING(0, 1)) uniform sampler2D u_msRt1;
+layout(ANKI_TEX_BINDING(0, 2)) uniform sampler2D u_msRt2;
+layout(ANKI_TEX_BINDING(0, 3)) uniform sampler2D u_msDepthRt;
 
 layout(location = 0) in vec2 in_uv;
 layout(location = 1) in vec2 in_clusterIJ;
@@ -77,25 +74,6 @@ const float SUBSURFACE_MIN = 0.05;
 	float att = computeAttenuationFactor(light.posRadius.w, frag2Light); \
 	float lambert = nol;
 
-// Compute the colors of a decal.
-void appendDecalColors(in Decal decal, in vec3 worldPos, inout vec3 diffuseColor, inout float roughness)
-{
-	vec4 texCoords4 = decal.texProjectionMat * vec4(worldPos, 1.0);
-	vec2 texCoords2 = texCoords4.xy / texCoords4.w;
-
-	// Clamp the tex coords. Expect a border in the texture atlas
-	texCoords2 = saturate(texCoords2);
-
-	vec2 diffUv = mad(texCoords2, decal.diffUv.zw, decal.diffUv.xy);
-	vec4 dcol = texture(u_diffDecalTex, diffUv);
-	diffuseColor = mix(diffuseColor, dcol.rgb, dcol.a * decal.blendFactors[0]);
-
-	// Roughness
-	vec2 roughnessUv = mad(texCoords2, decal.normRoughnessUv.zw, decal.normRoughnessUv.xy);
-	float r = texture(u_normalRoughnessDecalTex, roughnessUv).w;
-	roughness = mix(roughness, r, dcol.a * decal.blendFactors[1]);
-}
-
 void readIndirect(uint idxOffset, vec3 pos, vec3 r, vec3 n, float lod, out vec3 specIndirect, out vec3 diffIndirect)
 {
 	specIndirect = vec3(0.0);
@@ -172,18 +150,9 @@ void main()
 		idxOffset = u_clusters[clusterIdx];
 	}
 
-	// Decals
+	// Skip decals
 	uint count = u_lightIndices[idxOffset++];
-	while(count-- != 0)
-	{
-		Decal decal = u_decals[u_lightIndices[idxOffset++]];
-
-		appendDecalColors(decal, worldPos, diffCol, roughness);
-	}
-
-	// Apply SSAO
-	float ssao = textureLod(u_ssaoTex, in_uv, 0.0).r;
-	diffCol *= ssao;
+	idxOffset += count;
 
 	// Ambient and emissive color
 	vec3 outC = diffCol * emission;

+ 1 - 1
shaders/ClusterLightCommon.glsl

@@ -158,7 +158,7 @@ layout(std140, row_major, ANKI_UBO_BINDING(LIGHT_SET, _NEXT_UBO_BINDING_3)) unif
 };
 
 layout(ANKI_TEX_BINDING(LIGHT_SET, _NEXT_TEX_BINDING_3 + 0)) uniform sampler2D u_diffDecalTex;
-layout(ANKI_TEX_BINDING(LIGHT_SET, _NEXT_TEX_BINDING_3 + 1)) uniform sampler2D u_normalRoughnessDecalTex;
+layout(ANKI_TEX_BINDING(LIGHT_SET, _NEXT_TEX_BINDING_3 + 1)) uniform sampler2D u_specularRoughnessDecalTex;
 #endif
 
 //

+ 2 - 2
src/anki/gr/CommandBuffer.h

@@ -204,8 +204,8 @@ public:
 	void setColorChannelWriteMask(U32 attachment, ColorBit mask);
 
 	/// Set blend factors seperate.
-	/// By default the values of srcRgb, dstRgb, srcA and dstA are BlendFactor::ONE, BlendFactor::ONE,
-	/// BlendFactor::ZERO, BlendFactor::ZERO respectively.
+	/// By default the values of srcRgb, dstRgb, srcA and dstA are BlendFactor::ONE, BlendFactor::ZERO,
+	/// BlendFactor::ONE, BlendFactor::ZERO respectively.
 	void setBlendFactors(U32 attachment, BlendFactor srcRgb, BlendFactor dstRgb, BlendFactor srcA, BlendFactor dstA);
 
 	/// Set blend factors.

+ 1 - 0
src/anki/renderer/Common.h

@@ -20,6 +20,7 @@ namespace anki
 // Forward
 class Renderer;
 class GBuffer;
+class GBufferPost;
 class ShadowMapping;
 class LightShading;
 class ForwardShading;

+ 40 - 2
src/anki/renderer/GBufferPost.cpp

@@ -7,6 +7,7 @@
 #include <anki/renderer/Renderer.h>
 #include <anki/renderer/GBuffer.h>
 #include <anki/renderer/Ssao.h>
+#include <anki/renderer/LightShading.h>
 #include <anki/misc/ConfigSet.h>
 
 namespace anki
@@ -76,9 +77,46 @@ void GBufferPost::populateRenderGraph(RenderingContext& ctx)
 
 void GBufferPost::run(RenderPassWorkContext& rgraphCtx)
 {
+	const LightShadingResources& rsrc = m_r->getLightShading().getResources();
 	CommandBufferPtr& cmdb = rgraphCtx.m_commandBuffer;
 
-	// TODO
+	cmdb->setViewport(0, 0, m_r->getWidth(), m_r->getHeight());
+	cmdb->bindShaderProgram(m_grProg);
+
+	cmdb->setBlendFactors(0, BlendFactor::ONE, BlendFactor::SRC_ALPHA, BlendFactor::ZERO, BlendFactor::ONE);
+	cmdb->setBlendFactors(1, BlendFactor::ONE, BlendFactor::SRC_ALPHA, BlendFactor::ZERO, BlendFactor::ONE);
+
+	// Bind textures
+	rgraphCtx.bindTextureAndSampler(0,
+		0,
+		m_r->getGBuffer().getDepthRt(),
+		TextureSubresourceInfo(DepthStencilAspectBit::DEPTH),
+		m_r->getNearestSampler());
+	rgraphCtx.bindColorTextureAndSampler(0, 1, m_r->getSsao().getRt(), m_r->getLinearSampler());
+	cmdb->bindTextureAndSampler(0,
+		2,
+		(rsrc.m_diffDecalTexView) ? rsrc.m_diffDecalTexView : m_r->getDummyTextureView(),
+		m_r->getTrilinearRepeatSampler(),
+		TextureUsageBit::SAMPLED_FRAGMENT);
+	cmdb->bindTextureAndSampler(0,
+		3,
+		(rsrc.m_specularRoughnessDecalTexView) ? rsrc.m_specularRoughnessDecalTexView : m_r->getDummyTextureView(),
+		m_r->getTrilinearRepeatSampler(),
+		TextureUsageBit::SAMPLED_FRAGMENT);
+
+	// Uniforms
+	bindUniforms(cmdb, 0, 0, rsrc.m_commonUniformsToken);
+	bindUniforms(cmdb, 0, 1, rsrc.m_decalsToken);
+
+	// Storage
+	bindStorage(cmdb, 0, 0, rsrc.m_clustersToken);
+	bindStorage(cmdb, 0, 1, rsrc.m_lightIndicesToken);
+
+	cmdb->drawArrays(PrimitiveTopology::TRIANGLES, 3);
+
+	// Restore state
+	cmdb->setBlendFactors(0, BlendFactor::ONE, BlendFactor::ZERO);
+	cmdb->setBlendFactors(1, BlendFactor::ONE, BlendFactor::ZERO);
 }
 
-} // end namespace anki
+} // end namespace anki

+ 9 - 9
src/anki/renderer/LightBin.cpp

@@ -320,8 +320,8 @@ public:
 
 	TextureViewPtr m_diffDecalTexAtlas;
 	SpinLock m_diffDecalTexAtlasMtx;
-	TextureViewPtr m_normalRoughnessDecalTexAtlas;
-	SpinLock m_normalRoughnessDecalTexAtlasMtx;
+	TextureViewPtr m_specularRoughnessDecalTexAtlas;
+	SpinLock m_specularRoughnessDecalTexAtlasMtx;
 
 	LightBin* m_bin = nullptr;
 };
@@ -494,7 +494,7 @@ Error LightBin::bin(const Mat4& viewMat,
 	ANKI_CHECK(m_threadPool->waitForAllThreadsToFinish());
 
 	out.m_diffDecalTexView = ctx.m_diffDecalTexAtlas;
-	out.m_normRoughnessDecalTexView = ctx.m_normalRoughnessDecalTexAtlas;
+	out.m_specularRoughnessDecalTexView = ctx.m_specularRoughnessDecalTexAtlas;
 
 	return Error::NONE;
 }
@@ -807,20 +807,20 @@ void LightBin::writeAndBinDecal(const DecalQueueElement& decalEl, LightBinContex
 		ctx.m_diffDecalTexAtlas = atlas;
 	}
 
-	atlas.reset(const_cast<TextureView*>(decalEl.m_normalRoughnessAtlas));
-	uv = decalEl.m_normalRoughnessAtlasUv;
+	atlas.reset(const_cast<TextureView*>(decalEl.m_specularRoughnessAtlas));
+	uv = decalEl.m_specularRoughnessAtlasUv;
 	decal.m_normRoughnessUv = Vec4(uv.x(), uv.y(), uv.z() - uv.x(), uv.w() - uv.y());
-	decal.m_blendFactors[1] = decalEl.m_normalRoughnessAtlasBlendFactor;
+	decal.m_blendFactors[1] = decalEl.m_specularRoughnessAtlasBlendFactor;
 
 	if(atlas)
 	{
-		LockGuard<SpinLock> lock(ctx.m_normalRoughnessDecalTexAtlasMtx);
-		if(ctx.m_normalRoughnessDecalTexAtlas && ctx.m_normalRoughnessDecalTexAtlas != atlas)
+		LockGuard<SpinLock> lock(ctx.m_specularRoughnessDecalTexAtlasMtx);
+		if(ctx.m_specularRoughnessDecalTexAtlas && ctx.m_specularRoughnessDecalTexAtlas != atlas)
 		{
 			ANKI_R_LOGF("All decals should have the same tex atlas");
 		}
 
-		ctx.m_normalRoughnessDecalTexAtlas = atlas;
+		ctx.m_specularRoughnessDecalTexAtlas = atlas;
 	}
 
 	// bias * proj_l * view_

+ 1 - 1
src/anki/renderer/LightBin.h

@@ -28,7 +28,7 @@ public:
 	StagingGpuMemoryToken m_lightIndicesToken;
 
 	TextureViewPtr m_diffDecalTexView;
-	TextureViewPtr m_normRoughnessDecalTexView;
+	TextureViewPtr m_specularRoughnessDecalTexView;
 };
 
 /// Bins lights and probes to clusters.

+ 11 - 22
src/anki/renderer/LightShading.cpp

@@ -6,7 +6,6 @@
 #include <anki/renderer/LightShading.h>
 #include <anki/renderer/Renderer.h>
 #include <anki/renderer/ShadowMapping.h>
-#include <anki/renderer/Ssao.h>
 #include <anki/renderer/Indirect.h>
 #include <anki/renderer/GBuffer.h>
 #include <anki/renderer/LightBin.h>
@@ -139,41 +138,32 @@ void LightShading::run(const RenderingContext& ctx, RenderPassWorkContext& rgrap
 	cmdb->setViewport(0, 0, m_r->getWidth(), m_r->getHeight());
 	cmdb->bindShaderProgram(m_progVariant->getProgram());
 
-	rgraphCtx.bindColorTextureAndSampler(1, 0, m_r->getGBuffer().getColorRt(0), m_r->getNearestSampler());
-	rgraphCtx.bindColorTextureAndSampler(1, 1, m_r->getGBuffer().getColorRt(1), m_r->getNearestSampler());
-	rgraphCtx.bindColorTextureAndSampler(1, 2, m_r->getGBuffer().getColorRt(2), m_r->getNearestSampler());
-	rgraphCtx.bindTextureAndSampler(1,
+	// Bind textures
+	rgraphCtx.bindColorTextureAndSampler(0, 0, m_r->getGBuffer().getColorRt(0), m_r->getNearestSampler());
+	rgraphCtx.bindColorTextureAndSampler(0, 1, m_r->getGBuffer().getColorRt(1), m_r->getNearestSampler());
+	rgraphCtx.bindColorTextureAndSampler(0, 2, m_r->getGBuffer().getColorRt(2), m_r->getNearestSampler());
+	rgraphCtx.bindTextureAndSampler(0,
 		3,
 		m_r->getGBuffer().getDepthRt(),
 		TextureSubresourceInfo(DepthStencilAspectBit::DEPTH),
 		m_r->getNearestSampler());
-	rgraphCtx.bindColorTextureAndSampler(1, 4, m_r->getSsao().getRt(), m_r->getLinearSampler());
 
-	rgraphCtx.bindColorTextureAndSampler(0, 0, m_r->getShadowMapping().getShadowmapRt(), m_r->getLinearSampler());
-	rgraphCtx.bindColorTextureAndSampler(0, 1, m_r->getIndirect().getReflectionRt(), m_r->getTrilinearRepeatSampler());
-	rgraphCtx.bindColorTextureAndSampler(0, 2, m_r->getIndirect().getIrradianceRt(), m_r->getLinearSampler());
+	rgraphCtx.bindColorTextureAndSampler(0, 4, m_r->getShadowMapping().getShadowmapRt(), m_r->getLinearSampler());
+	rgraphCtx.bindColorTextureAndSampler(0, 5, m_r->getIndirect().getReflectionRt(), m_r->getTrilinearRepeatSampler());
+	rgraphCtx.bindColorTextureAndSampler(0, 6, m_r->getIndirect().getIrradianceRt(), m_r->getLinearSampler());
 	cmdb->bindTextureAndSampler(0,
-		3,
+		7,
 		m_r->getIndirect().getIntegrationLut(),
 		m_r->getIndirect().getIntegrationLutSampler(),
 		TextureUsageBit::SAMPLED_FRAGMENT);
-	cmdb->bindTextureAndSampler(0,
-		4,
-		(rsrc.m_diffDecalTexView) ? rsrc.m_diffDecalTexView : m_r->getDummyTextureView(),
-		m_r->getTrilinearRepeatSampler(),
-		TextureUsageBit::SAMPLED_FRAGMENT);
-	cmdb->bindTextureAndSampler(0,
-		5,
-		(rsrc.m_normRoughnessDecalTexView) ? rsrc.m_normRoughnessDecalTexView : m_r->getDummyTextureView(),
-		m_r->getTrilinearRepeatSampler(),
-		TextureUsageBit::SAMPLED_FRAGMENT);
 
+	// Bind uniforms
 	bindUniforms(cmdb, 0, 0, rsrc.m_commonUniformsToken);
 	bindUniforms(cmdb, 0, 1, rsrc.m_pointLightsToken);
 	bindUniforms(cmdb, 0, 2, rsrc.m_spotLightsToken);
 	bindUniforms(cmdb, 0, 3, rsrc.m_probesToken);
-	bindUniforms(cmdb, 0, 4, rsrc.m_decalsToken);
 
+	// Bind storage
 	bindStorage(cmdb, 0, 0, rsrc.m_clustersToken);
 	bindStorage(cmdb, 0, 1, rsrc.m_lightIndicesToken);
 
@@ -237,7 +227,6 @@ void LightShading::populateRenderGraph(RenderingContext& ctx)
 	pass.newConsumer({m_r->getGBuffer().getDepthRt(),
 		TextureUsageBit::SAMPLED_FRAGMENT,
 		TextureSubresourceInfo(DepthStencilAspectBit::DEPTH)});
-	pass.newConsumer({m_r->getSsao().getRt(), TextureUsageBit::SAMPLED_FRAGMENT});
 	pass.newConsumer({m_r->getShadowMapping().getShadowmapRt(), TextureUsageBit::SAMPLED_FRAGMENT});
 	pass.newConsumer({m_r->getIndirect().getReflectionRt(), TextureUsageBit::SAMPLED_FRAGMENT});
 	pass.newConsumer({m_r->getIndirect().getIrradianceRt(), TextureUsageBit::SAMPLED_FRAGMENT});

+ 3 - 3
src/anki/renderer/RenderQueue.h

@@ -145,11 +145,11 @@ public:
 	/// Totaly unsafe but we can't have a smart ptr in here since there will be no deletion.
 	const TextureView* m_diffuseAtlas;
 	/// Totaly unsafe but we can't have a smart ptr in here since there will be no deletion.
-	const TextureView* m_normalRoughnessAtlas;
+	const TextureView* m_specularRoughnessAtlas;
 	Vec4 m_diffuseAtlasUv;
-	Vec4 m_normalRoughnessAtlasUv;
+	Vec4 m_specularRoughnessAtlasUv;
 	F32 m_diffuseAtlasBlendFactor;
-	F32 m_normalRoughnessAtlasBlendFactor;
+	F32 m_specularRoughnessAtlasBlendFactor;
 	Mat4 m_textureMatrix;
 	Vec3 m_obbCenter;
 	Vec3 m_obbExtend;

+ 5 - 0
src/anki/renderer/Renderer.cpp

@@ -11,6 +11,7 @@
 
 #include <anki/renderer/Indirect.h>
 #include <anki/renderer/GBuffer.h>
+#include <anki/renderer/GBufferPost.h>
 #include <anki/renderer/LightShading.h>
 #include <anki/renderer/ShadowMapping.h>
 #include <anki/renderer/FinalComposite.h>
@@ -112,6 +113,9 @@ Error Renderer::initInternal(const ConfigSet& config)
 	m_gbuffer.reset(m_alloc.newInstance<GBuffer>(this));
 	ANKI_CHECK(m_gbuffer->init(config));
 
+	m_gbufferPost.reset(m_alloc.newInstance<GBufferPost>(this));
+	ANKI_CHECK(m_gbufferPost->init(config));
+
 	m_shadowMapping.reset(m_alloc.newInstance<ShadowMapping>(this));
 	ANKI_CHECK(m_shadowMapping->init(config));
 
@@ -269,6 +273,7 @@ Error Renderer::populateRenderGraph(RenderingContext& ctx)
 	m_refl->populateRenderGraph(ctx);
 	m_vol->populateRenderGraph(ctx);
 	m_ssao->populateRenderGraph(ctx);
+	m_gbufferPost->populateRenderGraph(ctx);
 	m_lensFlare->populateRenderGraph(ctx);
 	m_forwardShading->populateRenderGraph(ctx);
 	m_lightShading->populateRenderGraph(ctx);

+ 1 - 0
src/anki/renderer/Renderer.h

@@ -353,6 +353,7 @@ private:
 	UniquePtr<Indirect> m_indirect;
 	UniquePtr<ShadowMapping> m_shadowMapping; ///< Shadow mapping.
 	UniquePtr<GBuffer> m_gbuffer; ///< Material rendering stage
+	UniquePtr<GBufferPost> m_gbufferPost;
 	UniquePtr<Reflections> m_refl;
 	UniquePtr<LightShading> m_lightShading; ///< Illumination rendering stage
 	UniquePtr<DepthDownscale> m_depth;

+ 13 - 13
src/anki/scene/components/DecalComponent.h

@@ -34,9 +34,9 @@ public:
 		return setLayer(texAtlasFname, texAtlasSubtexName, blendFactor, LayerType::DIFFUSE);
 	}
 
-	ANKI_USE_RESULT Error setNormalRoughnessDecal(CString texAtlasFname, CString texAtlasSubtexName, F32 blendFactor)
+	ANKI_USE_RESULT Error setSpecularRoughnessDecal(CString texAtlasFname, CString texAtlasSubtexName, F32 blendFactor)
 	{
-		return setLayer(texAtlasFname, texAtlasSubtexName, blendFactor, LayerType::NORMAL_ROUGHNESS);
+		return setLayer(texAtlasFname, texAtlasSubtexName, blendFactor, LayerType::SPECULAR_ROUGHNESS);
 	}
 
 	/// Update the internal structures.
@@ -99,18 +99,18 @@ public:
 		blendFactor = m_layers[LayerType::DIFFUSE].m_blendFactor;
 	}
 
-	void getNormalRoughnessAtlasInfo(Vec4& uv, TexturePtr& tex, F32& blendFactor) const
+	void getSpecularRoughnessAtlasInfo(Vec4& uv, TexturePtr& tex, F32& blendFactor) const
 	{
-		uv = m_layers[LayerType::NORMAL_ROUGHNESS].m_uv;
-		if(m_layers[LayerType::NORMAL_ROUGHNESS].m_atlas)
+		uv = m_layers[LayerType::SPECULAR_ROUGHNESS].m_uv;
+		if(m_layers[LayerType::SPECULAR_ROUGHNESS].m_atlas)
 		{
-			tex = m_layers[LayerType::NORMAL_ROUGHNESS].m_atlas->getGrTexture();
+			tex = m_layers[LayerType::SPECULAR_ROUGHNESS].m_atlas->getGrTexture();
 		}
 		else
 		{
 			tex.reset(nullptr);
 		}
-		blendFactor = m_layers[LayerType::NORMAL_ROUGHNESS].m_blendFactor;
+		blendFactor = m_layers[LayerType::SPECULAR_ROUGHNESS].m_blendFactor;
 	}
 
 	const Vec3& getVolumeSize() const
@@ -123,13 +123,13 @@ public:
 		el.m_diffuseAtlas = (m_layers[LayerType::DIFFUSE].m_atlas)
 								? m_layers[LayerType::DIFFUSE].m_atlas->getGrTextureView().get()
 								: nullptr;
-		el.m_normalRoughnessAtlas = (m_layers[LayerType::NORMAL_ROUGHNESS].m_atlas)
-										? m_layers[LayerType::NORMAL_ROUGHNESS].m_atlas->getGrTextureView().get()
-										: nullptr;
+		el.m_specularRoughnessAtlas = (m_layers[LayerType::SPECULAR_ROUGHNESS].m_atlas)
+										  ? m_layers[LayerType::SPECULAR_ROUGHNESS].m_atlas->getGrTextureView().get()
+										  : nullptr;
 		el.m_diffuseAtlasUv = m_layers[LayerType::DIFFUSE].m_uv;
-		el.m_normalRoughnessAtlasUv = m_layers[LayerType::NORMAL_ROUGHNESS].m_uv;
+		el.m_specularRoughnessAtlasUv = m_layers[LayerType::SPECULAR_ROUGHNESS].m_uv;
 		el.m_diffuseAtlasBlendFactor = m_layers[LayerType::DIFFUSE].m_blendFactor;
-		el.m_normalRoughnessAtlasBlendFactor = m_layers[LayerType::NORMAL_ROUGHNESS].m_blendFactor;
+		el.m_specularRoughnessAtlasBlendFactor = m_layers[LayerType::SPECULAR_ROUGHNESS].m_blendFactor;
 		el.m_textureMatrix = m_biasProjViewMat;
 		el.m_obbCenter = m_obb.getCenter().xyz();
 		el.m_obbExtend = m_obb.getExtend().xyz();
@@ -142,7 +142,7 @@ private:
 	enum class LayerType
 	{
 		DIFFUSE,
-		NORMAL_ROUGHNESS,
+		SPECULAR_ROUGHNESS,
 		COUNT
 	};
 

+ 7 - 7
src/anki/script/Scene.cpp

@@ -1176,8 +1176,8 @@ static int wrapDecalComponentsetDiffuseDecal(lua_State* l)
 	return 0;
 }
 
-/// Pre-wrap method DecalComponent::setNormalRoughnessDecal.
-static inline int pwrapDecalComponentsetNormalRoughnessDecal(lua_State* l)
+/// Pre-wrap method DecalComponent::setSpecularRoughnessDecal.
+static inline int pwrapDecalComponentsetSpecularRoughnessDecal(lua_State* l)
 {
 	LuaUserData* ud;
 	(void)ud;
@@ -1216,7 +1216,7 @@ static inline int pwrapDecalComponentsetNormalRoughnessDecal(lua_State* l)
 	}
 
 	// Call the method
-	Error ret = self->setNormalRoughnessDecal(arg0, arg1, arg2);
+	Error ret = self->setSpecularRoughnessDecal(arg0, arg1, arg2);
 
 	// Push return value
 	if(ANKI_UNLIKELY(ret))
@@ -1230,10 +1230,10 @@ static inline int pwrapDecalComponentsetNormalRoughnessDecal(lua_State* l)
 	return 1;
 }
 
-/// Wrap method DecalComponent::setNormalRoughnessDecal.
-static int wrapDecalComponentsetNormalRoughnessDecal(lua_State* l)
+/// Wrap method DecalComponent::setSpecularRoughnessDecal.
+static int wrapDecalComponentsetSpecularRoughnessDecal(lua_State* l)
 {
-	int res = pwrapDecalComponentsetNormalRoughnessDecal(l);
+	int res = pwrapDecalComponentsetSpecularRoughnessDecal(l);
 	if(res >= 0)
 	{
 		return res;
@@ -1306,7 +1306,7 @@ static inline void wrapDecalComponent(lua_State* l)
 {
 	LuaBinder::createClass(l, classnameDecalComponent);
 	LuaBinder::pushLuaCFuncMethod(l, "setDiffuseDecal", wrapDecalComponentsetDiffuseDecal);
-	LuaBinder::pushLuaCFuncMethod(l, "setNormalRoughnessDecal", wrapDecalComponentsetNormalRoughnessDecal);
+	LuaBinder::pushLuaCFuncMethod(l, "setSpecularRoughnessDecal", wrapDecalComponentsetSpecularRoughnessDecal);
 	LuaBinder::pushLuaCFuncMethod(l, "updateShape", wrapDecalComponentupdateShape);
 	lua_settop(l, 0);
 }

+ 1 - 1
src/anki/script/Scene.xml

@@ -147,7 +147,7 @@ static SceneGraph* getSceneGraph(lua_State* l)
 					</args>
 					<return>Error</return>
 				</method>
-				<method name="setNormalRoughnessDecal">
+				<method name="setSpecularRoughnessDecal">
 					<args>
 						<arg>CString</arg>
 						<arg>CString</arg>

+ 5 - 5
tools/scene/Exporter.cpp

@@ -895,11 +895,11 @@ void Exporter::visitNode(const aiNode* ainode)
 					}
 					else if(pr.first == "decal_normal_roughness_atlas")
 					{
-						decal.m_normalRoughnessAtlasFilename = pr.second;
+						decal.m_specularRoughnessAtlasFilename = pr.second;
 					}
 					else if(pr.first == "decal_normal_roughness_sub_texture")
 					{
-						decal.m_normalRoughnessSubTextureName = pr.second;
+						decal.m_specularRoughnessSubTextureName = pr.second;
 					}
 					else if(pr.first == "decal_normal_roughness_factor")
 					{
@@ -1116,10 +1116,10 @@ void Exporter::exportAll()
 			 << decal.m_diffuseSubTextureName << "\", " << decal.m_factors[0] << ")\n";
 		file << "decalc:updateShape(" << decal.m_size.x << ", " << decal.m_size.y << ", " << decal.m_size.z << ")\n";
 
-		if(!decal.m_normalRoughnessAtlasFilename.empty())
+		if(!decal.m_specularRoughnessAtlasFilename.empty())
 		{
-			file << "decalc:setNormalRoughnessDecal(\"" << decal.m_normalRoughnessAtlasFilename << "\", \""
-				 << decal.m_normalRoughnessSubTextureName << "\", " << decal.m_factors[1] << ")\n";
+			file << "decalc:setSpecularRoughnessDecal(\"" << decal.m_specularRoughnessAtlasFilename << "\", \""
+				 << decal.m_specularRoughnessSubTextureName << "\", " << decal.m_factors[1] << ")\n";
 		}
 
 		++i;

+ 2 - 2
tools/scene/Exporter.h

@@ -97,8 +97,8 @@ public:
 	aiMatrix4x4 m_transform;
 	std::string m_diffuseTextureAtlasFilename;
 	std::string m_diffuseSubTextureName;
-	std::string m_normalRoughnessAtlasFilename;
-	std::string m_normalRoughnessSubTextureName;
+	std::string m_specularRoughnessAtlasFilename;
+	std::string m_specularRoughnessSubTextureName;
 	aiVector3D m_size;
 	std::array<float, 2> m_factors = {{1.0, 1.0}};
 };