gpt4 book ai didi

opengl - 传递给片段着色器的纹理坐标均为 0

转载 作者:行者123 更新时间:2023-12-02 01:23:39 25 4
gpt4 key购买 nike

我已经为我正在开发的一个小型 openGL 2.0 应用程序编写了自己的顶点和片段着色器。一切似乎都工作得很好,除了一件事,每个顶点的纹理坐标似乎是 (0, 0)。

当我不使用自己的着色器时,即当我使用openGL的默认着色器时,那么一切都会绘制 精细

当我激活自己的着色器时,形状仍然没问题,顶点位置是正确的。但纹理坐标全部变成(0, 0)。

这是顶点着色器的代码:

in vec2 position;
in vec2 texcoord;

out vec2 coord;

void main(void) {
gl_Position = gl_ModelViewProjectionMatrix * vec4(position, 0, 1);
coord = vec2(gl_TextureMatrix[0] * vec4(texcoord, 1, 1));
}

这是片段着色器:

uniform sampler2D texture;

uniform float redFactor;
uniform float greenFactor;
uniform float blueFactor;

in vec2 coord;
void main(void) {
vec4 color = texture2D(texture, coord);
float grey = (color.r * redFactor + color.g * greenFactor + color.b * blueFactor);
gl_FragColor = vec4(grey, grey, grey, color.a);
}

再说一遍,没有我自己的着色器它也能正常工作。因此 VBO 设置正确。

顺便说一句,纹理坐标已正确地从顶点着色器传递到片段着色器。例如,当我更改行时

coord = vec2(gl_TextureMatrix[0] * vec4(texcoord, 1, 1));  

在顶点着色器中:

coord = vec2(0.5, 0.5);  

我得到了正确的结果。

这是我的 VBO 内容的样子:
[0.0, 0.0,
0.0, 0.0,
0.0、1.0、
0.0、1.0、
1.0、1.0、
1.0、1.0、
1.0, 0.0,
1.0, 0.0]

这是绘图的 IBO:

[0, 1, 2, 2, 3, 0]

这里是指针:

VERTEX_ARRAY_POINTER(size = 2, stride = 16, offset = 0),   
TEXCOORD_ARRAY_POINTER(size = 2, stride = 16, offset = 8)

编辑:顺便问一下,这个编辑器中的换行符有什么问题吗?

最佳答案

听起来您需要为纹理坐标启用客户端状态,因此请务必调用 glEnableVertexAttribArray​ 来获取位置和纹理坐标

了解更多详情:http://www.opengl.org/wiki/Vertex_Specification#Vertex_Array_Object

但是,如果您正在使用顶点数组,并且从您的问题来看,您似乎是这样。

就个人而言,我在调用 glDraw*() 之前启用我正在使用的所有数组,然后在绘制调用后禁用除位置数组之外的所有数组。

为了知道用于 glEnableVertexAttribArray 的索引,您可以使用 0 作为您的位置,使用 1 作为您的纹理坐标。

更可靠的答案是,在编译并链接程序后,使用 glUseProgram() 使其保持最新状态,然后

GLuint positionIndex = 0;
GLuint texcoordIndex = 1;
glUseProgram(programId);
glBindAttribLocation(programId, positionIndex, "position");
glBindAttribLocation(programId, texcoordIndex, "texcoord");

然后在你的glDraw*()

之前

glEnableVertexAttribArray(positionIndex);
glEnableVertexAttribArray(texcoordIndex);

这仍然是一种相当硬编码的处理方式,如果您想要更通用的方法,请发表评论。

因为这里要求的是一种了解着色器正在使用多少个顶点属性的通用方法

glUseProgram(programId);

int attribCount;
glGetProgramiv(programId, GL_ACTIVE_ATTRIBUTES, &attribCount);

GLuint attribLoc[] = new GLuint[attribCount];

for (int attrib=0; attrib<attribCount; ++attrib) {
char szName[32];
int size;
GLenum vecType;
glGetActiveAttrib(programId, attrib, sizeof(szName), 0, &size, &vecType, szName);

attribLoc[attrib] = glGetAttribLocation(programId, szName);
glBindAttribLocation(programId, attribLoc[attrib], szName);
}

然后你去画画的时候

for (int attrib=0; attrib<attribCount; ++attrib) {
glEnableVertexAttribArray(attribLoc[attrib]);
}

glDraw*();

for (int attrib=0; attrib<attribCount; ++attrib) {
glDisableVertexAttribArray(attribLoc[attrib]);
}

关于opengl - 传递给片段着色器的纹理坐标均为 0,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18082630/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com