我有一个着色器,理想情况下需要28位尾数,但可以使用较少的位数来降低性能。 如何确定OpenGL ES中“highp”精度是多少?它可能是FP24,具有16位尾数,但我无法确定或询问OpenGL。 有什么想法吗?
从OpenGL ES Shading Language 参考文献:
highp
- 16位,浮点数范围:-262到262,整数范围:-216到216mediump
- 10位,浮点数范围:-214到214,整数范围:-210到210lowp
- 8位,浮点数范围:-2到2,整数范围:-28到28在OpenGL ES 3中,这些保证已经升级,请参见GLSL ES 3.00规范:
highp
- 24位,浮点数范围:-2126到2127,有符号整数范围:-231到231-1,无符号整数范围:0到232-1mediump
- 10位,浮点数范围:-214到214,有符号整数范围:-215 到 215-1,无符号整数范围0到216-1lowp
- 8/9位(有符号/无符号),
浮点数范围:-2到2,
有符号整数范围:-28到28-1,无符号整数范围0到29-1
在我对自己一系列昂贵的玩具进行测试时:
因此,我不会详尽列出所有组合。
另外,请注意int的精度始终定义为0。
lowp
可以精确地表示达到 2
或 -2
的值,不过我不知道如何进行测试,也不应该过于关注这些限制,遇到问题时只需使用 mediump
)以下是查询数值的示例。
int range[2], precision;
glGetShaderPrecisionFormat(GL_FRAGMENT_SHADER, GL_HIGH_FLOAT, range, &precision);
NSLog(@"Fragment shader high precision float range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_FRAGMENT_SHADER, GL_MEDIUM_FLOAT, range, &precision);
NSLog(@"Fragment shader medium precision float range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_FRAGMENT_SHADER, GL_LOW_FLOAT, range, &precision);
NSLog(@"Fragment shader low precision float range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_FRAGMENT_SHADER, GL_HIGH_INT, range, &precision);
NSLog(@"Fragment shader high precision int range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_FRAGMENT_SHADER, GL_MEDIUM_INT, range, &precision);
NSLog(@"Fragment shader medium precision int range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_FRAGMENT_SHADER, GL_LOW_INT, range, &precision);
NSLog(@"Fragment shader low precision int range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_VERTEX_SHADER, GL_HIGH_FLOAT, range, &precision);
NSLog(@"Vertex shader high precision float range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_VERTEX_SHADER, GL_MEDIUM_FLOAT, range, &precision);
NSLog(@"Vertex shader medium precision float range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_VERTEX_SHADER, GL_LOW_FLOAT, range, &precision);
NSLog(@"Vertex shader low precision float range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_VERTEX_SHADER, GL_HIGH_INT, range, &precision);
NSLog(@"Vertex shader high precision int range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_VERTEX_SHADER, GL_MEDIUM_INT, range, &precision);
NSLog(@"Vertex shader medium precision int range: %d %d precision: %d", range[0], range[1], precision);
glGetShaderPrecisionFormat(GL_VERTEX_SHADER, GL_LOW_INT, range, &precision);
NSLog(@"Vertex shader low precision int range: %d %d precision: %d", range[0], range[1], precision);
我还不确定,在选择低精度类型时是否可以期望获得实质性的性能提升(即使在现在已经有三年历史的某些手机上也是如此)。
很明显,趋势是朝着与桌面硬件的融合方向发展,因为可以看到最近的GPU已完全淘汰了8位类型,并将mediump
用于lowp
。
int range[2], precision;
glGetShaderPrecisionFormat(GL_FRAGMENT_SHADER, GL_HIGH_FLOAT, range, &precision);
这将给出高精度浮点数的范围和精度。
glGetShaderPrecisionFormat
?glGetShaderPrecisionType
似乎是一个打字错误。 - gonzojiveglGetShaderPrecisionFormat
确实有效,也许您应该编辑您的回复以修复拼写错误,这样我就可以将其标记为正确。只是为了让下一个人更容易理解。感谢您的答案! - gonzojive
lowp
、mediump
或highp
所需的位数,只规定了最小值范围和精度。 因此,对于lowp
浮点值,我们保证其范围为 [-2.0, 2.0],精度为 2.0^-8,但这并不表示系统用多少位来表示它。请注意,本次翻译尽量简明扼要地表达原文含义。 - Andon M. Colemanhighp
的规范为+/- 2^16个整数,那么这是否意味着它具有16位的尾数,并且总位数超过了这个值? - Aaron Franke