0

我使用 LWJGL 用 Ja​​va 编写了一个小型粒子系统。
因此,我使用的是 openGL。
现在我读到,改变纹理非常慢。所以我确保我只更改用于一堆粒子的纹理,然后绘制所有这些粒子。
尽管同时绘制了 60 个粒子,但我的 FPS 仍然从大约 8000 下降到 4000。
我知道问题在于渲染,因为当我只更新粒子但不绘制它们时,我的 FPS 没有下降。
如果有人能告诉我我的 OpenGL 代码有什么问题,那就太好了。

这是管理粒子的粒子发射器:

public void render() {
//Initialize....
GL11.glMatrixMode(GL11.GL_MODELVIEW);
BloodParticle.PARTICLE_TEXTURE.bind();

for(Integer index : this.getBlockedParticles()){
    this.getParticles()[index].render();
}

GL11.glDisable(GL11.GL_TEXTURE_2D);
}

这是单个粒子的渲染方法:

public void render() {
if(!this.isAlive()){
    return;
}

// Store matrix
GL11.glPushMatrix();

// Set to particle's position and scale
GL11.glTranslatef(this.getPosition().getX(), this.getPosition().getY(), 0);
GL11.glScalef(3.5f, 3.5f, 1.0f);

// Set the current alpha.
GL11.glColor4f(1.0f, 1.0f, 1.0f, this.getAlphaFade());

//Draw the texture on a quad.
GL11.glBegin(GL11.GL_QUADS);
{
    GL11.glTexCoord2f(0, 0);
    GL11.glVertex2f(-PARTICLE_TEXTURE.getImageWidth()/2.0f,
            -PARTICLE_TEXTURE.getImageHeight()/2.0f);

    GL11.glTexCoord2f(0, 1);
    GL11.glVertex2f(-PARTICLE_TEXTURE.getImageWidth()/2.0f,
            PARTICLE_TEXTURE.getImageHeight()/2.0f);

    GL11.glTexCoord2f(1, 1);
    GL11.glVertex2f(PARTICLE_TEXTURE.getImageWidth()/2.0f,
            PARTICLE_TEXTURE.getImageHeight()/2.0f);

    GL11.glTexCoord2f(1, 0);
    GL11.glVertex2f(PARTICLE_TEXTURE.getImageWidth()/2.0f, 
            -PARTICLE_TEXTURE.getImageHeight()/2.0f);

}
GL11.glEnd();

//Get the matrix again.
GL11.glPopMatrix();
}

我知道 4000 FPS 绰绰有余。但我只是害怕这种下降到一半的 FPS 并且目前游戏中只有一个发射器。
我知道这将成为固定 FPS 为 60 且发射器超过 3 个的问题。

4

1 回答 1

4

状态更改与您的性能问题无关。

这有:

//Draw the texture on a quad.
GL11.glBegin(GL11.GL_QUADS);
{
    GL11.glTexCoord2f(0, 0);
    GL11.glVertex2f(-PARTICLE_TEXTURE.getImageWidth()/2.0f,
            -PARTICLE_TEXTURE.getImageHeight()/2.0f);

    GL11.glTexCoord2f(0, 1);
    GL11.glVertex2f(-PARTICLE_TEXTURE.getImageWidth()/2.0f,
            PARTICLE_TEXTURE.getImageHeight()/2.0f);

    GL11.glTexCoord2f(1, 1);
    GL11.glVertex2f(PARTICLE_TEXTURE.getImageWidth()/2.0f,
            PARTICLE_TEXTURE.getImageHeight()/2.0f);

    GL11.glTexCoord2f(1, 0);
    GL11.glVertex2f(PARTICLE_TEXTURE.getImageWidth()/2.0f, 
            -PARTICLE_TEXTURE.getImageHeight()/2.0f);

}
GL11.glEnd();

想一想:每个粒子都会导致 8 次调用 OpenGL。对于几千个粒子,这是一个巨大的开销。更糟糕的是,您甚至没有将多个四边形批处理到一个glBegin /*glEnd* 块中。

以下是提高性能的方法:不要使用glBegin/glVertex/glEnd aka the immediate mode

使用顶点数组!

于 2013-06-17T12:00:46.087 回答