diff --git a/src/tangerine.cpp b/src/tangerine.cpp index 6fa33b8..5ed870f 100644 --- a/src/tangerine.cpp +++ b/src/tangerine.cpp @@ -314,19 +314,31 @@ initLights(MemoryArena* arena, GLContext* gl_ctx, u32 max_lights) // FIXME: revisit for 'Scene' abstraction // TODO: we need a way to do this automatically somehow - u32 buf_size = 8 * sizeof(u32) // NOTE: 'header' + LightsBuffer* lb = ARENA_ALLOC(arena, LightsBuffer, 1); + lb->buf_size = 8 * sizeof(u32) // NOTE: 'header' + 6 * max_lights * sizeof(glm::vec4); // NOTE: vector arrays + LOGF(Debug, "buf_size: %d\n", lb->buf_size); + lb->buffer = ARENA_ALLOC(arena, u8, lb->buf_size); - LOGF(Debug, "buf_size: %d\n", buf_size); + lb->max_p_lights = (u32*) lb->buffer; + lb->active_p_lights = + (u32*) arenaGetAddressOffset(lb->max_p_lights, sizeof(u32)); + lb->max_d_lights = + (u32*) arenaGetAddressOffset(lb->active_p_lights, sizeof(u32)); + lb->active_d_lights = + (u32*) arenaGetAddressOffset(lb->max_d_lights, sizeof(u32)); - LightsBuffer* lb = (LightsBuffer*) ARENA_ALLOC(arena, u8, buf_size); - lb->buf_size = buf_size; - lb->max_p_lights = max_lights; - lb->max_d_lights = max_lights; + *lb->max_p_lights = max_lights; + *lb->max_d_lights = max_lights; + + // NOTE: add padding, we're not actually using this since 4 * u32 is on a + // 16 byte boundary, but will be helpful if we need to add more 'headers' + // in the future + void* arr_start = arenaGetAddressOffset(lb->buffer, 8 * sizeof(u32)); // NOTE: set offsets for array pointers - lb->pl_positions = (glm::vec4*) arenaGetAddressOffset(lb, sizeof(*lb)); u32 arr_size = max_lights * sizeof(glm::vec4); + lb->pl_positions = (glm::vec4*) arr_start; lb->pl_colors = (glm::vec4*) arenaGetAddressOffset(lb->pl_positions, arr_size); lb->pl_intensities = @@ -350,8 +362,8 @@ initLights(MemoryArena* arena, GLContext* gl_ctx, u32 max_lights) glGenBuffers(1, &lights_ubo->id); glBindBuffer(lights_ubo->target, lights_ubo->id); glBufferData(lights_ubo->target, - buf_size, - lb, + lb->buf_size, + lb->buffer, GL_DYNAMIC_DRAW); glBindBufferBase(lights_ubo->target, lights_ubo->binding_idx, diff --git a/src/tangerine.h b/src/tangerine.h index e7e1ee8..4a202fd 100644 --- a/src/tangerine.h +++ b/src/tangerine.h @@ -107,16 +107,17 @@ struct GLClearColor }; // NOTE: structure to match the layout of the 'lights' uniform in a shader +// all the pointers are pointers into the address space of 'buffer'. the vec4 +// pointers are required to start on 16 byte boundaries as per layout std140, +// so there may be some padding added between the 'header', and the start of +// the arrays struct LightsBuffer { u32 buf_size; - u32 max_p_lights; - u32 active_p_lights; - u32 max_d_lights; - u32 active_d_lights; - - // NOTE: padding for std140, vec4 need to be aligned at 16 bytes - u8 padding[12]; + u32* max_p_lights; + u32* active_p_lights; + u32* max_d_lights; + u32* active_d_lights; glm::vec4* pl_positions; glm::vec4* pl_colors; @@ -125,6 +126,8 @@ struct LightsBuffer glm::vec4* dl_directions; glm::vec4* dl_colors; glm::uvec4* dl_intensities; + + void* buffer; }; struct RenderState @@ -146,11 +149,6 @@ struct RenderState // could match up with gltf scene graph where everyting is part of a node // TODO: will also need other types of lights: directional, spotlight LightsBuffer* lights_buf; -#if 0 - u32 num_lights; - u32 max_lights; - PointLight* lights; -#endif };