我试图创建一个类来绘制一个正方形,这个类将被实例化一次,每次我想绘制一个正方形我只会... Square :: draw(float posx,float posy,float sizex,float sizey)。 我这样做的方法是在着色器上有一个unifor vec4,我将传输pos和大小。 并且在vbo上:GLint _vertID [4] = {0,1,2,3}一个识别,这样我就知道着色器正在处理哪个顶点所以我可以放置正确的位置
问题在于它不绘制正方形而是随机绘制一些三角形。(有些错误)。 我想知道我的逻辑是错误的,还是执行错误。
以下是代码:
void Square::initVertex(){
GLint _vertID[4] = {0,1,2,3};
GLfloat _uvs[8] = {0,0,1,0,1,1,0,1};
glGenVertexArrays(1, vao);
glBindVertexArray(vao[0]);
glGenBuffers(2, vbo);
glBindBuffer( GL_ARRAY_BUFFER, vbo[0]);
glBufferData( GL_ARRAY_BUFFER, 4 * sizeof(GLint), _vertID, GL_STATIC_DRAW);
glVertexAttribPointer(0, 1, GL_INT, false, 0, 0);
glEnableVertexAttribArray(0);
glBindBuffer( GL_ARRAY_BUFFER, vbo[1]);
glBufferData( GL_ARRAY_BUFFER, 8 * sizeof(GLfloat), _uvs, GL_STATIC_DRAW);
glVertexAttribPointer(1, 2, GL_FLOAT, false, 0, 0);
glEnableVertexAttribArray(1);
}
和VertexShader: posSh是vec4,我每次想要绘制一个正方形时都会传递位置,而vertID是让我知道正在处理哪个顶点的vbo
#version 150
in int vertID;
in vec2 uvs;
in vec4 posSh;
out vec2 ex_uvs;
void main(void){
vec2 pos;
if(vertID == 0){
pos = vec2(posSh.x, posSh.y);
}else if(vertID == 1){
pos = vec2(posSh.x + posSh.z, posSh.y);
}else if(vertID == 2){
pos = vec2(posSh.x + posSh.z, posSh.y + posSh.w);
}else if(vertID == 3){
pos = vec2(posSh.x, posSh.y + posSh.w);
}
gl_Position = vec4(pos.x, pos.y, 1,1);
ex_uvs = uvs;
}
答案 0 :(得分:0)
我希望删除这些_vertID
索引。
对我来说,看起来你试图通过使用单个vec4渲染4个顶点而不是4x vec2(或vec3,如果需要)来节省内存。 vertID
,uvs
和posSh
都是属性,这意味着它们必须具有相同的元素数。例如:
position: 1[x, y, z], 2[x, y, z], 3[x, y, z]
uvCoords: 1[x, y] , 2[x, y] , 3[x, y]
如果我是对的,posSh
就不是这样了。
这就是我在你设置和安装中看到的内容。着色器代码:
vertID: 1[n] , 2[n] , 3[n] , 4[n]
uvs: 1[x, y] , 2[x, y] , 3[x, y] , 4[x, y]
posSh: 1[x, y, z, w] , ??? , ??? , ???
所以,如果是这种情况,我们现在就解决这个问题。
vbo[0]
从GL_ARRAY_BUFFER
更改为GL_ELEMENT_ARRAY_BUFFER
。元素数组缓冲区包含您绑定的数组缓冲区的每个元素的索引(查看上面的代码部分,数字是您可以指定的索引)。 (请记住,vbo[0]
将保持绑定,直到另一个GL_ELEMENT_ARRAY_BUFFER被绑定为止)vbo[]
数组中创建第3个vbo,其中包含四元组的所有位置。这将取代posSh
。您必须像_uvs
的数组缓冲区一样进行设置(这将是一个vec2位置)这就是你怎么做的。 试试这段代码(我还没有测试过):
void Square::initVertex(){
GLint _vertID[4] = {0,1,2,3};
GLfloat _uvs[8] = {0,0,1,0,1,1,0,1};
GLfloat _pos[8] = {0.5f, 0.5f, -0.5f, 0.5f, -0.5f, -0.5f, 0.5f, -0.5f };
glGenVertexArrays(1, vao);
glBindVertexArray(vao[0]);
glGenBuffers(3, vbo); // the first index is an Element Array Buffer!
glBindBuffer( GL_ELEMENT_ARRAY_BUFFER, vbo[0]);
glBufferData( GL_ELEMENT_ARRAY_BUFFER, 4 * sizeof(GLint), _vertID, GL_STATIC_DRAW);
glBindBuffer( GL_ARRAY_BUFFER, vbo[1]);
glBufferData( GL_ARRAY_BUFFER, 8 * sizeof(GLfloat), _pos, GL_STATIC_DRAW);
glVertexAttribPointer(0, 2, GL_FLOAT, false, 0, 0);
glEnableVertexAttribArray(0);
glBindBuffer( GL_ARRAY_BUFFER, vbo[2]);
glBufferData( GL_ARRAY_BUFFER, 8 * sizeof(GLfloat), _pos, GL_STATIC_DRAW);
glVertexAttribPointer(1, 2, GL_FLOAT, false, 0, 0);
glEnableVertexAttribArray(1);
}
着色器代码:
#version 150
in vec2 uvs;
in vec2 pos;
out vec2 ex_uvs;
void main(void){
gl_Position = vec4(pos.x, pos.y, 1,1);
ex_uvs = uvs;
}
您的绘图代码:
glDrawElements(
GL_QUADS, // mode
4, // count
GL_UNSIGNED_INT, // type
(void*)0 // element array buffer offset
);
我希望它对你有所帮助。尝试代码,我不知道是否有任何拼写错误,我用记事本++编写。
这是一个关于如何正确渲染VBO的进展教程:Tutorial 9 : VBO Indexing