VideoBackends / VideoCommon: add new uniform buffer object for custom shader materials (slot 3, geometry shader buffer moves to slot 4 if available)

This commit is contained in:
iwubcode 2023-09-19 19:29:38 -05:00
parent 92accc3ef7
commit b6d321bfb1
16 changed files with 214 additions and 83 deletions

View file

@ -105,9 +105,9 @@ void SHADER::SetProgramVariables()
if (VSBlock_id != -1)
glUniformBlockBinding(glprogid, VSBlock_id, 2);
if (GSBlock_id != -1)
glUniformBlockBinding(glprogid, GSBlock_id, 3);
glUniformBlockBinding(glprogid, GSBlock_id, 4);
if (UBERBlock_id != -1)
glUniformBlockBinding(glprogid, UBERBlock_id, 4);
glUniformBlockBinding(glprogid, UBERBlock_id, 5);
// Bind Texture Samplers
for (int a = 0; a < 8; ++a)
@ -232,35 +232,54 @@ void ProgramShaderCache::UploadConstants()
auto& pixel_shader_manager = system.GetPixelShaderManager();
auto& vertex_shader_manager = system.GetVertexShaderManager();
auto& geometry_shader_manager = system.GetGeometryShaderManager();
if (pixel_shader_manager.dirty || vertex_shader_manager.dirty || geometry_shader_manager.dirty)
if (pixel_shader_manager.dirty || vertex_shader_manager.dirty || geometry_shader_manager.dirty ||
pixel_shader_manager.custom_constants_dirty)
{
auto buffer = s_buffer->Map(s_ubo_buffer_size, s_ubo_align);
const u32 custom_constants_size = static_cast<u32>(
Common::AlignUp(pixel_shader_manager.custom_constants.size(), s_ubo_align));
auto buffer = s_buffer->Map(s_ubo_buffer_size + custom_constants_size, s_ubo_align);
memcpy(buffer.first, &pixel_shader_manager.constants, sizeof(PixelShaderConstants));
memcpy(buffer.first + Common::AlignUp(sizeof(PixelShaderConstants), s_ubo_align),
&vertex_shader_manager.constants, sizeof(VertexShaderConstants));
u64 size = Common::AlignUp(sizeof(PixelShaderConstants), s_ubo_align);
memcpy(buffer.first + Common::AlignUp(sizeof(PixelShaderConstants), s_ubo_align) +
Common::AlignUp(sizeof(VertexShaderConstants), s_ubo_align),
&geometry_shader_manager.constants, sizeof(GeometryShaderConstants));
memcpy(buffer.first + size, &vertex_shader_manager.constants, sizeof(VertexShaderConstants));
size += Common::AlignUp(sizeof(VertexShaderConstants), s_ubo_align);
if (!pixel_shader_manager.custom_constants.empty())
{
memcpy(buffer.first + size, pixel_shader_manager.custom_constants.data(),
pixel_shader_manager.custom_constants.size());
size += custom_constants_size;
}
memcpy(buffer.first + size, &geometry_shader_manager.constants,
sizeof(GeometryShaderConstants));
s_buffer->Unmap(s_ubo_buffer_size + custom_constants_size);
s_buffer->Unmap(s_ubo_buffer_size);
glBindBufferRange(GL_UNIFORM_BUFFER, 1, s_buffer->m_buffer, buffer.second,
sizeof(PixelShaderConstants));
glBindBufferRange(GL_UNIFORM_BUFFER, 2, s_buffer->m_buffer,
buffer.second + Common::AlignUp(sizeof(PixelShaderConstants), s_ubo_align),
size = Common::AlignUp(sizeof(PixelShaderConstants), s_ubo_align);
glBindBufferRange(GL_UNIFORM_BUFFER, 2, s_buffer->m_buffer, buffer.second + size,
sizeof(VertexShaderConstants));
glBindBufferRange(GL_UNIFORM_BUFFER, 3, s_buffer->m_buffer,
buffer.second + Common::AlignUp(sizeof(PixelShaderConstants), s_ubo_align) +
Common::AlignUp(sizeof(VertexShaderConstants), s_ubo_align),
size += Common::AlignUp(sizeof(VertexShaderConstants), s_ubo_align);
if (!pixel_shader_manager.custom_constants.empty())
{
glBindBufferRange(GL_UNIFORM_BUFFER, 3, s_buffer->m_buffer, buffer.second + size,
pixel_shader_manager.custom_constants.size());
size += Common::AlignUp(pixel_shader_manager.custom_constants.size(), s_ubo_align);
}
glBindBufferRange(GL_UNIFORM_BUFFER, 4, s_buffer->m_buffer, buffer.second + size,
sizeof(GeometryShaderConstants));
pixel_shader_manager.dirty = false;
vertex_shader_manager.dirty = false;
geometry_shader_manager.dirty = false;
pixel_shader_manager.custom_constants_dirty = false;
ADDSTAT(g_stats.this_frame.bytes_uniform_streamed, s_ubo_buffer_size);
ADDSTAT(g_stats.this_frame.bytes_uniform_streamed, s_ubo_buffer_size + custom_constants_size);
}
}
@ -273,7 +292,7 @@ void ProgramShaderCache::UploadConstants(const void* data, u32 data_size)
s_buffer->Unmap(alloc_size);
// bind the same sub-buffer to all stages
for (u32 index = 1; index <= 3; index++)
for (u32 index = 1; index <= 4; index++)
glBindBufferRange(GL_UNIFORM_BUFFER, index, s_buffer->m_buffer, buffer.second, data_size);
ADDSTAT(g_stats.this_frame.bytes_uniform_streamed, data_size);