Saturday, January 7, 2017

c++ - Finding direction of travel in a world with wrapped edges


I need to find the shortest distance direction from one point in my 2D world to another point where the edges are wrapped (like asteroids etc). I know how to find the shortest distance but am struggling to find which direction it's in.


The shortest distance is given by:


int rows = MapY;
int cols = MapX;

int d1 = abs(S.Y - T.Y);
int d2 = abs(S.X - T.X);

int dr = min(d1, rows-d1);
int dc = min(d2, cols-d2);

double dist = sqrt((double)(dr*dr + dc*dc));

Example of the world


                   :         
: T
:
:--------------:---------

: :
: S :
: :
: :
: T :
: :
:--------------:

In the diagram the edges are shown with : and -. I've shown a wrapped repeat of the world at the top right too. I want to find the direction in degrees from S to T. So the shortest distance is to the top right repeat of T. but how do I calculate the direction in degreed from S to the repeated T in the top right?


I know the positions of both S and T but I suppose I need to find the position of the repeated T however there more than 1.



The worlds coordinates system starts at 0,0 at the top left and 0 degrees for the direction could start at West.


It seems like this shouldn’t be too hard but I haven’t been able to work out a solution. I hope somone can help? Any websites would be appreciated.



Answer



You'll have to tweak your algorithm a bit to calculate the angle - currently you only record the absolute difference in position, but you need the relative difference (i.e. can be positive or negative depending on positioning).


int dx = T.X - S.X; // difference in position
int dy = T.Y - S.Y;

if (dx > MapX / 2) // if distance is bigger than half map width, then looping must be closer
dx = (dx - MapX) * -1; // reduce distance by map width, reverse
else if (dx < -MapX / 2) // handle the case that dx is negative

dx = (dx + MapX) * -1;

//Do the same for dy
if (dy > MapY / 2)
dy = (dy - MapY) * -1;
else if (dy < -MapY / 2)
dy = (dy + MapY) * -1;

double dist = sqrt(dy*dy+dx*dx); // same as before
double angle = atan2(dy,dx) * 180 / PI; // provides angle in degrees

No comments:

Post a Comment

Simple past, Present perfect Past perfect

Can you tell me which form of the following sentences is the correct one please? Imagine two friends discussing the gym... I was in a good s...