0

一些背景:这是我的第一个 OpenGL ES 2 程序,所以我没有经验。我一直在研究一个着色器来显示颜色索引的纹理。它从一个纹理中采样一个点,将其乘以 256.0 以将其缩放到 8 位整数范围,从调色板纹理中的偏移量中采样相应的 RGBA 值,并设置 gl_FragColor。

我已经在我的三星 Galaxy S2 上完美运行了一个月,但它从未在我的 Galaxy S1 上运行过,只显示黑色纹理。在无数次尝试将我的头撞在墙上试图通过我代码的所有部分的反复试验来找到问题之后,我最终将其缩小为一段着色器代码,可以有效地简化为以下内容:

precision highp float;

varying vec2 v_texCoord;
uniform sampler2D texture;

void main()
{
    float multiplied = texture2D(texture, v_texCoord).s * 256.0;

    float divided = multiplied / 256.0;

    gl_FragColor = vec4(divided, divided, divided, 1.0);
}

例如,texture是一个 256x256 像素的纹理,每个值都设置为 0xFF。如果我在我的 Galaxy S2 上运行该代码,它工作正常:我得到一个完全白色的屏幕,正好是 0xFFFFFF。如果我在我原来的 Galaxy S1 上运行它,屏幕正好是 0x000000。

现在,我发现如果我降低 256.0 的值然后运行它,我的 Galaxy S1 上的输出开始从全黑增加到各种灰度。例如,8.0 给了我 0x424142,4.0 给了我 0x848284。当我乘/除以 2.0 时,它开始像我的 Galaxy S2 一样输出 0xFFFFFF!

知道什么可能导致这样的问题吗?我会接受你最疯狂的猜测,因为在这一点上我完全被打败了。我看不出有什么可能导致这种情况。

4

1 回答 1

1

Is the answer floating point truncation?

A fragment shader is allowed to use "lowp" float precision, which means 16-bit floating point, which 256 * 256 would overflow (see http://en.wikipedia.org/wiki/Half-precision_floating-point_format). At this point the math falls apart and results are undefined.

However, as far as I can tell (see glblenchmark.com data) the Galaxy S1 should support highp floats in the fragment shader as it has the "OES_fragment_precision_high" extension in the glGetString(GL_EXTENSIONS) output. (Though I may have the wrong model there...)

Maybe there is some other reason you're not getting high precision floats though. What #version are you using in your shader?

于 2013-04-07T07:51:57.117 回答