6

OpenGLを使用してテキストを表示するアプリケーションを作成しようとしています。Matrix.translateM指定したオブジェクトを特定の位置に移動しようとすると、予期しない動作が発生します。他のすべての変換行列は、私が期待するとおりに機能します。

これは私が電話したときに私が得るものですMatrix.translateM(model_matrix, 0, -1.0f, 0, 0)結果画像

これは翻訳なしの画像です: ここに画像の説明を入力してください

これは私のレンダラーコードです。

@Override
public void onSurfaceCreated(GL10 unused, EGLConfig config) {
    GLES20.glClearColor(0.5f, 0.5f, 0.5f, 1.0f);
    GLES20.glDisable(GLES20.GL_DEPTH_TEST);
    GLES20.glEnable(GLES20.GL_BLEND);
    GLES20.glBlendFunc(GLES20.GL_SRC_ALPHA, GLES20.GL_ONE_MINUS_SRC_ALPHA);

    // create programs
    simple_texture = new SimpleTexture();

    // create shapes
    square = new Square();

    // create debug text handlers
    text_fps = new Text(this.font, this.text_scale);
    text_fps.setSize(50);
    text_fps.setText("Test\nLonger line");

    // set camera position
    final float eyeX = 0.0f;
    final float eyeY = 0.0f;
    final float eyeZ = -3.0f;

    final float lookX = 0.0f;
    final float lookY = 0.0f;
    final float lookZ = 0.0f;

    final float upX = 0.0f;
    final float upY = 1.0f;
    final float upZ = 0.0f;

    Matrix.setLookAtM(view_matrix, 0, eyeX, eyeY, eyeZ, lookX, lookY, lookZ, upX, upY, upZ);
}

@Override
public void onSurfaceChanged(GL10 unused, int width, int height) {
    GLES20.glViewport(0, 0, width, height);

    // set projection matrix
    float ratio = (float) width / height;
    Matrix.orthoM(projection_matrix, 0, -ratio, ratio, -1, 1, 3, 7);

    setScreenRatio(ratio);
    setScreenHeight(height);
}

@Override
public void onDrawFrame(GL10 unused) {
    GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);

    // calculate projection and view transformation
    Matrix.multiplyMM(vp_matrix, 0, projection_matrix, 0, view_matrix, 0);

    // if we are connected to debugger draw statistics
    drawStatistics(vp_matrix);
}

そして、これは私drawのテキストのコードです。

    // use predefined program
    GLES20.glUseProgram(program);

    // get attribute positions
    attr_matrix = GLES20.glGetUniformLocation(program, "u_Matrix");
    attr_position = GLES20.glGetAttribLocation(program, "a_Position");
    attr_texture_position = GLES20.glGetAttribLocation(program, "a_TexturePosition");
    attr_texture = GLES20.glGetUniformLocation(program, "u_Texture");

    // set program parameters
    GLES20.glEnableVertexAttribArray(attr_position);
    GLES20.glVertexAttribPointer(attr_position, 2, GLES20.GL_FLOAT, false, 2 * 4, square_buffer);

    // set texture parameters
    GLES20.glEnableVertexAttribArray(attr_texture_position);
    GLES20.glVertexAttribPointer(attr_texture_position, 2, GLES20.GL_FLOAT, false, 2 * 4, texture_buffer);

    // set matrix
    float[] result = new float[16];
    float ratio = (float) texture_height / texture_width;
    float screen_scale = (float) texture_height / PageRenderer.getScreenHeight();

    Matrix.setIdentityM(model_matrix, 0);
    Matrix.translateM(model_matrix, 0, -1, 0, 0);
    Matrix.scaleM(model_matrix, 0, screen_scale, screen_scale * ratio, screen_scale);

    Matrix.setIdentityM(result, 0);
    Matrix.multiplyMM(result, 0, matrix, 0, model_matrix, 0);
    GLES20.glUniformMatrix4fv(attr_matrix, 1, false, result, 0);

    // assign texture
    GLES20.glActiveTexture(GLES20.GL_TEXTURE0);
    GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, index);
    GLES20.glUniform1i(attr_texture, 0);

    // perform drawing
    GLES20.glDrawArrays(GLES20.GL_TRIANGLE_STRIP, 0, 4);

    // disable vertex array
    GLES20.glDisableVertexAttribArray(attr_position);
    GLES20.glDisableVertexAttribArray(attr_texture_position);

シェーダー:

    int vertex_shader = PageRenderer.loadShader(
            GLES20.GL_VERTEX_SHADER, 
            "uniform mat4 u_Matrix;" + 
            "attribute vec4 a_Position;" +
            "attribute vec2 a_TexturePosition;" +
            "varying vec2 v_TexturePosition;" +
            "void main() {" + 
            "   gl_Position = a_Position * u_Matrix;" +
            "   v_TexturePosition = a_TexturePosition;" +
            "}"
        );
    int fragment_shader = PageRenderer.loadShader(
            GLES20.GL_FRAGMENT_SHADER, 
            "precision mediump float;" +
            "varying vec2 v_TexturePosition;" +
            "uniform sampler2D u_Texture;" +
            "void main() {" +
            "   gl_FragColor = texture2D(u_Texture, v_TexturePosition);" +
            "}"
        );

スケーリングとローテーションは期待どおりに機能しますが、変換が機能しない理由がわかりません。私は最近までOpenGLを使用していなかったことに注意してください。

translateMテキストを「回転」させるのではなく、左に移動することを期待していました。

4

1 に答える 1

11

計算時の変数の順序gl_Positionは重要です!ワールドマトリックスが最初に移動し、次に頂点座標に移動します。質問をするとき、私はこれを知っていましたが、シェーダーコードはAndroid OpenGLチュートリアルから取得されているため、注意を払っていませんでした。人々に注意してください。チュートリアルが正しくありません!

正しいシェーダーコード:

    int vertex_shader = PageRenderer.loadShader(
            GLES20.GL_VERTEX_SHADER, 
            "uniform mat4 u_Matrix;" + 
            "attribute vec4 a_Position;" +
            "attribute vec2 a_TexturePosition;" +
            "varying vec2 v_TexturePosition;" +
            "void main() {" + 
            "   gl_Position = u_Matrix * a_Position;" +
            "   v_TexturePosition = a_TexturePosition;" +
            "}"
        );
    int fragment_shader = PageRenderer.loadShader(
            GLES20.GL_FRAGMENT_SHADER, 
            "precision mediump float;" +
            "varying vec2 v_TexturePosition;" +
            "uniform sampler2D u_Texture;" +
            "void main() {" +
            "   gl_FragColor = texture2D(u_Texture, v_TexturePosition);" +
            "}"
        );
于 2012-10-04T09:18:12.810 に答える