【问题标题】:Android OpenGL ES 2.0 - Rotation in placeAndroid OpenGL ES 2.0 - 就地旋转
【发布时间】:2014-03-27 02:50:45
【问题描述】:

我想在 Z 轴上旋转我的三角形,但我想围绕三角形的中心进行,而不是屏幕的中心。我对此进行了很多研究,但没有找到任何解决方案。

知道我可以尝试解决什么问题吗?

public class RendererClass implements Renderer {

FloatBuffer bufferObj1;
FloatBuffer bufferObj2;

int programObj1;
int programObj2;

int positionObj1;
int positionObj2;

int rotationMatrixLocationObj1;
int rotationMatrixLocationObj2;

int colorObj1;
int colorObj2;

float[] rotationMatrixObj1 = new float[16];
float[] rotationMatrixObj2 = new float[16];

@Override
public void onSurfaceCreated(GL10 arg0, EGLConfig config) {

    GLES20.glClearColor(0.0f, 1.0f, 1.0f, 1.0f);    

    float[] vertexObj1 = {

            -0.8f, 0.8f,
            -0.8f, 0.0f,
             0.0f, 0.0f

    };

    float[] vertexObj2 = {

             0.8f, 0.8f,
             0.8f, 0.0f,
             0.0f, 0.0f

    };

    bufferObj1 = ByteBuffer.allocateDirect(vertexObj1.length*4).order(ByteOrder.nativeOrder()).asFloatBuffer().put(vertexObj1);
    bufferObj2 = ByteBuffer.allocateDirect(vertexObj2.length*4).order(ByteOrder.nativeOrder()).asFloatBuffer().put(vertexObj2);

    String vssObj1 = "attribute vec4 positionObj1;" +
                     "uniform mat4 rotationMatrixObj1;" +
                     "void main(){" +
                     "gl_Position = rotationMatrixObj1 * positionObj1;" +
                     "}";

    String vssObj2 = "attribute vec4 positionObj2;" +
                     "uniform mat4 rotationMatrixObj2;" +
                     "void main(){" +
                     "gl_Position = rotationMatrixObj2 * positionObj2;" +
                     "}";

    String fssObj1 = "precision mediump float;" +
                     "uniform vec4 colorObj1;" +
                     "void main(){" +
                     "gl_FragColor = colorObj1;" +
                     "}";

    String fssObj2 = "precision mediump float;" +
                     "uniform vec4 colorObj2;" +
                     "void main(){" +
                     "gl_FragColor = colorObj2;" +
                     "}";

    int vsObj1 = glCreateShader(GL_VERTEX_SHADER);
    int vsObj2 = glCreateShader(GL_VERTEX_SHADER);

    int fsObj1 = glCreateShader(GL_FRAGMENT_SHADER);
    int fsObj2 = glCreateShader(GL_FRAGMENT_SHADER);

    glShaderSource(vsObj1, vssObj1);
    glShaderSource(vsObj2, vssObj2);

    glShaderSource(fsObj1, fssObj1);
    glShaderSource(fsObj2, fssObj2);

    glCompileShader(vsObj1);
    glCompileShader(vsObj2);

    glCompileShader(fsObj1);
    glCompileShader(fsObj2);

    programObj1 = glCreateProgram();
    programObj2 = glCreateProgram();

    glAttachShader(programObj1, vsObj1);
    glAttachShader(programObj2, vsObj2);

    glAttachShader(programObj1, fsObj1);
    glAttachShader(programObj2, fsObj2);

    glLinkProgram(programObj1);
    glLinkProgram(programObj2);

    positionObj1 = glGetAttribLocation(programObj1, "positionObj1");
    positionObj2 = glGetAttribLocation(programObj2, "positionObj2");

    rotationMatrixLocationObj1 = glGetUniformLocation(programObj1, "rotationMatrixObj1");
    rotationMatrixLocationObj2 = glGetUniformLocation(programObj2, "rotationMatrixObj2");       

    colorObj1 = glGetUniformLocation(programObj1, "colorObj1");
    colorObj2 = glGetUniformLocation(programObj2, "colorObj2");     

}

@Override
public void onSurfaceChanged(GL10 arg0, int width, int height) {

    Matrix.setIdentityM(rotationMatrixObj1, 0);
    Matrix.rotateM(rotationMatrixObj1, 0, MainActivity.angle, 0, 0, 1);     

    Matrix.setIdentityM(rotationMatrixObj2, 0);
    Matrix.rotateM(rotationMatrixObj2, 0, MainActivity.angle, 0, 0, -1);

}

GL10 gl;

@Override
public void onDrawFrame(GL10 glUnused) {

    GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);     

    onSurfaceChanged(gl, 0, 0);

    glUseProgram(programObj1);
    bufferObj1.position(0);
    glVertexAttribPointer(positionObj1, 2, GL_FLOAT, false, 0, bufferObj1);
    glEnableVertexAttribArray(positionObj1);
    glUniform4f(colorObj1, 0.0f, 0.0f, 1.0f, 1.0f);
    glUniformMatrix4fv(rotationMatrixLocationObj1, 1, false, rotationMatrixObj1, 0);
    glDrawArrays(GL_TRIANGLES, 0, 3);

    glUseProgram(programObj2);
    bufferObj2.position(0);
    glVertexAttribPointer(positionObj2, 2, GL_FLOAT, false, 0, bufferObj2);
    glEnableVertexAttribArray(positionObj2);
    glUniform4f(colorObj2, 1.0f, 0.0f, 0.0f, 1.0f);
    glUniformMatrix4fv(rotationMatrixLocationObj2, 1, false, rotationMatrixObj2, 0);
    glDrawArrays(GL_TRIANGLES, 0, 3);

}   

}

【问题讨论】:

    标签: android opengl-es-2.0


    【解决方案1】:

    您使用glDrawArrays,因此您可以随意更改代码中的三角形。使用简单的三角函数独立旋转顶点。

    【讨论】:

    • 三角函数已经在着色器中,我的“rotationMatrixObj1”和“rotationMatrixObj2”。问题是它们围绕屏幕的中心点旋转,而不是围绕三角形中心。你能发表任何建议吗?
    【解决方案2】:

    旋转矩阵围绕坐标系中心旋转顶点。 如果你想围绕其他点(x0、y0、z0)旋转场景,你必须通过 3 个简单的步骤来完成:

    1. 以这样的方式平移场景,使您的点位于坐标系的中心(通过 -x0、-y0、-z0)
    2. 旋转
    3. 向后平移(按 x0、y0、z0)

    当然不需要3步转换,矩阵乘法可以为我们完成这项工作。

    【讨论】:

    • 谢谢,我认为这就是解决方案。最后一个问题,如果我翻译场景,我的坐标系统中心和三角形(在坐标系统上)都将被翻译。这样做三角形和中心之间的距离将与以前相同,并且旋转将与以前一样 - 不是围绕三角形中心。我想我没有遵循我应该在代码中做什么。您能否提供更多关于步骤 1 的详细信息?旋转和平移我可以弄清楚。谢谢。
    • 我解决了我的问题。我应该把我的三角形放在坐标系的中心(不是),然后平移和旋转。完美的伴侣,谢谢。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多