Точки проекта на ближней плоскости с использованием пространства НДЦ - PullRequest
0 голосов
/ 06 июня 2018

У меня есть несколько пар точек в мировом пространстве, каждая пара имеет разную глубину.Я хочу спроецировать эти точки на ближнюю плоскость поля зрения, а затем пересчитать их новую мировую позицию.

примечание: я хочу сохранить эффект перспективы

Для этого я преобразую местоположение точки в пространстве NDC.Я думаю, что каждая пара точек в пространстве NDC с одинаковым значением z лежит на одной плоскости, параллельной направлению обзора.Так что, если я установлю их значение z равным -1, они должны лежать на ближней плоскости.

Теперь, когда у меня есть тысячи новых локаций NDC, мне нужна их мировая позиция, я потерял компонент w, изменив глубину.нужно пересчитать его.

Я нашел эту ссылку: unproject ndc

, который сказал, что:

wclip * inverse(mvp) * vec4(ndc.xyz, 1.0f) = 1.0f
wclip = 1.0f / (inverse(mvp) * vec4(ndc.xyz, 1.0f))

мой полный код:

glm::vec4 homogeneousClipSpaceLeft  = mvp * leftAnchor;
glm::vec4 homogeneousClipSpaceRight = mvp * rightAnchor;

glm::vec3 ndc_left  = homogeneousClipSpaceLeft.xyz() / homogeneousClipSpaceLeft.w;
glm::vec3 ndc_right = homogeneousClipSpaceRight.xyz() / homogeneousClipSpaceRight.w;

ndc_left.z  = -1.0f;
ndc_right.z = -1.0f;

float clipWLeft  = (1.0f / (inverseMVP * glm::vec4(ndc_left, 1.0f)).w);
float clipWRight = (1.0f / (inverseMVP * glm::vec4(ndc_right, 1.0f)).w);

glm::vec3 worldPositionLeft  = clipWLeft * inverseMVP * (glm::vec4(ndc_left, 1.0f));
glm::vec3 worldPositionRight = clipWRight * inverseMVP * (glm::vec4(ndc_right, 1.0f));

Это должно работать на практике, но я получаю странный результат, я начинаю с 2-х точек в мировом пространстве:

left world position:  -116.463 15.6386 -167.327
right world position: 271.014 15.6386 -167.327
left NDC position: -0.59719 0.0790622 -1
right NDC position: 0.722784 0.0790622 -1
final left position:  31.4092 -9.22973 1251.16
final right position: 31.6823 -9.22981 1251.17
mvp
4.83644 0 0 0
0 4.51071 0 0
0 0 -1.0002 -1
-284.584 41.706 1250.66 1252.41

Я что-то не так делаю?

Вы бы порекомендовали этот способ проецировать пару точек на ближнюю плоскость с перспективой?

1 Ответ

0 голосов
/ 07 июня 2018

Если glm::vec3 ndc_left и glm::vec3 ndc_right являются нормализованными координатами устройства, то следующие проекции проецируют координаты на ближнюю плоскость в нормированном пространстве устройства:

ndc_left.z  = -1.0f;
ndc_right.z = -1.0f;

Если вы хотите получить положение моделиточка в нормализованном пространстве устройства в декартовых координатах , затем необходимо преобразовать точку с помощью матрицы проекции вида модели Инверса и разделить компоненты x, y и z на wсоставляющая результата.Не преобразование inverseMVP дает Однородную координату :

glm::vec4 wlh = inverseMVP * glm::vec4(ndc_left, 1.0f);
glm::vec4 wrh = inverseMVP * glm::vec4(ndc_right, 1.0f);

glm::vec3 worldPositionLeft  = glm::vec3( wlh.x, wlh.y, wlh.z ) / wlh.w;
glm::vec3 worldPositionRight = glm::vec3( wrh.x, wrh.y, wrh.z ) / wrh.w;

Обратите внимание, что библиотека OpenGL Matmatics (GLM) предоставляет операции для "unproject".См glm::unProject.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...