Войти
ПрограммированиеФорумГрафика

Z-Buffer reprojection

#0
17:17, 5 сен. 2018

Помогите найти статью. Это точно кем-то используется, но я не могу найти гайда по ключевым словам.

Суть: я рендерю фреймы с задержкой в один кадр. При рендере кадра я уже знаю view и perspective матрицу следущего.
Идея: после рендера текущего кадра, брать полученный z-buffer, репроецировать его с новыми view и perspective матриц, делать occlusion culling на AABB и на след. кадре доставать результаты.

Репроекцию точно делают как минимум в VR, но статьи по этому сабжу не гуглятся от слова никак


#1
18:11, 5 сен. 2018

https://developer.oculus.com/blog/introducing-stereo-shading-repr… on-for-unity/

#2
22:34, 5 сен. 2018

а в чем проблема? я не очень понимаю
с какой именно частью затык?

#3
2:44, 6 сен. 2018

Ну грубо говоря, для того, чтобы сделать такую репроекцию правильно, нужно каждый пиксель depthbuffer'а воспринимать как отдельный вексель и делать над ним математику в вертексном шейдере.(потому что glFragCoord мы модифицировать не можем)

Я надеялся, что есть некая техника или что-то такое, чего я не вижу. Может быть нужно репроекцию делать в computation шейдере?

#4
7:34, 6 сен. 2018

Deamon
> вексель
Кого?
> некая техника
Эта техника называется возьми экранные координаты x,y засемпли по ним z и умножь на инвертированную старую матрицу projView, а потом умножь на новую projView.

#5
10:47, 6 сен. 2018

Deamon
> Суть: я рендерю фреймы с задержкой в один кадр. При рендере кадра я уже знаю view и perspective матрицу следущего.
лол, если ты её уже знаешь, с ней тогда и рендерь. репроекция используется там, где тебе матрица известна с текущего кадра(поступили данные с устройства, например), а сцена обновиться ещё не успела. тогда имеет смысл делать репроекцию, чтобы взять рендер с предыдущего кадра и приблизительно пересчитать, как он будет выглядеть с текущего положения камеры.

Deamon
> Идея: после рендера текущего кадра, брать полученный z-buffer, репроецировать
> его с новыми view и perspective матриц, делать occlusion culling на AABB и на
> след. кадре доставать результаты.
смысл предельно простой:

  vec2 screenCoord = gl_FragCoord.xy / viewportSize;
  vec3 worldPos = Unrpoject(vec3(screenCoord, texture2D(prevDepth, screenCoord).r), prevViewProjMatrix); //мировая позиция фрагмента на предыдущем кадре считается равной мировой позиции на текущем
  gl_Position = Project(worldPos, viewProjMatrix); //из мировых координат просто считаем новые экранные
#6
12:01, 6 сен. 2018

Suslik
Ну вот с этими формулами проблемка. gl_FragCoord существует только в Fragment shader, а gl_Position существует только в Vertex Shader  ¯\_(ツ)_/¯. Штука не сильно очевидная, пока не начинаешь о ней думать. 

А так, да, спасибо. Мне нужно подумать, может быть действительно не стоит морочится и делать проход z-fill уже с новой матрицей вида. А если дополнительный FrameBuffer, не связанный с основным может, работать в параллель - то вообще прекрасно

#7
12:56, 6 сен. 2018

Ну так в чём проблема-то? Создай новую varying vec2, запихай в ея gl_Position и передавай фрагментному. Авось шина не треснет.

#8
15:10, 6 сен. 2018

Cheb
И в Vertex Shader'е делать чтение из текстуры, и в VBO передавать screen_width*screen_height значений, просто чтобы заставить vertex_shader работать.

Можеть быть я могу использовать vertexId в шейдере без VBO...  https://stackoverflow.com/questions/8039929/opengl-drawarrays-wit… t-binding-vbo Мда, таки могу, но только с glDrawArraysInstanced и в VBO все равно должна быть хотя бы 1 вершина.

Ну уже что-то. Вырисовывается glDrawArraysInstanced с GL_POINTS.

#9
1:08, 10 сен. 2018

Suslik, а можешь по моему вопросу подсказать? Складывается ощущение, что я чего-то не понимаю
А то я так и забросил сейчас.

https://gamedev.ru/code/forum/?id=237887

ПрограммированиеФорумГрафика

Тема в архиве.