Создание буфера позиции для отложенного рендеринга - шум в сгенерированных текстурах - PullRequest
0 голосов
/ 25 декабря 2018

Я пытаюсь реализовать отложенное затенение в первый раз, но у меня возникают проблемы при создании буферов.Я начал пытаться создать только буфер позиции, поэтому вот соответствующий код:

glGenFramebuffers(1, &gBuffer);
glBindFramebuffer(GL_FRAMEBUFFER, gBuffer);

glGenTextures(1, &gPosition);
glBindTexture(GL_TEXTURE_2D, gPosition);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB16F, 1024, 1024, 0, GL_RGB, GL_FLOAT,
    NULL);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, gPosition, 0);
unsigned int rbo;
glGenRenderbuffers(1, &rbo);
glBindRenderbuffer(GL_RENDERBUFFER, rbo);
glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH24_STENCIL8, 1024, 1024);
glBindRenderbuffer(GL_RENDERBUFFER, 0);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rbo);
if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)
    std::cout << "ERROR::FRAMEBUFFER:: Framebuffer is not complete!" << std::endl;


glBindFramebuffer(GL_FRAMEBUFFER, 0);

Кадр-буфер успешно завершен, и мы переходим к основному циклу:

glBindFramebuffer(GL_FRAMEBUFFER, gBuffer);
glActiveTexture(gPosition);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glViewport(0, 0, 1024, 1024);
mat4 modelMatrix = mat4(1);
glUseProgram(gShader);
glUniformMatrix4fv(mgLoc, 1, GL_FALSE, &modelMatrix[0][0]);
glUniformMatrix4fv(pgLoc, 1, GL_FALSE, &projectionMatrix[0][0]);
glUniformMatrix4fv(vgLoc, 1, GL_FALSE, &viewMatrix[0][0]);
glBindVertexArray(objVAO);
glDrawArrays(GL_TRIANGLES, 0, objVertices.size());
glBindFramebuffer(GL_FRAMEBUFFER, 0);

Иэто фрагментный шейдер:

layout (location=0) out vec3 gPosition;
in vec3 vertex_world;
out vec4 FragColor;

void main()
    {

     FragColor=vec4(vertex_world,1.0);


    }

Буфер позиции выглядит нормально:

enter image description here

Однако, если вы посмотрите на мой шейдерЯ не дал значение для gPosition.Похоже, что буфер просто принимает вывод fragColor.

Это то, что я планирую сделать, но это дает мне неправильные результаты:

layout (location=0) out vec3 gPosition;
in vec3 vertex_world;


void main()
{

     gPosition=vertex_world;


}` 

Это что-то передает в буфер позиции, но вы увидите, что это довольно странно: enter image description here

Что может быть не так?

Редактировать / Решено

Оказывается, мне пришлось определить gPosition как vec4 вфрагмент шейдера.Теперь это прекрасно работает.Итак, новый вопрос: почему это работает сейчас?

1 Ответ

0 голосов
/ 25 декабря 2018

glActiveTexture не принимает имя текстуры, но выбирает активную текстуру единицу (GL_TEXTURE0 + n) - да, название вводит в заблуждение.

В любом случае, похоже, что выхочу связать текстуру буфера позиции перед рендерингом.Зачем?Если вы действительно сделали это, у вас может получиться петля обратной связи - см. https://www.khronos.org/opengl/wiki/Framebuffer_Object#Feedback_Loops. У вас все в порядке, если вы не берете из нее сэмпл, но простая возможность иметь петлю обратной связи может привести вас кмедленный путь кодирования.Поэтому постарайтесь не делать этого.Вы связали текстуру как вложение к FBO, этого достаточно.

Что касается рендеринга буфера фактической позиции: зачем это вообще нужно?Просто используйте текстуру буфера глубины (вместо рендеринга буфера) и восстановите положение из единственного значения глубины и непроекции.

...