了解现代 OpenGL 中的代码绘制 .obj 并设置不同的位置

Posted

技术标签:

【中文标题】了解现代 OpenGL 中的代码绘制 .obj 并设置不同的位置【英文标题】:Understanding code drawing .obj in modern OpenGL and setting different positions 【发布时间】:2019-10-02 11:35:53 【问题描述】:

我正在观看现代 OpenGL 教程,但我并不完全理解绘制 .obj 文件的代码。我的意思是它工作得很好,但我在改变显示对象的位置时遇到了一点问题。

顶点数组是由 glGenVertexArrays() 生成的,我认为有一行我应该更改,但不知道如何更改。

有我使用的代码:

Mesh::Mesh(const std::string& fileName)

    InitMesh(OBJModel(fileName).ToIndexedModel());


void Mesh::InitMesh(const IndexedModel& model)

    m_numIndices = model.indices.size();

    glGenVertexArrays(1, &m_vertexArrayObject);
    glBindVertexArray(m_vertexArrayObject);

    glGenBuffers(NUM_BUFFERS, m_vertexArrayBuffers);

    glBindBuffer(GL_ARRAY_BUFFER, m_vertexArrayBuffers[POSITION_VB]);
    glBufferData(GL_ARRAY_BUFFER, sizeof(model.positions[0]) * model.positions.size(), &model.positions[0], GL_STATIC_DRAW);
    glEnableVertexAttribArray(0);
    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, 0);

    glBindBuffer(GL_ARRAY_BUFFER, m_vertexArrayBuffers[TEXCOORD_VB]);
    glBufferData(GL_ARRAY_BUFFER, sizeof(model.texCoords[0]) * model.texCoords.size(), &model.texCoords[0], GL_STATIC_DRAW);
    glEnableVertexAttribArray(1);
    glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 0, 0);

    glBindBuffer(GL_ARRAY_BUFFER, m_vertexArrayBuffers[NORMAL_VB]);
    glBufferData(GL_ARRAY_BUFFER, sizeof(model.normals[0]) * model.normals.size(), &model.normals[0], GL_STATIC_DRAW);
    glEnableVertexAttribArray(2);
    glVertexAttribPointer(2, 3, GL_FLOAT, GL_FALSE, 0, 0);

    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_vertexArrayBuffers[INDEX_VB]);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(model.indices[0]) * model.indices.size(), &model.indices[0], GL_STATIC_DRAW);

    glBindVertexArray(0);

我的对象从 (0,0,0) 位置绘制,我希望它在 Y 轴上平移 (-1.0f)。我知道如何翻译矩阵,但不知道如何使用 .obj 进行管理。

编辑: 谢谢你的回答

我的 vs 代码如下:

#version 330

uniform mat4 P;
uniform mat4 V;
uniform mat4 M;


layout (location=0) in vec4 vertex;
layout (location=2) in vec2 texCoord; 

out vec2 i_tc;

void main(void) 
    gl_Position=P*V*M*vertex;
    i_tc=texCoord;

【问题讨论】:

更改透视是您在实际渲染调用中所做的事情,而不是在网格中。顶点着色器代码应包含从in 顶点属性获取输入并将其分配给gl_Position 的代码。在那里应用您的转换,最好通过体现翻译的mat4 制服。如果这一切对您来说都是中文,请发布您的着色器代码(和绘图代码),以便我们提供具体建议。 该设置非常标准:您拥有三个统一矩阵,一个用于投影、视图和模型。请参阅open.gl 以讨论每个矩阵的作用以及它们如何协同工作,但要点是您应该将M 矩阵的旋转部分设置为单位矩阵,并将其转换部分设置为(0,-1,0)跨度> 现在可以了,你们太棒了,非常感谢! Wavefront 已被解析,您的功能只是将此数据绑定到着色器 GPU 程序。检查将 M、V 和 P 矩阵作为统一传输的代码。您需要翻译视图矩阵。附言最好将预乘 MVP 矩阵传输到共享矩阵以提高渲染性能。 【参考方案1】:

如果您的问题是“我如何在空间中移动 obj”,则可以使用平移矩阵和着色器(模型视图投影)矩阵中的 MVP 矩阵来完成(在现代 opengl 中)。 仅您的代码,只是在要绘制的 gpu 上设置顶点,但根本不绘制。

选择缓冲区后,您将需要一个 glDrawElements 操作。 此外,您将需要设置着色器和矩阵,否则 obj 将始终在原点 (0.,0.) 上呈现。

如果您有 glDraw,则需要显示您正在使用的着色器。

【讨论】:

以上是关于了解现代 OpenGL 中的代码绘制 .obj 并设置不同的位置的主要内容,如果未能解决你的问题,请参考以下文章

OpenGL学习脚印: 绘制一个三角形

OpenGL - 绘制存储在 VBO 中的大量信息

如何在现代opengl中绘制圆柱体

如何在 OpenGL 中绘制 3D 矢量?

基于Qt的OpenGL可编程管线学习- obj模型绘制

我的OpenGL学习进阶之旅解决OpenGL绘制带透明通道的png纹理时出现黑边问题,并彻底了解其原理