I have a plane defined in space by 3 points and I would like to rotate this plane around the axis which is formed by the first two points of this plane. To do this, I used the rotation matrix suited for this purpose, taken from wikipedia. (Rotation matrix). However, I seem to get wrong results, and can not find what I am doing wrong. I used the following code in Matlab:

clear all

Here I am defining the 3 points for the plane

lm1 = [1,0,6];
lm2 = [2,3,2]; 
lm3 = [1.5,2,1];

I want to rotate pont lm3 around the axis between lm1 and lm2

rotation = 90;  
theta = degtorad(rotation);

Defining the rotation axis between lm1 and lm2 and make a unit vector of it

  rot_axis = [lm2(1)-lm1(1), lm2(2) - lm1(2), lm2(3) - lm1(3)];
    urot = rot_axis/norm(rot_axis);

Defining the rotation matrix (as taken from Wiki)

R = [cos(theta) + urot(1)^2*(1-cos(theta)), urot(1)*urot(2)*(1-cos(theta))-urot(3)*sin(theta), urot(1)*urot(3)*(1-cos(theta)) + urot(2)*sin(theta);...
    urot(2)*urot(1)*(1-cos(theta)) + urot(3)*sin(theta), cos(theta) + urot(2)^2*(1-cos(theta)), urot(2)*urot(3)*(1-cos(theta)) - urot(1)*sin(theta);...
    urot(3)*urot(1)*(1-cos(theta))-urot(2)*sin(theta), urot(3)*urot(2)*(1-cos(theta))+ urot(1)*sin(theta), cos(theta) + urot(3)^2*(1-cos(theta))]

Calculate new lm3 after rotation around the axis between lm1 and lm2

 lm3_new = lm3*R

Plotting to check the results

plane_initial = [lm1', lm2', lm3']; 
plane_rotated = [lm1', lm2', lm3_new'];

hold on
grid on

vector on old plane

vec_old = [lm3(1)-lm2(1), lm3(2) - lm2(2), lm3(3) - lm2(3)]; 

vector on new plane

vec_new = [lm3_new(1)-lm2(1), lm3_new(2) - lm2(2), lm3_new(3) - lm2(3)];

Checking the angle between those two vectors on both planes

 angle_check = atan2d(norm(cross(vec_old,vec_new)),dot(vec_old,vec_new))

The planes should now have an angle of 90 degrees with each other. However, both the anglecheck (= 41 degrees) and the plot see here for 3D-plot show different results. I have checked the rotation matrix multiple times for hours but I think it should be correct. I was wondering if anyone has experience with this and can see the mistake. Thanks in advance!

  • $\begingroup$ This isn’t really a site for getting help debugging your code. That said, it looks like you’re making a basic conceptual error: the rotation matrix that you copied from wherever is for a rotation axis that passes through the origin. The rotation axis that you really want doesn’t, so you’ll need to do something different. $\endgroup$ – amd Jul 11 '18 at 19:52
  • $\begingroup$ Hi there, sorry, I was trying to explain my aproach but it was a bit longer than I planned. Thanks for stating the problem, do you have an idea how to do this rotation if the axis is not going through the origin? $\endgroup$ – Nick Jul 11 '18 at 20:12

Your rotation matrix rotates about an axis that passes through the origin. Whatever source you cribbed it from most likely mentions that somewhere. Unless you happen to be very lucky, the rotation axis defined by your two points doesn’t. So, what you’re doing is rotating about an axis that’s parallel to the one you want.

There are several ways to fix this problem. The simplest for your code would be to translate lm3 by an amount that puts the rotation axis through the origin, rotate using the method you already have, then translate back. That is, rotate either lm3-lm1 or lm3-lm2, then add lm1 or lm2 as appropriate to the result.

  • $\begingroup$ Hi, thanks for your help, but even if I choose lm1 in the origin, it is still is not working. $\endgroup$ – Nick Jul 11 '18 at 20:25
  • $\begingroup$ @Nick Your “angle check” doesn’t do what you think. The angle between vec_new and vec_old will only be equal to the rotation angle if lm_1, lm_2 and lm_3 happened to form a right angle. Indeed, if you compute the angle using lm_1 instead of lm_2 you’ll get a different value. The correct way to test the angle between the before and after planes is to compare their normals. $\endgroup$ – amd Jul 11 '18 at 20:39
  • $\begingroup$ You are right, I forgot that aspect. I compared the normals and applied your method and it worked. Many thanks $\endgroup$ – Nick Jul 11 '18 at 20:53

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.