Reputation: 32273
I'm trying to achieve something simple: Set a translation on X axis, and rotate the object around it's center by a fixed angle.
To achieve this, as far my current knowledge, it's necessary to move the object to the center, rotate, and move back to the original position. Okay. The problem I get although, is that it looks like the object rotate it's local axis and do the last translation along these axis, so it ends in a wrong position.
This is my code:
public void draw(GL10 gl) {
gl.glLoadIdentity();
GLU.gluLookAt(gl, 0, 0, 5, 0, 0, 0, 0, 1, 0);
gl.glTranslatef(x, 0, 0);
gl.glTranslatef(-x, 0, 0);
gl.glRotatef(-80, 0, 1, 0);
gl.glTranslatef(x, 0, 0);
gl.glBindTexture(GL10.GL_TEXTURE_2D, textureId);
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, verticesBuffer);
gl.glTexCoordPointer(2, GL10.GL_FLOAT, 0, textureBuffer);
gl.glDrawElements(GLES20.GL_TRIANGLES, indices.length, GLES10.GL_UNSIGNED_SHORT, indicesBuffer);
}
Before the rotation the object should be at 0,0,0. It rotates correctly. But then it comes near to the screen as if the x axis would be pointing to me (80°).
Note: I let only "opengl" as tag, since this is a general OpenGL question, the answer should not be Android related.
Upvotes: 1
Views: 2022
Reputation: 503
This is the deprecated way of doing this, but I guess that is no excuse for not answering the question.
OpenGL performs matrices multiplications in reverse order if multiple transforms are applied to a vertex. For example, If a vertex is transformed by MA first, and transformed by MB second, then OpenGL performs MB x MA first before multiplying the vertex. So, the last transform comes first and the first transform occurs last in your code.
gl.glPushMatrix();
gl.glTranslatef(globalX, 0, 0);
gl.glTranslatef(localX, 0 ,0);
gl.glRotatef(-80, 0, 1, 0);
gl.glTranslatef(-globalX, 0, 0);
gl.glPopMatrix();
First move from where you are in a hierarchy of transforms to the origin. Then rotate around that origin. Apply some local movement along any axis. Move the object back to its global positioning.
Use glPushMatrix() and glPopMatrix() to undo changes for elements in the same level of relative positioning, this is having the same parent element to which they are relatively positioned. The push preserves translations from previous (parent) objects that OpenGL applies after operations in the local code above, as it is the order of a common stack (LIFO), in this case the matrix stack.
Upvotes: 4