У меня есть некоторые модели, которые я хочу вращать, используя кватернионы обычным способом, за исключением того, что вместо поворота вокруг источника я хочу, чтобы он был слегка смещен. Я знаю, что в трехмерном пространстве вы не говорите, что вращаетесь вокруг точки; Вы говорите, что вращаетесь вокруг оси. Так что я визуализирую это как вращение вокруг вектора, хвост которого расположен не у локального источника.
Все аффинные преобразования в моем механизме рендеринга / физики хранятся с использованием SQT (масштаб, кватернион, перевод; идея заимствована из книги « Архитектура игрового движка» ). Поэтому я строю матрицу каждого кадра из этих компонентов и передаю ее вершинному шейдеру. В этой системе применяется перевод, затем масштабирование, затем вращение.
В одном конкретном случае мне нужно перевести объект в мировое пространство, масштабировать его и повернуть вокруг вершины, не центрированной в локальном начале объекта.
Вопрос: Учитывая ограничения моей нынешней системы, описанные выше, как я могу добиться локального вращения с центром в точке, отличной от начала координат? Автоматическое upvote для тех, кто может описать, как это сделать, используя только матрицы :)
источник
Ответы:
Короче говоря
Вам нужно всего лишь изменить T в своей форме SQT.
Замените вектор перевода
v
наv' = v-invscale(p-invrotate(p))
гдеv
начальный вектор перевода,p
это точка, вокруг которой вы хотите, чтобы вращение происходило,invrotate
иinvscale
инверсии вашего вращения и масштаба.Быстрая демонстрация
Позвольте
p
быть точкой, вокруг которой вы применяете вращениеr
. Позвольтеs
быть ваши параметры масштабирования иv
ваш вектор перевода. Окончательное преобразование матрицыT(p)R(r)T(-p)S(s)T(v)
вместоR(r)S(s)T(v)
.То, что вы хотите, это новые параметры преобразования
v'
,r'
иs'
так, чтобы окончательное преобразование матрицы было,R(r')S(s')T(v')
и мы имеем:Поведение на бесконечности указывает, что параметры вращения и параметры масштабирования не могут изменяться (это можно продемонстрировать). У нас при этом есть
r = r'
иs = s'
. Поэтому единственный отсутствующий параметр -v'
ваш новый вектор перевода:Если эти матрицы равны, их обратные значения равны:
Это особенно верно для происхождения
O
:Масштабирование и вращение начала координат дает начало координат, таким образом получая:
v'
это новый вектор перевода, который вы ищете, который позволяет сохранить ваше преобразование в форме SQT. Возможно, возможно упростить вычисления; но по крайней мере необходимое хранилище не увеличивается.источник
Все канонические формулы вращения, используемые для получения ваших матриц вращения, предназначены для вращения вокруг начала координат. Если вы хотите вместо этого применить это вращение вокруг определенной точки, вы должны сначала сместить начало координат или, что то же самое, переместить объект так, чтобы точка, вокруг которой вы хотите повернуть, находилась в начале координат.
Сначала рассмотрим 2D-случай, потому что он проще, а метод масштабируется. Если бы у вас был куб шириной 2 с центром в начале координат, и вы хотели повернуть его на 45 градусов вокруг своего центра, это было бы тривиальным применением матрицы вращения 2D .
Но если вместо этого вы хотите повернуть его вокруг его верхнего правого угла (расположенного в
1,1
), вам сначала нужно перевести его так, чтобы этот угол был в начале координат. Это может быть достигнуто с переводом-1,-1
. Затем вы можете вращать объект, как и раньше, но вы должны следить за этим, переводя его обратно (мимо1,1
). Итак, в общем, для достижения матрицы поворотаR
для поворотаr
около точкиP
вы делаете:где
translate
иrotate
- канонические матрицы перевода / вращения соответственно. Как это случается, это тривиально масштабируется до 3D, за исключением того, что необходимо также включить ось для вращения - вы всегда можете выбрать канонические матрицы вращения X, Y или Z, но это будет скучно. Вы хотите использовать произвольную матрицу вращения оси-угла . Ваш финалR
в 3D, таким образом:где
a
- единичный вектор, представляющий ось вращения, иP
теперь это трехмерная точка в пространстве модели, представляющая точку вращения.Когда это происходит, кватернионы могут быть преобразованы в матричные представления и из них , так что вы можете выполнить конкатенацию таким образом, если захотите. Или вы можете просто оставить все в виде матриц (кватернионы имеют некоторые приятные преимущества, такие как простота интерполяции в разумной манере, но нужно ли вам это или нет).
Также:
Строго говоря, хотя векторы можно использовать для представления позиций, рассматривая их как смещения от начала координат, сами векторы не имеют самих позиций, поэтому немного необычно визуализировать их как таковые.
источник