GLSL for-loop数组索引

Bas*_*stl 7 opengl intel glsl

我在使用GLSL中的变量索引时遇到了一些麻烦.下面的GLSL代码在NVidia卡上运行良好.但它不适用于我的Intel HD 4000:

for(int i=0;i<int(uLightCount);++i)
{
    vec3 lightPos = uLightsPos[i];
    ....
}
Run Code Online (Sandbox Code Playgroud)

没有着色器编译器错误.该程序只是崩溃了glUseProgram

我怎样才能解决这个问题?

编辑:

uLightCount并且uLightsPos是制服:

#define MAX_LIGHTS 10
uniform float uLightCount;
uniform vec3 uLightsPos[MAX_LIGHTS];
Run Code Online (Sandbox Code Playgroud)

编辑2:

我找到了一个奇怪的解决方法:

#define i0  0
#define i1  1
#define i2  2
...

for(int i=0;i<int(uLightCount);++i)
{
    vec3 lightPos;

    if (i==i0) 
        lightPos = uLightsPos[i0];
    if (i==i1) 
        lightPos = uLightsPos[i1];
    ....
}
Run Code Online (Sandbox Code Playgroud)

知道为什么这个有用吗?

小智 3

索引必须是常数。这就是您的解决方法有效的原因。

所以不可能这样写

for(int i=0;i<10;++i)
{
  result += uLightsPos[i];
}
Run Code Online (Sandbox Code Playgroud)

  • 不,现代卡支持动态分支和循环。与许多人所说的相反,根据应用程序和线程差异,开销也可能很小。`glUseProgram` 不应该崩溃。这是一个驱动程序错误。 (8认同)
  • 这个答案是不正确的。即使在 GLSL 1.20 中,循环遍历统一数组也是可能的,更不用说 4.x+ 了。OP 显然遇到了驱动程序错误。 (3认同)
  • 啊是的,你是对的,webgl 在那里非常有限。在这种情况下使用[动态索引](http://stackoverflow.com/questions/6247572/variable-array-index-not-possible-in-webgl-shaders)。诸如“for (int i = 0; i &lt; n &amp;&amp; i &lt; MAX_N; ++i)”之类的模式给出了动态绑定并允许编译器展开(嵌套的 if 语句)。尽管如此,不同的驱动程序/glsl 编译器很容易混淆,有时最好手动展开。宏确实有帮助。 (2认同)