|
|
@@ -19,23 +19,26 @@ Error VolumetricMain::init(const ConfigSet& config)
|
|
|
// Misc
|
|
|
ANKI_CHECK(getResourceManager().loadResource("engine_data/BlueNoiseLdrRgb64x64.ankitex", m_noiseTex));
|
|
|
|
|
|
- // RT
|
|
|
- TextureInitInfo rtInit = m_r->create2DRenderTargetInitInfo(m_vol->m_width,
|
|
|
- m_vol->m_height,
|
|
|
- IS_COLOR_ATTACHMENT_PIXEL_FORMAT,
|
|
|
- TextureUsageBit::SAMPLED_FRAGMENT | TextureUsageBit::FRAMEBUFFER_ATTACHMENT_READ_WRITE,
|
|
|
- SamplingFilter::LINEAR,
|
|
|
- 1,
|
|
|
- "volmain");
|
|
|
- rtInit.m_initialUsage = TextureUsageBit::SAMPLED_FRAGMENT;
|
|
|
- m_rt = m_r->createAndClearRenderTarget(rtInit);
|
|
|
-
|
|
|
- // FB
|
|
|
- FramebufferInitInfo fbInit("volmain");
|
|
|
- fbInit.m_colorAttachmentCount = 1;
|
|
|
- fbInit.m_colorAttachments[0].m_texture = m_rt;
|
|
|
- fbInit.m_colorAttachments[0].m_loadOperation = AttachmentLoadOperation::LOAD;
|
|
|
- m_fb = getGrManager().newInstance<Framebuffer>(fbInit);
|
|
|
+ for(U i = 0; i < 2; ++i)
|
|
|
+ {
|
|
|
+ // RT
|
|
|
+ TextureInitInfo rtInit = m_r->create2DRenderTargetInitInfo(m_vol->m_width,
|
|
|
+ m_vol->m_height,
|
|
|
+ IS_COLOR_ATTACHMENT_PIXEL_FORMAT,
|
|
|
+ TextureUsageBit::SAMPLED_FRAGMENT | TextureUsageBit::FRAMEBUFFER_ATTACHMENT_WRITE,
|
|
|
+ SamplingFilter::LINEAR,
|
|
|
+ 1,
|
|
|
+ "volmain");
|
|
|
+ rtInit.m_initialUsage = TextureUsageBit::SAMPLED_FRAGMENT;
|
|
|
+ m_rt[i] = m_r->createAndClearRenderTarget(rtInit);
|
|
|
+
|
|
|
+ // FB
|
|
|
+ FramebufferInitInfo fbInit("volmain");
|
|
|
+ fbInit.m_colorAttachmentCount = 1;
|
|
|
+ fbInit.m_colorAttachments[0].m_texture = m_rt[i];
|
|
|
+ fbInit.m_colorAttachments[0].m_loadOperation = AttachmentLoadOperation::DONT_CARE;
|
|
|
+ m_fb[i] = getGrManager().newInstance<Framebuffer>(fbInit);
|
|
|
+ }
|
|
|
|
|
|
// Shaders
|
|
|
ANKI_CHECK(m_r->createShaderf("shaders/Volumetric.frag.glsl",
|
|
|
@@ -55,11 +58,16 @@ Error VolumetricMain::init(const ConfigSet& config)
|
|
|
return ErrorCode::NONE;
|
|
|
}
|
|
|
|
|
|
+TexturePtr VolumetricMain::getRt() const
|
|
|
+{
|
|
|
+ return m_rt[m_r->getFrameCount() & 1];
|
|
|
+}
|
|
|
+
|
|
|
void VolumetricMain::setPreRunBarriers(RenderingContext& ctx)
|
|
|
{
|
|
|
- ctx.m_commandBuffer->setTextureSurfaceBarrier(m_rt,
|
|
|
- TextureUsageBit::SAMPLED_FRAGMENT,
|
|
|
- TextureUsageBit::FRAMEBUFFER_ATTACHMENT_READ_WRITE,
|
|
|
+ ctx.m_commandBuffer->setTextureSurfaceBarrier(m_rt[m_r->getFrameCount() & 1],
|
|
|
+ TextureUsageBit::NONE,
|
|
|
+ TextureUsageBit::FRAMEBUFFER_ATTACHMENT_WRITE,
|
|
|
TextureSurfaceInfo(0, 0, 0, 0));
|
|
|
}
|
|
|
|
|
|
@@ -71,62 +79,51 @@ void VolumetricMain::run(RenderingContext& ctx)
|
|
|
// Main pass
|
|
|
//
|
|
|
cmdb->setViewport(0, 0, m_vol->m_width, m_vol->m_height);
|
|
|
- cmdb->setBlendFactors(0, BlendFactor::SRC_ALPHA, BlendFactor::ONE_MINUS_SRC_ALPHA);
|
|
|
|
|
|
cmdb->bindTexture(0, 0, m_r->getDepthDownscale().m_qd.m_depthRt);
|
|
|
cmdb->bindTexture(0, 1, m_noiseTex->getGrTexture());
|
|
|
- cmdb->bindTexture(0, 2, m_r->getSm().m_spotTexArray);
|
|
|
- cmdb->bindTexture(0, 3, m_r->getSm().m_omniTexArray);
|
|
|
+ TexturePtr& history = m_rt[(m_r->getFrameCount() + 1) & 1];
|
|
|
+ cmdb->informTextureCurrentUsage(history, TextureUsageBit::SAMPLED_FRAGMENT);
|
|
|
+ cmdb->bindTexture(0, 2, history);
|
|
|
+ cmdb->bindTexture(0, 3, m_r->getSm().m_spotTexArray);
|
|
|
+ cmdb->bindTexture(0, 4, m_r->getSm().m_omniTexArray);
|
|
|
|
|
|
bindUniforms(cmdb, 0, 0, ctx.m_is.m_commonToken);
|
|
|
bindUniforms(cmdb, 0, 1, ctx.m_is.m_pointLightsToken);
|
|
|
bindUniforms(cmdb, 0, 2, ctx.m_is.m_spotLightsToken);
|
|
|
|
|
|
- Vec4* uniforms = allocateAndBindUniforms<Vec4*>(sizeof(Vec4) * 2, cmdb, 0, 3);
|
|
|
- computeLinearizeDepthOptimal(ctx.m_near, ctx.m_far, uniforms[0].x(), uniforms[0].y());
|
|
|
-
|
|
|
- F32 texelOffset = 1.0 / m_noiseTex->getWidth();
|
|
|
- uniforms[0].z() = m_r->getFrameCount() * texelOffset;
|
|
|
- uniforms[0].w() = m_r->getFrameCount() & (m_noiseTex->getLayerCount() - 1);
|
|
|
-
|
|
|
- // Compute the blend factor. If the camera rotated or moved alot don't blend with previous frames
|
|
|
- F32 dotZ = ctx.m_camTrfMat.getZAxis().xyz().dot(ctx.m_prevCamTransform.getZAxis().xyz());
|
|
|
- F32 dotY = ctx.m_camTrfMat.getYAxis().xyz().dot(ctx.m_prevCamTransform.getYAxis().xyz());
|
|
|
-
|
|
|
- const F32 ANG_TOLERANCE = cos(toRad(1.0f / 8.0f));
|
|
|
- const F32 DIST_TOLERANCE = 0.1f;
|
|
|
- F32 blendFactor;
|
|
|
- const F32 dist = (ctx.m_camTrfMat.getTranslationPart().xyz0() - ctx.m_prevCamTransform.getTranslationPart().xyz0())
|
|
|
- .getLengthSquared();
|
|
|
- if(clamp(dotZ, 0.0f, 1.0f) > ANG_TOLERANCE && clamp(dotY, 0.0f, 1.0f) > ANG_TOLERANCE
|
|
|
- && dist < DIST_TOLERANCE * DIST_TOLERANCE)
|
|
|
+ struct Unis
|
|
|
{
|
|
|
- blendFactor = 1.0 / 4.0;
|
|
|
- }
|
|
|
- else
|
|
|
- {
|
|
|
- blendFactor = 1.0 / 2.0;
|
|
|
- }
|
|
|
-
|
|
|
- uniforms[1] = Vec4(m_fogParticleColor, blendFactor);
|
|
|
+ Vec4 m_linearizeNoiseTexOffsetLayer;
|
|
|
+ Vec4 m_fogParticleColorPad1;
|
|
|
+ Mat4 m_prevViewProjMatMulInvViewProjMat;
|
|
|
+ };
|
|
|
+
|
|
|
+ Unis* uniforms = allocateAndBindUniforms<Unis*>(sizeof(Unis), cmdb, 0, 3);
|
|
|
+ computeLinearizeDepthOptimal(ctx.m_near,
|
|
|
+ ctx.m_far,
|
|
|
+ uniforms->m_linearizeNoiseTexOffsetLayer.x(),
|
|
|
+ uniforms->m_linearizeNoiseTexOffsetLayer.y());
|
|
|
+ F32 texelOffset = 1.0 / m_noiseTex->getWidth();
|
|
|
+ uniforms->m_linearizeNoiseTexOffsetLayer.z() = m_r->getFrameCount() * texelOffset;
|
|
|
+ uniforms->m_linearizeNoiseTexOffsetLayer.w() = m_r->getFrameCount() & (m_noiseTex->getLayerCount() - 1);
|
|
|
+ uniforms->m_fogParticleColorPad1 = Vec4(m_fogParticleColor, 0.0);
|
|
|
+ uniforms->m_prevViewProjMatMulInvViewProjMat = ctx.m_prevViewProjMat * ctx.m_viewProjMat.getInverse();
|
|
|
|
|
|
bindStorage(cmdb, 0, 0, ctx.m_is.m_clustersToken);
|
|
|
bindStorage(cmdb, 0, 1, ctx.m_is.m_lightIndicesToken);
|
|
|
|
|
|
cmdb->bindShaderProgram(m_prog);
|
|
|
|
|
|
- cmdb->beginRenderPass(m_fb);
|
|
|
+ cmdb->beginRenderPass(m_fb[m_r->getFrameCount() & 1]);
|
|
|
m_r->drawQuad(cmdb);
|
|
|
cmdb->endRenderPass();
|
|
|
-
|
|
|
- // Restore state
|
|
|
- cmdb->setBlendFactors(0, BlendFactor::ONE, BlendFactor::ZERO);
|
|
|
}
|
|
|
|
|
|
void VolumetricMain::setPostRunBarriers(RenderingContext& ctx)
|
|
|
{
|
|
|
- ctx.m_commandBuffer->setTextureSurfaceBarrier(m_rt,
|
|
|
- TextureUsageBit::FRAMEBUFFER_ATTACHMENT_READ_WRITE,
|
|
|
+ ctx.m_commandBuffer->setTextureSurfaceBarrier(m_rt[m_r->getFrameCount() & 1],
|
|
|
+ TextureUsageBit::FRAMEBUFFER_ATTACHMENT_WRITE,
|
|
|
TextureUsageBit::SAMPLED_FRAGMENT,
|
|
|
TextureSurfaceInfo(0, 0, 0, 0));
|
|
|
}
|
|
|
@@ -173,7 +170,7 @@ void VolumetricHBlur::run(RenderingContext& ctx)
|
|
|
{
|
|
|
CommandBufferPtr& cmdb = ctx.m_commandBuffer;
|
|
|
|
|
|
- cmdb->bindTexture(0, 0, m_vol->m_main.m_rt);
|
|
|
+ cmdb->bindTexture(0, 0, m_vol->m_main.m_rt[m_r->getFrameCount() & 1]);
|
|
|
cmdb->bindShaderProgram(m_prog);
|
|
|
cmdb->setViewport(0, 0, m_vol->m_width, m_vol->m_height);
|
|
|
|
|
|
@@ -193,11 +190,14 @@ void VolumetricHBlur::setPostRunBarriers(RenderingContext& ctx)
|
|
|
Error VolumetricVBlur::init(const ConfigSet& config)
|
|
|
{
|
|
|
// Create FBs
|
|
|
- FramebufferInitInfo fbInit;
|
|
|
- fbInit.m_colorAttachmentCount = 1;
|
|
|
- fbInit.m_colorAttachments[0].m_texture = m_vol->m_main.m_rt;
|
|
|
- fbInit.m_colorAttachments[0].m_loadOperation = AttachmentLoadOperation::DONT_CARE;
|
|
|
- m_fb = getGrManager().newInstance<Framebuffer>(fbInit);
|
|
|
+ for(U i = 0; i < 2; ++i)
|
|
|
+ {
|
|
|
+ FramebufferInitInfo fbInit;
|
|
|
+ fbInit.m_colorAttachmentCount = 1;
|
|
|
+ fbInit.m_colorAttachments[0].m_texture = m_vol->m_main.m_rt[i];
|
|
|
+ fbInit.m_colorAttachments[0].m_loadOperation = AttachmentLoadOperation::DONT_CARE;
|
|
|
+ m_fb[i] = getGrManager().newInstance<Framebuffer>(fbInit);
|
|
|
+ }
|
|
|
|
|
|
ANKI_CHECK(m_r->createShaderf("shaders/LumaAwareBlurGeneric.frag.glsl",
|
|
|
m_frag,
|
|
|
@@ -215,7 +215,7 @@ Error VolumetricVBlur::init(const ConfigSet& config)
|
|
|
|
|
|
void VolumetricVBlur::setPreRunBarriers(RenderingContext& ctx)
|
|
|
{
|
|
|
- ctx.m_commandBuffer->setTextureSurfaceBarrier(m_vol->m_main.m_rt,
|
|
|
+ ctx.m_commandBuffer->setTextureSurfaceBarrier(m_vol->m_main.m_rt[m_r->getFrameCount() & 1],
|
|
|
TextureUsageBit::NONE,
|
|
|
TextureUsageBit::FRAMEBUFFER_ATTACHMENT_WRITE,
|
|
|
TextureSurfaceInfo(0, 0, 0, 0));
|
|
|
@@ -229,14 +229,14 @@ void VolumetricVBlur::run(RenderingContext& ctx)
|
|
|
cmdb->bindShaderProgram(m_prog);
|
|
|
cmdb->setViewport(0, 0, m_vol->m_width, m_vol->m_height);
|
|
|
|
|
|
- cmdb->beginRenderPass(m_fb);
|
|
|
+ cmdb->beginRenderPass(m_fb[m_r->getFrameCount() & 1]);
|
|
|
m_r->drawQuad(cmdb);
|
|
|
cmdb->endRenderPass();
|
|
|
}
|
|
|
|
|
|
void VolumetricVBlur::setPostRunBarriers(RenderingContext& ctx)
|
|
|
{
|
|
|
- ctx.m_commandBuffer->setTextureSurfaceBarrier(m_vol->m_main.m_rt,
|
|
|
+ ctx.m_commandBuffer->setTextureSurfaceBarrier(m_vol->m_main.m_rt[m_r->getFrameCount() & 1],
|
|
|
TextureUsageBit::FRAMEBUFFER_ATTACHMENT_WRITE,
|
|
|
TextureUsageBit::SAMPLED_FRAGMENT,
|
|
|
TextureSurfaceInfo(0, 0, 0, 0));
|