@@ -26,11 +26,20 @@ void OpenGLDebugCallback(GLenum source, GLenum type, GLuint id,
2626
2727// Matches the definition in vpl_tiled_deferred_culling.glsl
2828// See https://fvcaputo.github.io/2019/02/06/memory-alignment.html for alignment info
29- struct GpuVirtualPointLightData {
30- alignas (16 ) glm::vec4 lightPosition = glm::vec4(0 .0f );
31- alignas (16 ) glm::vec4 lightColor = glm::vec4(0 .0f );
32- alignas (16 ) glm::vec4 shadowFarPlaneRadius = glm::vec4(0 .0f ); // last element padding
33- alignas (16 ) glm::vec4 numShadowSamples = glm::vec4(0 .0f ); // last 3 elements padding
29+ struct alignas (16 ) GpuVec {
30+ float v[4 ];
31+
32+ GpuVec (float x, float y, float z, float w) {
33+ v[0 ] = x;
34+ v[1 ] = y;
35+ v[2 ] = z;
36+ v[3 ] = w;
37+ }
38+
39+ GpuVec (float xyzw) : GpuVec (xyzw, xyzw, xyzw, xyzw) {}
40+ GpuVec (const glm::vec4& v) : GpuVec (v[0 ], v[1 ], v[2 ], v[3 ]) {}
41+ GpuVec (const glm::vec3& v) : GpuVec (glm::vec4 (v, 0 .0f )) {}
42+ GpuVec () : GpuVec (0 .0f ) {}
3443};
3544
3645static void printGLInfo (const GFXConfig & config) {
@@ -93,6 +102,8 @@ static void printGLInfo(const GFXConfig & config) {
93102}
94103
95104RendererBackend::RendererBackend (const uint32_t width, const uint32_t height, const std::string& appName) {
105+ static_assert (sizeof (GpuVec) == 16 , " Memory alignment must match up with GLSL" );
106+
96107 STRATUS_LOG << " Initializing SDL video" << std::endl;
97108 if (SDL_Init (SDL_INIT_VIDEO) != 0 ) {
98109 STRATUS_ERROR << " Unable to initialize sdl2" << std::endl;
@@ -325,8 +336,12 @@ void RendererBackend::_InitializeVplData() {
325336 const Bitfield flags = GPU_DYNAMIC_DATA | GPU_MAP_READ | GPU_MAP_WRITE;
326337 std::vector<int > visibleIndicesData (_state.vpls .maxTotalVirtualPointLightsPerFrame , 0 );
327338 _state.vpls .vplVisibleIndices = GpuBuffer ((const void *)visibleIndicesData.data (), sizeof (int ) * visibleIndicesData.size (), flags);
328- std::vector<GpuVirtualPointLightData> vplData (_state.vpls .maxTotalVirtualPointLightsPerFrame , GpuVirtualPointLightData ());
329- _state.vpls .vplLightData = GpuBuffer ((const void *)vplData.data (), sizeof (GpuVirtualPointLightData) * vplData.size (), flags);
339+ _state.vpls .vplPositions = GpuBuffer (nullptr , sizeof (GpuVec) * _state.vpls .maxTotalVirtualPointLightsPerFrame , flags);
340+ _state.vpls .vplColors = GpuBuffer (nullptr , sizeof (GpuVec) * _state.vpls .maxTotalVirtualPointLightsPerFrame , flags);
341+ _state.vpls .vplShadowFactors = GpuBuffer (nullptr , sizeof (float ) * _state.vpls .maxTotalVirtualPointLightsPerFrame , flags);
342+ _state.vpls .vplFarPlanes = GpuBuffer (nullptr , sizeof (float ) * _state.vpls .maxTotalVirtualPointLightsPerFrame , flags);
343+ _state.vpls .vplRadii = GpuBuffer (nullptr , sizeof (float ) * _state.vpls .maxTotalVirtualPointLightsPerFrame , flags);
344+ _state.vpls .vplShadowSamples = GpuBuffer (nullptr , sizeof (float ) * _state.vpls .maxTotalVirtualPointLightsPerFrame , flags);
330345 _state.vpls .vplNumVisible = GpuBuffer (nullptr , sizeof (int ), flags);
331346}
332347
@@ -1277,29 +1292,37 @@ void RendererBackend::_PerformVirtualPointLightCulling(std::vector<std::pair<Lig
12771292 }
12781293
12791294 // Pack data into system memory
1280- std::vector<GpuVirtualPointLightData> vplData (perVPLDistToViewer.size ());
1295+ std::vector<GpuVec> lightPositions (perVPLDistToViewer.size ());
1296+ std::vector<GpuVec> lightColors (perVPLDistToViewer.size ());
1297+ std::vector<float > lightFarPlanes (perVPLDistToViewer.size ());
1298+ std::vector<float > lightRadii (perVPLDistToViewer.size ());
1299+ std::vector<float > lightShadowSamples (perVPLDistToViewer.size ());
12811300 for (size_t i = 0 ; i < perVPLDistToViewer.size (); ++i) {
1282- GpuVirtualPointLightData data;
12831301 VirtualPointLight * point = (VirtualPointLight *)perVPLDistToViewer[i].first .get ();
1284- data. lightPosition = glm::vec4 (point->position , 1 .0f );
1285- data. shadowFarPlaneRadius = glm::vec4 ( 0 . 0f , point->getFarPlane (), point-> getRadius (), 0 . 0f );
1286- data. lightColor = glm::vec4 ( point->getBaseColor () * point-> getIntensity (), 1 . 0f );
1287- data. numShadowSamples = glm::vec4 (point->GetNumShadowSamples (), 0 . 0f , 0 . 0f , 0 .0f );
1288- vplData [i] = std::move (data );
1302+ lightPositions[i] = GpuVec ( glm::vec4 (point->position , 1 .0f ) );
1303+ lightFarPlanes[i] = point->getFarPlane ();
1304+ lightRadii[i] = point->getRadius ( );
1305+ lightColors[i] = GpuVec ( glm::vec4 (point->getBaseColor () * point-> getIntensity (), 1 .0f ) );
1306+ lightShadowSamples [i] = float (point-> GetNumShadowSamples () );
12891307 }
12901308
1291- _state.vplCulling ->bind ();
1292-
12931309 // Move data to GPU memory
1294- _state.vpls .vplLightData .CopyDataToBuffer (0 , sizeof (GpuVirtualPointLightData) * vplData.size (), (const void *)vplData.data ());
1310+ _state.vpls .vplPositions .CopyDataToBuffer (0 , sizeof (GpuVec) * lightPositions.size (), (const void *)lightPositions.data ());
1311+ _state.vpls .vplColors .CopyDataToBuffer (0 , sizeof (GpuVec) * lightColors.size (), (const void *)lightColors.data ());
1312+ _state.vpls .vplFarPlanes .CopyDataToBuffer (0 , sizeof (float ) * lightFarPlanes.size (), (const void *)lightFarPlanes.data ());
1313+ _state.vpls .vplRadii .CopyDataToBuffer (0 , sizeof (float ) * lightRadii.size (), (const void *)lightRadii.data ());
1314+ _state.vpls .vplShadowSamples .CopyDataToBuffer (0 , sizeof (float ) * lightShadowSamples.size (), (const void *)lightShadowSamples.data ());
1315+
1316+ _state.vplCulling ->bind ();
12951317
12961318 // Set up # visible atomic counter
12971319 int numVisible = 0 ;
12981320 _state.vpls .vplNumVisible .CopyDataToBuffer (0 , sizeof (int ), (const void *)&numVisible);
12991321 _state.vpls .vplNumVisible .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 1 );
13001322
13011323 // Bind light data and visibility indices
1302- _state.vpls .vplLightData .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 0 );
1324+ _state.vpls .vplShadowFactors .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 0 );
1325+ _state.vpls .vplPositions .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 4 );
13031326 _state.vpls .vplVisibleIndices .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 3 );
13041327
13051328 _InitCoreCSMData (_state.vplCulling .get ());
@@ -1312,7 +1335,8 @@ void RendererBackend::_PerformVirtualPointLightCulling(std::vector<std::pair<Lig
13121335
13131336 // Bind inputs
13141337 _state.vplTileDeferredCulling ->bindTexture (" gPosition" , _state.buffer .position );
1315- _state.vpls .vplLightData .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 0 );
1338+ _state.vpls .vplPositions .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 0 );
1339+ _state.vpls .vplRadii .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 7 );
13161340 _state.vpls .vplNumVisible .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 1 );
13171341 _state.vpls .vplVisibleIndices .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 3 );
13181342
@@ -1374,7 +1398,11 @@ void RendererBackend::_ComputeVirtualPointLightGlobalIllumination(const std::vec
13741398 // All relevant rendering data is moved to the GPU during the light cull phase
13751399 _state.vpls .vplNumLightsVisiblePerTile .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 3 );
13761400 _state.vpls .vplLightIndicesVisiblePerTile .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 4 );
1377- _state.vpls .vplLightData .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 5 );
1401+ _state.vpls .vplPositions .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 5 );
1402+ _state.vpls .vplColors .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 6 );
1403+ _state.vpls .vplRadii .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 7 );
1404+ _state.vpls .vplFarPlanes .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 8 );
1405+ _state.vpls .vplShadowSamples .BindBase (GpuBaseBindingPoint::SHADER_STORAGE_BUFFER, 9 );
13781406
13791407 _state.vplGlobalIllumination ->bindTexture (" screen" , _state.lightingColorBuffer );
13801408 _state.vplGlobalIllumination ->bindTexture (" gPosition" , _state.buffer .position );
0 commit comments