我正在为 Android 相机编写一个着色器,并且我有一个值数组,我想用它们来创建叠加层。实际上,它是一个 2D 数组,但我将其设置为 1D 并进行数学运算以找到正确的索引。当我使用计算出的索引时,着色器看起来像是崩溃了,所以我要么根本没有任何输出,要么输出“损坏”。在 android 上 opengl 调试能力非常有限,而且我不是 OpenGL 专家。
#version 320 es
#extension GL_OES_EGL_image_external_essl3 : require
precision highp float;
uniform samplerExternalOES sTexture;
in vec2 vTextureCoord;
out vec4 fragColor;
layout(std430, binding=2) readonly buffer Overlay {
int cols;
int rows;
float data[];
} overlay;
void main() {
int x = int(gl_FragCoord.x);
int y = int(gl_FragCoord.y);
int index = y * overlay.cols + x;
if (index > overlay.data.length()) {
// use overlay.data to set the color
float value = overlay.data[index];
fragColor = vec4(...); // TODO: Use the value here
} else {
fragColor = texture(sTexture, vTextureCoord);
}
}
private fun addOverlay(cols: Int, rows: Int, data: FloatArray) {
val buffer = createByteBuffer(data.size * Float.SIZE_BYTES + 2 * Int.SIZE_BYTES)
buffer.putInt(cols)
buffer.putInt(rows)
data.values.forEach(buffer::putFloat)
buffer.position(0)
val bo = intArrayOf(0)
GLES32.glGenBuffers(1, bo, 0)
GLES32.glBindBuffer(GLES32.GL_SHADER_STORAGE_BUFFER, bo[0])
GLES32.glBufferData(
GLES32.GL_SHADER_STORAGE_BUFFER,
data.values.size * Float.SIZE_BYTES + 2 * Int.SIZE_BYTES,
buffer,
GLES32.GL_STATIC_READ
)
GLES32.glBindBufferBase(GLES32.GL_SHADER_STORAGE_BUFFER, 2, bo[0])
}
我注意到的一件奇怪的事情是,如果我直接比较
cols * rows == overlay.data.length()
,我会得到false
,但我100%确定它应该是真的。当我使用额外的变量时,它会正常工作:
int size = cols * rows;
int length = overlay.data.length();
if (size == length) { // true
}
if (cols * rows == overlay.data.length()) { // false
}
我做错了什么?显然,我在 SSBO 中设置的值是正确的,但是当我尝试将它们一起使用时,会发生一些奇怪的事情。
(如果您分享您认为有用的调试技术,我将不胜感激)
很确定您想反转它,如果检查...
if (index > overlay.data.length()) {
// use overlay.data to set the color
float value = overlay.data[index];