BloomDownsamplePass.cpp 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130
  1. /*
  2. * Copyright (c) Contributors to the Open 3D Engine Project.
  3. * For complete copyright and license terms please see the LICENSE at the root of this distribution.
  4. *
  5. * SPDX-License-Identifier: Apache-2.0 OR MIT
  6. *
  7. */
  8. #include <PostProcessing/BloomDownsamplePass.h>
  9. #include <PostProcess/Bloom/BloomSettings.h>
  10. #include <PostProcess/PostProcessFeatureProcessor.h>
  11. #include <Atom/RHI/CommandList.h>
  12. #include <Atom/RHI/Factory.h>
  13. #include <Atom/RHI/FrameScheduler.h>
  14. #include <Atom/RPI.Reflect/Pass/PassTemplate.h>
  15. #include <Atom/RPI.Public/Pass/PassUtils.h>
  16. #include <Atom/RPI.Public/Pass/PassAttachment.h>
  17. #include <Atom/RPI.Public/RPIUtils.h>
  18. #include <Atom/RPI.Public/RenderPipeline.h>
  19. #include <Atom/RPI.Public/View.h>
  20. #include <Atom/RPI.Public/RPISystemInterface.h>
  21. #include <Atom/RPI.Public/Shader/ShaderResourceGroup.h>
  22. #include <Atom/RPI.Public/Scene.h>
  23. #include <Atom/RPI.Public/Image/AttachmentImagePool.h>
  24. #include <Atom/RPI.Public/Image/ImageSystemInterface.h>
  25. namespace AZ
  26. {
  27. namespace Render
  28. {
  29. RPI::Ptr<BloomDownsamplePass> BloomDownsamplePass::Create(const RPI::PassDescriptor& descriptor)
  30. {
  31. RPI::Ptr<BloomDownsamplePass> pass = aznew BloomDownsamplePass(descriptor);
  32. return AZStd::move(pass);
  33. }
  34. BloomDownsamplePass::BloomDownsamplePass(const RPI::PassDescriptor& descriptor)
  35. : ComputePass(descriptor)
  36. { }
  37. void BloomDownsamplePass::BuildOutAttachmentBinding()
  38. {
  39. RPI::Ptr<RPI::PassAttachment> outAttachment = m_ownedAttachments[0];
  40. for (uint16_t i = 0; i < Render::Bloom::MaxStageCount; ++i)
  41. {
  42. // Create bindings
  43. // Set pass slot
  44. RPI::PassAttachmentBinding outBinding;
  45. outBinding.m_name = Name{ AZStd::string::format("Downsampled%d", i) };
  46. outBinding.m_shaderInputName = Name{ AZStd::string::format("m_targetMipLevel%d", i) };
  47. outBinding.m_slotType = RPI::PassSlotType::Output;
  48. outBinding.m_scopeAttachmentUsage = RHI::ScopeAttachmentUsage::Shader;
  49. // Set image view descriptor
  50. RHI::ImageViewDescriptor outViewDesc;
  51. outViewDesc.m_mipSliceMin = i;
  52. outViewDesc.m_mipSliceMax = i;
  53. outBinding.m_unifiedScopeDesc.SetAsImage(outViewDesc);
  54. outBinding.SetAttachment(outAttachment);
  55. AddAttachmentBinding(outBinding);
  56. }
  57. ComputePass::BuildInternal();
  58. }
  59. void BloomDownsamplePass::BuildInternal()
  60. {
  61. BuildOutAttachmentBinding();
  62. }
  63. AZ::Vector4 BloomDownsamplePass::CalThresholdConstants()
  64. {
  65. // These constants will be used in shader to compute a soft knee based threshold
  66. float x = m_threshold;
  67. float y = x * m_knee;
  68. float z = 2.0f * y;
  69. float w = 1.0f / (4.0f * y + 1e-5f);
  70. y -= x;
  71. return AZ::Vector4(x, y, z, w);
  72. }
  73. void BloomDownsamplePass::FrameBeginInternal(FramePrepareParams params)
  74. {
  75. RPI::Scene* scene = GetScene();
  76. PostProcessFeatureProcessor* fp = scene->GetFeatureProcessor<PostProcessFeatureProcessor>();
  77. RPI::ViewPtr view = m_pipeline->GetFirstView(GetPipelineViewTag());
  78. if (fp)
  79. {
  80. PostProcessSettings* postProcessSettings = fp->GetLevelSettingsFromView(view);
  81. if (postProcessSettings)
  82. {
  83. BloomSettings* bloomSettings = postProcessSettings->GetBloomSettings();
  84. if (bloomSettings)
  85. {
  86. m_threshold = bloomSettings->GetThreshold();
  87. m_knee = bloomSettings->GetKnee();
  88. m_shaderResourceGroup->SetConstant(m_thresholdConstantsInputIndex, CalThresholdConstants());
  89. }
  90. }
  91. }
  92. RHI::Size targetImageSize;
  93. if (m_isFullscreenPass)
  94. {
  95. RPI::PassAttachment* outputAttachment = GetOutputBinding(0).GetAttachment().get();
  96. targetImageSize = outputAttachment->m_descriptor.m_image.m_size;
  97. SetTargetThreadCounts(targetImageSize.m_width, targetImageSize.m_height, targetImageSize.m_depth);
  98. }
  99. RHI::Size sourceImageSize;
  100. RPI::PassAttachment* inputAttachment = GetInputBinding(0).GetAttachment().get();
  101. sourceImageSize = inputAttachment->m_descriptor.m_image.m_size;
  102. // Update shader constant
  103. m_shaderResourceGroup->SetConstant(m_sourceImageTexelSizeInputIndex, AZ::Vector2(1.0f / static_cast<float>(sourceImageSize.m_width), 1.0f / static_cast<float>(sourceImageSize.m_height)));
  104. RenderPass::FrameBeginInternal(params);
  105. }
  106. } // namespace RPI
  107. } // namespace AZ