From ef1bca542460c84bbf571d55e0fa0defd2bdddef Mon Sep 17 00:00:00 2001 From: vlj Date: Sun, 13 Jul 2014 00:11:35 +0200 Subject: [PATCH] Try to factorize shader using variadic templates. --- src/graphics/shaders.cpp | 28 ++++++++++++---------------- src/graphics/shaders.hpp | 39 ++++++++++++++++++++++++++++++++++++--- 2 files changed, 48 insertions(+), 19 deletions(-) diff --git a/src/graphics/shaders.cpp b/src/graphics/shaders.cpp index de08cb62e..a8ab85918 100644 --- a/src/graphics/shaders.cpp +++ b/src/graphics/shaders.cpp @@ -394,7 +394,7 @@ void Shaders::check(const int num) const } } -static void bypassUBO(GLint Program) +void bypassUBO(GLuint Program) { GLint VM = glGetUniformLocation(Program, "ViewMatrix"); glUniformMatrix4fv(VM, 1, GL_FALSE, irr_driver->getViewMatrix().pointer()); @@ -455,13 +455,20 @@ AssignTextureUnit(GLuint Program, const std::vector &uniforms, const std::vector &name) +{ + for (unsigned i = 0; i < name.size(); i++) + { + uniforms.push_back(glGetUniformLocation(Program, name[i])); + } +} + namespace MeshShader { // Solid Normal and depth pass shaders GLuint ObjectPass1Shader::Program; - GLuint ObjectPass1Shader::uniform_MM; - GLuint ObjectPass1Shader::uniform_IMM; GLuint ObjectPass1Shader::TU_tex; void ObjectPass1Shader::init() @@ -470,8 +477,7 @@ namespace MeshShader GL_VERTEX_SHADER, file_manager->getAsset("shaders/object_pass.vert").c_str(), GL_FRAGMENT_SHADER, file_manager->getAsset("shaders/utils/encode_normal.frag").c_str(), GL_FRAGMENT_SHADER, file_manager->getAsset("shaders/object_pass1.frag").c_str()); - uniform_MM = glGetUniformLocation(Program, "ModelMatrix"); - uniform_IMM = glGetUniformLocation(Program, "InverseModelMatrix"); + AssignUniforms(Program, uniforms, {"ModelMatrix", "InverseModelMatrix"}); if (!UserConfigParams::m_ubo_disabled) { GLuint uniform_ViewProjectionMatrixesUBO = glGetUniformBlockIndex(Program, "MatrixesData"); @@ -481,14 +487,6 @@ namespace MeshShader AssignTextureUnit(Program, { { TU_tex, "tex" } }); } - void ObjectPass1Shader::setUniforms(const core::matrix4 &ModelMatrix, const core::matrix4 &InverseModelMatrix) - { - if (UserConfigParams::m_ubo_disabled) - bypassUBO(Program); - glUniformMatrix4fv(uniform_MM, 1, GL_FALSE, ModelMatrix.pointer()); - glUniformMatrix4fv(uniform_IMM, 1, GL_FALSE, InverseModelMatrix.pointer()); - } - GLuint ObjectRefPass1Shader::Program; GLuint ObjectRefPass1Shader::uniform_MM; GLuint ObjectRefPass1Shader::uniform_IMM; @@ -517,9 +515,7 @@ namespace MeshShader { if (UserConfigParams::m_ubo_disabled) bypassUBO(Program); - glUniformMatrix4fv(uniform_MM, 1, GL_FALSE, ModelMatrix.pointer()); - glUniformMatrix4fv(uniform_TM, 1, GL_FALSE, TextureMatrix.pointer()); - glUniformMatrix4fv(uniform_IMM, 1, GL_FALSE, InverseModelMatrix.pointer()); + setUniformsHelper({ uniform_MM, uniform_TM, uniform_IMM }, ModelMatrix, InverseModelMatrix, TextureMatrix); } GLuint GrassPass1Shader::Program; diff --git a/src/graphics/shaders.hpp b/src/graphics/shaders.hpp index cc71800a0..f7d967bae 100644 --- a/src/graphics/shaders.hpp +++ b/src/graphics/shaders.hpp @@ -47,17 +47,50 @@ public: }; } +template +void setUniformsHelper(const std::vector &uniforms) +{ +} + +template +void setUniformsHelper(const std::vector &uniforms, const core::matrix4 &mat, Args... arg) +{ +#ifndef GL_FALSE +#define GL_FALSE 0 +#endif + glUniformMatrix4fv(uniforms[N], 1, GL_FALSE, mat.pointer()); + ::template setUniformsHelper(uniforms, arg...); +} + +void bypassUBO(GLuint Program); + +template +class ShaderHelper +{ +protected: + static std::vector uniforms; + static GLuint Program; +public: + static void setUniforms(const Args & ... args) + { + if (UserConfigParams::m_ubo_disabled) + bypassUBO(Program); + ::template setUniformsHelper(uniforms, args...); + } +}; + +template std::vector ShaderHelper::uniforms; +template GLuint ShaderHelper::Program; + namespace MeshShader { -class ObjectPass1Shader +class ObjectPass1Shader : public ShaderHelper { public: static GLuint Program; - static GLuint uniform_MM, uniform_IMM; static GLuint TU_tex; static void init(); - static void setUniforms(const core::matrix4 &ModelMatrix, const core::matrix4 &InverseModelMatrix); }; class ObjectRefPass1Shader