Getting open gl to work

opengl

#1

I’m trying to set up a very basic opengl component to visualize a reverb effect but I’m having some trouble with it.

I’ve stripped the openglApp example to a bare minimum but for some reason the fragmentshader is not working. Maybe somebody can point me into the right direction?

Here’s my code which contains a vertex struct (with only a position right now because I couldn’t find my error), a small attributes struct (also only containing position) and small VBO struct and the rendering code:

class ReverbRenderer :  public OpenGLRenderer {

    public:
        struct Vertex {
            float position[3];
        };

        class VBO {
        public:
            VBO(OpenGLContext &glContext, std::vector<Vertex> vertices) : ctx(glContext), size(vertices.size()) {
                ctx.extensions.glGenBuffers(1, &vbo);
                ctx.extensions.glBindBuffer(GL_ARRAY_BUFFER, vbo);
                ctx.extensions.glBufferData(GL_ARRAY_BUFFER,
                                            static_cast<GLsizeiptr>(static_cast<size_t>(vertices.size()) * sizeof(Vertex)),
                                            vertices.data(),
                                            GL_STATIC_DRAW);
            }

            void bind() {
                ctx.extensions.glBindBuffer(GL_ARRAY_BUFFER, vbo);
            }

            int getSize() {
                return size;
            }

        private:
            GLuint          vbo;
            OpenGLContext   &ctx;
            int             size;
        };

        struct Attributes {

            Attributes (OpenGLContext& ctx, OpenGLShaderProgram& shaderProgram) {
                position = createAttribute(ctx, shaderProgram, "position");
            }

            void enable (OpenGLContext& ctx) {
                if (position != nullptr) {
                    ctx.extensions.glVertexAttribPointer(position->attributeID, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), 0);
                    ctx.extensions.glEnableVertexAttribArray(position->attributeID);
                }
            }

            void disable (OpenGLContext& ctx) {
                if (position != nullptr)
                    ctx.extensions.glDisableVertexAttribArray(position->attributeID);
            }

            ScopedPointer<OpenGLShaderProgram::Attribute> position;

        private:
            static OpenGLShaderProgram::Attribute* createAttribute (OpenGLContext& openGLContext, OpenGLShaderProgram& shader, const char* attributeName) {
                if (openGLContext.extensions.glGetAttribLocation (shader.getProgramID(), attributeName) < 0)
                    return nullptr;
                return new OpenGLShaderProgram::Attribute(shader, attributeName);
            }
        };



        ReverbRenderer(OpenGLContext &glContext)
                : ctx(glContext)
        {
        }


        ~ReverbRenderer() {
            ctx.detach();
        }


        void newOpenGLContextCreated() override {
            std::vector<ReverbRenderer::Vertex> vertices;

            Vertex v1 = {{-.5f, -.5f, 0}};
            Vertex v2 = {{.5f, -.5f, 0}};
            Vertex v3 = {{.5f, .5f, 0}};
            Vertex v4 = {{.5f, .5f, 0}};
            Vertex v5 = {{-.5f, .5f, 0}};
            Vertex v6 = {{-.5f, -.5f, 0}};

            vertices.push_back(v1);
            vertices.push_back(v2);
            vertices.push_back(v3);
            vertices.push_back(v4);
            vertices.push_back(v5);
            vertices.push_back(v6);

            vbo = std::make_unique<VBO>(ctx, vertices);
            createShaders();
        }


        void createShaders()
        {
            vertexShader =      "attribute vec3 position;\n"
                                "\n"
                                "void main()\n"
                                "{\n"
                                "    gl_Position = vec4(position, 1.0);\n"
                                "}\n";

            fragmentShader =    "void main()\n"
                                "{\n"
                                "   gl_FragColor = vec4(0.0, 1.0, 0.0, 1.0);\n"
                                "}\n";

            std::unique_ptr<OpenGLShaderProgram> newShader = std::make_unique<OpenGLShaderProgram>(ctx);
            String statusText;

            if (newShader->addVertexShader(vertexShader) && newShader->addFragmentShader(fragmentShader) && newShader->link()) {
                shader.reset(newShader.get());
                shader->use();
                attributes = std::make_unique<Attributes>(ctx, *shader.get());
                statusText = "GLSL: v" + String(OpenGLShaderProgram::getLanguageVersion(), 2);
            }
            else
                statusText = newShader->getLastError();

            std::cout << statusText << std::endl;
        }
        
        void renderOpenGL() override {
            jassert (OpenGLHelpers::isContextActive());
            OpenGLHelpers::clear(Colours::black);

            shader->use();
            vbo->bind();
            attributes->enable(ctx);
            glDrawArrays(GL_TRIANGLES, 0, vbo->getSize());
            attributes->disable(ctx);

            // reset buffers for further drawing
            ctx.extensions.glBindBuffer(GL_ARRAY_BUFFER, 0);
        }

        void openGLContextClosing() override {
        }


    private:
        OpenGLContext                           &ctx;
        std::string                             vertexShader, fragmentShader;
        std::unique_ptr<OpenGLShaderProgram>    shader;
        std::unique_ptr<Attributes>             attributes;
        std::unique_ptr<VBO>                    vbo;
    };

In the reverbs component I initialize the gl context as follows:

gl.setRenderer(&renderer);
gl.attachTo(*this);
gl.setContinuousRepainting(true);

For some reason the result is always just a white square on a black background. But in the fragment shader the colour should be set differently. The output generated by create shaders says I’m using GLSL 1.20. So the code should be fine.