I am a newbie with opengl on android. I am trying to draw two different shapes. Shape one has a texture while shape two is supposed to have a color, lets say green. When I run the application, the first shape gets its texture but has also the green color. The texture itself is turned greenish in color. Shape two is green as i wanted. Here is my draw method:
public void draw(GL10 gl) {
gl.glBindTexture(GL10.GL_TEXTURE_2D, textures[0]);
//My first shape
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glPushMatrix();
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, vertexBuffer);
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, textureBuffer);
gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, vertices.length / 3);
gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glPopMatrix();
//My second shape
gl.glPushMatrix();
//Setting the color green
gl.glColor4f(0.0f, 1.0f, 0.0f, 0.5f);
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, locvertexBuffer);
gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, locvertices.length / 3);
gl.glPopMatrix();
gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);
}
Can anyone help me with this?
Try to put gl.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); before drawing the first shape
OR
use gl.glTexEnvf(GL10.GL_TEXTURE_ENV, GL10.GL_TEXTURE_ENV_MODE, GL10.GL_REPLACE);
after you bind the texture
Related
I'm trying to change color of my textures, I have 2 render methods inside my sprite, one without color params and one with, It works fine if there is just 1 object being rendered, but If i render for example 1 colored texture and 1 normal texture, both will be colored
I'm guessing I somehow have to reset the glTextEnvf state but I got no idea how.
Here is my source code
public void Render(GL10 gl)
{
gl.glBindTexture(GL10.GL_TEXTURE_2D,textures[0]);
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glVertexPointer(2, GL10.GL_FLOAT,0, verticesBuffer);
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, textureBuffer);
gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP,0, vertices.length/2);
//RESTORE
gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);
gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
}
public void Render(GL10 gl,float r,float g,float b)
{
gl.glBindTexture(GL10.GL_TEXTURE_2D,textures[0]);
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glColor4f(r,g,b,1.0f);
gl.glTexEnvf(GL10.GL_TEXTURE_ENV, GL10.GL_TEXTURE_ENV_MODE, GL10.GL_MODULATE);
gl.glVertexPointer(2, GL10.GL_FLOAT, 0, verticesBuffer);
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, textureBuffer);
gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, vertices.length / 2);
//RESTORE
gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);
gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
}
After you've called glDrawArrays in the sprite you want to be colored, set the color back to 1:
gl.glColor4f(1, 1, 1, 1);
Hope this helps
I completed the 3D earth. Now I am trying to draw a triangle on the earth? but I failed to complete it, could you give me some cues or code to complete it? the following is drawing part in the sphere code. I could draw the triangle on the screen, but I do not know how to draw the triangle or point on the surface of 3D earth to render the latitude and longitude data on the earth.
public void draw(GL10 gl)
{
float vertexArray[] = {
SphereCoordinate(lat1, long1, 2).x,SphereCoordinate(lat1, long1, 2).y,SphereCoordinate(lat1, long1, 2).z,0.0f,
SphereCoordinate(lat2, long2, 2).x,SphereCoordinate(lat2, long2, 2).y,SphereCoordinate(lat2, long2, 2).z,0.0f,
SphereCoordinate(lat3, long3, 2).x,SphereCoordinate(lat3, long3, 2).y,SphereCoordinate(lat3, long3, 2).z,0.0f,
};
gl.glMatrixMode(GL10.GL_MODELVIEW);
gl.glEnable(GL10.GL_CULL_FACE);
gl.glCullFace(GL10.GL_BACK);
gl.glEnable(GL10.GL_LIGHTING);
gl.glEnable(GL10.GL_BLEND);
gl.glFrontFace(GL10.GL_CCW);
gl.glEnable(GL10.GL_TEXTURE_2D);
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, makeFloatBuffer(vertexArray));
gl.glColor4f(.0f, 1.0f, 0.0f, 1);
gl.glDrawArrays(GL10.GL_TRIANGLES, 0, 3); // I want to draw the triangle on earth.
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, m_VertexData);
gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glClientActiveTexture(GL10.GL_TEXTURE0);
gl.glBindTexture(GL10.GL_TEXTURE_2D, m_Texture0);
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, m_TextureData);
gl.glClientActiveTexture(GL10.GL_TEXTURE1);
gl.glTexCoordPointer(2, GL10.GL_FLOAT,0,m_TextureData);
gl.glMatrixMode(GL10.GL_MODELVIEW);
gl.glEnableClientState(GL10.GL_NORMAL_ARRAY);
gl.glNormalPointer(GL10.GL_FLOAT, 0, m_NormalData);
gl.glColorPointer(4, GL10.GL_UNSIGNED_BYTE, 0, m_ColorData);
multiTextureBumpMap(gl, m_Texture0, m_Texture1);
gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, (m_Slices+1)*2*(m_Stacks-1)+2);
}
At the beginning, the SphereCoordinate(lat1, long1, 2(r)), the r is 1 which is equal with radius of sphere, but the triangle could not be viewed. Then I made the r be 2. And run, the final slot is the following image:
Actually, I want to draw the triangle on the surface of earth.
I use 2D sprite texture applied to a square with transparent or semi-transparent area but I can't see anything through them (except the background) if there are other textures behind. I can see the background image because I use a transparent GLSurfaceView, the background is applied in a ImageView behind the GLSurfaceView.
My problem in an image:
Actually I use this code in the onSurfaceCreated method:
gl.glEnable(GL10.GL_TEXTURE_2D);
gl.glShadeModel(GL10.GL_SMOOTH);
gl.glClearDepthf(1.0f);
gl.glEnable(GL10.GL_DEPTH_TEST);
gl.glDepthFunc(GL10.GL_LEQUAL);
gl.glHint(GL10.GL_PERSPECTIVE_CORRECTION_HINT, GL10.GL_NICEST);
this in onDrawFrame method:
gl.glClear(GL10.GL_COLOR_BUFFER_BIT | GL10.GL_DEPTH_BUFFER_BIT);
gl.glMatrixMode(GL10.GL_MODELVIEW);
gl.glLoadIdentity();
mObject1.draw(gl);
mObject2.draw(gl);
and this in draw method of mObject1 and mObject2:
gl.glPushMatrix();
gl.glEnable(GL10.GL_TEXTURE_2D);
gl.glBindTexture(GL10.GL_TEXTURE_2D, textures[0]);
gl.glTranslatef((float) mPosition.getX(), (float) mPosition.getY(), 0f);
float scaleFactor = (float) (2 * mRadius);
gl.glScalef(scaleFactor, scaleFactor, 0);
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glColor4f (1f, 1.0f, 1, 1f);
gl.glFrontFace(GL10.GL_CW);
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, vertexBuffer);
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, textureBuffer);
gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, vertices.length / 3);
gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);
gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glPopMatrix();
after
gl.glClear(GL10.GL_COLOR_BUFFER_BIT | GL10.GL_DEPTH_BUFFER_BIT);
gl.glMatrixMode(GL10.GL_MODELVIEW);
gl.glLoadIdentity();
put
gl.glEnable(GL10.GL_BLEND);
gl.glBlendFunc(GL10.GL_SRC_ALPHA, GL10.GL_ONE_MINUS_SRC_ALPHA);
I have been searching for this for the pass two days .I am developing an android game using Open GL in which there is a situation where i have to display two images at the same time, one should be the background image and second one is displayed depending on a condition.
I have displayed the background imgae using Open GL Texture property.But when i tried to display the second image by using texture first one is not displaying.Since i am dealing with multiple texture i have used a GLTexture class to manipulate the texture (http://tkcodesharing.blogspot.in/2008/05/working-with-textures-in-androids.html).Even then i am not able to display two images at the same time.
Here is some code :
public void onSurfaceCreated(GL10 gl, EGLConfig config) {
glTextures= new GLTextures(gl,this.context);//class to manipulate textures
//adding image resources
this.glTextures.add(R.drawable.back);
this.glTextures.add(R.drawable.hand);
//loading texture
this.glTextures.loadTextures();
gl.glEnable(GL10.GL_TEXTURE_2D);
...
}
In onDrawFrame
gl.glClear(GL10.GL_COLOR_BUFFER_BIT|GL10.GL_DEPTH_BUFFER_BIT);
gl.glLoadIdentity();
gl.glTranslatef(0.0f, 0.0f, -3.5f);
glTextures.setTexture(R.drawable.back);//it will bind this particular texture for drawing
draw(gl);
if(condition == 1){
gl.glLoadIdentity();
gl.glTranslatef(0.0f, 1.0f, -7.0f);
glTextures.setTexture(R.drawable.hand);
drawSecond(gl);
}
////////////////////////////////////////////////////////
In draw code
public void draw(GL10 gl){
gl.glActiveTexture(GL10.GL_TEXTURE0);
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glFrontFace(GL10.GL_CW);
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, vertexBuffer);
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, textureBuffer);
gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, vertices.length/3);
gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);
}
public void drawSecond(GL10 gl){
gl.glActiveTexture(GL10.GL_TEXTURE1);
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
//GLES20.glUniform1i(isShaked, 1);
gl.glFrontFace(GL10.GL_CW);
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, vertexBuffer);
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, textureBuffer);
gl.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, vertices.length/3);
gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);
}
remove "gl.glActiveTexture(GL10.GL_TEXTURE0);" and gl.glActiveTexture(GL10.GL_TEXTURE1);
lines from the rendering code.
you use multiple texture units only if you need multi-texturing,
which is using multiple textures in one draw call.
just bind the first texture to the active texture unit (default to GL_TEXTURE0) and draw the first triangle strip, than bind the second texture (without changing the active texture unit GL_TEXTURE0) and draw the second triangle strip.
UPDATE: Summary:
I can draw a circle using TRIANGLE_FAN and, separately, I also can draw two squares with bitmaps as textures. But the problem is when I draw the textures and then the circles. Circles aren't drawn.
I'm drawing two texturized squares (4 vertex each). Then I draw a circle using GL_TRIANGLE_FAN but it isn't being drawn correctly (see images).
When I draw the circles without the squares, it is drawn correctly.
Any ideas where could be the problem?
Please, ask for more information. Thanks
Adding some code that I think is important:
public void onSurfaceCreated(GL10 gl, EGLConfig config) {
gl.glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
gl.glShadeModel(GL10.GL_SMOOTH);
gl.glFrontFace(GL10.GL_CCW);
gl.glEnable(GL10.GL_CULL_FACE);
gl.glEnable(GL10.GL_BLEND);
gl.glCullFace(GL10.GL_BACK);
gl.glBlendFunc(GL10.GL_SRC_ALPHA, GL10.GL_ONE_MINUS_SRC_ALPHA);
gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
gl.glEnable(GL10.GL_TEXTURE_2D);
}
public void onSurfaceChanged(GL10 gl, int w, int h) {
gl.glViewport(0, 0, width, height);
gl.glMatrixMode(GL10.GL_PROJECTION);
gl.glOrthof(0, w, -0, h, -1, 1);
gl.glMatrixMode(GL10.GL_MODELVIEW);
gl.glLoadIdentity();
}
public void onDrawFrame(GL10 gl) {
gl.glClear(GL10.GL_COLOR_BUFFER_BIT);
gl.glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
circle.draw(gl);
needle.draw(gl);
synchronized (tokens) {
for (Token d : tokens) {
d.draw(gl);
}
}
}
Update:
Some screenshots.
Without drawing circle and needle objects:
Drawing circle and needle:
(Look at those red lines where should be a circle)
The only change in the code between those images is commenting the lines
circle.draw(gl);
needle.draw(gl);
Token:
public void draw(GL10 gl) {
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, vertexBuffer);
gl.glPushMatrix();
gl.glTranslatef(x, y, 0f);
gl.glScalef(radius, radius, 0f);
gl.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
gl.glDrawArrays(GL10.GL_TRIANGLE_FAN, 0, nVertices+2);
gl.glPopMatrix();
}
Circle and Needle:
public void draw(GL10 gl) {
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, vertexBuffer);
if (shouldLoadTexture) {
loadGLTexture(gl);
shouldLoadTexture = false;
}
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, textureBuffer);
gl.glBindTexture(GL10.GL_TEXTURE_2D, textureId);
gl.glPushMatrix();
gl.glTranslatef(x, y, 0f);
gl.glRotatef((float) angle, 0f, 0f, 1f);
angle += rotAngle;
if(angle+rotAngle > 360.0)
angle -= 360.0;
gl.glScalef(width, height, 0f);
gl.glDrawElements(GL10.GL_TRIANGLES, indices.length,
GL10.GL_UNSIGNED_SHORT, indexBuffer);
gl.glPopMatrix();
}
private void loadGLTexture(GL10 gl) {
int[] textures = new int[1];
gl.glGenTextures(1, textures, 0);
textureId = textures[0];
gl.glBindTexture(GL10.GL_TEXTURE_2D, textureId);
gl.glTexParameterf(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_MIN_FILTER,
GL10.GL_LINEAR);
gl.glTexParameterf(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_MAG_FILTER,
GL10.GL_LINEAR);
gl.glTexParameterf(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_WRAP_S,
GL10.GL_CLAMP_TO_EDGE);
gl.glTexParameterf(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_WRAP_T,
GL10.GL_REPEAT);
GLUtils.texImage2D(GL10.GL_TEXTURE_2D, 0, bitmap, 0);
}
Update:
Following what Arne says in the first answer, I changed:
public void draw(GL10 gl) {
//New line
gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
gl.glVertexPointer(3, GL10.GL_FLOAT, 0, vertexBuffer);
if (shouldLoadTexture) {
loadGLTexture(gl);
shouldLoadTexture = false;
}
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, textureBuffer);
gl.glBindTexture(GL10.GL_TEXTURE_2D, textureId);
gl.glPushMatrix();
gl.glTranslatef(x, y, 0f);
gl.glRotatef((float) angle, 0f, 0f, 1f);
angle += rotAngle;
if(angle+rotAngle > 360.0)
angle -= 360.0;
gl.glScalef(width, height, 0f);
gl.glDrawElements(GL10.GL_TRIANGLES, indices.length,
GL10.GL_UNSIGNED_SHORT, indexBuffer);
gl.glPopMatrix();
//New line
gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
}
Now I get no circle at all. Neither red line as in the second image.
Update:
When I don't load the texture of circle and needle (just commenting the call to loadTexture() ), I get this:
So the problem should be with the textures.
You enable texturing (by calling glEnable(GL_TEXTURE_2D)) at the beginning, but you don't provide your circles (tokens) any texture coordinates. As I suppose these shouldn't be textured, you should only enable texturing for the objects that are really textured and disable texturing again after drawing them, the same way you enable and disable the texCoord array in your updated code.
Try to disable GL_TEXTURE_COORD_ARRAY before drawing the circles with
gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);