Search code examples
openglglsllwjglvertex-shader

LWJGL shader normal's alias


I'm writing my app with LWJGL and on some graphic cards (AMD Radeon series) I can not change the normal's name in vertex shader because something goes wrong and only one big triangle appears on the screen. Here is my code:

#version 150

//our attributes
in vec3 a_position;
in vec2 a_textureCoords;
in vec3 a_normal; //Here is an error

//send the color out to the fragment shader
out vec2 vTextureCoords;

void main(void)
{
    a_normal;
    gl_Position = vec4(a_position, 1.0);
    vTextureCoords = a_textureCoords;
}

if I change shader to this:

#version 150

//our attributes
in vec3 a_position;
in vec2 a_textureCoords;
in vec3 normal;

//send the color out to the fragment shader
out vec2 vTextureCoords;

void main(void)
{
    normal;
    gl_Position = vec4(a_position, 1.0);
    vTextureCoords = a_textureCoords;
}

Everything works fine and mesh appear as it should be. Is it normal? And my bind attribute function:

//Before
GL20.glBindAttribLocation(s_programID, 2, "a_normal");

//After
GL20.glBindAttribLocation(s_programID, 2, "normal");

edit

Attributes locations in shader:

//Before
a_normal 0
a_position 1
a_textureCoords 2

//After
a_position 0
a_textureCoords 1
normal 2

Solution

  • I'd suggest you to write something like this:

    #version 150
    
    #define POSITION  0
    #define TEX_COORD 1 
    #define NORMAL    2 
    
    //our attributes
    layout (location = POSITION) in vec3 a_position;
    layout (location = TEX_COORD) in vec2 a_textureCoords;
    layout (location = NORMAL) in vec3 a_normal;
    
    //send the color out to the fragment shader
    out vec2 vTextureCoords;
    
    void main(void)
    {
        a_normal;
        gl_Position = vec4(a_position, 1.0);
        vTextureCoords = a_textureCoords;
    }
    

    And then on java you have something like:

    interface Semantic {
    
       interface Attr {
    
          int POSITION = 0;
          int TEX_COORD = 1;
          int NORMAL = 2;
       }
    }
    

    that you will use in your glVertexAttribPointer and glEnableVertexAttribute functions

    Otherwise, remember to glBindAttribLocation before or glGetAttribLocation after linking the program

    Ps: remember to do something useful with that a_normal otherwise the glsl compiler will optimize it out by removing it completely