使用 OpenGL 绘制对象并让我的片段着色器输出一个标量整数 ID。为了绘制对象,我使用多重采样进行抗锯齿,所以当我为整数 ID 创建缓冲区时,我必须将其创建为 MSAA 缓冲区以及完整的 FBO:
glBindRenderbuffer(GL_RENDERBUFFER, rboColorId);
glRenderbufferStorageMultisample(GL_RENDERBUFFER, msaaSamples, GL_RGBA8,
cam.getWidth(), cam.getHeight());
glBindRenderbuffer(GL_RENDERBUFFER, rboDepthId);
glRenderbufferStorageMultisample(GL_RENDERBUFFER, msaaSamples, GL_DEPTH_COMPONENT,
cam.getWidth(), cam.getHeight());
glBindRenderbuffer(GL_RENDERBUFFER, rboObjId);
glRenderbufferStorageMultisample(GL_RENDERBUFFER, msaaSamples, GL_R32UI,
cam.getWidth(), cam.getHeight());
glBindRenderbuffer(GL_RENDERBUFFER, rboColorNoMsaaId);
glRenderbufferStorage(GL_RENDERBUFFER, GL_RGBA8,
cam.getWidth(), cam.getHeight());
glBindRenderbuffer(GL_RENDERBUFFER, rboObjNoMsaaId);
glRenderbufferStorage(GL_RENDERBUFFER, GL_R32UI,
cam.getWidth(), cam.getHeight());
glBindRenderbuffer(GL_RENDERBUFFER, 0);
glBindFramebuffer(GL_FRAMEBUFFER, fboId);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, rboColorId);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rboDepthId);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT1, GL_RENDERBUFFER, rboObjId);
glBindFramebuffer(GL_FRAMEBUFFER, fboNoMsaaId);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, rboColorNoMsaaId);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT1, GL_RENDERBUFFER, rboObjNoMsaaId);
正如您在上面的代码中看到的,我有 2 个 FBO。第一个是 MSAA,它有一个用于绘制场景的缓冲区、一个深度缓冲区和一个用于 ID 的整数缓冲区。第二个 FBO 是单采样(非 MSAA),只有绘图场景缓冲区和整数缓冲区。在我绘制完所有内容(片段着色器为每个像素设置索引)之后,我首先将整数 ID 缓冲区(GL_COLOR_ATTACHMENT1)读取到单个采样的 FBO,以便从中获取 glReadPixels。在这个特定的代码中,我只是读取鼠标指向的 1 个像素:
glBindFramebuffer(GL_READ_FRAMEBUFFER, fboId);
glReadBuffer(GL_COLOR_ATTACHMENT1);
glBindFramebuffer(GL_DRAW_FRAMEBUFFER, fboNoMsaaId);
glDrawBuffer(GL_COLOR_ATTACHMENT1);
glBlitFramebuffer(mouse_x_pos, cam.getHeight() - mouse_y_pos, mouse_x_pos+1, cam.getHeight() - mouse_y_pos + 1,
0, 0, 1, 1,
GL_COLOR_BUFFER_BIT, GL_NEAREST);
glBindFramebuffer(GL_READ_FRAMEBUFFER, fboNoMsaaId);
glReadBuffer(GL_COLOR_ATTACHMENT1);
GLuint objectId;
glReadPixels(0, 0, 1, 1, GL_RED_INTEGER, GL_UNSIGNED_INT, &objectId);
我的问题是,当我进行 blit 时,我想要的像素的多样本被插入到我要读取的单个像素中。我想要它用于我用来绘制场景的颜色缓冲区,但我不希望它用于我读取的整数 ID。如果我正在读取一个包含 ID 为 50 和 ID 为 100 的片段的像素,我想读取 50 或 100(不在乎哪个)。但我得到的是 50 到 100 之间的某个值,比如 75。75 实际上可能是一个完全不同的像素,所以我根本不想要那个。
我可以做些什么来读取整数 ID 的单个样本而不是多个样本的插值?