Want to make sure i get this correctly...

Started by
3 comments, last by Imperio59 19 years, 7 months ago
Hi, for the past year in college i've struggled in physics with vector math... After looking at some tutorials on the net, i've started to understand more and more vector physics... I wanted to make sure i understood some stuff before moving on: Calculating an angle between 2 vectors: let's say u and v are 2 non-colinear vectors in 2D space. The Dot product u.v = x1 * x2 + y1 * y2 It could also be reprensented as u.v= |u||v|*cos theta, theta being the angle between the 2 vectors... So if i want to calculate the angle between the 2 vectors, i have to normalize them both, so now |u| = |v| = 1, thus u.v=cos theta So the angle between the two would then be ArcCosine(u.v) when u and v are normalised... Correct? I imagine this would also work in 3D... I wanted to make sure i made no mistake... As I said, i've struggled with it in the past (especially in physics, trying to grasp the concepts of point mechanics while at the same time not understanding whta half the vector stuff meant... :( ) thanks...
Imperio59 - C++ Programmer
Advertisement
that's all correct. carry on :)

Everything is better with Metal.

Thanks, heh

I have to retake first semester physics because i failed it, i hope this time it won't be as hard as the first... The first lesson last year was all about this vector math stuff, and at that moment i knew i was gonna fail :(

All i actually remembered were some stuff like how to calculate a cross product (with an easy to remember formula, wich is always good :) )

Well, as you said, i'm gonna carry on with making my game :)
Imperio59 - C++ Programmer
as a side note, to get the angle between two vectors in 2D i use the arc tangent, which saves normalisation.

...ok, since I started....

similar to the dot product, is the cross product. At least in 2D.

a x b = |A|*|B|*sin(a, b) = ax*by - ay*bx

so sin (a, b) = (a x b) / (|a|*|b|)

sin (a, b) = (ax*by - ay*bx) / (|a|*|b|)
cos (a, b) = (ax*bx + ay*by) / (|a|*|b|)

tan (a, b) = sin(a, b) / cos(a, b) = (ax*by - ay*bx) / (ax*bx + ay*by);

angle(a, b) = atan((ax*by - ay*bx) / (ax*bx + ay*by));

or in code,

angle(a, b) = atan2(ax*by - ay*bx, ax*bx + ay*by);

which gives me the angle in the range [-PI, PI], whereas acos()., asin(), atan() return angles in a half-range. And acos() has some issues...

acos(ac)
if ac close to 1, there can be some accuracy issues. Also if ac > 1 (like ac = 1.0000001f), it will fail.
similarly

asin(as)
if as close to 0, there can be some accuracy issues. Also if as > 1 (like as = 1.0000001f), it will fail.

there are no such issues when using atan2(). it's the best of both worlds and more :)


but be careful with the cross product in 3D, it's a vector (in 2D, sort of too...), so you can't really use it that way.

best of luck ;)

Everything is better with Metal.

Well since i was looking at ways to do it in 3D, i think i'll go with the acos routine, making sure to check for errors and adapting the code to include that it only returns angles from 0 to 180...

Anyways, i haven't started doing anything complicated in 3D yet, i need to learn some OpenGL first as well as more algorithms to help me understand how to make my 3D engine, wich is still a long ways off ;)
Imperio59 - C++ Programmer

This topic is closed to new replies.

Advertisement