【问题标题】:GLSL shader uniform locations can't be found找不到 GLSL 着色器统一位置
【发布时间】:2017-11-03 15:03:59
【问题描述】:

我正在开发一个顶点蒙皮着色器,由于某种原因我的程序找不到统一的位置。

顶点着色器代码:

#version 330

const int MAX_JOINTS = 30;
const int MAX_WEIGHTS = 3;

in vec3 position;
in vec2 textureCoords;
in vec3 normal;
in ivec3 boneIndices;
in vec3 weights;

out vec4 fragPos;
out vec3 n;
out vec2 texCoords;
out vec4 mcolor;


uniform mat4 modelMatrix;
uniform mat4 projectionMatrix;
uniform mat4 viewMatrix;
uniform mat4 normalMatrix;

uniform mat4[MAX_JOINTS] boneTransforms;


void main() {



vec4 totalLocalPos = vec4(0.0);
vec4 totalNormal = vec4(0.0);

for(int i = 0; i < 3; i++){
    mat4 boneTransform = boneTransforms[boneIndices[i]];
    vec4 posePosition = boneTransform * vec4(position, 1);
    totalLocalPos += posePosition * weights[i];

    vec4 worldNormal = boneTransform * vec4(normal, 1);
    totalNormal += worldNormal * weights[i];
}
texCoords = textureCoords;

fragPos = modelMatrix * vec4(position,1);

n = totalNormal.xyz;


gl_Position = projectionMatrix * viewMatrix * modelMatrix * totalLocalPos;
}

boneTransforms 制服似乎没有正确设置;如果我用

查询现役制服
GLint uniforms;
    glGetProgramiv(shaderProgramID, GL_ACTIVE_UNIFORMS, &uniforms);
    for (int i = 0; i < uniforms; i++){
        int name_len = -1, num = -1;
        GLenum type = GL_ZERO;
        char name[100];
        glGetActiveUniform(shaderProgramID, GLuint(i), sizeof(name) - 1,
            &name_len, &num, &type, name);
        name[name_len] = 0;

    }

我总是得到零;但是,如果我只是输入 gl_Position = projectionMatrix * viewMatrix * modelMatrix * vec4(position,1) 我会得到预期的结果(没有任何顶点蒙皮的正确渲染),所以尽管它告诉我他们没有其他变换似乎正在工作存在? 编辑:有时是这种情况,有时我在位置 (0,0,0) 处获取模型,但在其他情况下正确渲染。

我已阅读有关编译器剥离未使用/非活动制服的信息,但如果我使用 boneTransforms 计算 totalLocalPos 并将其用于 gl_Positions,则制服应该是活动的。

我尝试用

设置制服
vector<glm::mat4> boneTransforms = model.getBoneTransforms();
int location = glGetUniformLocation(shaderProgramID, "boneTransforms");
glUniformMatrix4fv(location, boneTransforms.size(), false, (GLfloat*)&boneTransforms);

位置始终为 -1。 我尝试设置此特定制服的方式是否有问题,或者是着色器代码中的错误?

EDIT2:我刚刚注意到,当我从场景中添加或删除对象(使用不同的着色器)时,我的着色器的行为发生了变化。我不知道该怎么做。
EDIT3:如果我从场景中删除所有其他网格,着色器会因访问冲突而崩溃。只要正在渲染另一个对象,当前就没有崩溃。
另一个编辑:显然访问 weights 变量会使我的着色器崩溃。

【问题讨论】:

  • 您应该检查glGetProgramivglGetActiveUniform 不会引发任何错误。
  • 我怀疑正如上面的海报所说,你的程序编译失败,这就是为什么你得到 0 个找到的制服。
  • 我检查了 glGetError() 并没有收到任何错误代码。如果程序无法编译,那是否意味着我根本不会输出?
  • glGetError 不会报告着色器编译失败
  • 再一次,如果着色器没有编译它根本不会渲染网格,对吧?它确实被渲染了,只是不正确。编辑:显然我确实遇到了着色器错误,但为什么在这种情况下我什么都看不到?

标签: c++ opengl glsl


【解决方案1】:

我正在阅读此关于顶点蒙皮着色器的快速教程:khronos,它似乎使用的是稍旧版本的 GLSL,但他们确实提到了 MVP 矩阵的乘法(模型视图 proj 矩阵)或在您的情况下,PVM矩阵(proj视图模型矩阵)与vec4在您的情况下总位置并将其存储回gl_Position,他们声称w可能并不总是具有1的值所以为了安全起见,他们建议改为这样做,我将使用您的代码作为他们的示例来解决这个可能的问题。

改变这个:

gl_Position = projectionMatrix * viewMatrix * modelMatrix * totalLocalPos;

到这里:

gl_Position = projectionMatrix * viewMatrix * modelMatrix * vec4(totalLocalPos.xyz, 1.0);

看看这是否对你有帮助。我不知道这是否是您的问题的原因,但从您所显示的情况来看,除此之外,您的着色器似乎还可以。

【讨论】:

  • 感谢您的建议,我会更改的。目前我的问题是制服没有被加载,所以 totalLocalPos 无论如何都没有正确计算..
  • @dragon 我明白这一点,但从我所见,我也不确定为什么。您的制服似乎“拼写正确”。然而,这里的这一行可能是一个问题:glUniformMatrix4fv(location, boneTransforms.size(), false, (GLfloat*)&amp;boneTransforms);...glUniformMatrix4fv 期望浮点数组的位置、大小、布尔值和起始位置。在我的通用着色器源代码中,我有:glUniformMatrix4fv( it-&gt;second.uLocation, 1, false, &amp;m4Matrix[0][0] ); 其中m4Matrixglm::mat4 对象,而不是它们的向量...
  • @dragon ...(续)我不确定您如何将vectorglm::mat4 对象传递给此函数。然后你又将它转换回(GLFloat*)。您可能必须索引到该向量的第一个元素。 (GLFloat*)&amp;boneTransforms[0]) ?不过不确定。
  • 我也不确定是否要传递一个数组,但只要位置为 -1,这行在任何一种情况下都不会执行任何操作。
【解决方案2】:

我看到你将 mat4 推入着色器的方式有点不对劲。当我执行“glUniformMatrix4fv”时,我说第一个参数是着色器的 ID,即从“glCreateProgram()”获得的 ID。第二个是着色器中变量的名称,因此在您的情况下为“boneTransforms”。第三个是“1”。第四个我把“GL_FALSE”而不是“false”,但我认为这不会有什么不同。接下来是 mat4 的第一个浮点数,看起来更像这样:
&amp;boneTransforms[0][0]

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2022-01-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多