Translation after rotation

I am using OpenGL ES 2.0 for Android. I translate and rotate the model using the touch screen. My translations are performed only in the (x, y) plane, and my rotation is performed only on the z axis. Imagine that you are looking directly at the map on the table and go to different coordinates on the map and you can rotate the map around the point you are looking at .

The problem is that after I turn around, my subsequent translations will more correspond to the movements of the pointer on the screen, the axes will be different.

Everything I tried gives me one of two behaviors. One is equivalent:

Matrix.setIdentityM(mModelMatrix, 0);
Matrix.translateM(mModelMatrix, 0, Xposition, Yposition, 0.0f);
Matrix.rotateM(mModelMatrix, 0, rotationAngle, 0.0f, 0.0f, 1.0f);

This allows me to translate as expected (up / down on the screen moves the model up and down, left / right moves the model left and right), regardless of rotation. The problem is that the rotation is around the center of the object, and I need the rotation to be around the point I am looking at, which is different from the center of the object.

Other behavior that I can get is equivalent to:

Matrix.setIdentityM(mModelMatrix, 0);
Matrix.rotateM(mModelMatrix, 0, rotationAngle, 0.0f, 0.0f, 1.0f);
Matrix.translateM(mModelMatrix, 0, Xposition, Yposition, 0.0f);

It gives me the twist I want, always about what I look at. The problem is that after the rotation, the translations are incorrect. The object is moved to the left / right on the screen at a different angle along the rotated axes.

I need a way to get both behaviors at the same time. It should rotate around the point I'm looking at, and translate in the direction in which the finger moves around the screen.

? ?

, , .

EDIT: .

, (0, 0, 0) . z , x/y. z. .

, , , , .

, , , . , , , . ?

+4
4

, , .

, , , onDrawFrame().

//Initialize the model matrix for the current transformation
Matrix.setIdentityM(mModelMatrixCurrent, 0);
//Apply the current transformations
Matrix.translateM(mModelMatrixCurrent, 0, cameraX, cameraY, cameraZ);
Matrix.rotateM(mModelMatrixCurrent, 0, mAngle, 0.0f, 0.0f, 1.0f);
//Multiply the accumulated transformations by the current transformations
Matrix.multiplyMM(mTempMatrix, 0, mModelMatrixCurrent, 0, mModelMatrixAccumulated, 0);
System.arraycopy(mTempMatrix, 0, mModelMatrixAccumulated, 0, 16);

.

+1

. # OpenGL (SharpGL) .

. . , .

.

(Xposition, Yposition) = (Xposition, Yposition) + mRotation.transposed() * (XIncr, YIncr)

NewTranslationPosition = oldTranslationPosition + rotationMatrix.Transposed * UserTranslationIncrement.

reto.koradi( OpenGL)!

, 3D, :

double gXposition = 0;
double gYposition = 0;
double gZposition = 0;

double gXincr = 0;
double gYincr = 0;
double gZincr = 0;

float[] rotMatrix = new float[16]; //Rotational matrix

private void openGLControl_OpenGLDraw(object sender, PaintEventArgs e)
{

  OpenGL gl = openGLControl.OpenGL;

  gl.Clear(OpenGL.GL_COLOR_BUFFER_BIT | OpenGL.GL_DEPTH_BUFFER_BIT);

  gl.LoadIdentity();
  gl.MultMatrix(rotMatrix); //This is my rotation, using a rotation matrix
  gl.Translate(gXposition, gYposition, gZposition); //translate second to keep rotation at center of screen

  DrawCube(ref  gl);

}

private void buttonTransLeft_Click(object sender, EventArgs e)
{
        double tX = -0.1;
        double tY = 0;
        double tZ = 0;

        TransposeRotMatrixFindPoint(ref tX, ref tY, ref tZ);

        gXposition = gXposition + tX;
        gYposition = gYposition + tY;
        gZposition = gZposition + tZ;

 }

 private void buttonTransRight_Click(object sender, EventArgs e)
 {

        double tX = 0.1;
        double tY = 0;
        double tZ = 0;

        TransposeRotMatrixFindPoint(ref tX, ref tY, ref tZ);


        gXposition = gXposition + tX;
        gYposition = gYposition + tY;
        gZposition = gZposition + tZ;

  }

public void TransposeRotMatrixFindPoint(ref double x, ref double y, ref double z)
    {
        //Multiply [x,y,z] by Transpose Rotation matrix to generate new [x,y,z]
        double Xt = 0; //Tempoary variable
        double Yt = 0; //Tempoary variable
        Xt = (x * rotMatrix[0, 0]) + (y * rotMatrix[0, 1]) + (z * rotMatrix[0, 2]);
        Yt = (x * rotMatrix[1, 0]) + (y * rotMatrix[1, 1]) + (z * rotMatrix[1, 2]);
        z = (x * rotMatrix[2, 0]) + (y * rotMatrix[2, 1]) + (z * rotMatrix[2, 2]);

        //or try this 
        //Xt = (x * rotMatrix[0, 0]) + (y * rotMatrix[1, 0]) + (z * rotMatrix[2, 0]);
        //Yt = (x * rotMatrix[0, 1]) + (y * rotMatrix[1, 1]) + (z * rotMatrix[2, 1]);
        //z = (x * rotMatrix[0, 2]) + (y * rotMatrix[1, 2]) + (z * rotMatrix[2, 2]);


        x = Xt;
        y = Yt;
    }
+1

, : , . , .

- , XY , , , . , . , - , , .

, , -

translate (dx, dy); (A); (cx, cy); ()

cx cy - . ( -dx, -dy)

, .

0

, . , OpenGL Android. , , 4 ?

"". this .

, "" .

:

, (x1, y1, z1). (Ox, Oy, Oz).

Set Origin:

Matrix.setIdentityM(mModelMatrix, 0);

, :

Matrix.translateM(mModelMatrix, 0, -x1, -y1, -z1);

  Matrix.rotateM(mModelMatrix, 0, rotationAngle, 0.0f, 0.0f, 1.0f);

:

Matrix.translateM(mModelMatrix, 0, x1, y1, z1);

, :

Matrix.translateM(mModelMatrix, 0, x, y, z);

.

Try: Set Origin:

Matrix.setIdentityM(mModelMatrix, 0);

:

Matrix.translateM(mModelMatrix, 0, x, y, z);

Matrix.translateM(mModelMatrix, 0, x1, y1, z1);

Matrix.rotateM(mModelMatrix, 0, rotationAngle, 0.0f, 0.0f, 1.0f);

Matrix.translateM(mModelMatrix, 0, -x1, -y1, -z1);

, .

Edit

, , : :

Matrix.setIdentityM(mModelMatrix, 0);

Matrix.translateM(mModelMatrix, 0, x1, y1, z1);

Matrix.rotateM(mModelMatrix, 0, rotationAngle, 0.0f, 0.0f, 1.0f);

Matrix.Multiply(mViewProjection, 0, mProjection, 0, mCameraView, 0);  //something like this, but do you have the right order?

mViewProjection * mModelMatrix * a_Position;

?

/ ( ) . , , -

0

Source: https://habr.com/ru/post/1532060/


All Articles