Описание проблемы мне было не совсем понятно. Я думаю, что, вероятно, лучше всего вывести формулу, которую вы нашли. Надеюсь, это должно позволить вам понять (и визуализировать), почему вы можете получить именно тот результат, который у вас есть.
Для двух кватернионов, Q1 и Q2, относительный поворот кватерниона от Q1 до Q2 равен:
Quaternion = relativeRotation = Q1^(-1) * Q2
Где Q1^(-1)
обозначает инверсию Q1. Вы можете думать об этом как о применении противоположного вращения Q1 к Q2. Результатом будет относительное вращение между ними. Инверсию кватерниона можно вычислить следующим образом:
Q^(-1) = (Q*) / ||Q||^2
Где Q*
обозначает конъюгат Q
. Я предполагаю, что вы уже знаете, как найти сопряжение кватерниона. Теперь, если Q
является единичным кватернионом, то и норма, и квадрат нормы Q
равны 1,0. Следовательно, мы имеем:
Q^(-1) = Q*
Это упрощает нашу формулу:
Quaternion relativeRotation = (Q1*) * Q2
Обратите внимание, что только единичные кватернионы представляют повороты. Однако, поскольку произведение Гамильтона двух единичных кватернионов само по себе является единичным кватернионом, нам не нужно нормализовать результат.
Теперь из этого относительного кватерниона можно определить угол (в радианах):
float angle = 2.0f * acos(relativeRotation.w)
Здесь w
— скалярная составляющая кватерниона, а acos
— тригонометрическая функция арккосинуса. Этот угол равен оси:
Vector3 axis = (relativeRotation.x, relativeRotation.y, relativeRotation.z)
Теперь, найдя и угол, и ось, вы сможете визуализировать вращение.
Наконец, в качестве примечания, произведение Гамильтона (*) не коммутативно. Это означает, что (Q1*) * Q2
не обязательно равно Q2 * (Q1*)
. Следуя тому же выводу, что и выше, относительное единичное вращение кватерниона от Q2 до Q1 можно рассчитать по формуле:
relativeRotation = (Q2*) * Q1
person
Homar
schedule
31.05.2014