Jump to content
  • Advertisement
Sign in to follow this  
p1p1

GL_ACTIVE_ATTRIBUTES always returns 0 attribs, but they still work... how ?

This topic is 1231 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hello!

I am using the following code while loading my shaders, before linking... The 3 glBindAttribLocation calls at the beginning do all the job (they actually work), but the following listing does not show any attribs, because glGetProgramiv (_program, GL_ACTIVE_ATTRIBUTES, &numActiveAttribs) always returns 0 (zero) in the variable passed by reference. How can that be? My attribs are definitely working, otherwise I would not be able to see my shading and textures, etc... So, why does glGetProgramiv with GL_ACTIVE_ATTRIBUTES behave so strange? Can anybody help with fixing it please? Thanks in advance!


    glBindAttribLocation (_program, GLKVertexAttribPosition,    "position");
    glBindAttribLocation (_program, GLKVertexAttribNormal,      "normal");
    glBindAttribLocation (_program, GLKVertexAttribTexCoord0,   "texcoord0");
    
    NSLog(@"Listing all bindAttribs:");
    
    GLint numActiveAttribs = -1;
    GLint maxAttribNameLength = -1;
    
    glGetProgramiv (_program, GL_ACTIVE_ATTRIBUTES, &numActiveAttribs);
    glGetProgramiv (_program, GL_ACTIVE_ATTRIBUTE_MAX_LENGTH, &maxAttribNameLength);
    
    for (int i = 0; i < numActiveAttribs; ++i) {
        
        int nameLength = -1, size = -1;
        GLenum type = GL_ZERO;
        char name[maxAttribNameLength];
        glGetActiveAttrib (_program, i, maxAttribNameLength, &nameLength, &size, &type, name);
        GLuint location = glGetAttribLocation(_program, name);
        NSLog (@"%i: %s", location, name);
    }

Edited by p1p1

Share this post


Link to post
Share on other sites
Advertisement

You say you are doing this before calling glLinkProgram()? That would be your bug. Attributes aren't active until after linking.
 

Attribute variables have arbitrary names and obtain their values through numbered generic vertex attributes. An attribute variable is considered active if it is determined during the link operation that it may be accessed during program execution. Therefore, program should have previously been the target of a call to glLinkProgram, but it is not necessary for it to have been linked successfully. (source)


You can however assign them explicit locations before linking, via glBindAttribLocation().

Share this post


Link to post
Share on other sites


You can however assign them explicit locations before linking, via glBindAttribLocation()

Thank you for your answer. The problem is that I want to know the names of the atrtibutes prior to binding, because I want to determine the set of bound attribs in runtime when loading the shader, so that I could link the attributes with my params later on rendering stage. Therefore I need to know the names of the locations of attributes.
Say, I have a shader which receives everything except normals or everything except texture coords. A call to glBindAttribLocation would then complain that it cannot find a named attribute 'normal' or 'texcoord0' if the are not used in the shader code itself. So, how do I know which attribs (with their respective names) to bind when loading and building the shader without parsing the shader code manually?

Share this post


Link to post
Share on other sites

To be more specific, I get the following:

Program link log: WARNING: Could not find vertex shader attribute 'normal' to match BindAttributeLocation request.

(I am not using the 'normal' attribute in the shader here, for example)

The program still compiles and links and works, but I wanted to get rid of those annoying warnings, and not just silence them, but to get rid of the cause.

Share this post


Link to post
Share on other sites

So, how do I know which attribs (with their respective names) to bind when loading and building the shader without parsing the shader code manually?

Do exactly what you showed in the first post, but call glLinkProgram() first.

 

You won't have the warnings if you don't call glBindAttribLocation(), and the linking step will assign default locations to all attributes.

Edited by swiftcoder

Share this post


Link to post
Share on other sites

If it is viable in your case of designing, you should consider some cpu-side data describing particular shaders you plan to use, or incorporate some construction technique for shaders if you want it more arbitrary-ready.

 

In opengl there are calls that operate only on the current state, and there is no workaround.

 

 

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

GameDev.net is your game development community. Create an account for your GameDev Portfolio and participate in the largest developer community in the games industry.

Sign me up!