繁体   English   中英

C ++ OpenGL网格渲染

[英]C++ OpenGL mesh rendering

我知道互联网上有很多这方面的资源,但它们似乎并没有帮助我。

我想要实现的目标:
我正在从数据中烘焙网格,该数据将顶点存储在vector<Vector3>
Vector3sctruct方含float x, y, z
它将三角形存储在map<int, vector<int>>
(地图的关键是子网格, vector<int>是三角形)
vector<Vector2>的紫外线
Vector2是一个包含float x, ystruct
vector<Color>的颜色值
(颜色值适用于像uv那样的顶点)

现在我想编写一个代码,可以读取该数据并以最大的性能将其绘制到屏幕上

我得到了什么:

static void renderMesh(Mesh mesh, float x, float y, float z) {
    if (mesh.triangles.empty()) return;
    if (mesh.vertices.empty()) return;
    if (mesh.uvs.empty()) return;
    glColor3f(1, 1, 1);
    typedef std::map<int, std::vector<int>>::iterator it_type;
    for (it_type iterator = mesh.triangles.begin(); iterator != mesh.triangles.end(); iterator++) {
        int submesh = iterator->first;
        if (submesh < mesh.textures.size()) glBindTexture(GL_TEXTURE_2D, mesh.textures[submesh].id);
        else glBindTexture(GL_TEXTURE_2D, 0);
        glEnable(GL_BLEND);
        glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
        for (int i = 0; i < iterator->second.size(); i += 3) {
            int t0 = iterator->second[i + 0];
            int t1 = iterator->second[i + 1];
            int t2 = iterator->second[i + 2];
            Vector3 v0 = mesh.vertices[t0];
            Vector3 v1 = mesh.vertices[t1];
            Vector3 v2 = mesh.vertices[t2];
            Color c0 = mesh.vertexColors[t0];
            Color c1 = mesh.vertexColors[t1];
            Color c2 = mesh.vertexColors[t2];
            Vector2 u0 = mesh.uvs[t0];
            Vector2 u1 = mesh.uvs[t1];
            Vector2 u2 = mesh.uvs[t2];
            glBegin(GL_TRIANGLES);
            glColor4f(c0.r / 255.0f, c0.g / 255.0f, c0.b / 255.0f, c0.a / 255.0f); glTexCoord2d(u0.x, u0.y); glVertex3f(v0.x + x, v0.y + y, v0.z + z);
            glColor4f(c1.r / 255.0f, c1.g / 255.0f, c1.b / 255.0f, c1.a / 255.0f); glTexCoord2d(u1.x, u1.y); glVertex3f(v1.x + x, v1.y + y, v1.z + z);
            glColor4f(c2.r / 255.0f, c2.g / 255.0f, c2.b / 255.0f, c2.a / 255.0f); glTexCoord2d(u2.x, u2.y); glVertex3f(v2.x + x, v2.y + y, v2.z + z);
            glEnd();
            glColor3f(1, 1, 1);
        }
    }
}

问题:
我发现我渲染的方式不是最好的方法,你可以使用glDrawArrays获得更高的性能(我认为它被称为)。
你能帮我改写我的代码以适应glDrawArrays,因为我到目前为止在互联网上找到的东西并没有太多帮助我。

谢谢,如果还有更多信息需要请问。

不推荐使用glBeginglEnd等函数。 glDrawArrays这样的函数具有更好的性能,但使用起来稍微复杂一些。

glBegin渲染技术的问题是,每次想要绘制某些东西时,你必须逐个传递每个顶点。 今天,图形卡能够非常快速地渲染数千个顶点,但是如果你逐一渲染它,无论你的显卡性能如何,渲染都会变得迟钝。

glDrawArrays的主要优点是你必须初始化一次数组,然后用一次调用绘制它。 首先,您需要在程序的开头填充每个属性的数组。 在你的情况下:位置,颜色和纹理坐标。 它必须是float数组,如下所示:

std::vector<float> vertices;
std::vector<float> colors;
std::vector<float> textureCoords;

for (int i = 0; i < iterator->second.size(); i += 3) {
    int t0 = iterator->second[i + 0];
    int t1 = iterator->second[i + 1];
    int t2 = iterator->second[i + 2];
    vertices.push_back(mesh.vertices[t0].x);
    vertices.push_back(mesh.vertices[t0].y);
    vertices.push_back(mesh.vertices[t0].z);
    vertices.push_back(mesh.vertices[t1].x);
    vertices.push_back(mesh.vertices[t1].y);
    vertices.push_back(mesh.vertices[t1].z);
    vertices.push_back(mesh.vertices[t2].x);
    vertices.push_back(mesh.vertices[t2].y);
    vertices.push_back(mesh.vertices[t2].z);

    // [...] Same for colors and texture coords.
}

然后,在另一个仅用于显示的函数集中,您可以使用这些数组来绘制它:

// Enable everything you need
glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_COLOR_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);

// Set your used arrays
glVertexPointer(3, GL_FLOAT, 0, vertices.data());
glColorPointer(4, GL_FLOAT, 0, colors.data());
glTexCoordPointer(2, GL_FLOAT, 0, textureCoords.data());

// Draw your mesh
glDrawArrays(GL_TRIANGLES, 0, size); // 'size' is the number of your vertices.

// Reset initial state
glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_COLOR_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);

当然,您必须启用要使用的其他属性,例如纹理或混合。


注意:

如果您想了解性能,还有其他函数使用索引来减少使用的数据大小,如glDrawElements

还有其他更先进的OpenGL技术,通过将数据直接保存在图形卡内存(如Vertex Buffer Objects)上,可以提高性能。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM