From fb23c8d47f6dcef429423256d8dddcc0f7184fc4 Mon Sep 17 00:00:00 2001 From: Samuel Fadel Date: Sun, 4 Jun 2023 13:02:14 +0200 Subject: Further advances in nuklear port. Rendering now looks similar to Qt version, needs a few tweaks: * Proper multisampling * Background Missing features: * Barcharts * Interactivity (e.g. brushing/linking in all objects) * History view of interactions --- shader.cpp | 137 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 137 insertions(+) create mode 100644 shader.cpp (limited to 'shader.cpp') diff --git a/shader.cpp b/shader.cpp new file mode 100644 index 0000000..0a1268e --- /dev/null +++ b/shader.cpp @@ -0,0 +1,137 @@ +#include "shader.h" + +#include + +static int setupShader(GLenum shaderType, const char *src) +{ + GLuint shader = glCreateShader(shaderType); + glShaderSource(shader, 1, &src, nullptr); + glCompileShader(shader); + + int status; + glGetShaderiv(shader, GL_COMPILE_STATUS, &status); + if (status == GL_FALSE) { + char buf[1024]; + glGetShaderInfoLog(shader, sizeof buf, nullptr, buf); + std::cerr << "Error: " + << (shaderType == GL_VERTEX_SHADER ? "vertex" : "fragment") + << " shader: compilation failed: " + << buf + << std::endl; + } + return shader; +} + +Shader::Shader(const char *vertexSrc, const char *fragmentSrc, const char *geometrySrc) +{ + GLuint vertex = setupShader(GL_VERTEX_SHADER, vertexSrc); + GLuint fragment = setupShader(GL_FRAGMENT_SHADER, fragmentSrc); + GLuint geometry; + if (geometrySrc != nullptr) { + geometry = setupShader(GL_GEOMETRY_SHADER, geometrySrc); + } + + int status; + m_program = glCreateProgram(); + glAttachShader(m_program, vertex); + glAttachShader(m_program, fragment); + if (geometrySrc != nullptr) { + glAttachShader(m_program, geometry); + } + glLinkProgram(m_program); + glGetProgramiv(m_program, GL_LINK_STATUS, &status); + if (status == GL_FALSE) { + char buf[1024]; + glGetProgramInfoLog(m_program, sizeof buf, nullptr, buf); + std::cerr << "Error: shader linking failed: " + << buf + << std::endl; + } + + if (geometrySrc != nullptr) { + glDeleteShader(geometry); + } + glDeleteShader(fragment); + glDeleteShader(vertex); +} + +Shader::~Shader() +{ + glDeleteProgram(m_program); +} + +void Shader::use() const +{ + glUseProgram(m_program); +} + +void Shader::release() const +{ + glUseProgram(0); +} + +GLint Shader::uniformLocation(const char *name) const +{ + return glGetUniformLocation(m_program, name); +} + +void Shader::setUniform(GLint location, GLint value) const +{ + glUniform1i(location, value); +} + +void Shader::setUniform(GLint location, GLfloat value) const +{ + glUniform1f(location, value); +} + +void Shader::setUniform(GLint location, GLfloat mat[4][4]) const +{ + // GL_FALSE for column-major + glUniformMatrix4fv(location, 1, GL_FALSE, &mat[0][0]); +} + +void Shader::setUniform1dArray(GLint location, const GLfloat *values, int count) const +{ + glUniform1fv(location, count, values); +} + +void Shader::setUniform2dArray(GLint location, const GLfloat *values, int count) const +{ + glUniform2fv(location, count, values); +} + +void Shader::setUniform3dArray(GLint location, const GLfloat *values, int count) const +{ + glUniform3fv(location, count, values); +} + +void Shader::setUniform(const char *name, GLint value) const +{ + setUniform(uniformLocation(name), value); +} + +void Shader::setUniform(const char *name, GLfloat value) const +{ + setUniform(uniformLocation(name), value); +} + +void Shader::setUniform1dArray(const char *name, const GLfloat *values, int count) const +{ + setUniform1dArray(uniformLocation(name), values, count); +} + +void Shader::setUniform2dArray(const char *name, const GLfloat *values, int count) const +{ + setUniform2dArray(uniformLocation(name), values, count); +} + +void Shader::setUniform3dArray(const char *name, const GLfloat *values, int count) const +{ + setUniform3dArray(uniformLocation(name), values, count); +} + +void Shader::setUniform(const char *name, GLfloat mat[4][4]) const +{ + setUniform(uniformLocation(name), mat); +} -- cgit v1.2.3