diff --git a/src/AbstractShaderProgram.cpp b/src/AbstractShaderProgram.cpp index feddb2c8a..f6c42240d 100644 --- a/src/AbstractShaderProgram.cpp +++ b/src/AbstractShaderProgram.cpp @@ -17,9 +17,11 @@ #include +#include "Math/Matrix.h" #include "Shader.h" #include "Implementation/State.h" #include "Implementation/ShaderProgramState.h" +#include "Extensions.h" #define LINKER_MESSAGE_MAX_LENGTH 1024 @@ -27,6 +29,46 @@ using namespace std; namespace Magnum { +AbstractShaderProgram::Uniform1fImplementation AbstractShaderProgram::uniform1fImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform2fvImplementation AbstractShaderProgram::uniform2fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform3fvImplementation AbstractShaderProgram::uniform3fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform4fvImplementation AbstractShaderProgram::uniform4fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform1iImplementation AbstractShaderProgram::uniform1iImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform2ivImplementation AbstractShaderProgram::uniform2ivImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform3ivImplementation AbstractShaderProgram::uniform3ivImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform4ivImplementation AbstractShaderProgram::uniform4ivImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform1uiImplementation AbstractShaderProgram::uniform1uiImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform2uivImplementation AbstractShaderProgram::uniform2uivImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform3uivImplementation AbstractShaderProgram::uniform3uivImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform4uivImplementation AbstractShaderProgram::uniform4uivImplementation = &AbstractShaderProgram::uniformImplementationDefault; +#ifndef MAGNUM_TARGET_GLES +AbstractShaderProgram::Uniform1dImplementation AbstractShaderProgram::uniform1dImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform2dvImplementation AbstractShaderProgram::uniform2dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform3dvImplementation AbstractShaderProgram::uniform3dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::Uniform4dvImplementation AbstractShaderProgram::uniform4dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +#endif + +AbstractShaderProgram::UniformMatrix2fvImplementation AbstractShaderProgram::uniformMatrix2fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix3fvImplementation AbstractShaderProgram::uniformMatrix3fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix4fvImplementation AbstractShaderProgram::uniformMatrix4fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix2x3fvImplementation AbstractShaderProgram::uniformMatrix2x3fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix3x2fvImplementation AbstractShaderProgram::uniformMatrix3x2fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix2x4fvImplementation AbstractShaderProgram::uniformMatrix2x4fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix4x2fvImplementation AbstractShaderProgram::uniformMatrix4x2fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix3x4fvImplementation AbstractShaderProgram::uniformMatrix3x4fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix4x3fvImplementation AbstractShaderProgram::uniformMatrix4x3fvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +#ifndef MAGNUM_TARGET_GLES +AbstractShaderProgram::UniformMatrix2dvImplementation AbstractShaderProgram::uniformMatrix2dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix3dvImplementation AbstractShaderProgram::uniformMatrix3dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix4dvImplementation AbstractShaderProgram::uniformMatrix4dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix2x3dvImplementation AbstractShaderProgram::uniformMatrix2x3dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix3x2dvImplementation AbstractShaderProgram::uniformMatrix3x2dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix2x4dvImplementation AbstractShaderProgram::uniformMatrix2x4dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix4x2dvImplementation AbstractShaderProgram::uniformMatrix4x2dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix3x4dvImplementation AbstractShaderProgram::uniformMatrix3x4dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +AbstractShaderProgram::UniformMatrix4x3dvImplementation AbstractShaderProgram::uniformMatrix4x3dvImplementation = &AbstractShaderProgram::uniformImplementationDefault; +#endif + AbstractShaderProgram::~AbstractShaderProgram() { /* Remove current usage from the state */ GLuint& current = Context::current()->state()->shaderProgram->current; @@ -114,4 +156,361 @@ GLint AbstractShaderProgram::uniformLocation(const std::string& name) { return location; } +void AbstractShaderProgram::initializeContextBasedFunctionality(Context* context) { + if(context->isExtensionSupported() || + context->isExtensionSupported()) { + Debug() << "AbstractShaderProgram: using" << (context->isExtensionSupported() ? + Extensions::GL::ARB::separate_shader_objects::string() : Extensions::GL::EXT::direct_state_access::string()) << "features"; + uniform1fImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform2fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform3fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform4fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform1iImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform2ivImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform3ivImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform4ivImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform1uiImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform2uivImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform3uivImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform4uivImplementation = &AbstractShaderProgram::uniformImplementationDSA; + #ifndef MAGNUM_TARGET_GLES + uniform1dImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform2dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform3dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniform4dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + #endif + + uniformMatrix2fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix3fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix4fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix2x3fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix3x2fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix2x4fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix4x2fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix3x4fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix4x3fvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + #ifndef MAGNUM_TARGET_GLES + uniformMatrix2dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix3dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix4dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix2x3dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix3x2dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix2x4dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix4x2dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix3x4dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + uniformMatrix4x3dvImplementation = &AbstractShaderProgram::uniformImplementationDSA; + #endif + } +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, GLfloat value) { + use(); + glUniform1f(location, value); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, GLfloat value) { + glProgramUniform1f(_id, location, value); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<2, GLfloat>& value) { + use(); + glUniform2fv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<2, GLfloat>& value) { + glProgramUniform2fv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<3, GLfloat>& value) { + use(); + glUniform3fv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<3, GLfloat>& value) { + glProgramUniform3fv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<4, GLfloat>& value) { + use(); + glUniform4fv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<4, GLfloat>& value) { + glProgramUniform4fv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, GLint value) { + use(); + glUniform1i(location, value); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, GLint value) { + glProgramUniform1i(_id, location, value); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<2, GLint>& value) { + use(); + glUniform2iv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<2, GLint>& value) { + glProgramUniform2iv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<3, GLint>& value) { + use(); + glUniform3iv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<3, GLint>& value) { + glProgramUniform3iv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<4, GLint>& value) { + use(); + glUniform4iv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<4, GLint>& value) { + glProgramUniform4iv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, GLuint value) { + use(); + glUniform1ui(location, value); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, GLuint value) { + glProgramUniform1ui(_id, location, value); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<2, GLuint>& value) { + use(); + glUniform2uiv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<2, GLuint>& value) { + glProgramUniform2uiv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<3, GLuint>& value) { + use(); + glUniform3uiv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<3, GLuint>& value) { + glProgramUniform3uiv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<4, GLuint>& value) { + use(); + glUniform4uiv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<4, GLuint>& value) { + glProgramUniform4uiv(_id, location, 1, value.data()); +} + +#ifndef MAGNUM_TARGET_GLES +void AbstractShaderProgram::uniformImplementationDefault(GLint location, GLdouble value) { + use(); + glUniform1d(location, value); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, GLdouble value) { + glProgramUniform1d(_id, location, value); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<2, GLdouble>& value) { + use(); + glUniform2dv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<2, GLdouble>& value) { + glProgramUniform2dv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<3, GLdouble>& value) { + use(); + glUniform3dv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<3, GLdouble>& value) { + glProgramUniform3dv(_id, location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Vector<4, GLdouble>& value) { + use(); + glUniform4dv(location, 1, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Vector<4, GLdouble>& value) { + glProgramUniform4dv(_id, location, 1, value.data()); +} +#endif + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Matrix<2, GLfloat>& value) { + use(); + glUniformMatrix2fv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Matrix<2, GLfloat>& value) { + glProgramUniformMatrix2fv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Matrix<3, GLfloat>& value) { + use(); + glUniformMatrix3fv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Matrix<3, GLfloat>& value) { + glProgramUniformMatrix3fv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Matrix<4, GLfloat>& value) { + use(); + glUniformMatrix4fv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Matrix<4, GLfloat>& value) { + glProgramUniformMatrix4fv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<2, 3, GLfloat>& value) { + use(); + glUniformMatrix2x3fv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<2, 3, GLfloat>& value) { + glProgramUniformMatrix2x3fv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<3, 2, GLfloat>& value) { + use(); + glUniformMatrix3x2fv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<3, 2, GLfloat>& value) { + glProgramUniformMatrix3x2fv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<2, 4, GLfloat>& value) { + use(); + glUniformMatrix2x4fv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<2, 4, GLfloat>& value) { + glProgramUniformMatrix2x4fv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<4, 2, GLfloat>& value) { + use(); + glUniformMatrix4x2fv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<4, 2, GLfloat>& value) { + glProgramUniformMatrix4x2fv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<3, 4, GLfloat>& value) { + use(); + glUniformMatrix3x4fv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<3, 4, GLfloat>& value) { + glProgramUniformMatrix3x4fv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<4, 3, GLfloat>& value) { + use(); + glUniformMatrix4x3fv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<4, 3, GLfloat>& value) { + glProgramUniformMatrix4x3fv(_id, location, 1, GL_FALSE, value.data()); +} + +#ifndef MAGNUM_TARGET_GLES +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Matrix<2, GLdouble>& value) { + use(); + glUniformMatrix2dv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Matrix<2, GLdouble>& value) { + glProgramUniformMatrix2dv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Matrix<3, GLdouble>& value) { + use(); + glUniformMatrix3dv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Matrix<3, GLdouble>& value) { + glProgramUniformMatrix3dv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::Matrix<4, GLdouble>& value) { + use(); + glUniformMatrix4dv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::Matrix<4, GLdouble>& value) { + glProgramUniformMatrix4dv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<2, 3, GLdouble>& value) { + use(); + glUniformMatrix2x3dv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<2, 3, GLdouble>& value) { + glProgramUniformMatrix2x3dv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<3, 2, GLdouble>& value) { + use(); + glUniformMatrix3x2dv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<3, 2, GLdouble>& value) { + glProgramUniformMatrix3x2dv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<2, 4, GLdouble>& value) { + use(); + glUniformMatrix2x4dv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<2, 4, GLdouble>& value) { + glProgramUniformMatrix2x4dv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<4, 2, GLdouble>& value) { + use(); + glUniformMatrix4x2dv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<4, 2, GLdouble>& value) { + glProgramUniformMatrix4x2dv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<3, 4, GLdouble>& value) { + use(); + glUniformMatrix3x4dv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<3, 4, GLdouble>& value) { + glProgramUniformMatrix3x4dv(_id, location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDefault(GLint location, const Math::RectangularMatrix<4, 3, GLdouble>& value) { + use(); + glUniformMatrix4x3dv(location, 1, GL_FALSE, value.data()); +} + +void AbstractShaderProgram::uniformImplementationDSA(GLint location, const Math::RectangularMatrix<4, 3, GLdouble>& value) { + glProgramUniformMatrix4x3dv(_id, location, 1, GL_FALSE, value.data()); +} +#endif + } diff --git a/src/AbstractShaderProgram.h b/src/AbstractShaderProgram.h index fbe4dcb9b..57d36c8e5 100644 --- a/src/AbstractShaderProgram.h +++ b/src/AbstractShaderProgram.h @@ -19,15 +19,22 @@ * @brief Class Magnum::AbstractShaderProgram */ -#include +#include +#include -#include "Math/RectangularMatrix.h" #include "Magnum.h" #include "magnumVisibility.h" namespace Magnum { +namespace Math { + template class RectangularMatrix; + template class Matrix; + template class Vector; +} + +class Context; class Shader; /** @@ -191,9 +198,10 @@ void draw(const Magnum::Matrix4& transformationMatrix, Magnum::Camera* camera) { @endcode @todo Uniform arrays support -@todo DSA for uniforms - glProgramUniform*() (OpenGL 4.1, @extension{ARB,separate_shader_objects}) */ class MAGNUM_EXPORT AbstractShaderProgram { + friend class Context; + AbstractShaderProgram(const AbstractShaderProgram& other) = delete; AbstractShaderProgram(AbstractShaderProgram&& other) = delete; AbstractShaderProgram& operator=(const AbstractShaderProgram& other) = delete; @@ -232,7 +240,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { virtual ~AbstractShaderProgram() = 0; /** - * @brief Use shader + * @brief Use shader for rendering * @return False if the program wasn't successfully linked, true * otherwise. * @@ -369,46 +377,49 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @param location Uniform location (see uniformLocation()) * @param value Value * - * @attention This function doesn't check whether this shader is in use! - * @see @fn_gl{Uniform} + * If neither @extension{ARB,separate_shader_objects} nor + * @extension{EXT,direct_state_access} is available, use() is called + * before the operation. + * @see use(), @fn_gl{Uniform} or `glProgramUniform()` from + * @extension{ARB,separate_shader_objects}/@extension{EXT,direct_state_access}. */ inline void setUniform(GLint location, GLfloat value) { - glUniform1f(location, value); + (this->*uniform1fImplementation)(location, value); } /** @copydoc setUniform(GLint, GLfloat) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 2, GLfloat>& value) { - glUniform2fv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<2, GLfloat>& value) { + (this->*uniform2fvImplementation)(location, value); } /** @copydoc setUniform(GLint, GLfloat) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 3, GLfloat>& value) { - glUniform3fv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<3, GLfloat>& value) { + (this->*uniform3fvImplementation)(location, value); } /** @copydoc setUniform(GLint, GLfloat) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 4, GLfloat>& value) { - glUniform4fv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<4, GLfloat>& value) { + (this->*uniform4fvImplementation)(location, value); } /** @copydoc setUniform(GLint, GLfloat) */ inline void setUniform(GLint location, GLint value) { - glUniform1i(location, value); + (this->*uniform1iImplementation)(location, value); } /** @copydoc setUniform(GLint, GLfloat) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 2, GLint>& value) { - glUniform2iv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<2, GLint>& value) { + (this->*uniform2ivImplementation)(location, value); } /** @copydoc setUniform(GLint, GLfloat) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 3, GLint>& value) { - glUniform3iv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<3, GLint>& value) { + (this->*uniform3ivImplementation)(location, value); } /** @copydoc setUniform(GLint, GLfloat) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 4, GLint>& value) { - glUniform4iv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<4, GLint>& value) { + (this->*uniform4ivImplementation)(location, value); } /** @@ -417,7 +428,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gles30 (no extension providing this functionality) */ inline void setUniform(GLint location, GLuint value) { - glUniform1ui(location, value); + (this->*uniform1uiImplementation)(location, value); } /** @@ -425,8 +436,8 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl30 Extension @extension{EXT,gpu_shader4} * @requires_gles30 (no extension providing this functionality) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 2, GLuint>& value) { - glUniform2uiv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<2, GLuint>& value) { + (this->*uniform2uivImplementation)(location, value); } /** @@ -434,8 +445,8 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl30 Extension @extension{EXT,gpu_shader4} * @requires_gles30 (no extension providing this functionality) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 3, GLuint>& value) { - glUniform3uiv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<3, GLuint>& value) { + (this->*uniform3uivImplementation)(location, value); } /** @@ -443,8 +454,8 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl30 Extension @extension{EXT,gpu_shader4} * @requires_gles30 (no extension providing this functionality) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 4, GLuint>& value) { - glUniform4uiv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<4, GLuint>& value) { + (this->*uniform4uivImplementation)(location, value); } #ifndef MAGNUM_TARGET_GLES @@ -454,7 +465,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl Only floats are available in OpenGL ES. */ inline void setUniform(GLint location, GLdouble value) { - glUniform1d(location, value); + (this->*uniform1dImplementation)(location, value); } /** @@ -462,8 +473,8 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl40 Extension @extension{ARB,gpu_shader_fp64} * @requires_gl Only floats are available in OpenGL ES. */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 2, GLdouble>& value) { - glUniform2dv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<2, GLdouble>& value) { + (this->*uniform2dvImplementation)(location, value); } /** @@ -471,8 +482,8 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl40 Extension @extension{ARB,gpu_shader_fp64} * @requires_gl Only floats are available in OpenGL ES. */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 3, GLdouble>& value) { - glUniform3dv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<3, GLdouble>& value) { + (this->*uniform3dvImplementation)(location, value); } /** @@ -480,24 +491,24 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl40 Extension @extension{ARB,gpu_shader_fp64} * @requires_gl Only floats are available in OpenGL ES. */ - inline void setUniform(GLint location, const Math::RectangularMatrix<1, 4, GLdouble>& value) { - glUniform4dv(location, 1, value.data()); + inline void setUniform(GLint location, const Math::Vector<4, GLdouble>& value) { + (this->*uniform4dvImplementation)(location, value); } #endif /** @copydoc setUniform(GLint, GLfloat) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<2, 2, GLfloat>& value) { - glUniformMatrix2fv(location, 1, GL_FALSE, value.data()); + inline void setUniform(GLint location, const Math::Matrix<2, GLfloat>& value) { + (this->*uniformMatrix2fvImplementation)(location, value); } /** @copydoc setUniform(GLint, GLfloat) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<3, 3, GLfloat>& value) { - glUniformMatrix3fv(location, 1, GL_FALSE, value.data()); + inline void setUniform(GLint location, const Math::Matrix<3, GLfloat>& value) { + (this->*uniformMatrix3fvImplementation)(location, value); } /** @copydoc setUniform(GLint, GLfloat) */ - inline void setUniform(GLint location, const Math::RectangularMatrix<4, 4, GLfloat>& value) { - glUniformMatrix4fv(location, 1, GL_FALSE, value.data()); + inline void setUniform(GLint location, const Math::Matrix<4, GLfloat>& value) { + (this->*uniformMatrix4fvImplementation)(location, value); } /** @@ -505,7 +516,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gles30 (no extension providing this functionality) */ inline void setUniform(GLint location, const Math::RectangularMatrix<2, 3, GLfloat>& value) { - glUniformMatrix2x3fv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix2x3fvImplementation)(location, value); } /** @@ -513,7 +524,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gles30 (no extension providing this functionality) */ inline void setUniform(GLint location, const Math::RectangularMatrix<3, 2, GLfloat>& value) { - glUniformMatrix3x2fv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix3x2fvImplementation)(location, value); } /** @@ -521,7 +532,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gles30 (no extension providing this functionality) */ inline void setUniform(GLint location, const Math::RectangularMatrix<2, 4, GLfloat>& value) { - glUniformMatrix2x4fv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix2x4fvImplementation)(location, value); } /** @@ -529,7 +540,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gles30 (no extension providing this functionality) */ inline void setUniform(GLint location, const Math::RectangularMatrix<4, 2, GLfloat>& value) { - glUniformMatrix4x2fv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix4x2fvImplementation)(location, value); } /** @@ -537,7 +548,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gles30 (no extension providing this functionality) */ inline void setUniform(GLint location, const Math::RectangularMatrix<3, 4, GLfloat>& value) { - glUniformMatrix3x4fv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix3x4fvImplementation)(location, value); } /** @@ -545,7 +556,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gles30 (no extension providing this functionality) */ inline void setUniform(GLint location, const Math::RectangularMatrix<4, 3, GLfloat>& value) { - glUniformMatrix4x3fv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix4x3fvImplementation)(location, value); } #ifndef MAGNUM_TARGET_GLES @@ -554,8 +565,8 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl40 Extension @extension{ARB,gpu_shader_fp64} * @requires_gl Only floats are available in OpenGL ES. */ - inline void setUniform(GLint location, const Math::RectangularMatrix<2, 2, GLdouble>& value) { - glUniformMatrix2dv(location, 1, GL_FALSE, value.data()); + inline void setUniform(GLint location, const Math::Matrix<2, GLdouble>& value) { + (this->*uniformMatrix2dvImplementation)(location, value); } /** @@ -563,8 +574,8 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl40 Extension @extension{ARB,gpu_shader_fp64} * @requires_gl Only floats are available in OpenGL ES. */ - inline void setUniform(GLint location, const Math::RectangularMatrix<3, 3, GLdouble>& value) { - glUniformMatrix3dv(location, 1, GL_FALSE, value.data()); + inline void setUniform(GLint location, const Math::Matrix<3, GLdouble>& value) { + (this->*uniformMatrix3dvImplementation)(location, value); } /** @@ -572,8 +583,8 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl40 Extension @extension{ARB,gpu_shader_fp64} * @requires_gl Only floats are available in OpenGL ES. */ - inline void setUniform(GLint location, const Math::RectangularMatrix<4, 4, GLdouble>& value) { - glUniformMatrix4dv(location, 1, GL_FALSE, value.data()); + inline void setUniform(GLint location, const Math::Matrix<4, GLdouble>& value) { + (this->*uniformMatrix4dvImplementation)(location, value); } /** @@ -582,7 +593,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl Only floats are available in OpenGL ES. */ inline void setUniform(GLint location, const Math::RectangularMatrix<2, 3, GLdouble>& value) { - glUniformMatrix2x3dv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix2x3dvImplementation)(location, value); } /** @@ -591,7 +602,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl Only floats are available in OpenGL ES. */ inline void setUniform(GLint location, const Math::RectangularMatrix<3, 2, GLdouble>& value) { - glUniformMatrix3x2dv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix3x2dvImplementation)(location, value); } /** @@ -600,7 +611,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl Only floats are available in OpenGL ES. */ inline void setUniform(GLint location, const Math::RectangularMatrix<2, 4, GLdouble>& value) { - glUniformMatrix2x4dv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix2x4dvImplementation)(location, value); } /** @@ -609,7 +620,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl Only floats are available in OpenGL ES. */ inline void setUniform(GLint location, const Math::RectangularMatrix<4, 2, GLdouble>& value) { - glUniformMatrix4x2dv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix4x2dvImplementation)(location, value); } /** @@ -618,7 +629,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl Only floats are available in OpenGL ES. */ inline void setUniform(GLint location, const Math::RectangularMatrix<3, 4, GLdouble>& value) { - glUniformMatrix3x4dv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix3x4dvImplementation)(location, value); } /** @@ -627,7 +638,7 @@ class MAGNUM_EXPORT AbstractShaderProgram { * @requires_gl Only floats are available in OpenGL ES. */ inline void setUniform(GLint location, const Math::RectangularMatrix<4, 3, GLdouble>& value) { - glUniformMatrix4x3dv(location, 1, GL_FALSE, value.data()); + (this->*uniformMatrix4x3dvImplementation)(location, value); } #endif @@ -638,6 +649,162 @@ class MAGNUM_EXPORT AbstractShaderProgram { Failed }; + static void initializeContextBasedFunctionality(Context* context); + + typedef void(AbstractShaderProgram::*Uniform1fImplementation)(GLint, GLfloat); + typedef void(AbstractShaderProgram::*Uniform2fvImplementation)(GLint, const Math::Vector<2, GLfloat>&); + typedef void(AbstractShaderProgram::*Uniform3fvImplementation)(GLint, const Math::Vector<3, GLfloat>&); + typedef void(AbstractShaderProgram::*Uniform4fvImplementation)(GLint, const Math::Vector<4, GLfloat>&); + typedef void(AbstractShaderProgram::*Uniform1iImplementation)(GLint, GLint); + typedef void(AbstractShaderProgram::*Uniform2ivImplementation)(GLint, const Math::Vector<2, GLint>&); + typedef void(AbstractShaderProgram::*Uniform3ivImplementation)(GLint, const Math::Vector<3, GLint>&); + typedef void(AbstractShaderProgram::*Uniform4ivImplementation)(GLint, const Math::Vector<4, GLint>&); + typedef void(AbstractShaderProgram::*Uniform1uiImplementation)(GLint, GLuint); + typedef void(AbstractShaderProgram::*Uniform2uivImplementation)(GLint, const Math::Vector<2, GLuint>&); + typedef void(AbstractShaderProgram::*Uniform3uivImplementation)(GLint, const Math::Vector<3, GLuint>&); + typedef void(AbstractShaderProgram::*Uniform4uivImplementation)(GLint, const Math::Vector<4, GLuint>&); + #ifndef MAGNUM_TARGET_GLES + typedef void(AbstractShaderProgram::*Uniform1dImplementation)(GLint, GLdouble); + typedef void(AbstractShaderProgram::*Uniform2dvImplementation)(GLint, const Math::Vector<2, GLdouble>&); + typedef void(AbstractShaderProgram::*Uniform3dvImplementation)(GLint, const Math::Vector<3, GLdouble>&); + typedef void(AbstractShaderProgram::*Uniform4dvImplementation)(GLint, const Math::Vector<4, GLdouble>&); + #endif + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, GLfloat value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<2, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<3, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<4, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, GLint value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<2, GLint>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<3, GLint>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<4, GLint>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, GLuint value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<2, GLuint>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<3, GLuint>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<4, GLuint>& value); + #ifndef MAGNUM_TARGET_GLES + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, GLdouble value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<2, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<3, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Vector<4, GLdouble>& value); + #endif + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, GLfloat value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<2, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<3, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<4, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, GLint value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<2, GLint>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<3, GLint>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<4, GLint>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, GLuint value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<2, GLuint>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<3, GLuint>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<4, GLuint>& value); + #ifndef MAGNUM_TARGET_GLES + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, GLdouble value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<2, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<3, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Vector<4, GLdouble>& value); + #endif + static Uniform1fImplementation uniform1fImplementation; + static Uniform2fvImplementation uniform2fvImplementation; + static Uniform3fvImplementation uniform3fvImplementation; + static Uniform4fvImplementation uniform4fvImplementation; + static Uniform1iImplementation uniform1iImplementation; + static Uniform2ivImplementation uniform2ivImplementation; + static Uniform3ivImplementation uniform3ivImplementation; + static Uniform4ivImplementation uniform4ivImplementation; + static Uniform1uiImplementation uniform1uiImplementation; + static Uniform2uivImplementation uniform2uivImplementation; + static Uniform3uivImplementation uniform3uivImplementation; + static Uniform4uivImplementation uniform4uivImplementation; + #ifndef MAGNUM_TARGET_GLES + static Uniform1dImplementation uniform1dImplementation; + static Uniform2dvImplementation uniform2dvImplementation; + static Uniform3dvImplementation uniform3dvImplementation; + static Uniform4dvImplementation uniform4dvImplementation; + #endif + + typedef void(AbstractShaderProgram::*UniformMatrix2fvImplementation)(GLint, const Math::Matrix<2, GLfloat>&); + typedef void(AbstractShaderProgram::*UniformMatrix3fvImplementation)(GLint, const Math::Matrix<3, GLfloat>&); + typedef void(AbstractShaderProgram::*UniformMatrix4fvImplementation)(GLint, const Math::Matrix<4, GLfloat>&); + typedef void(AbstractShaderProgram::*UniformMatrix2x3fvImplementation)(GLint, const Math::RectangularMatrix<2, 3, GLfloat>&); + typedef void(AbstractShaderProgram::*UniformMatrix3x2fvImplementation)(GLint, const Math::RectangularMatrix<3, 2, GLfloat>&); + typedef void(AbstractShaderProgram::*UniformMatrix2x4fvImplementation)(GLint, const Math::RectangularMatrix<2, 4, GLfloat>&); + typedef void(AbstractShaderProgram::*UniformMatrix4x2fvImplementation)(GLint, const Math::RectangularMatrix<4, 2, GLfloat>&); + typedef void(AbstractShaderProgram::*UniformMatrix3x4fvImplementation)(GLint, const Math::RectangularMatrix<3, 4, GLfloat>&); + typedef void(AbstractShaderProgram::*UniformMatrix4x3fvImplementation)(GLint, const Math::RectangularMatrix<4, 3, GLfloat>&); + #ifndef MAGNUM_TARGET_GLES + typedef void(AbstractShaderProgram::*UniformMatrix2dvImplementation)(GLint, const Math::Matrix<2, GLdouble>&); + typedef void(AbstractShaderProgram::*UniformMatrix3dvImplementation)(GLint, const Math::Matrix<3, GLdouble>&); + typedef void(AbstractShaderProgram::*UniformMatrix4dvImplementation)(GLint, const Math::Matrix<4, GLdouble>&); + typedef void(AbstractShaderProgram::*UniformMatrix2x3dvImplementation)(GLint, const Math::RectangularMatrix<2, 3, GLdouble>&); + typedef void(AbstractShaderProgram::*UniformMatrix3x2dvImplementation)(GLint, const Math::RectangularMatrix<3, 2, GLdouble>&); + typedef void(AbstractShaderProgram::*UniformMatrix2x4dvImplementation)(GLint, const Math::RectangularMatrix<2, 4, GLdouble>&); + typedef void(AbstractShaderProgram::*UniformMatrix4x2dvImplementation)(GLint, const Math::RectangularMatrix<4, 2, GLdouble>&); + typedef void(AbstractShaderProgram::*UniformMatrix3x4dvImplementation)(GLint, const Math::RectangularMatrix<3, 4, GLdouble>&); + typedef void(AbstractShaderProgram::*UniformMatrix4x3dvImplementation)(GLint, const Math::RectangularMatrix<4, 3, GLdouble>&); + #endif + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Matrix<2, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Matrix<3, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Matrix<4, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<2, 3, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<3, 2, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<2, 4, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<4, 2, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<3, 4, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<4, 3, GLfloat>& value); + #ifndef MAGNUM_TARGET_GLES + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Matrix<2, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Matrix<3, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::Matrix<4, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<2, 3, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<3, 2, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<2, 4, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<4, 2, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<3, 4, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDefault(GLint location, const Math::RectangularMatrix<4, 3, GLdouble>& value); + #endif + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Matrix<2, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Matrix<3, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Matrix<4, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<2, 3, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<3, 2, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<2, 4, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<4, 2, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<3, 4, GLfloat>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<4, 3, GLfloat>& value); + #ifndef MAGNUM_TARGET_GLES + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Matrix<2, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Matrix<3, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::Matrix<4, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<2, 3, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<3, 2, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<2, 4, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<4, 2, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<3, 4, GLdouble>& value); + void MAGNUM_LOCAL uniformImplementationDSA(GLint location, const Math::RectangularMatrix<4, 3, GLdouble>& value); + #endif + static UniformMatrix2fvImplementation uniformMatrix2fvImplementation; + static UniformMatrix3fvImplementation uniformMatrix3fvImplementation; + static UniformMatrix4fvImplementation uniformMatrix4fvImplementation; + static UniformMatrix2x3fvImplementation uniformMatrix2x3fvImplementation; + static UniformMatrix3x2fvImplementation uniformMatrix3x2fvImplementation; + static UniformMatrix2x4fvImplementation uniformMatrix2x4fvImplementation; + static UniformMatrix4x2fvImplementation uniformMatrix4x2fvImplementation; + static UniformMatrix3x4fvImplementation uniformMatrix3x4fvImplementation; + static UniformMatrix4x3fvImplementation uniformMatrix4x3fvImplementation; + #ifndef MAGNUM_TARGET_GLES + static UniformMatrix2dvImplementation uniformMatrix2dvImplementation; + static UniformMatrix3dvImplementation uniformMatrix3dvImplementation; + static UniformMatrix4dvImplementation uniformMatrix4dvImplementation; + static UniformMatrix2x3dvImplementation uniformMatrix2x3dvImplementation; + static UniformMatrix3x2dvImplementation uniformMatrix3x2dvImplementation; + static UniformMatrix2x4dvImplementation uniformMatrix2x4dvImplementation; + static UniformMatrix4x2dvImplementation uniformMatrix4x2dvImplementation; + static UniformMatrix3x4dvImplementation uniformMatrix3x4dvImplementation; + static UniformMatrix4x3dvImplementation uniformMatrix4x3dvImplementation; + #endif + GLuint _id; State state; }; diff --git a/src/Context.cpp b/src/Context.cpp index 92247c051..d3361f8a5 100644 --- a/src/Context.cpp +++ b/src/Context.cpp @@ -19,6 +19,7 @@ #include #include +#include "AbstractShaderProgram.h" #include "Buffer.h" #include "Extensions.h" #include "Implementation/State.h" @@ -198,6 +199,7 @@ Context::Context() { _state = new Implementation::State; /* Initialize functionality based on current OpenGL version and extensions */ + AbstractShaderProgram::initializeContextBasedFunctionality(this); Buffer::initializeContextBasedFunctionality(this); }