OpenGL / Libgdx:方形网格渲染优化

时间:2017-10-05 12:44:33

标签: optimization opengl-es libgdx opengl-es-2.0

我的游戏背景渲染占所有渲染持续时间的1/4我一直在努力改进它,但我仍然认为它很常见需要这么长时间才能知道它是多么简单它是:

背景是一个正方形网格(如棋盘),每个正方形都有自己的颜色,每个帧都会改变,正方形y位置也会改变每一帧,但不是x位置

这是我的主要渲染功能

public void main.render() {
    Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);

    final float deltaS = Gdx.graphics.getDeltaTime();

    background.update(deltaS);
    updateTheGame(deltaS);

    background.render();

    spriteBatch.setProjectionMatrix(uiCamera.combined);
    spriteBatch.begin();
    renderTheGame(spriteBatch);
    spriteBatch.end();

}

这是背景网格声明

mesh = new Mesh(true, nbVertices, nbIndices,
                new VertexAttribute(VertexAttributes.Usage.Position, 2, ShaderProgram.POSITION_ATTRIBUTE),
                new VertexAttribute(VertexAttributes.Usage.ColorUnpacked, 3, GL20.GL_FLOAT, false, ShaderProgram.COLOR_ATTRIBUTE));

这是后台更新功能(在每次调用render()之前调用)  (这不是我想要优化的那个)

void background.update(float deltaS) {
    for (BGSquareRow row : squareRows)
        row.update(deltaS);
    setupVerticesArray();
    mesh.updateVertices(0, verticesArray);
}


private final Color tmpColor = new Color();

private void setupVerticesArray() {
    int index = 0;
    for (BGSquareRow row : squareRows) {
        final float y0 = row.y;
        final float y1 = row.y + squareSize;
        for (int i=0; i<nbSquareX; i++) {
            row.getSquareColor(i, tmpColor);
            final float x0 = squareXs[i];
            final float x1 = squareXs[i+1];
            verticesArray[index++] = x0;
            verticesArray[index++] = y0;
            verticesArray[index++] = tmpColor.r;
            verticesArray[index++] = tmpColor.g;
            verticesArray[index++] = tmpColor.b;
            verticesArray[index++] = x1;
            verticesArray[index++] = y0;
            verticesArray[index++] = tmpColor.r;
            verticesArray[index++] = tmpColor.g;
            verticesArray[index++] = tmpColor.b;
            verticesArray[index++] = x1;
            verticesArray[index++] = y1;
            verticesArray[index++] = tmpColor.r;
            verticesArray[index++] = tmpColor.g;
            verticesArray[index++] = tmpColor.b;
            verticesArray[index++] = x0;
            verticesArray[index++] = y1;
            verticesArray[index++] = tmpColor.r;
            verticesArray[index++] = tmpColor.g;
            verticesArray[index++] = tmpColor.b;
        }
    }
}

这是背景渲染函数,在background.update()之后的每一帧都调用(这是太省钱了)

 void background.render() {
      shaderProgram.begin();
      shaderProgram.setUniformMatrix("u_projTrans", parent.uiCamera.combined);
      mesh.render(shaderProgram, GL20.GL_TRIANGLES);
      shaderProgram.end();
 }

我试图只提出理解我的问题的最低要求,所以如果我忘了重要的事情,请告诉我

我有一些优化的想法,但我不知道该怎么做:

  • 是否可以在主spriteBatch上绘制背景网格?如果我是对的,这将导致在main.render()函数中进行1次绘制调用

  • 是否可以仅更新网格顶点缓冲区中的y,红色,蓝色和绿色值?我找到了更新顶点缓冲区的一部分的方法,但前提是它是一个连续的部分

  • verticesArray设置是否有任何可能的优化?

(我也尝试将ColorPacked用于顶点缓冲区,但它不是更好)

1 个答案:

答案 0 :(得分:1)

您可以使用meshParts创建网格,其中每个meshPart代表单个网格方块。然后,您可以使用GLSL着色器为每个具有不同颜色的正方形着色。这应该可以最大限度地减少CPU工作时间并利用GPU功能。

Here's an example of colorizing shader with libGDX. MeshPart render方法支持将ShaderProgram作为参数传递,并且可以包含特定材料。