Sign in to follow this  

Simple Angle question (hopefully)

This topic is 4057 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Forgive for asking for what will probably seem like an obvious solution to a maths problem here... In a shootemup I'm making (sorta like an invaders thing), I have enemies rotated at and moving towards invisible nodes that move around the screen in various ways to create different behavior types and 'flight paths'. At the moment, the vector / rotation value is calculated absolutely at each iteration: { motion = getVector(getAngle(getRadians(sourceX,sourceY,targetX,targetY))); } // I'm sure you can imagine the contents of the functions involved in above What I'd like to do however is ease the current angle into the target angle (the reason being that I want the motion of the enemies to arc towards a change in target rather than sharply turning at it in an instant): { a = getAngle(getRadians(sourceX,sourceY,targetX,targetY)); angle += (a - angle)*0.2; motion = getVector(angle); } The problem with this second way though is the crossover between 0 and 360 degrees. The process of the current angle seeking the target angle flips at the seem. Can some one help with a solution for this? Any means at all that would achieve the effect intended would be great. If the solution is not completely straight forward and cannot easily be explained, any directions towards specific tutorials/instructions would also help greatly. I suck at trig. Or more specifically, never payed attention to it in my wee days, and am suffering for it now :). Many thanks, Onfu

Share this post


Link to post
Share on other sites
This question has come up a few times recently, but I'm not sure where the relevant threads are. Anyway, YMMV, but I usually recommend not expressing these sorts of problems in terms of absolute angles (due to, among other things, the very problem you mention).

Instead I would suggest the use of relative angles (e.g. the target node is 15 degrees to the left) and/or transformation of the nodes to local object space. Either of these methods will bypass the 'wrap-around' problem completely.

Post back if you need further details.

Share this post


Link to post
Share on other sites
The offset/relative idea is intruiging. I'm experimenting with it now (it's 1am though and I work full time so maybe I should leave it alone tonight)...

If you have time to clarify it further I could definitely put the info to good use.

I'm not sure on the other hand what you mean by local space on the nodes - or rather what to do with it in terms of easing the angle transformations.

I'm a self taught programmer with a rather chaotic assortment of experience, so apologies again for any apparent lack in basic knowledge/know-how

thanks,
onfu

Share this post


Link to post
Share on other sites
There are plenty of algorithms to interpolate the angles correctly over the discontinuity, but I'd like to suggest some alternatives.

1. If you arrange the object's heading as a vector, interpolation is dead-straightforward and there is no need for so much horrible trigonometry. Making the switch can be as easy or as hard as you make it. Eliminating angles altogether is probably a bad idea, but shifting the angle-to-vector transformation to an earlier point in the code would avoid this little mess.

2. Use a more suitable representation, such as relative angles (a la jyk).

3. Allow your angles to stray from the range [0, 360) so that no discontinuity is even present. Beware that if a lot of winding is expected, this could cause floating-point inaccuracy as angles get large, so you may want to periodically chop the values down to size. One simple way to do this would be
if (abs(angle) > 1000.0f) {
float excess = (360.0f * floor(angle / 360.0f));
angle -= excess;
a -= excess;
}

Regards
Admiral

Share this post


Link to post
Share on other sites
Quote:

1. If you arrange the object's heading as a vector, interpolation is dead-straightforward and there is no need for so much horrible trigonometry. Making the switch can be as easy or as hard as you make it. Eliminating angles altogether is probably a bad idea, but shifting the angle-to-vector transformation to an earlier point in the code would avoid this little mess.


I can't believe I got so caught up in refusing defeat with the angle-seem problem that I overlooked this painfully obvious solution that can produce an identical visual result. Thanks for snapping me out of that one, Admiral.

In previous games where I had no enemy graphic rotation at all (old school arcade-style) the interpolation and ease-ins were done purely at a vector level...straight forward and no mess - exactly. I guess with this one I wanted a different approach to motion (experimenting I suppose). I want the enemies to look like they're gliding and swooping, etc... So I thought I'd have a lagging/easing-angle driving the motion. Given this unnecessary seem problem I guess the angle should be purely aesthetic and left til the last minute where possible. I'm usually the first person to pick the simplest paradigm to achieve a result - just overloooked this one.

I'd still like to know how to get around the seem problem as I'm sure it'll come up again in the future.

I thought about allowing the angle var (like you mention) to freely hold any value and then use divisions of 360 etc to work out exactly what it is, but I thought there would have to be a nicer way. The idea of relative angles (as far as I could see it in my mind) uses pretty similar ideas (I think?) - allowing a result outside of 0-360 and then bring back into bounds...Maybe I have a different idea.

Anyway thanks both. Interpolating the vector seems to be by far my most painless option at the moment.

Cheers,
onfu

[Edited by - onfu on November 6, 2006 6:30:45 PM]

Share this post


Link to post
Share on other sites
Actually,
interpolation between two vectors that would be connected by a line that passes exactly through the point of origon would cause a snap in the angle, but it's still a good enough solution for the purpose. It's a rare-case scenario and work arounds probably aren't too hard to put in place.

Share this post


Link to post
Share on other sites
Quote:
Original post by onfu
Actually,
interpolation between two vectors that would be connected by a line that passes exactly through the point of origon would cause a snap in the angle, but it's still a good enough solution for the purpose. It's a rare-case scenario and work arounds probably aren't too hard to put in place.

You're right on both counts. The usual workaround it to simply not update the orientation if the heading vector is null. Providing your normalise this vector each frame, the discontinuity caused by an instantaneously undefined orientation won't be noticeable (as the object is facing roughly the right way already) and it means less work for the CPU [wink].

Regards
Admiral

Share this post


Link to post
Share on other sites

This topic is 4057 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this