I was having extreme trouble getting a vertex shader of mine to run under OpenGL 3.3 core on an ATI driver:
#version 150
uniform mat4 graph_matrix, view_matrix, proj_matrix;
uniform bool align_origin;
attribute vec2 graph_position;
attribute vec2 screen_position;
attribute vec2 texcoord0;
attribute vec4 color;
varying vec2 texcoord0_px;
varying vec4 color_px;
void main() {
// Pick the position or the annotation position
vec2 pos = graph_position;
// Transform the coordinates
pos = vec2(graph_matrix * vec4(pos, 0.0, 1.0));
if( align_origin )
pos = floor(pos + vec2(0.5, 0.5)) + vec2(0.5, 0.5);
gl_Position = proj_matrix * view_matrix * vec4(pos + screen_position, 0.0, 1.0);
texcoord0_px = texcoord0;
color_px = color;
}
I used glVertexAttrib4f to specify the color attribute, and turned the attribute array off. According to page 33 of the 3.3 core spec, that should work:
If an array corresponding to a generic attribute required by a vertex shader is not enabled, then the corresponding element is taken from the current generic attribute state (see section 2.7).
But (most of the time, depending on the profile and driver) the shader either didn't run at all or used black if I accessed the disabled color attribute. Replacing it with a constant got it to run.
Much searching yielded this page of tips regarding WebGL, which had the following to say:
Always have vertex attrib 0 array enabled. If you draw with vertex attrib 0 array disabled, you will force the browser to do complicated emulation when running on desktop OpenGL (e.g. on Mac OSX). This is because in desktop OpenGL, nothing gets drawn if vertex attrib 0 is not array-enabled. You can use bindAttribLocation() to force a vertex attribute to use location 0, and use enableVertexAttribArray() to make it array-enabled.
Sure enough, not only was the color attribute assigned to index zero, but if I force-bound a different, array-enabled attribute to zero, the code ran and produced the right color.
I can't find any other mention of this rule anywhere, and certainly not on ATI hardware. Does anyone know where this rule comes from? Or is this a bug in the implementation that the Mozilla folks noticed and warned about?