浮点均匀舍入是否存在 GLSL 问题



我从Java代码将Unix时间传递给我的着色器: gl.uniform1f(shader, System.currentTimeMillis());

着色器看起来像(简单形式,只是为了调查问题(:

#ifdef GLES
precision highp float;
#endif
uniform float u_time;
void main() {
  int d = 1000;
  float result = floor(u_time / d) * d;
  if (result > u_time) {
    s = 1.0;
  } else {
    s = 0.5;
  }
  gl_FragColor = vec4(s, 0, 0, 1.0);
}

我希望result永远不会大于u_time.令人惊讶的是,它是(着色器产生鲜红色(。

此外,例如,如果将 d 的值替换为 100,它会按预期工作 - 呈现深红色。

尝试将d替换为float值 100.0,但没有任何效果。

即使我用直接浮点常量替换表达式中的u_time,例如 1563854457241.0,它也可以工作 - 这与 Java 放入着色器大致相同。

可能有什么问题?我怀疑它与精度有关,但不了解如何解决它。

附言毕竟,如果将条件表达式替换为

1000000123.0 * 1000 == 1000000123456.0

努夫说。

在着色器代码中,已超出 32 位浮点数的精度限制。
请参阅 IEEE 754 和 GLSL ES - 精度和精度限定符。
当您使用精度限定符 highp 时,有效位的数量为 23(+1 表示符号(,因此像 1000000123456.0 这样的数字不能以全精度表示,因为十进制数字的近似位数是 7.22。

相关内容

最新更新