Is opneGL 3.2+ supported on windows?


#1

I tried to run my progrma on windows, I defined JUCE_OPENGL3, but I got a bunch of errors saying it could not find functions like glGenVertexArrays and glBindVertexArray also when I look in the file native/juce_OpenGL_win32.h I dont see anything related to opengl 3.2.

JUCE_OPENGL3, is not used in that file and it doesnt seem to use the OpenGl version variable.


#2

Can you give us a piece of self-contained code we could use to reproduce this?


#3

Yeah With intro Jucer , create an openGLApplication and define JUCE_OPENGL3. Then open a Visual Studio 13 project and replace the MainComponent.cpp with this:

 

/*
  ==============================================================================

    This file was auto-generated!

  ==============================================================================
*/

#ifndef MAINCOMPONENT_H_INCLUDED
#define MAINCOMPONENT_H_INCLUDED

#include "../JuceLibraryCode/JuceHeader.h"
#include <memory>

float points[] = {
    0.0f,  0.5f,  0.0f,
    0.5f, -0.5f,  0.0f,
    -0.5f, -0.5f,  0.0f
};

const char* vertex_shader =
"#version 150\n"
"in vec3 vp;"
"void main () {"
"  gl_Position = vec4 (vp, 1.0);"
"}";

const char* fragment_shader =
"#version 150\n"
"out vec4 frag_colour;"
"void main () {"
"  frag_colour = vec4 (0.5, 0.0, 0.5, 1.0);"
"}";

//==============================================================================
/*
    This component lives inside our window, and this is where you should put all
    your controls and content.
*/
class MainContentComponent   : public OpenGLAppComponent
{
public:
    //==============================================================================
    MainContentComponent()
    {
        setSize (800, 600);
        openGLContext.setOpenGLVersionRequired(OpenGLContext::openGL3_2);
        
    }

    ~MainContentComponent()
    {
        shutdownOpenGL();
    }

    void initialise() override
    {
        //load shaders
        program = std::make_shared<OpenGLShaderProgram>(openGLContext);
        program->addVertexShader(vertex_shader);
        program->addFragmentShader(fragment_shader);
        program->link();
        positionA = std::make_shared<OpenGLShaderProgram::Attribute>(*program,"vp");
        
        // create vertex buffer
        openGLContext.extensions.glGenBuffers (1, &vbo);
        openGLContext.extensions.glBindBuffer (GL_ARRAY_BUFFER, vbo);
        openGLContext.extensions.glBufferData (GL_ARRAY_BUFFER, 9 * sizeof (float), points, GL_STATIC_DRAW);
        openGLContext.extensions.glBindBuffer(GL_ARRAY_BUFFER, 0);
        
        // create vao object
        glGenVertexArrays (1, &vao);
        glBindVertexArray (vao);
        openGLContext.extensions.glEnableVertexAttribArray (0);
        openGLContext.extensions.glBindBuffer (GL_ARRAY_BUFFER, vbo);
        openGLContext.extensions.glVertexAttribPointer (0, 3, GL_FLOAT, GL_FALSE, 0, NULL);
        openGLContext.extensions.glBindBuffer(GL_ARRAY_BUFFER, 0);
        glBindVertexArray(0);
        
    }

    void shutdown() override
    {
        openGLContext.extensions.glDeleteBuffers(1, &vbo);
        glDeleteVertexArrays(1, &vao);
    }

    void render() override
    {
        OpenGLHelpers::clear (Colours::black);
        glBindVertexArray(vao);
        program->use();
        glDrawArrays(GL_TRIANGLES, 0, 3);
        glBindVertexArray(0);
    }

    void paint (Graphics& g) override
    {
        // You can add your component specific drawing code here!
        // This will draw over the top of the openGL background.
    }

    void resized() override
    {
        // This is called when the MainContentComponent is resized.
        // If you add any child components, this is where you should
        // update their positions.
    }


private:
    //==============================================================================

    // private member variables
    GLuint vao;
    GLuint vbo;
    std::shared_ptr<OpenGLShaderProgram> program;
    std::shared_ptr<OpenGLShaderProgram::Attribute> positionA;
    
    JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (MainContentComponent)
};


// (This function is called by the app startup code to create our main component)
Component* createMainContentComponent()    { return new MainContentComponent(); }


#endif  // MAINCOMPONENT_H_INCLUDED

 

this code works on MAC OSX no problems but wont even complie on windows.

 


#4

I got it to work by  not defining juce_opengl3 and adding these inside juce_openGLExtensions..h

    USE_FUNCTION (glGenVertexArrays,        void, (GLsizei p1, GLuint* p2),(p1,p2))\
    USE_FUNCTION (glBindVertexArray,        void, (GLuint p1),(p1)) \
    USE_FUNCTION (glDeleteVertexArrays,     void, (GLsizei p1, const GLuint* p2),(p1,p2))\

 

also inside juce_OpenGlContext.h is there a reason why only OSX executes this code? Shouldnt this be in all platforms?

       #if JUCE_OPENGL3
        if (OpenGLShaderProgram::getLanguageVersion() > 1.2)
        {
            glGenVertexArrays (1, &vertexArrayObject);
            glBindVertexArray (vertexArrayObject);
        }
       #endif

 also this code seems inefficienti, is it necessary to create and delete a buffer each frame?

         GLuint vertexBuffer = 0;
        extensions.glGenBuffers (1, &vertexBuffer);
        extensions.glBindBuffer (GL_ARRAY_BUFFER, vertexBuffer);
        extensions.glBufferData (GL_ARRAY_BUFFER, sizeof (vertices), vertices, GL_STATIC_DRAW); 

        const GLuint index = (GLuint) program.params.positionAttribute.attributeID;
        extensions.glVertexAttribPointer (index, 2, GL_SHORT, GL_FALSE, 4, 0);
        extensions.glEnableVertexAttribArray (index);
        JUCE_CHECK_OPENGL_ERROR

        glDrawArrays (GL_TRIANGLE_STRIP, 0, 4);

        extensions.glBindBuffer (GL_ARRAY_BUFFER, 0);
        extensions.glUseProgram (0);
        extensions.glDisableVertexAttribArray (index);
        extensions.glDeleteBuffers (1, &vertexBuffer);

     

 

 

 

 


#5

More problems, now on mac os the the paint function does not work,  and I cant add any componets to the view in the above example the  error comes at

OpenGLRendering::StateHelpers::CurrentShader::setShader

 void setShader (const Rectangle<int>& bounds, ShaderQuadQueue& quadQueue, ShaderPrograms::ShaderBase& shader)
        {
            if (activeShader != &shader)
            {
                clearShader (quadQueue);

                activeShader = &shader;
                shader.program.use();

                shader.bindAttributes (context);

                currentBounds = bounds;
                shader.set2DBounds (bounds.toFloat());

                JUCE_CHECK_OPENGL_ERROR
            }
            else if (bounds != currentBounds)
            {
                currentBounds = bounds;
                shader.set2DBounds (bounds.toFloat());
            }
        }

 

at the JUCE_CHECK_OPENGL_ERROR is where it crashes

 

i can fix this if I add

              #if JUCE_OPENGL3
                if (vertexArrayObject != 0)
                    glBindVertexArray (vertexArrayObject);
               #endif

 

inside OpenGLContext::CachedImage::renderFrame though