Существует ли стандартный способ поворота вокруг локальных координат (то есть из матрицы вида модели) в OpenGL 4.0?

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

Я знаю, что в прямом режиме вы бы

glTranslatef(x, y, z);   //move back to origin
glRotatef(angle, x_rot, y_rot, z_rot);   //turn using a quaternion
glTranslatef(-x, -y, -z);   //move back to original location

но я не уверен, как это переведет на более современное приложение. Сделаете ли вы по сути то же самое, создадите матрицу перевода обратно в исходное положение, поверните и переведите обратно? Для каждого объекта, который вы хотите вращать? Из того, что я тестировал до сих пор, этот метод работает для просмотра, но управлять им в трехмерном пространстве неудобно (я не уверен, как постоянно регулировать вращение. Преобразуйте компоненты движения в один vec4, умножьте на вращение, применить к переводу, а затем сделать фактическое вращение?)

Кажется, что есть более эффективный способ, чем три или более умножения матрицы 4х4, которые я пропускаю.

Вот конкретный раздел после опробования предложенного решения.

0

Решение

Вы можете сделать в основном то же самое, что и последовательность, которую вы разместили, не делая полных матричных умножений во время выполнения. Поскольку матрицы перевода очень просты, вы можете умножать вручную. С R будучи матрицей вращения 3х3, и p будучи позицией, которую вы хотите вращать, вы можете построить матрицу 4×4:

  1. хранить R в поворотной части матрицы 4х4.
  2. подсчитывать p - R * pи сохраните результат в части перевода матрицы 4×4.

Это уменьшит его до умножения одной матрицы * на вектор и вычитания вектора. Вы можете перепроверить мою математику, так как я только что вывел ее на бумаге.

Другой подход заключается в том, что вы храните повороты и переводы отдельно в коде вашего ЦП, обновляете их по мере необходимости и объединяете их только в матрицу 4х4 при обновлении униформы.

Поскольку у вас есть контроль над кодом шейдера, вам даже не нужно использовать матрицу 4×4, чтобы содержать все преобразования. Например, если вам удобнее применять переводы перед поворотами, вы можете подать матрицу вращения mat3 и вектор перевода vec3 в свой шейдер и добавить вектор перевода в позицию перед умножением на матрицу вращения. Хранение двух отдельных также может быть полезным, если вы обновляете один из них гораздо чаще, чем другой.

2

Другие решения

Я думаю, что вы слишком усложняете это, думая о старом трубопроводе.

Сформируйте вашу новую матрицу преобразования, T. Предположим, у вас есть существующая матрица камеры, C. Вы хотите C ‘, модифицированную матрицу камеры.

Там действительно только два варианта. Или:

C' = CT, or
C' = TC

Потому что какая другая информация у вас есть?

На практике то, что вы выбираете, — это новое преобразование, действующее «до» существующей матрицы камеры, в этом случае оно будет действовать в мировых координатах, или «после», и в этом случае оно будет иметь место в координатах камеры.

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

Старые подпрограммы OpenGL всегда публикуются умноженными.

0

По вопросам рекламы [email protected]