Flipping an angle using radians - trigonometry

Hello all you math whizzes out there!
I am struggling with a math problem I am hoping you can help me with. I have calculated an angle of direction using radians. Within OpenGL ES I move my guy by changing my point value as such:
spriteLocation.x -= playerSpeed * cosf(playerRadAngle);
spriteLocation.y -= playerSpeed * sinf(playerRadAngle);
// playerRadAgnle is my angle of direction using radians
This works very well to move my sprite in the correct direction. However, I have decided to keep my sprite "locked" in the middle of the screen and move the background instead. This requires me to Reverse my calculated angle. If my sprite's direction in radians is equivalent to 90 degrees, I want to convert it to 270 degrees. Again, keeping everything in radians.
I will admit that my knowledge of Trig is poor at best. Is there a way to figure out the opposite angle using radians? I know I could convert my radians into degrees, then add/subtract 180 degrees, then convert back to radians, but I'm looking for something more efficient.
Thanks in advance....
-Scott

Add/subtract pi instead.

You need to add Pi and then use the remainder after division by 2 Pi (to make it restricted within [0; 2 Pi] range).
JavaScript:
function invertAngle(angle) {
return (angle + Math.PI) % (2 * Math.PI);
}

object_sprite.rotation = warp_direction - 3.14;

Related

Drawing a circle without using a function for it

So I was wondering how does a circle() function work, and how can I draw to circle without using it (wanted to do something related to it). Does anyone know this stuff?
A classic way of rasterizing a circle is using the Midpoint Circle Algorithm.
It works by tracking the pixels which are as close to the x2 + y2 = r2 isoline as possible. This can even be done with purely integer calculations, which is particularly suitable for low-computation power devices.
A circle is the set of points located at a constant distance from another point, called the center.
If you can draw lines defined by two points, you can draw the representation of a circle on a canvas, knowing its center, and its radius.
The approach is to determine a set of consecutive points located on the circumference, then join them with lines.
for instance, in python (which reads like pseudocode):
import math
def make_circle(center, radius, num_points=40):
"""returns a sequence of points on the circumference
"""
points = [center]
d_theta = 2 * math.pi / num_points
cx, cy = center
for idx in range(num_points + 1):
theta = idx * d_theta
points.append((cx + math.cos(theta) * radius, cy + math.sin(theta) * radius))
return points
And if you want to try it, here it is: circles codeskulptor.
You will see that for display purposes, 40 points on the circumference is enough to give an acceptable rendition.

Finding internal angles of polygon

I have some lines that their intersection describes a polygon, like this:
I know the order of the lines, and their equations.
To find the internal angles, I found each lines orientations. But I've got confused as subtracting two lines orientation would give two different angles, even if I do it in the order of polygon's sides.
For example, in the following image, if I just subtract the orientation of the lines, I would get any of the following angles:
What made me more confused, is when the polygon is not convex, I will have angles greater than 180, and using my approach I don't get the correct angle at all:
And I found out that this way of approaching the problem is wrong.
So, What is the best way of finding the internal angles using just the lines? I know for a convex polygon, I may find vectors and then find the angle between them, but even for P6 in my example the vector approach fails.
Anyway, I prefer a method that won't include a conditional case for solving that concavity problem.
Thanks.
With ordered lines it is possible to find points of intersection (polygon vertexes) in clockwise order. Then you can calculate internal angles:
Angle[i] = Pi + ArcTan2(V[i] x V[i+1], V[i] * V[i+1])
(crossproduct and dotproduct of incoming and outgoing vectors for every vertex)
or
Angle[i] = Pi + ArcTan2( dx_in*dy_out-dx_out*dy_in, dx_in*dx_out+dy_in*dy_out2 )
Note: change plus sign after Pi to minus for anti-clockwise direction.
Edit:
Note that crossproduct and dotproduct are scalars, not vectors.
Example for your data:
dx1 = 5; dy1 = -15; dx2 = -15; dy2 = 5
Angle = Pi + ArcTan2(5*5-15*15, -5*15-5*15) = Pi - 2.11 radians ~ 59 degrees
Example for vectors:
(0,-1) (1,0) (L-curve)
Angle = Pi + ArcTan2(1, 0) = 270 degrees

Calculating direction angle from x and y speed

