Reputation: 31851
NOTE: I've updated this code now to the working form and provided everything I attempted in an answer. Hopefully it helps somebody else with the same problem.
My texture is being shown as black (that is, no texture). I've gone through several other questions here with the same problem, but could not find a solution. I'm sure I'm missing something quite simple (likely ordering), but can't figure it out.
I setup my texture like this (GLProgram.checkError checks for GL errors and logs them -- I get no errors anywhere):
/*Bitmap*/ bitmap = BitmapFactory.decodeResource( context.getResources(),
R.drawable.gears );
int textures[] = new int[1];
GLES20.glGenTextures( 1, textures, 0 );
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, textures[0]);
GLES20.glTexParameterf(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_WRAP_S, GLES20.GL_CLAMP_TO_EDGE);
GLES20.glTexParameterf(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_WRAP_T, GLES20.GL_CLAMP_TO_EDGE);
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_MIN_FILTER, GLES20.GL_NEAREST);
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_MAG_FILTER, GLES20.GL_NEAREST);
GLUtils.texImage2D(GLES20.GL_TEXTURE_2D, 0, bitmap, 0);
GLProgram.checkError( "texImage2D" );
texture = textures[0];
To draw a square which should be textured I do this:
GLES20.glVertexAttribPointer(glProgram.hATex, 2, GLES20.GL_FLOAT, false,
2*SIZEOF_FLOAT, texBuffer.under);
GLProgram.checkError( "hATex" );
GLES20.glActiveTexture(GLES20.GL_TEXTURE0 );
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, texture);
GLES20.glUniform1i(glProgram.hUTex, 0);
GLProgram.checkError( "Uniform" );
GLES20.glVertexAttribPointer( glProgram.hAttribPosition, COORDS_PER_VERTEX,
GLES20.GL_FLOAT, false,
vertexStride, vertexBuffer.under );
GLProgram.checkError( "Vertex" );
GLES20.glDrawArrays( GLES20.GL_TRIANGLE_FAN, 0, vertexBuffer.size/COORDS_PER_VERTEX );
GLProgram.checkError( "draw" );
My vertex shader is:
precision mediump float;
attribute vec4 vPosition;
uniform mat4 mTransform;
attribute vec2 aTex;
varying mediump vec2 vTex;
void main() {
gl_Position = mTransform * vPosition;
vTex = aTex;
}
My fragment shader is:
precision mediump float;
uniform vec4 vColor;
uniform sampler2D uTex;
varying mediump vec2 vTex;
void main(void)
{
//gl_FragColor = vColor;
//testing vTex, and it is fine
//gl_FragColor = vec4( vTex[0], vTex[1], 0, 1.0 );
//so it must be uTex which is program
gl_FragColor = texture2D(uTex,vTex);
}
I left in the commented bits to show what I checked. My vTex
parameter is correct, since that bit produces the expected red/green color sweep. So I assume it must be the texture itself.
Also, uTex, aTex are located via:
hATex = GLES20.glGetAttribLocation( hProgram, "aTex" );
checkError( "aTex" );
hUTex = GLES20.glGetUniformLocation( hProgram, "uTex" );
checkError( "uTex" );
My texture comes a JPG and is 64x64 in size. I checked just after loading and it has the correct size and does appear to have pixel colors (dumping a few at random were non-zero).
Upvotes: 2
Views: 1030
Reputation: 31851
The code, as presented, now works. I modified it as I tried things and for the comments. I can't be sure at which step it actually started working, since it didn't work before. Here are some of the things I checked/double-checked in the process -- I presume it has to be a combination of these somehow:
These are things I tried, and tried again now, and appear to make no different (that is, it works either way):
In the case when it wasn't working the error was silent: calls to glGetError returned okay and glGetProgramInfoLog was empty.
Upvotes: 2