GLSL 1.5无法获得颜色输入

时间:2014-01-23 10:26:28

标签: opengl glsl fragment-shader vertex-shader gouraud

我只想在我的物体上做一些简单的Gouraud Shading,颜色有些不同。基本上我的问题是,我无法将颜色值输入到着色器中,它只是呈现黑色。如果我在着色器中将矢量定义为整个对象的颜色,它可以正常工作。

主程序:

protected void initOpenGL() {
    glEnable(GL_DEPTH_TEST);
    glEnable(GL_CULL_FACE);
    startTime = Sys.getTime();

    m = new Matrix4f();
    m.m00 = 1;
    m.m11 = 1;
    m.m22 = -(101.0f / 99);
    m.m32 = -(200.0f / 99);
    m.m23 = -1;
    m.m33 = 0;

    makeCube();

    sp = new ShaderProgram("gouraud");
    glBindAttribLocation(sp.getId(), 0, "corners");
    glBindAttribLocation(sp.getId(), 1, "colors");

}

@Override
protected void render() {

    gamma = gamma + 1;
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

    Matrix4f newMat = new Matrix4f(m);
    Matrix4f.translate(new Vector3f(0, 0, -5), newMat, newMat);
    newMat.rotate(gamma/100, new Vector3f(0, 1, 0));
    newMat.rotate(gamma/200, new Vector3f(1, 0, 0));

    FloatBuffer fb = BufferUtils.createFloatBuffer(16);
    newMat.store(fb);
    fb.flip();
    GL20.glUniformMatrix4(GL20.glGetUniformLocation(sp.getId(), "matrix"),
            false, fb);

    GL20.glUseProgram(sp.getId());


    glBindVertexArray(vaoId);
    glEnableVertexAttribArray(0);
    glEnableVertexAttribArray(1);
    glDrawArrays(GL_QUADS, 0, corners.length/3);
    glDisableVertexAttribArray(1);
    glDisableVertexAttribArray(0);
    glBindVertexArray(0);

}

private void makeCube(){
    corners = new float[] {
            // cube
            // front
            -1, -1, 1, 1, -1, 1, 1, 1, 1, -1, 1, 1,
            // left
            -1, -1, 1, -1, 1, 1, -1, 1, -1, -1, -1, -1,
            // bottom
            -1, -1, 1, -1, -1, -1, 1, -1, -1, 1, -1, 1,
            // right
            1, -1, 1, 1, -1, -1, 1, 1, -1, 1, 1, 1,
            // top
            -1, 1, 1, 1, 1, 1, 1, 1, -1, -1, 1, -1,
            // back
            -1, -1, -1, -1, 1, -1, 1, 1, -1, 1, -1, -1,

    };

    FloatBuffer eckenBuffer = BufferUtils.createFloatBuffer(corners.length);
    eckenBuffer.put(corners);
    eckenBuffer.flip();

    vaoId = glGenVertexArrays();
    glBindVertexArray(vaoId);
    int vboId = glGenBuffers();
    glBindBuffer(GL_ARRAY_BUFFER, vboId);
    glBufferData(GL_ARRAY_BUFFER, eckenBuffer, GL_STATIC_DRAW);
    glVertexAttribPointer(0, 3, GL_FLOAT, false, 0, 0);
    glBindBuffer(GL_ARRAY_BUFFER, 0);


    colors = new float[] {
            // front
            1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f,

            // right
            1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f,

            // back
            1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f,

            // left
            0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f,

            // top
            0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f,

            // bottom
            1.0f, 1.0f, 0.0f, 1.0f, 1.0f, 0.0f, 1.0f, 1.0f, 0.0f, 1.0f, 1.0f, 0.0f };

    FloatBuffer colorBuffer = BufferUtils.createFloatBuffer(colors.length);
    colorBuffer.put(colors);
    colorBuffer.flip();

    int vboIdB = glGenBuffers();
    glBindBuffer(GL_ARRAY_BUFFER, vboIdB);
    glBufferData(GL_ARRAY_BUFFER, colorBuffer, GL_STATIC_DRAW);
    glVertexAttribPointer(1, 3, GL_FLOAT, false, 0, 0);
    glBindBuffer(GL_ARRAY_BUFFER, 0);
}

着色器:

顶点

#version 150
in vec4 corners;
in vec4 colors;

vec4 colorTest = vec4(1.0,0.0,0.0,1.0);

out vec4 colorToFrag;

uniform mat4 matrix;

void main(void) {
colorToFrag = colors ;
gl_Position = matrix * corners;

}

片段

#version 150
in vec4 colorToFrag;

out vec4 colorOut;

void main(void) {
colorOut = colorToFrag;
}

1 个答案:

答案 0 :(得分:1)

您没有发布着色器编译/链接的代码,但由于您调用glBindAttribLocation但未在其余代码中调用glLinkProgram,因此我做了有根据的猜测,即链接仅在ShaderProgram构造函数中发生。

glBindAttribLocation调用只会影响它之后的任何链接操作(显然)。所以你的位置绑定根本没有效果 - GL指定它们。

现在,如果您不在着色器中使用colors属性,它将被优化并且该属性将不会处于活动状态 - 因此它将根本没有位置,corners是可能会像你期望的那样获得指数0。请注意,从零开始,GL不需要按顺序分配属性位置,但大多数情况下都是如此。 如果您实际使用“颜色”,它可能会以位置0结束,完全破坏渲染。

另一方面注意:在nvidia上,我观察到GL分配的属性位置实际上是由着色器中的变量名按字典顺序排序 - 因此“颜色”将出现在“角落”之前。我不确定这只是巧合还是其他实现如何处理。