I'm developing game in Game Maker kind of program (not actual Game Maker, though), because I've failed in coding games in real languages (can code normal apps, just not games) so many times.
Anyway, in program that I'm using direction function was proven to be buggy at times. However x and y speed of object are always correct, so I'd like to calculate direction angle (in degrees) from those. Unfortunately I'm not math genius and I'm always failing at trigonometry ;(. Can you help me?
My game making IDE's angle coordinate system is as follows:
270 deg.
180 deg. 0 deg.
90 deg.
Positioning system is like in most environments (0,0 in top-left)
Math libraries usually come with a function called atan2 just for this purpose:
double angle = atan2(y, x);
The angle is measured in radians; multiply by 180/PI to convert to degrees. The range of the angle is from -pi to pi. The 0-angle is the positive x-axis and the angle grows clockwise. Minor changes are needed if you want some other configuration, like the 0-angle being the negative y-axis and the range going from 0 to 359.99 degrees.
The main reason to use atan2 instead of atan or any of the other inverse trig functions is because it determines the correct quadrant of the angle for you, and you don't need to do it yourself with a series of if-statements.
Use the arctangent function. It should be something like this:
double direction(double x, double y) {
if (x > 0)
return atan(y/x);
if (x < 0)
return atan(y/x)+M_PI;
if (y > 0)
return M_PI/2;
if (y < 0)
return -M_PI/2;
return 0; // no direction
}
(Where x and y is the horizontal and vertical speed, M_PI is pi and atan is arctangent function.)
In game maker specifically you may use following:
direction = point_direction(x, y, x+x_speed, y+y_speed)
speed = point_distance(x, y, x+x_speed, y+y_speed)
(compare current and future x/y coordinates and return values)
Reverse the process to get x/y_speed:
x_speed = lengthdir_x(speed, direction)
y_speed = lengthdir_y(speed, direction)
Note: Added this post because its still viewed in relation to Game Maker:
Studio and its specific functions. Maybe it has no value for the person who
asked originally but i hope it will help some Game Maker users who wander here.

Reproject rectangle from latlon to metres

I have this bounding box expressed in latlong:
POLYGON ((51.2913 -13.5599, 51.2913 13.1589,
35.0325 13.1589, 35.0325 -13.5599, 51.2913 -13.5599))
widthDeg="26.7188" heightDeg="16.2588" areaDeg="434.4156254400001"
I'd like to get the equivalent width/height/area in metres.
I found this formula:
1 degree of longitude = 60 * 1.852 km * cos (latitude)
How can I use this to translate the bounding box? Is this a valid approximation?
Thanks for any hints!
Mulone
The width in metres may be different at the north and south sides of the bounding box; unless your box is guaranteed to be quite small in latitude, you probably don't really want to try to describe it with a height and width in metres.
The area is well defined, though; you can find a formula at Link: it's equivalent to |sin(lat1)-sin(lat2)| * |long1-long2| * R^2 if you measure your longitudes in radians. (Multiply by pi/180 if they're in degrees, and don't forget to convert them to radians before passing them to the sine function in that case.) Here R is the radius of the earth, which is approximately 6400km; more accurately 6371km; if you think you need it more accurately than that, remember that the earth isn't really a sphere and think again.

Rotating 3D cube perspective problem

Since I was 13 and playing around with AMOS 3D I've been wanting to learn how to code 3D graphics. Now, 10 years later, I finally think I have have accumulated enough maths to give it a go.
I have followed various tutorials, and defined screenX (and screenY, equivalently) as
screenX = (pointX * cameraX) / distance
(Plus offsets and scaling.)
My problem is with what the distance variable actually refers to. I have seen distance being defined as the difference in z between the camera and the point. However, that cannot be completely right though, since x and y have the same effect as z on the actual distance from the camera to the point. I implemented distance as the actual distance, but the result gives a somewhat skewed perspective, as if it had "too much" perspective.
My "actual distance" implementation was along the lines of:
distance = new Vector(pointX, pointY, cameraZ - pointZ).magnitude()
Playing around with the code, I added an extra variable to my equation, a perspectiveCoefficient as follows:
distance = new Vector(pointX * perspectiveCoefficient,
pointY * perspectiveCoefficient, cameraZ - pointZ).magnitude()
For some reason, that is beyond me, I tend to get the best result setting the perspectiveCoefficient to 1/sqrt(2).
My 3D test cube is at http://vega.soi.city.ac.uk/~abdv866/3dcubetest/3dtest.svg. (Tested in Safari and FF.) It prompts you for a perspectiveCoefficient, where 0 gives a perspective without taking x/y distance into consideration, and 1 gives you a perspective where x, y and z distance is equally considered. It defaults to 1/sqrt(2). The cube can be rotated about x and y using the arrow keys. (For anyone interested, the relevant code is in update() in the View.js file.)
Grateful for any ideas on this.
Usually, projection is done on the Z=0 plane from an eye position behind this plane. The projected point is the intersection of the line (Pt,Eye) with the Z=0 plane. At the end you get something like:
screenX = scaling * pointX / (1 + pointZ/eyeDist)
screenY = scaling * pointY / (1 + pointZ/eyeDist)
I assume here the camera is at (0,0,0) and eye at (0,0,-eyeDist). If eyeDist becomes infinite, you obtain a parallel projection.

Resources