12

I need to calculate the 2 angles (yaw and pitch) for a 3D object to face an arbitrary 3D point. These rotations are known as "Euler" rotations simply because after the first rotation, (lets say Z, based on the picture below) the Y axis also rotates with the object.

This is the code I'm using but its not working fully. When on the ground plane (Y = 0) the object correctly rotates to face the point, but as soon as I move the point upwards in Y, the rotations don't look correct.

// x, y, z represent a fractional value between -[1] and [1]
// a "unit vector" of the point I need to rotate towards

yaw = Math.atan2( y, x )
pitch = Math.atan2( z, Math.sqrt( x * x + y * y ) )

Do you know how to calculate the 2 Euler angles given a point?


The picture below shows the way I rotate. These are the angles I need to calculate. (The only difference is I'm rotating the object in the order X,Y,Z and not Z,Y,X)

pic

enter image description here


This is my system.

  • coordinate system is x = to the right, y = downwards, z = further back
  • an object is by default at (0,0,1) which is facing backward
  • rotations are in the order X, Y, Z where rotation upon X is pitch, Y is yaw and Z is roll

my system

Glorfindel
  • 19,729
  • 13
  • 67
  • 91
Robin Rodricks
  • 99,791
  • 133
  • 372
  • 575
  • When you say "move the object upwards in Y", do you mean "move the point upwards in Y"? And which way is the object facing before rotation? – Beta Oct 27 '10 at 00:54
  • @Beta - Yes, that's what I mean. The object is facing backward before rotation, as if standing on a table. – Robin Rodricks Oct 27 '10 at 17:46
  • Hello @Robinicks can you tell me where did you take the picture pic http://i53.tinypic.com/33lo6jp.jpg please? – Gennaro Arguzzi Sep 30 '18 at 15:10
  • @GennaroArguzzi - I designed that graphic in Adobe Flash – Robin Rodricks Oct 17 '18 at 06:57
  • Hello @Robinicks, i referred to the above one, see the above link please. – Gennaro Arguzzi Oct 17 '18 at 10:48
  • @GennaroArguzzi - I designed the above link in Adobe Flash. Yes its a 3d diagram hand drawn in a 2d graphic program. Idk what more I can say. If you wanna try grab Inkscape and see for yourself. – Robin Rodricks Oct 18 '18 at 11:30
  • Sorry for the hassle @Robinicks. I ensure you that the first image is taken from a book because I have the complete image on slides (your image is half image because is only about local rotation, instead the mine is about global and local rotation). See this please http://s000.tinyupload.com/index.php?file_id=83705559891752145583 – Gennaro Arguzzi Oct 20 '18 at 12:25

4 Answers4

14

Here are my working assumptions:

  • The coordinate system (x,y,z) is such that positive x is to the right, positive y is down, and z is the remaining direction. In particular, y=0 is the ground plane.
  • An object at (0,0,0) currently facing towards (0,0,1) is being turned to face towards (x,y,z).
  • In order to accomplish this, there will be a rotation about the x-axis followed by one around the y-axis. Finally, there is a rotation about the z-axis in order to have things upright.

(The terminology yaw, pitch, and roll can be confusing, so I'd like to avoid using it, but roughly speaking the correspondence is x=pitch, y=yaw, z=roll.)

Here is my attempt to solve your problem given this setup:

rotx = Math.atan2( y, z )
roty = Math.atan2( x * Math.cos(rotx), z )
rotz = Math.atan2( Math.cos(rotx), Math.sin(rotx) * Math.sin(roty) )

Hopefully this is correct up to signs. I think the easiest way to fix the signs is by trial and error. Indeed, you appear to have gotten the signs on rotx and roty correct -- including a subtle issue with regards to z -- so you only need to fix the sign on rotz.

I expect this to be nontrivial (possibly depending on which octant you're in), but please try a few possibilities before saying it's wrong. Good luck!


Here is the code that finally worked for me.

I noticed a "flip" effect that occurred when the object moved from any front quadrant (positive Z) to any back quadrant. In the front quadrants the front of the object would always face the point. In the back quadrants the back of the object always faces the point.

This code corrects the flip effect so the front of the object always faces the point. I encountered it through trial-and-error so I don't really know what's happening!

 rotx = Math.atan2( y, z );
 if (z >= 0) {
    roty = -Math.atan2( x * Math.cos(rotx), z );
 }else{
    roty = Math.atan2( x * Math.cos(rotx), -z );
 }
A. Rex
  • 30,789
  • 21
  • 85
  • 95
  • So here's one misunderstanding I'm having. You say that your code works if the object is at y=0, but I can't understand how that would be the case. In that case you compute yaw=0 but pitch!=0, which doesn't seem right. (That's why I asked if z was up/down.) Any ideas? – A. Rex Oct 26 '10 at 16:27
  • Yes, it works because my object is some distance away from the point its facing and the only angle that really changes is yaw (rotation upon the Y axis, so the object rotates horizontally to face the point which is on the ground plane). Have I said anything confusing? – Robin Rodricks Oct 26 '10 at 17:30
  • @Rex - I've explained everything I can in my edited question, if you need anything more then please write back. Waiting for your updated code. – Robin Rodricks Oct 27 '10 at 18:03
  • @Rex - Thank you very much! correct answer!!! it works like a charm and my object correctly rotates to face the vector... phew!!! its been almost a week of struggling around trying to find the right answer. – Robin Rodricks Oct 28 '10 at 14:14
  • @Rex - One last problem however: During some X+Y rotations the object appears to be rotating on Z, such that the bottom of the object is not facing the ground plane. Can you calculate a Z rotation such that the object is always upright? I'm posting a video of my results. – Robin Rodricks Oct 28 '10 at 14:49
  • Well, I hope things worked out for you. PS. Watching that video is kind of fun. – A. Rex Oct 29 '10 at 14:35
  • Thanks very much :) it works as expected. You really are a god sent!!! Do you have any email that I can write to you at? You take minutes to solve things that others (and me) take weeks!!! – Robin Rodricks Oct 29 '10 at 18:28
  • Sorry, but the "A." in "A. Rex" stands for "Anonymous". Your best chance of catching me is randomly on Stack Overflow. I go through periods when I read this site and periods when I don't. – A. Rex Oct 29 '10 at 18:47
  • 1
    @Braineeee: Stack Overflow was launched 8 years ago. You are commenting on a question asked 7 years ago that was last active 6 years ago. – A. Rex Apr 02 '17 at 22:38
  • What bearing does that have on the validity of this answer? –  Apr 15 '17 at 19:38
6

Rich Seller's answer shows you how to rotate a point from one 3-D coordinate system to another system, given a set of Euler angles describing the rotation between the two coordinate systems.

But it sounds like you're asking for something different:

You have: 3-D coordinates of a single point

You want: a set of Euler angles

If that's what you're asking for, you don't have enough information. To find the Euler angles, you'd need coordinates of at least two points, in both coordinate systems, to determine the rotation from one coordinate system into the other.

You should also be aware that Euler angles can be ambiguous: Rich's answer assumes the rotations are applied to Z, then X', then Z', but that's not standardized. If you have to interoperate with some other code using Euler angles, you need to make sure you're using the same convention.

You might want to consider using rotation matrices or quaternions instead of Euler angles.

Jim Lewis
  • 39,858
  • 6
  • 80
  • 93
  • "you don't have enough information" .. haven't I already described the 2 points in 3D space? the 1st point is anything, and the 2nd point is 0,0,0 ... so I want to measure the Euler rotations between those 2 points in the order XYZ. – Robin Rodricks Oct 23 '10 at 00:30
  • Please consider updating your answer since I have edited my question and added a +500 bounty. – Robin Rodricks Oct 23 '10 at 21:48
3

This series of rotations will give you what you're asking for:

  1. About X: 0
  2. About Y: atan2(z, x)
  3. About Z: atan2(y, sqrt(x*x + z*z))

I cannot tell you what these are in terms of "roll", "pitch" and "yaw" unless you first define how you are using these terms. You are not using them in the standard way.

EDIT:
All right, then try this:

  1. About X: -atan2(y, z)
  2. About Y: atan2(x, sqrt(y*y + z*z))
  3. About Z: 0
Beta
  • 86,746
  • 10
  • 132
  • 141
  • @Beta - Thanks for your answer. Please see my edited question for my exact rotation system - and I don't really need them in terms of pitch/yaw but rather as rotation X and rotation Y (see my picture to know what I mean by that) – Robin Rodricks Oct 27 '10 at 17:59
  • I assume that x,y,z refer to a unit vector of the direction I'm trying to rotate towards? – Robin Rodricks Oct 28 '10 at 11:07
  • I tried your solution but it isn't working for some reason. Too tired to figure out why since Rex's answer already works 99% of the time. Thanks very much though! and keep up the good work. – Robin Rodricks Oct 28 '10 at 14:55
  • 1
    I think I know the reason: YOUR DIAGRAMS ARE WRONG. – Beta Oct 28 '10 at 16:09
  • Well, that's being mean, and guess what, my diagrams are correct since Rex figured out the correct answer. Look at the updated code that finally worked for me, its similar to yours, no doubt but still its the one that worked. – Robin Rodricks Oct 28 '10 at 18:26
  • I had a similar problem and this worked for me well. (After just a little adaptation.) – Roman Horváth Jul 12 '18 at 16:08
-2

Talking about the rotation of axes, I think step 3 should have been the rotation of X'-, Y''-, and Z'-axes about the Y''-axis.