简体   繁体   English

在OpenGL中使用imageStore写入图像

[英]Writing to an image using imageStore in OpenGL

Currently I am trying to write to an image using imageStore in OpenGL. 目前,我正在尝试使用OpenGL中的imageStore写入图像。 However, using renderdock as my debugger, I find only a black texture after running my program. 但是,使用renderdock作为调试器,运行程序后,我只会发现黑色纹理。

I create and bind the image to write to as follows: 我创建并绑定图像以写入如下:

glGenTextures(1, &textureID);
glBindTexture(target, textureID);
glObjectLabel(GL_TEXTURE, textureID, -1, "\"3D Texture\"");
glTexStorage3D(target, 1, GL_RGBA8, width, height, depth);

glTexParameteri(target, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(target, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameteri(target, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
glTexParameteri(target, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(target, GL_TEXTURE_MAG_FILTER, GL_NEAREST);

Then I load the texture to a program by doing: 然后,通过执行以下操作将纹理加载到程序中:

glBindImageTexture(0, textureID, 0, GL_TRUE, 0, GL_READ_WRITE, GL_RGBA8);
GLuint location = glGetUniformLocation(programID, uniform);
glUniform1i(location,0);

And finally I render by calling glDrawArrays(). 最后,我通过调用glDrawArrays()进行渲染。

My fragment shader looks like: 我的片段着色器看起来像:

#version 440

out vec3 f_pos;
out vec3 f_norm;
out vec2 f_uv;

layout(RGBA8) uniform image3D volumeMap;

void main()
{
    imageStore(volumeMap, ivec3(0,0,0),
        vec4(0,1,1,0));
}

So my expectation is to find a cyan pixel on the upper left corner of the first layer. 因此,我的期望是在第一层的左上角找到一个青色像素。 However that pixel is black. 但是那个像素是黑色的。

I have successfully loaded and read from samplers using the texture() call. 我已经使用texture()调用成功加载并读取了采样器。

I am not sure if I am missing steps or if the way I am doing stuff is wrong. 我不确定是否缺少步骤,或者我做事的方式是否错误。

EDIT: 编辑:

I modified my code to not rely on RenderDoc to check for the color. 我修改了代码,以不依赖RenderDoc检查颜色。

So I render things as follows 所以我渲染如下

Final Fragment Shader: 最终片段着色器:

#version 440

out vec4 fragment_color;

layout(binding=3, RGBA8) uniform image3D vMap;

void main()
{
    fragment_color = imageLoad(vMap, ivec3(0,0,0));
}

C++ C ++

glUseProgram(Program1);
/*load texture as above*/
draw();
glMemoryBarrier(GL_SHADER_IMAGE_ACCESS_BARRIER_BIT);

glUseProgram(Program2);
/*load texture as above*/
draw();

draw simply sets up the geometry buffers and then calls glDrawArrays(). 绘制仅设置几何缓冲区,然后调用glDrawArrays()。

The result is a black mesh where I expect a cyan mesh 结果是一个黑色网格,我期望有一个青色网格

Image load/store operations operate under the rules of incoherent memory access . 映像加载/存储操作在不连贯的内存访问规则下进行。 This means that writes to them are not visible to later reads unless you explicitly do something to make them visible. 这意味着对它们的写入对于以后的读取是不可见的,除非您明确地做一些使它们可见的操作。 Usually, this is a call to glMemoryBarrier . 通常,这是对glMemoryBarrier的调用。

Always remember that glMemoryBarrier specifies how you intend to access the written value, not how you wrote to it. 始终记住, glMemoryBarrier指定您打算如何访问写入的值,而不是您如何写入它。 In this case, the mechanism is the same either way: GL_SHADER_IMAGE_ACCESS_BARRIER_BIT . 在这种情况下,任何一种机制都是相同的: GL_SHADER_IMAGE_ACCESS_BARRIER_BIT This command must be placed after the command that writes the data, and before the one that reads it. 该命令必须放置在写入数据的命令之后和读取数据的命令之前。

Also, I cannot say whether this shader has undefined behavior or not. 另外,我不能说这个着色器是否具有未定义的行为。 You have multiple invocations that are all writing to the same memory location. 您有多个调用都写到相同的内存位置。 But in your case, they are writing the same value. 但是在您的情况下,他们正在书写相同的价值。 It is not clear from the description in the specification whether this is genuine UB or whether it is fine. 从说明书中的描述还不清楚这是真正的UB还是好的。 It would certainly be UB if the invocations were writing different data, but I don't know if some exception exists for them writing the same data. 如果调用正在写不同的数据,那肯定是UB,但是我不知道他们写相同的数据是否存在某种例外。

I would be very hesitant about doing this, however. 但是,我会非常犹豫。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM