путаница в преобразовании камеры OpenGL и пространства камеры - PullRequest
1 голос
/ 23 февраля 2020

При указании преобразования model-view нам нужны три вектора, которые определяют локальные оси камеры: direction vector (где указывает камера), up vector и right vector камеры, в этих 3 осях direction vector является локальной осью Z камеры.

Автор на сайте learnopengl.com упоминает в блоке направления камеры этого раздела:

Для системы координат матрицы вида мы хотим, чтобы ее ось z равнялась быть положительным, и поскольку по умолчанию (в OpenGL) камера указывает на отрицательную ось z , мы хотим отрицать вектор направления.

Мой вопрос таков:

  1. Мы формулируем матрицу вида и явно применяем преобразование в шейдере (передавая матрицу вида или матрицу lookAt) как униформу, поэтому не камера, созданная нами? Это не значит, что OpenGL предоставляет нам объект камеры по умолчанию, с которым мы можем работать, так как же получается эта камера по умолчанию? Мы могли бы предположить, что оси нашего координатного пространства указывают в любом направлении, верно?

Ответы [ 2 ]

2 голосов
/ 23 февраля 2020

В конце все, что находится в трехмерном нормированном пространстве устройства, проецируется на 2-мерное окно просмотра. Нормализованное пространство устройства - это куб с левым, нижним, ближним (-1, -1, -1) и правым, верхним, дальним (1, 1, 1).
Все преобразования, которые преобразуют координаты вершины однородные координаты пространства клипа (gl_Position) соответственно декартовы нормализованные координаты пространства устройства находятся на вашем усмотрении.
(нормализованные координаты устройства - это пространство клипа деление координат на составляющую w компонента координат клипа. Это называется деление перспективы )

Нормализованное пространство устройства представляет собой левостороннюю систему (см. Влево-вправо системы координат соответственно Правило правой руки ). Обычно мы хотим использовать правую систему. Таким образом, в какой-то момент cooridantes должны быть преобразованы из правшей в левостороннюю систему. В общем, это выполняется проекционной матрицей, которая инвертирует (отражает) ось Z.

В любом случае, совершенно не обязательно, чтобы "по умолчанию (в OpenGL) камера указывала на отрицательную ось z" . Это вопрос спецификации, но обычно используется такая система координат вида.


Подробнее Почему координата z переворачивается после умножения на матрицу в GLSL - OpenGL

2 голосов
/ 23 февраля 2020

Мы формулируем матрицу вида и явно применяем преобразование в шейдере (передавая матрицу вида или матрицу lookAt) как униформу, поэтому разве камера не создана нами?

Да, точно. И так было еще до шейдеров. Есть только преобразования координат, если мы интерпретируем, что «камера» полностью зависит от нас.

Это не значит, что OpenGL предоставляет нам объект камеры по умолчанию для работы с нами, так как эта камера по умолчанию вообще откуда?

Этот учебник здесь довольно неточен. Однако в устаревшем OpenGL существовали некоторые соглашения по умолчанию, но это были только соглашения, и их строго не нужно использовать. Однако некоторые из устаревших функций OpenGL были разработаны с учетом этих соглашений. Общая идея заключалась в том, что пользователь использует правое пространство для глаз, где x указывает вправо, y вверх и z вне экрана в направлении зрителя, и поэтому -z является направлением взгляда. Старая функция gluLookat() следует этим соглашениям.

А также старые функции для создания проекционных матриц придерживаются этого: glFrustum(), glOrtho(), gluPerspecitve() все принимают near и far как положительные расстояния в направлении просмотра, но используют z_eye = -near для ближней плоскости и z_eye = -far для дальней плоскости соответственно. Они также установили нижний ряд равным 0,0,-1,0, поэтому мы в конечном итоге делаем деление на перспективу на -z_eye и получаем левостороннюю систему координат ND C по ней (где z_ndc указывает на экран сейчас) .

Обратите внимание, что матричные функции в glm смоделированы так, чтобы следовать этим соглашениям, но вы также найдете функции с суффиксами с именами LH и RH, так что вы можете выбрать соглашение, которое вам нравится.

Мы могли бы предположить, что оси нашего координатного пространства указывают в любом направлении, верно?

Да. Однако пространство клипа (в котором находится вывод вершинного шейдера gl_Position) определяется GL: растеризатор всегда будет использовать x, полученный из x_cip/w_clip и y, полученный из y_clip/w_clip, с x горизонтальным и y вертикальным размером. Размер z используется только для проверки глубины, и если он указывает на экран, наш выбор в конечном итоге снова является вашим выбором (вы можете переключить направление сравнения проверки глубины, или glDepthRange, или оба). Графический процессор не будет заботиться о том, что вы используете между ними вообще, поэтому для объектного пространства , мирового пространства и _eye_space_ вы можете использовать любые соглашения, которые вам нравятся, или вы можете создавать совершенно разные пространства если это подходит вам лучше, чем традиционная модель.

...