2014-11-01 3 views
2

Я пытаюсь восстановить МИРОВОЕ положение точки, зная, что это глубина в пространстве EYE, вычисляются следующим образом (в вершинном шейдере):GLSL вычислить мир координаты из глубины глаз и положения экрана

float depth = - uModelView * vec4(inPos , 1.0) ; 

где INPOS является точкой в ​​мировом пространстве (Очевидно, я не хочу восстанавливать эту конкретную точку, но точка, в которой глубина выражается в этом формате).

И это нормализуется положение экрана (от 0 до 1), вычисляется следующим образом (в пиксельный шейдер):

vec2 screen_pos = (vec2(gl_FragCoord.xy) - vec2(0.5))/uScreenSize.xy ; 

я могу получить доступ к следующей информации:

  • uScreenSize: в это имя предложить, это ширина экрана и высота
  • uCameraPos: положение камеры в мировом пространстве

и стандартные матрицы:

  • uModelView: камера вид матричной модели
  • uModelViewProj: модель вид проекции матрицы
  • uProjMatrix: проекционный матричные

Как можно вычислить положение (X, Y, Z,) точки в МИРОВОМ пространстве? (не в пространстве EYE)

У меня нет доступа к другим (я не могу использовать ближний, дальний, левый, правый, ...), поскольку матрица проекции не ограничена перспективой или ортогональной.

Заранее спасибо.

ответ

3

я получаю свой вопрос правильно, у вас есть x и y как пространство окна (и уже преобразован в нормализованное пространстве [-1,1] устройство), но z в глазе пространстве, и хотите recosntruct позиции мирового пространства.

Я не могу получить доступ к другой (я не могу использовать вблизи, вдали, слева, справа, ...) потому, что проекция матрицы не ограничивается перспективой или ортогональной.

Ну, на самом деле, нет ничего, кроме ортогонального или проективного отображения, которое может быть достигнуто путем матричного умножения в однородном пространстве. Однако проекционная матрица достаточна, если она обратима (теоретически матрица проекции может преобразовывать все точки в плоскость, линию или одну точку. В этом случае некоторая информация теряется и она никогда не сможет восстановить исходные данные, но это было бы очень нетипичным случаем).

Так что вы можете получить от матрицы проекции и вашего 2D-положения на самом деле луч в пространстве глаза. И вы можете пересечь это с помощью плоскости z=depth, чтобы вернуть точку.

Так что вы должны сделать, это вычислить две точки

vec4 p = inverse(uProjMatrix) * vec4 (ndc_x, ndc_y, -1, 1); 
vec4 q = inverse(uProjMatrix) * vec4 (ndc_x, ndc_y, 1, 1); 

, который ознаменует две точки на луче в глаз пространстве. Не забудьте разделить p и q на соответствующий компонент w, чтобы получить 3D-координаты. Теперь вам просто нужно пересечь это с помощью вашего самолета z=depth и получить пространство для глаз x и y. Наконец, вы можете использовать инверсию матрицы uModelView для проецирования этой точки обратно в пространство объекта.

Однако вы сказали, что хотите мира. Но это невозможно. Для этого вам понадобится матрица view, но вы не указали это как заданное. Все, что у вас есть, это компиляция матрицы model и view, и вам необходимо знать хотя бы одно из них, чтобы восстановить место в мире. cameraPosition не энугух. Вам также нужна ориентация.

+0

Ну. Мне нравится ваш ответ. Я думаю, что могу передать матрицу вида в шейдер и вычислить пересечение. Я не могу проверить сейчас, но я скажу вам, если это сработает. – rperrot

+0

Это отлично работает. Спасибо ! – rperrot

Смежные вопросы