DiffuseProbeGrid.cpp 46 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864
  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 <Atom/Feature/RayTracing/RayTracingFeatureProcessorInterface.h>
  9. #include <Atom/RHI.Reflect/ShaderResourceGroupLayoutDescriptor.h>
  10. #include <Atom/RPI.Public/Shader/ShaderResourceGroup.h>
  11. #include <Render/DiffuseProbeGrid.h>
  12. #include <Atom/RPI.Public/Image/StreamingImage.h>
  13. #include <Atom/RPI.Public/View.h>
  14. #include <Atom/RHI/RHISystemInterface.h>
  15. #include <Atom/RHI/Factory.h>
  16. #include <AzCore/Math/MathUtils.h>
  17. namespace AZ
  18. {
  19. namespace Render
  20. {
  21. DiffuseProbeGrid::DiffuseProbeGrid()
  22. : m_textureReadback(this)
  23. {
  24. }
  25. DiffuseProbeGrid::~DiffuseProbeGrid()
  26. {
  27. m_scene->GetCullingScene()->UnregisterCullable(m_cullable);
  28. }
  29. void DiffuseProbeGrid::Init(RPI::Scene* scene, DiffuseProbeGridRenderData* renderData)
  30. {
  31. AZ_Assert(scene, "DiffuseProbeGrid::Init called with a null Scene pointer");
  32. m_scene = scene;
  33. m_renderData = renderData;
  34. // create attachment Ids
  35. AZStd::string uuidString = AZ::Uuid::CreateRandom().ToString<AZStd::string>();
  36. m_rayTraceImageAttachmentId = AZStd::string::format("ProbeRayTraceImageAttachmentId_%s", uuidString.c_str());
  37. m_irradianceImageAttachmentId = AZStd::string::format("ProbeIrradianceImageAttachmentId_%s", uuidString.c_str());
  38. m_distanceImageAttachmentId = AZStd::string::format("ProbeDistanceImageAttachmentId_%s", uuidString.c_str());
  39. m_probeDataImageAttachmentId = AZStd::string::format("ProbeDataImageAttachmentId_%s", uuidString.c_str());
  40. m_gridDataBufferAttachmentId = AZStd::string::format("ProbeGridDataBufferAttachmentId_%s", uuidString.c_str());
  41. m_visualizationTlasAttachmentId = AZStd::string::format("ProbeVisualizationTlasAttachmentId_%s", uuidString.c_str());
  42. m_visualizationTlasInstancesAttachmentId = AZStd::string::format("ProbeVisualizationTlasInstancesAttachmentId_%s", uuidString.c_str());
  43. // setup culling
  44. m_cullable.SetDebugName(AZ::Name("DiffuseProbeGrid Volume"));
  45. // create the visualization TLAS
  46. m_visualizationTlas = aznew RHI::RayTracingTlas;
  47. // create the grid data buffer
  48. m_gridDataBuffer = aznew RHI::Buffer;
  49. RHI::BufferDescriptor descriptor;
  50. descriptor.m_byteCount = DiffuseProbeGridRenderData::GridDataBufferSize;
  51. descriptor.m_bindFlags = RHI::BufferBindFlags::ShaderReadWrite;
  52. RHI::BufferInitRequest request;
  53. request.m_buffer = m_gridDataBuffer.get();
  54. request.m_descriptor = descriptor;
  55. [[maybe_unused]] RHI::ResultCode result = m_renderData->m_bufferPool->InitBuffer(request);
  56. AZ_Assert(result == RHI::ResultCode::Success, "Failed to initialize GridData buffer");
  57. }
  58. void DiffuseProbeGrid::Simulate(uint32_t probeIndex)
  59. {
  60. UpdateTextures();
  61. if (m_renderObjectSrg)
  62. {
  63. // the list index passed in from the feature processor is the index of this probe in the sorted probe list.
  64. // this is needed to render the probe volumes in order from largest to smallest
  65. RHI::DrawItemSortKey sortKey = static_cast<RHI::DrawItemSortKey>(probeIndex);
  66. if (sortKey != m_sortKey)
  67. {
  68. if (m_renderData->m_pipelineState->GetRHIPipelineState())
  69. {
  70. // the sort key changed, rebuild draw packets
  71. m_sortKey = sortKey;
  72. RHI::DrawPacketBuilder drawPacketBuilder{RHI::MultiDevice::AllDevices};
  73. drawPacketBuilder.Begin(nullptr);
  74. drawPacketBuilder.SetGeometryView(&m_renderData->m_geometryView);
  75. drawPacketBuilder.AddShaderResourceGroup(m_renderObjectSrg->GetRHIShaderResourceGroup());
  76. RHI::DrawPacketBuilder::DrawRequest drawRequest;
  77. drawRequest.m_streamIndices = m_renderData->m_geometryView.GetFullStreamBufferIndices();
  78. drawRequest.m_listTag = m_renderData->m_drawListTag;
  79. drawRequest.m_pipelineState = m_renderData->m_pipelineState->GetRHIPipelineState();
  80. drawRequest.m_sortKey = m_sortKey;
  81. drawPacketBuilder.AddDrawItem(drawRequest);
  82. m_drawPacket = drawPacketBuilder.End();
  83. // we also need to update culling with the new draw packet
  84. UpdateCulling();
  85. }
  86. }
  87. }
  88. m_probeRayRotation = AZ::Quaternion::CreateIdentity();
  89. m_frameUpdateIndex = (m_frameUpdateIndex + 1) % m_frameUpdateCount;
  90. }
  91. bool DiffuseProbeGrid::ValidateProbeSpacing(const AZ::Vector3& newSpacing)
  92. {
  93. return ValidateProbeCount(m_extents, newSpacing);
  94. }
  95. void DiffuseProbeGrid::SetProbeSpacing(const AZ::Vector3& probeSpacing)
  96. {
  97. // remove previous spacing from the render extents
  98. m_renderExtents -= m_probeSpacing;
  99. // update probe spacing
  100. m_probeSpacing = probeSpacing;
  101. // expand the extents by one probe spacing unit in order to blend properly around the edges of the volume
  102. m_renderExtents += m_probeSpacing;
  103. m_obbWs = Obb::CreateFromPositionRotationAndHalfLengths(m_transform.GetTranslation(), m_transform.GetRotation(), m_renderExtents / 2.0f);
  104. // recompute the number of probes since the spacing changed
  105. UpdateProbeCount();
  106. m_updateTextures = true;
  107. }
  108. void DiffuseProbeGrid::SetViewBias(float viewBias)
  109. {
  110. m_viewBias = viewBias;
  111. m_updateRenderObjectSrg = true;
  112. }
  113. void DiffuseProbeGrid::SetNormalBias(float normalBias)
  114. {
  115. m_normalBias = normalBias;
  116. m_updateRenderObjectSrg = true;
  117. }
  118. void DiffuseProbeGrid::SetNumRaysPerProbe(DiffuseProbeGridNumRaysPerProbe numRaysPerProbe)
  119. {
  120. m_numRaysPerProbe = numRaysPerProbe;
  121. m_updateTextures = true;
  122. }
  123. void DiffuseProbeGrid::SetTransform(const AZ::Transform& transform)
  124. {
  125. m_transform = transform;
  126. m_obbWs = Obb::CreateFromPositionRotationAndHalfLengths(m_transform.GetTranslation(), m_transform.GetRotation(), m_renderExtents / 2.0f);
  127. // probes need to be relocated since the grid position changed
  128. m_remainingRelocationIterations = DefaultNumRelocationIterations;
  129. m_updateRenderObjectSrg = true;
  130. }
  131. bool DiffuseProbeGrid::ValidateExtents(const AZ::Vector3& newExtents)
  132. {
  133. return ValidateProbeCount(newExtents, m_probeSpacing);
  134. }
  135. void DiffuseProbeGrid::SetExtents(const AZ::Vector3& extents)
  136. {
  137. m_extents = extents;
  138. // recompute the number of probes since the extents changed
  139. UpdateProbeCount();
  140. // expand the extents by one probe spacing unit in order to blend properly around the edges of the volume
  141. m_renderExtents = m_extents + m_probeSpacing;
  142. m_obbWs = Obb::CreateFromPositionRotationAndHalfLengths(m_transform.GetTranslation(), m_transform.GetRotation(), m_renderExtents / 2.0f);
  143. m_updateTextures = true;
  144. }
  145. void DiffuseProbeGrid::SetAmbientMultiplier(float ambientMultiplier)
  146. {
  147. m_ambientMultiplier = ambientMultiplier;
  148. m_updateRenderObjectSrg = true;
  149. }
  150. void DiffuseProbeGrid::Enable(bool enabled)
  151. {
  152. m_enabled = enabled;
  153. m_updateRenderObjectSrg = true;
  154. }
  155. void DiffuseProbeGrid::SetMode(DiffuseProbeGridMode mode)
  156. {
  157. // handle auto-select
  158. if (mode == DiffuseProbeGridMode::AutoSelect)
  159. {
  160. m_mode = (RHI::RHISystemInterface::Get()->GetRayTracingSupport() != RHI::MultiDevice::NoDevices) ? DiffuseProbeGridMode::RealTime : DiffuseProbeGridMode::Baked;
  161. }
  162. else
  163. {
  164. m_mode = mode;
  165. }
  166. m_updateTextures = true;
  167. }
  168. void DiffuseProbeGrid::SetScrolling(bool scrolling)
  169. {
  170. if (m_scrolling == scrolling)
  171. {
  172. return;
  173. }
  174. m_scrolling = scrolling;
  175. // probes need to be relocated since the scrolling mode changed
  176. m_remainingRelocationIterations = DefaultNumRelocationIterations;
  177. m_gridDataInitialized = false;
  178. }
  179. void DiffuseProbeGrid::SetEdgeBlendIbl(bool edgeBlendIbl)
  180. {
  181. if (m_edgeBlendIbl == edgeBlendIbl)
  182. {
  183. return;
  184. }
  185. m_edgeBlendIbl = edgeBlendIbl;
  186. m_updateRenderObjectSrg = true;
  187. }
  188. void DiffuseProbeGrid::SetBakedTextures(const DiffuseProbeGridBakedTextures& bakedTextures)
  189. {
  190. AZ_Assert(bakedTextures.m_irradianceImage.get(), "Invalid Irradiance image passed to SetBakedTextures");
  191. AZ_Assert(bakedTextures.m_distanceImage.get(), "Invalid Distance image passed to SetBakedTextures");
  192. AZ_Assert(bakedTextures.m_probeDataImage.get(), "Invalid ProbeData image passed to SetBakedTextures");
  193. m_bakedIrradianceImage = bakedTextures.m_irradianceImage;
  194. m_bakedDistanceImage = bakedTextures.m_distanceImage;
  195. m_bakedProbeDataImage = bakedTextures.m_probeDataImage;
  196. m_bakedIrradianceRelativePath = bakedTextures.m_irradianceImageRelativePath;
  197. m_bakedDistanceRelativePath = bakedTextures.m_distanceImageRelativePath;
  198. m_bakedProbeDataRelativePath = bakedTextures.m_probeDataImageRelativePath;
  199. m_updateTextures = true;
  200. }
  201. bool DiffuseProbeGrid::HasValidBakedTextures() const
  202. {
  203. return m_bakedIrradianceImage.get() &&
  204. m_bakedDistanceImage.get() &&
  205. m_bakedProbeDataImage.get();
  206. }
  207. void DiffuseProbeGrid::ResetCullingVisibility()
  208. {
  209. m_cullable.m_isVisible = false;
  210. }
  211. bool DiffuseProbeGrid::GetIsVisible() const
  212. {
  213. // we need to go through the DiffuseProbeGrid passes at least once in order to initialize
  214. // the RenderObjectSrg, which means we need to be visible until the RenderObjectSrg is created
  215. if (m_renderObjectSrg == nullptr)
  216. {
  217. return true;
  218. }
  219. // if a bake is in progress we need to make this DiffuseProbeGrid visible
  220. if (!m_textureReadback.IsIdle())
  221. {
  222. return true;
  223. }
  224. return m_cullable.m_isVisible;
  225. }
  226. void DiffuseProbeGrid::SetVisualizationEnabled(bool visualizationEnabled)
  227. {
  228. m_visualizationEnabled = visualizationEnabled;
  229. m_visualizationTlasUpdateRequired = true;
  230. }
  231. void DiffuseProbeGrid::SetVisualizationSphereRadius(float visualizationSphereRadius)
  232. {
  233. m_visualizationSphereRadius = visualizationSphereRadius;
  234. m_visualizationTlasUpdateRequired = true;
  235. }
  236. bool DiffuseProbeGrid::GetVisualizationTlasUpdateRequired() const
  237. {
  238. return m_visualizationTlasUpdateRequired || m_remainingRelocationIterations > 0;
  239. }
  240. bool DiffuseProbeGrid::ContainsPosition(const AZ::Vector3& position) const
  241. {
  242. return m_obbWs.Contains(position);
  243. }
  244. uint32_t DiffuseProbeGrid::GetTotalProbeCount() const
  245. {
  246. return m_probeCountX * m_probeCountY * m_probeCountZ;
  247. }
  248. // compute probe counts for a 2D texture layout
  249. void DiffuseProbeGrid::GetTexture2DProbeCount(uint32_t& probeCountX, uint32_t& probeCountY) const
  250. {
  251. // z-up left-handed
  252. probeCountX = m_probeCountY * m_probeCountZ;
  253. probeCountY = m_probeCountX;
  254. }
  255. void DiffuseProbeGrid::UpdateTextures()
  256. {
  257. if (!m_updateTextures)
  258. {
  259. return;
  260. }
  261. uint32_t probeCountX;
  262. uint32_t probeCountY;
  263. GetTexture2DProbeCount(probeCountX, probeCountY);
  264. if (m_mode == DiffuseProbeGridMode::RealTime)
  265. {
  266. AZStd::vector<uint8_t> initData;
  267. auto initImage = [&](const RHI::ImageInitRequest& request)
  268. {
  269. initData.resize(
  270. request.m_descriptor.m_size.m_width * request.m_descriptor.m_size.m_height *
  271. RHI::GetFormatSize(request.m_descriptor.m_format),
  272. 0);
  273. RHI::ImageUpdateRequest updateRequest;
  274. updateRequest.m_image = request.m_image;
  275. updateRequest.m_image->GetSubresourceLayout(updateRequest.m_sourceSubresourceLayout);
  276. updateRequest.m_sourceData = initData.data();
  277. m_renderData->m_imagePool->UpdateImageContents(updateRequest);
  278. };
  279. // advance to the next image in the frame image array
  280. m_currentImageIndex = (m_currentImageIndex + 1) % ImageFrameCount;
  281. // probe raytrace
  282. {
  283. uint32_t width = GetNumRaysPerProbe().m_rayCount;
  284. uint32_t height = GetTotalProbeCount();
  285. m_rayTraceImage[m_currentImageIndex] = aznew RHI::Image;
  286. RHI::ImageInitRequest request;
  287. request.m_image = m_rayTraceImage[m_currentImageIndex].get();
  288. request.m_descriptor = RHI::ImageDescriptor::Create2D(RHI::ImageBindFlags::ShaderReadWrite | RHI::ImageBindFlags::CopyRead, width, height, DiffuseProbeGridRenderData::RayTraceImageFormat);
  289. [[maybe_unused]] RHI::ResultCode result = m_renderData->m_imagePool->InitImage(request);
  290. AZ_Assert(result == RHI::ResultCode::Success, "Failed to initialize m_probeRayTraceImage image");
  291. m_rayTraceImage[m_currentImageIndex]->SetName(AZ::Name("ProbeRaytrace"));
  292. initImage(request);
  293. }
  294. // probe irradiance
  295. {
  296. uint32_t width = probeCountX * (DefaultNumIrradianceTexels + 2);
  297. uint32_t height = probeCountY * (DefaultNumIrradianceTexels + 2);
  298. m_irradianceImage[m_currentImageIndex] = aznew RHI::Image;
  299. RHI::ImageInitRequest request;
  300. request.m_image = m_irradianceImage[m_currentImageIndex].get();
  301. request.m_descriptor = RHI::ImageDescriptor::Create2D(RHI::ImageBindFlags::ShaderReadWrite | RHI::ImageBindFlags::CopyRead, width, height, DiffuseProbeGridRenderData::IrradianceImageFormat);
  302. RHI::ClearValue clearValue = RHI::ClearValue::CreateVector4Float(0.0f, 0.0f, 0.0f, 0.0f);
  303. request.m_optimizedClearValue = &clearValue;
  304. [[maybe_unused]] RHI::ResultCode result = m_renderData->m_imagePool->InitImage(request);
  305. AZ_Assert(result == RHI::ResultCode::Success, "Failed to initialize m_probeIrradianceImage image");
  306. m_irradianceImage[m_currentImageIndex]->SetName(AZ::Name("ProbeIrradiance"));
  307. initImage(request);
  308. }
  309. // probe distance
  310. {
  311. uint32_t width = probeCountX * (DefaultNumDistanceTexels + 2);
  312. uint32_t height = probeCountY * (DefaultNumDistanceTexels + 2);
  313. m_distanceImage[m_currentImageIndex] = aznew RHI::Image;
  314. RHI::ImageInitRequest request;
  315. request.m_image = m_distanceImage[m_currentImageIndex].get();
  316. request.m_descriptor = RHI::ImageDescriptor::Create2D(RHI::ImageBindFlags::ShaderReadWrite | RHI::ImageBindFlags::CopyRead, width, height, DiffuseProbeGridRenderData::DistanceImageFormat);
  317. [[maybe_unused]] RHI::ResultCode result = m_renderData->m_imagePool->InitImage(request);
  318. AZ_Assert(result == RHI::ResultCode::Success, "Failed to initialize m_probeDistanceImage image");
  319. m_distanceImage[m_currentImageIndex]->SetName(AZ::Name("ProbeDistance"));
  320. initImage(request);
  321. }
  322. // probe data
  323. {
  324. uint32_t width = probeCountX;
  325. uint32_t height = probeCountY;
  326. m_probeDataImage[m_currentImageIndex] = aznew RHI::Image;
  327. RHI::ImageInitRequest request;
  328. request.m_image = m_probeDataImage[m_currentImageIndex].get();
  329. request.m_descriptor = RHI::ImageDescriptor::Create2D(RHI::ImageBindFlags::ShaderReadWrite | RHI::ImageBindFlags::CopyRead, width, height, DiffuseProbeGridRenderData::ProbeDataImageFormat);
  330. [[maybe_unused]] RHI::ResultCode result = m_renderData->m_imagePool->InitImage(request);
  331. AZ_Assert(result == RHI::ResultCode::Success, "Failed to initialize m_probeDataImage image");
  332. m_probeDataImage[m_currentImageIndex]->SetName(AZ::Name("ProbeData"));
  333. initImage(request);
  334. }
  335. // probes need to be relocated since the textures changed
  336. m_remainingRelocationIterations = DefaultNumRelocationIterations;
  337. }
  338. m_updateTextures = false;
  339. // textures have changed so we need to update the render Srg to bind the new ones
  340. m_updateRenderObjectSrg = true;
  341. }
  342. void DiffuseProbeGrid::ComputeProbeCount(const AZ::Vector3& extents, const AZ::Vector3& probeSpacing, uint32_t& probeCountX, uint32_t& probeCountY, uint32_t& probeCountZ)
  343. {
  344. probeCountX = aznumeric_cast<uint32_t>(AZStd::floorf(extents.GetX() / probeSpacing.GetX()));
  345. probeCountY = aznumeric_cast<uint32_t>(AZStd::floorf(extents.GetY() / probeSpacing.GetY()));
  346. probeCountZ = aznumeric_cast<uint32_t>(AZStd::floorf(extents.GetZ() / probeSpacing.GetZ()));
  347. }
  348. bool DiffuseProbeGrid::ValidateProbeCount(const AZ::Vector3& extents, const AZ::Vector3& probeSpacing)
  349. {
  350. uint32_t probeCountX = 0;
  351. uint32_t probeCountY = 0;
  352. uint32_t probeCountZ = 0;
  353. ComputeProbeCount(extents, probeSpacing, probeCountX, probeCountY, probeCountZ);
  354. uint32_t totalProbeCount = probeCountX * probeCountY * probeCountZ;
  355. if (totalProbeCount == 0)
  356. {
  357. return false;
  358. }
  359. // radiance texture height is equal to the probe count
  360. if (totalProbeCount > MaxTextureDimension)
  361. {
  362. return false;
  363. }
  364. // distance texture uses the largest number of texels per probe
  365. // z-up left-handed
  366. uint32_t width = probeCountY * probeCountZ * (DefaultNumDistanceTexels + 2);
  367. uint32_t height = probeCountX * (DefaultNumDistanceTexels + 2);
  368. if (width > MaxTextureDimension || height > MaxTextureDimension)
  369. {
  370. return false;
  371. }
  372. return true;
  373. }
  374. void DiffuseProbeGrid::UpdateProbeCount()
  375. {
  376. ComputeProbeCount(m_extents,
  377. m_probeSpacing,
  378. m_probeCountX,
  379. m_probeCountY,
  380. m_probeCountZ);
  381. }
  382. void DiffuseProbeGrid::UpdatePrepareSrg(const Data::Instance<RPI::Shader>& shader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& layout)
  383. {
  384. if (!m_prepareSrg)
  385. {
  386. m_prepareSrg = RPI::ShaderResourceGroup::Create(shader->GetAsset(), shader->GetSupervariantIndex(), layout->GetName());
  387. AZ_Error("DiffuseProbeGrid", m_prepareSrg.get(), "Failed to create Prepare shader resource group");
  388. }
  389. // scale the normal bias based on the grid density to reduce artifacts on thin geometry, less density results in more bias
  390. float scaledNormalBias = m_normalBias + 0.15f * (m_probeSpacing.GetMaxElement() / 2.0f);
  391. // scale the probe distance exponent based on the grid density to reduce artifacts on thin geometry
  392. static const float MinProbeDistanceExponent = 50.0f;
  393. float scaledProbeDistanceExponent = AZStd::max(m_probeDistanceExponent * (m_probeSpacing.GetMaxElement() / 1.5f), MinProbeDistanceExponent);
  394. // setup packed data
  395. uint32_t packed0 = m_probeCountX | (m_probeCountY << 8) | (m_probeCountZ << 16);
  396. uint32_t packed1 = aznumeric_cast<uint32_t>(m_probeRandomRayBackfaceThreshold * 65535) | (aznumeric_cast<uint32_t>(m_probeFixedRayBackfaceThreshold * 65535) << 16);
  397. uint32_t packed2 = GetNumRaysPerProbe().m_rayCount | (DefaultNumIrradianceTexels << 16) | (DefaultNumDistanceTexels << 24);
  398. uint32_t packed3 = 0;
  399. uint32_t packed4 = (m_scrolling << 16) | (1 << 17) | (1 << 18) | (1 << 19) | (1 << 20); // scrolling, rayFormat, irradianceFormat, relocation, classification
  400. m_prepareSrg->SetBufferView(
  401. m_renderData->m_prepareSrgGridDataNameIndex,
  402. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  403. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgGridDataInitializedNameIndex, m_gridDataInitialized);
  404. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridOriginNameIndex, m_transform.GetTranslation());
  405. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeHysteresisNameIndex, m_probeHysteresis);
  406. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridRotationNameIndex, m_transform.GetRotation());
  407. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeRayRotationNameIndex, m_probeRayRotation);
  408. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeMaxRayDistanceNameIndex, m_probeMaxRayDistance);
  409. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeNormalBiasNameIndex, scaledNormalBias);
  410. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeViewBiasNameIndex, m_viewBias);
  411. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeDistanceExponentNameIndex, scaledProbeDistanceExponent);
  412. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeSpacingNameIndex, m_probeSpacing);
  413. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridPacked0NameIndex, packed0);
  414. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeIrradianceEncodingGammaNameIndex, m_probeIrradianceEncodingGamma);
  415. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeIrradianceThresholdNameIndex, m_probeIrradianceThreshold);
  416. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeBrightnessThresholdNameIndex, m_probeBrightnessThreshold);
  417. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridPacked1NameIndex, packed1);
  418. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridProbeMinFrontfaceDistanceNameIndex, m_probeMinFrontfaceDistance);
  419. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridPacked2NameIndex, packed2);
  420. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridPacked3NameIndex, packed3);
  421. m_prepareSrg->SetConstant(m_renderData->m_prepareSrgProbeGridPacked4NameIndex, packed4);
  422. m_gridDataInitialized = true;
  423. }
  424. void DiffuseProbeGrid::UpdateRayTraceSrg(const Data::Instance<RPI::Shader>& shader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& layout)
  425. {
  426. if (!m_rayTraceSrg)
  427. {
  428. m_rayTraceSrg = RPI::ShaderResourceGroup::Create(shader->GetAsset(), shader->GetSupervariantIndex(), layout->GetName());
  429. AZ_Error("DiffuseProbeGrid", m_rayTraceSrg.get(), "Failed to create RayTrace shader resource group");
  430. }
  431. m_rayTraceSrg->SetBufferView(
  432. m_renderData->m_rayTraceSrgGridDataNameIndex,
  433. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  434. m_rayTraceSrg->SetImageView(
  435. m_renderData->m_rayTraceSrgProbeRayTraceNameIndex,
  436. m_rayTraceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeRayTraceImageViewDescriptor).get());
  437. m_rayTraceSrg->SetImageView(
  438. m_renderData->m_rayTraceSrgProbeIrradianceNameIndex,
  439. m_irradianceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeIrradianceImageViewDescriptor).get());
  440. m_rayTraceSrg->SetImageView(
  441. m_renderData->m_rayTraceSrgProbeDistanceNameIndex,
  442. m_distanceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeDistanceImageViewDescriptor).get());
  443. m_rayTraceSrg->SetImageView(
  444. m_renderData->m_rayTraceSrgProbeDataNameIndex,
  445. m_probeDataImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeDataImageViewDescriptor).get());
  446. m_rayTraceSrg->SetConstant(m_renderData->m_rayTraceSrgAmbientMultiplierNameIndex, m_ambientMultiplier);
  447. m_rayTraceSrg->SetConstant(m_renderData->m_rayTraceSrgGiShadowsNameIndex, m_giShadows);
  448. m_rayTraceSrg->SetConstant(m_renderData->m_rayTraceSrgUseDiffuseIblNameIndex, m_useDiffuseIbl);
  449. m_rayTraceSrg->SetConstant(m_renderData->m_rayTraceSrgFrameUpdateCountNameIndex, m_frameUpdateCount);
  450. m_rayTraceSrg->SetConstant(m_renderData->m_rayTraceSrgFrameUpdateIndexNameIndex, m_frameUpdateIndex);
  451. m_rayTraceSrg->SetConstant(m_renderData->m_rayTraceSrgTransparencyModeNameIndex, aznumeric_cast<uint32_t>(m_transparencyMode));
  452. m_rayTraceSrg->SetConstant(m_renderData->m_rayTraceSrgEmissiveMultiplierNameIndex, m_emissiveMultiplier);
  453. }
  454. void DiffuseProbeGrid::UpdateBlendIrradianceSrg(const Data::Instance<RPI::Shader>& shader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& layout)
  455. {
  456. if (!m_blendIrradianceSrg)
  457. {
  458. m_blendIrradianceSrg = RPI::ShaderResourceGroup::Create(shader->GetAsset(), shader->GetSupervariantIndex(), layout->GetName());
  459. AZ_Error("DiffuseProbeGrid", m_blendIrradianceSrg.get(), "Failed to create BlendIrradiance shader resource group");
  460. }
  461. m_blendIrradianceSrg->SetBufferView(
  462. m_renderData->m_blendIrradianceSrgGridDataNameIndex,
  463. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  464. m_blendIrradianceSrg->SetImageView(
  465. m_renderData->m_blendIrradianceSrgProbeRayTraceNameIndex,
  466. m_rayTraceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeRayTraceImageViewDescriptor).get());
  467. m_blendIrradianceSrg->SetImageView(
  468. m_renderData->m_blendIrradianceSrgProbeIrradianceNameIndex,
  469. m_irradianceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeIrradianceImageViewDescriptor).get());
  470. m_blendIrradianceSrg->SetImageView(
  471. m_renderData->m_blendIrradianceSrgProbeDataNameIndex,
  472. m_probeDataImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeDataImageViewDescriptor).get());
  473. m_blendIrradianceSrg->SetConstant(m_renderData->m_blendIrradianceSrgFrameUpdateCountNameIndex, m_frameUpdateCount);
  474. m_blendIrradianceSrg->SetConstant(m_renderData->m_blendIrradianceSrgFrameUpdateIndexNameIndex, m_frameUpdateIndex);
  475. }
  476. void DiffuseProbeGrid::UpdateBlendDistanceSrg(const Data::Instance<RPI::Shader>& shader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& layout)
  477. {
  478. if (!m_blendDistanceSrg)
  479. {
  480. m_blendDistanceSrg = RPI::ShaderResourceGroup::Create(shader->GetAsset(), shader->GetSupervariantIndex(), layout->GetName());
  481. AZ_Error("DiffuseProbeGrid", m_blendDistanceSrg.get(), "Failed to create BlendDistance shader resource group");
  482. }
  483. m_blendDistanceSrg->SetBufferView(
  484. m_renderData->m_blendDistanceSrgGridDataNameIndex,
  485. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  486. m_blendDistanceSrg->SetImageView(
  487. m_renderData->m_blendDistanceSrgProbeRayTraceNameIndex,
  488. m_rayTraceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeRayTraceImageViewDescriptor).get());
  489. m_blendDistanceSrg->SetImageView(
  490. m_renderData->m_blendDistanceSrgProbeDistanceNameIndex,
  491. m_distanceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeDistanceImageViewDescriptor).get());
  492. m_blendDistanceSrg->SetImageView(
  493. m_renderData->m_blendDistanceSrgProbeDataNameIndex,
  494. m_probeDataImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeDataImageViewDescriptor).get());
  495. m_blendDistanceSrg->SetConstant(m_renderData->m_blendDistanceSrgFrameUpdateCountNameIndex, m_frameUpdateCount);
  496. m_blendDistanceSrg->SetConstant(m_renderData->m_blendDistanceSrgFrameUpdateIndexNameIndex, m_frameUpdateIndex);
  497. }
  498. void DiffuseProbeGrid::UpdateBorderUpdateSrgs(
  499. const Data::Instance<RPI::Shader>& rowShader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& rowSrgLayout,
  500. const Data::Instance<RPI::Shader>& columnShader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& columnSrgLayout)
  501. {
  502. // border update row irradiance
  503. {
  504. if (!m_borderUpdateRowIrradianceSrg)
  505. {
  506. m_borderUpdateRowIrradianceSrg = RPI::ShaderResourceGroup::Create(rowShader->GetAsset(), rowShader->GetSupervariantIndex(), rowSrgLayout->GetName());
  507. AZ_Error("DiffuseProbeGrid", m_borderUpdateRowIrradianceSrg.get(), "Failed to create BorderUpdateRowIrradiance shader resource group");
  508. }
  509. m_borderUpdateRowIrradianceSrg->SetImageView(
  510. m_renderData->m_borderUpdateRowIrradianceSrgProbeTextureNameIndex,
  511. m_irradianceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeIrradianceImageViewDescriptor).get());
  512. m_borderUpdateRowIrradianceSrg->SetConstant(m_renderData->m_borderUpdateRowIrradianceSrgNumTexelsNameIndex, DefaultNumIrradianceTexels);
  513. }
  514. // border update column irradiance
  515. {
  516. if (!m_borderUpdateColumnIrradianceSrg)
  517. {
  518. m_borderUpdateColumnIrradianceSrg = RPI::ShaderResourceGroup::Create(columnShader->GetAsset(), columnShader->GetSupervariantIndex(), columnSrgLayout->GetName());
  519. AZ_Error("DiffuseProbeGrid", m_borderUpdateColumnIrradianceSrg.get(), "Failed to create BorderUpdateColumnRowIrradiance shader resource group");
  520. }
  521. m_borderUpdateColumnIrradianceSrg->SetImageView(
  522. m_renderData->m_borderUpdateColumnIrradianceSrgProbeTextureNameIndex,
  523. m_irradianceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeIrradianceImageViewDescriptor).get());
  524. m_borderUpdateColumnIrradianceSrg->SetConstant(m_renderData->m_borderUpdateColumnIrradianceSrgNumTexelsNameIndex, DefaultNumIrradianceTexels);
  525. }
  526. // border update row distance
  527. {
  528. if (!m_borderUpdateRowDistanceSrg)
  529. {
  530. m_borderUpdateRowDistanceSrg = RPI::ShaderResourceGroup::Create(rowShader->GetAsset(), rowShader->GetSupervariantIndex(), rowSrgLayout->GetName());
  531. AZ_Error("DiffuseProbeGrid", m_borderUpdateRowDistanceSrg.get(), "Failed to create BorderUpdateRowDistance shader resource group");
  532. }
  533. m_borderUpdateRowDistanceSrg->SetImageView(
  534. m_renderData->m_borderUpdateRowDistanceSrgProbeTextureNameIndex,
  535. m_distanceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeDistanceImageViewDescriptor).get());
  536. m_borderUpdateRowDistanceSrg->SetConstant(m_renderData->m_borderUpdateRowDistanceSrgNumTexelsNameIndex, DefaultNumDistanceTexels);
  537. }
  538. // border update column distance
  539. {
  540. if (!m_borderUpdateColumnDistanceSrg)
  541. {
  542. m_borderUpdateColumnDistanceSrg = RPI::ShaderResourceGroup::Create(columnShader->GetAsset(), columnShader->GetSupervariantIndex(), columnSrgLayout->GetName());
  543. AZ_Error("DiffuseProbeGrid", m_borderUpdateColumnDistanceSrg.get(), "Failed to create BorderUpdateColumnRowDistance shader resource group");
  544. }
  545. m_borderUpdateColumnDistanceSrg->SetImageView(
  546. m_renderData->m_borderUpdateColumnDistanceSrgProbeTextureNameIndex,
  547. m_distanceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeDistanceImageViewDescriptor).get());
  548. m_borderUpdateColumnDistanceSrg->SetConstant(m_renderData->m_borderUpdateColumnDistanceSrgNumTexelsNameIndex, DefaultNumDistanceTexels);
  549. }
  550. }
  551. void DiffuseProbeGrid::UpdateRelocationSrg(const Data::Instance<RPI::Shader>& shader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& layout)
  552. {
  553. if (!m_relocationSrg)
  554. {
  555. m_relocationSrg = RPI::ShaderResourceGroup::Create(shader->GetAsset(), shader->GetSupervariantIndex(), layout->GetName());
  556. AZ_Error("DiffuseProbeGrid", m_relocationSrg.get(), "Failed to create Relocation shader resource group");
  557. }
  558. m_relocationSrg->SetBufferView(
  559. m_renderData->m_relocationSrgGridDataNameIndex,
  560. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  561. m_relocationSrg->SetImageView(
  562. m_renderData->m_relocationSrgProbeRayTraceNameIndex,
  563. m_rayTraceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeRayTraceImageViewDescriptor).get());
  564. m_relocationSrg->SetImageView(
  565. m_renderData->m_relocationSrgProbeDataNameIndex,
  566. m_probeDataImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeDataImageViewDescriptor).get());
  567. m_relocationSrg->SetConstant(m_renderData->m_relocationSrgFrameUpdateCountNameIndex, m_frameUpdateCount);
  568. m_relocationSrg->SetConstant(m_renderData->m_relocationSrgFrameUpdateIndexNameIndex, m_frameUpdateIndex);
  569. }
  570. void DiffuseProbeGrid::UpdateClassificationSrg(const Data::Instance<RPI::Shader>& shader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& layout)
  571. {
  572. if (!m_classificationSrg)
  573. {
  574. m_classificationSrg = RPI::ShaderResourceGroup::Create(shader->GetAsset(), shader->GetSupervariantIndex(), layout->GetName());
  575. AZ_Error("DiffuseProbeGrid", m_classificationSrg.get(), "Failed to create Classification shader resource group");
  576. }
  577. m_classificationSrg->SetBufferView(
  578. m_renderData->m_classificationSrgGridDataNameIndex,
  579. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  580. m_classificationSrg->SetImageView(
  581. m_renderData->m_classificationSrgProbeRayTraceNameIndex,
  582. m_rayTraceImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeRayTraceImageViewDescriptor).get());
  583. m_classificationSrg->SetImageView(
  584. m_renderData->m_classificationSrgProbeDataNameIndex,
  585. m_probeDataImage[m_currentImageIndex]->GetImageView(m_renderData->m_probeDataImageViewDescriptor).get());
  586. m_classificationSrg->SetConstant(m_renderData->m_classificationSrgFrameUpdateCountNameIndex, m_frameUpdateCount);
  587. m_classificationSrg->SetConstant(m_renderData->m_classificationSrgFrameUpdateIndexNameIndex, m_frameUpdateIndex);
  588. }
  589. void DiffuseProbeGrid::UpdateRenderObjectSrg()
  590. {
  591. if (!m_updateRenderObjectSrg)
  592. {
  593. return;
  594. }
  595. if (!m_renderObjectSrg)
  596. {
  597. m_renderObjectSrg = RPI::ShaderResourceGroup::Create(m_renderData->m_shader->GetAsset(), m_renderData->m_shader->GetSupervariantIndex(), m_renderData->m_srgLayout->GetName());
  598. AZ_Error("DiffuseProbeGrid", m_renderObjectSrg.get(), "Failed to create render shader resource group");
  599. }
  600. m_renderObjectSrg->SetBufferView(
  601. m_renderData->m_renderSrgGridDataNameIndex,
  602. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  603. AZ::Matrix3x4 modelToWorld = AZ::Matrix3x4::CreateFromTransform(m_transform) * AZ::Matrix3x4::CreateScale(m_renderExtents);
  604. m_renderObjectSrg->SetConstant(m_renderData->m_renderSrgModelToWorldNameIndex, modelToWorld);
  605. AZ::Matrix3x4 modelToWorldInverse = modelToWorld.GetInverseFull();
  606. m_renderObjectSrg->SetConstant(m_renderData->m_renderSrgModelToWorldInverseNameIndex, modelToWorldInverse);
  607. m_renderObjectSrg->SetConstant(m_renderData->m_renderSrgObbHalfLengthsNameIndex, m_obbWs.GetHalfLengths());
  608. m_renderObjectSrg->SetConstant(m_renderData->m_renderSrgEnableDiffuseGiNameIndex, m_enabled);
  609. m_renderObjectSrg->SetConstant(m_renderData->m_renderSrgAmbientMultiplierNameIndex, m_ambientMultiplier);
  610. m_renderObjectSrg->SetConstant(m_renderData->m_renderSrgEdgeBlendIblNameIndex, m_edgeBlendIbl);
  611. m_renderObjectSrg->SetImageView(
  612. m_renderData->m_renderSrgProbeIrradianceNameIndex,
  613. GetIrradianceImage()->GetImageView(m_renderData->m_probeIrradianceImageViewDescriptor).get());
  614. m_renderObjectSrg->SetImageView(
  615. m_renderData->m_renderSrgProbeDistanceNameIndex,
  616. GetDistanceImage()->GetImageView(m_renderData->m_probeDistanceImageViewDescriptor).get());
  617. m_renderObjectSrg->SetImageView(
  618. m_renderData->m_renderSrgProbeDataNameIndex,
  619. GetProbeDataImage()->GetImageView(m_renderData->m_probeDataImageViewDescriptor).get());
  620. m_updateRenderObjectSrg = false;
  621. // update culling now since the position and/or extents may have changed
  622. UpdateCulling();
  623. }
  624. void DiffuseProbeGrid::UpdateVisualizationPrepareSrg(const Data::Instance<RPI::Shader>& shader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& layout)
  625. {
  626. if (!m_visualizationPrepareSrg)
  627. {
  628. m_visualizationPrepareSrg = RPI::ShaderResourceGroup::Create(shader->GetAsset(), shader->GetSupervariantIndex(), layout->GetName());
  629. AZ_Error("DiffuseProbeGrid", m_visualizationPrepareSrg.get(), "Failed to create VisualizationPrepare shader resource group");
  630. }
  631. uint32_t tlasInstancesBufferByteCount = aznumeric_cast<uint32_t>(m_visualizationTlas->GetTlasInstancesBuffer()->GetDescriptor().m_byteCount);
  632. RHI::BufferViewDescriptor bufferViewDescriptor = RHI::BufferViewDescriptor::CreateStructured(0, tlasInstancesBufferByteCount / RayTracingTlasInstanceElementSize, RayTracingTlasInstanceElementSize);
  633. m_visualizationPrepareSrg->SetBufferView(
  634. m_renderData->m_visualizationPrepareSrgTlasInstancesNameIndex,
  635. m_visualizationTlas->GetTlasInstancesBuffer()->GetBufferView(bufferViewDescriptor).get());
  636. m_visualizationPrepareSrg->SetBufferView(
  637. m_renderData->m_visualizationPrepareSrgGridDataNameIndex,
  638. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  639. m_visualizationPrepareSrg->SetImageView(
  640. m_renderData->m_visualizationPrepareSrgProbeDataNameIndex,
  641. GetProbeDataImage()->GetImageView(m_renderData->m_probeDataImageViewDescriptor).get());
  642. m_visualizationPrepareSrg->SetConstant(m_renderData->m_visualizationPrepareSrgProbeSphereRadiusNameIndex, m_visualizationSphereRadius);
  643. }
  644. void DiffuseProbeGrid::UpdateVisualizationRayTraceSrg(const Data::Instance<RPI::Shader>& shader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& layout, const RHI::ImageView* outputImageView)
  645. {
  646. if (!m_visualizationRayTraceSrg)
  647. {
  648. m_visualizationRayTraceSrg = RPI::ShaderResourceGroup::Create(shader->GetAsset(), shader->GetSupervariantIndex(), layout->GetName());
  649. AZ_Error("DiffuseProbeGrid", m_visualizationRayTraceSrg.get(), "Failed to create VisualizationRayTrace shader resource group");
  650. }
  651. uint32_t tlasBufferByteCount = aznumeric_cast<uint32_t>(m_visualizationTlas->GetTlasBuffer()->GetDescriptor().m_byteCount);
  652. RHI::BufferViewDescriptor bufferViewDescriptor = RHI::BufferViewDescriptor::CreateRayTracingTLAS(tlasBufferByteCount);
  653. m_visualizationRayTraceSrg->SetBufferView(
  654. m_renderData->m_visualizationRayTraceSrgTlasNameIndex,
  655. m_visualizationTlas->GetTlasBuffer()->GetBufferView(bufferViewDescriptor).get());
  656. m_visualizationRayTraceSrg->SetBufferView(
  657. m_renderData->m_visualizationRayTraceSrgGridDataNameIndex,
  658. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  659. m_visualizationRayTraceSrg->SetImageView(
  660. m_renderData->m_visualizationRayTraceSrgProbeIrradianceNameIndex,
  661. GetIrradianceImage()->GetImageView(m_renderData->m_probeIrradianceImageViewDescriptor).get());
  662. m_visualizationRayTraceSrg->SetImageView(
  663. m_renderData->m_visualizationRayTraceSrgProbeDistanceNameIndex,
  664. GetDistanceImage()->GetImageView(m_renderData->m_probeDistanceImageViewDescriptor).get());
  665. m_visualizationRayTraceSrg->SetImageView(
  666. m_renderData->m_visualizationRayTraceSrgProbeDataNameIndex,
  667. GetProbeDataImage()->GetImageView(m_renderData->m_probeDataImageViewDescriptor).get());
  668. m_visualizationRayTraceSrg->SetConstant(m_renderData->m_visualizationRayTraceSrgShowInactiveProbesNameIndex, m_visualizationShowInactiveProbes);
  669. m_visualizationRayTraceSrg->SetImageView(m_renderData->m_visualizationRayTraceSrgOutputNameIndex, outputImageView);
  670. }
  671. void DiffuseProbeGrid::UpdateQuerySrg(const Data::Instance<RPI::Shader>& shader, const RHI::Ptr<RHI::ShaderResourceGroupLayout>& layout)
  672. {
  673. if (!m_querySrg)
  674. {
  675. m_querySrg = RPI::ShaderResourceGroup::Create(shader->GetAsset(), shader->GetSupervariantIndex(), layout->GetName());
  676. AZ_Error("DiffuseProbeGrid", m_querySrg.get(), "Failed to create Query shader resource group");
  677. }
  678. m_querySrg->SetBufferView(
  679. m_renderData->m_querySrgGridDataNameIndex,
  680. m_gridDataBuffer->GetBufferView(m_renderData->m_gridDataBufferViewDescriptor).get());
  681. m_querySrg->SetImageView(
  682. m_renderData->m_querySrgProbeIrradianceNameIndex,
  683. GetIrradianceImage()->GetImageView(m_renderData->m_probeIrradianceImageViewDescriptor).get());
  684. m_querySrg->SetImageView(
  685. m_renderData->m_querySrgProbeDistanceNameIndex,
  686. GetDistanceImage()->GetImageView(m_renderData->m_probeDistanceImageViewDescriptor).get());
  687. m_querySrg->SetImageView(
  688. m_renderData->m_querySrgProbeDataNameIndex,
  689. GetProbeDataImage()->GetImageView(m_renderData->m_probeDataImageViewDescriptor).get());
  690. m_querySrg->SetConstant(m_renderData->m_querySrgAmbientMultiplierNameIndex, m_ambientMultiplier);
  691. }
  692. void DiffuseProbeGrid::UpdateCulling()
  693. {
  694. if (!m_drawPacket)
  695. {
  696. return;
  697. }
  698. // set draw list mask
  699. m_cullable.m_cullData.m_drawListMask.reset();
  700. m_cullable.m_cullData.m_drawListMask = m_drawPacket->GetDrawListMask();
  701. // setup the Lod entry, only one entry is needed for the draw packet
  702. m_cullable.m_lodData.m_lods.clear();
  703. m_cullable.m_lodData.m_lods.resize(1);
  704. RPI::Cullable::LodData::Lod& lod = m_cullable.m_lodData.m_lods.back();
  705. // add the draw packet
  706. lod.m_drawPackets.push_back(m_drawPacket.get());
  707. // set screen coverage
  708. // probe volume should cover at least a screen pixel at 1080p to be drawn
  709. static const float MinimumScreenCoverage = 1.0f / 1080.0f;
  710. lod.m_screenCoverageMin = MinimumScreenCoverage;
  711. lod.m_screenCoverageMax = 1.0f;
  712. // update cullable bounds
  713. Aabb aabbWs = Aabb::CreateFromObb(m_obbWs);
  714. Vector3 center;
  715. float radius;
  716. aabbWs.GetAsSphere(center, radius);
  717. m_cullable.m_cullData.m_boundingSphere = Sphere(center, radius);
  718. m_cullable.m_cullData.m_boundingObb = m_obbWs;
  719. m_cullable.m_cullData.m_visibilityEntry.m_boundingVolume = aabbWs;
  720. m_cullable.m_cullData.m_visibilityEntry.m_userData = &m_cullable;
  721. m_cullable.m_cullData.m_visibilityEntry.m_typeFlags = AzFramework::VisibilityEntry::TYPE_RPI_Cullable;
  722. // register with culling system
  723. m_scene->GetCullingScene()->RegisterOrUpdateCullable(m_cullable);
  724. }
  725. } // namespace Render
  726. } // namespace AZ