Quaternion from two vector pairs

匿名 (未验证) 提交于 2019-12-03 09:14:57

问题:

I have two vector pairs (before and after rotation).

before rotation: [x1,y1,z1] [x2,y2,z2]

after rotation: [x1',y1',z1'] [x2',y2',z2']

How to create a quaternion representing this rotation?

回答1:

In most cases there is no rotation which transforms 2 vectors into 2 other vectors. Here is a simple way to visualize why: a rotation does not change the angle between vectors. If the angle between the 2 vectors before the rotation is different from the angle between the 2 vectors after the rotation, then there is no rotation which meets your criteria.

This said there may be an optimal quaternion with an acceptable error which "almost" rotates your 2 vector pairs. There are a number of algorithms which vary in speed and precision to find such a quaternion. I wrote a fast C++ algorithm for an Arduino application where the speed is critical but the precision is less important.

http://robokitchen.tumblr.com/post/67060392720/finding-a-rotation-quaternion-from-two-pairs-of-vectors

Before rotation: u0, v0. After rotation: u2, v2.

Quaternion q2 = Quaternion::fromTwoVectors(u0, u2); Vector v1 = v2.rotate(q2.conjugate()); Vector v0_proj = v0.projectPlane(u0); Vector v1_proj = v1.projectPlane(u0); Quaternion q1 = Quaternion::fromTwoVectors(v0_proj, v1_proj); return (q2 * q1).normalized(); 

If this does not meet the requirements of your own application try to google Wabha's problem.



回答2:

Well, first you can find the rotation axis using vector-multiplication (cross-multiplication):

axis = v1 x v2; 

Then you can compute the rotation angle:

sinA = |axis| / |v1|*|v2| cosA = v1 . v2 / |v1|*|v2| 

Here | | - is vector length operation, and . - is dot-multiplication

And finally, your quaternion is:

Q(w,x,y,z) = (cosA, axis.x * sinA, axis.y * sinA, axis.z * sinA) 


标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!