ue5-lumen的场景重建BeginUpdateLumenSceneTasks

lumen在渲染的时候会走几个步骤:

第一是BeginUpdateLumenSceneTasks对场景的距离场体素重建

第二是UpdateLumenScene更新lumen的场景以及包括用nanite提出并且上传lumen的card

第三是RenderLumenSceneLighting获取lumen光照的直接光与间接光

第四是RenderLumenSceneVisualization可视化探针的获取与设置,体素步进与辐射度设置。

第五是RenderDiffuseIndirectAndAmbientOcclusion中对lumen的探针执行计算获取探针的光照来叠加。

UpdateDistantScene

这个是更新场景的card的分布信息。他叫做带距离场景。

首先获取NumDesiredCascades来获取从相机到远端的分布。最多是8个分布的包围盒。

如果数量不一致则要删除之前的card的分布。

然后开始建立类似级联阴影的长方体范围(简称包围盒吧)

GenerateCoordinateSystem(CardToLocalRotationZ, CardToLocalRotationX, CardToLocalRotationY);这里是通过CardToLocalRotationZ来建立出x轴和y轴。这个是为了后面建立每个包围盒下的范围做准备的。

SplitNear = GetCascadeStartDistance(CascadeIndex, NumDesiredCascades);

这里是获取包围盒离相机最近的距离。

SplitFar = GetCascadeStartDistance(CascadeIndex + 1, NumDesiredCascades);是包围盒离相机的最远距离。

CascadeBounds = GetCascadeBounds(View, SplitNear, SplitFar);这里是获取包围盒的整个bounds。

LumenSceneData.Cards[DistantCardIndex].SetTransform(FMatrix::Identity, CascadeCenter, CardToLocalRotationX, CardToLocalRotationY, CardToLocalRotationZ, LocalExtent);这里是设置整个card的包围盒的范围到card上。

完成整个card的设置。

如果设置了需要显示这个card的包围盒的信息,在后面会设置显示。

其中DrawWireBox是底层提供的绘制线框的接口

FSimpleElementCollector::DrawLine这里画线。画整个线框是:

UpdateLumenScenePrimitives:

这个是对lumen场景中的三角形做卸载和加载。

首先要对要移除的三角形从大到小排序,LumenSceneData.PendingRemoveOperations.Sort(FGreaterLumenPrimitiveIndex())

然后移除三角形,

接下来就是对需要加入到场景的对象做加入场景的操作。

首先会通过LocalToWorld和LocalBoundingBox来确定是否所有三角形都在范围内。然后如果是nanite下的话必然有一个instances。

然后查看这些三角形是否能合并成一个meshcard来处理,主要让三角形大小跟GLumenMeshCardsMergedMaxWorldSize比较,如果小于这个大小则可以合并成一个meshcard。然后组成一个FLumenPrimitive。如果不能合并则每个instance都单独一个FLumenPrimitive

然后会看是否可以执行raytracing,然后用sdf来加入sdf的index进来。加入到可以加入到lumen更新的sdf信息。

以上的添加三角形的过程,然后就会进行更新三角形的过程。还是通过bMergedInstances来确定是否可以合并到一个meshcard,如果可以就只执行一个LumenSceneData.UpdateMeshCards,如果不能合并就每个单独走LumenSceneData.UpdateMeshCards

这里的UpdateMeshCards主要做FLumenMeshCards中的所有MeshCardsInstance的数据更新到FLumenCard中,然后让FLumenCard的SetTransform应用到场景中。并存到CardIndicesToUpdateInBuffer来方便后面对card处理。

完成UpdateLumenScenePrimitives处理。

完成UpdateDirtyCards(Scene, bReallocateAtlas, bRecaptureLumenSceneOnce);

UpdateLumenScenePrimitives(Scene);UpdateDistantScene(Scene, Views[0]);后

用TArray<FLumenSurfaceCacheUpdatePacket, SceneRenderingAllocator> Packets;来保存三角形,meshcard,card等信息。

优先级:

NumMeshCardsAddsPerBucket这里对每个meshcard的权重数量增加,对meshcard的优先级排序MeshCardsAddsSortedByPriority。

距离添加:

然后就是添加FCardRenderData此信息到CardsToRender中,这个CardsToRender是用于在UpdateLumenScene中执行正式的渲染SubmitMeshDrawCommandsRange用的,首先根据距离添加

然后把新的meshcard添加

静态网格处理:

AllocateOptionalCardAtlases,主要给到LumenSceneData.IrradianceAtlas和LumenSceneData.IndirectIrradianceAtlas,这里是给到直接光照的rt和间接光照的rt。

UpdateLumenCardAtlasAllocation这里是拿到CardsToRender然后更新FLumenCard。

后面就开始更新CardsToRender下的rhi的uniform,如果是静态的则加入到静态处理的PrimitivesToUpdateStaticMeshes。

通过FPrimitiveSceneInfo::UpdateStaticMeshes来更新静态的网格。这里的UpdateStaticMeshes是ue通用的关于三角形的静态处理。他分为普通的静态处理和nanite的静态处理。

处理完静态网格后就是正式的丢到渲染中了

这里也是分为nanite版本和普通静态网格版本。如果是nanite则加入到NaniteInstanceIds让nanite单独处理。如果是普通版本则执行NewVisibleMeshDrawCommand.Setup

加入到MeshPassProcessor中,让mesh统一处理,这里只是设置了lumen的渲染指令,还没提交渲染,提交渲染是用MeshPassProcessor中的SubmitMeshDrawCommands或SubmitMeshDrawCommandsRange的。

猜你喜欢

转载自blog.csdn.net/llsansun/article/details/123192182