The Math of Circles and Right Triangles - Trigonometry!
32 replies, posted
Trigonometry is a really useful tool to have in your coder's utility belt, and lots of people have a hard time grasping Sine and Cosine (and Tangent), so here's a crash course tutorial on their use.
Trigonometry is the math of [I]right triangles[/I] and [I]circles[/I].
[B]PART 1:[/B]
First, let's look at [B]SOH[/B], [B]CAH[/B], [B]TOA[/B]:
[B]SOH[/B] = [B]S[/B]ine equals [B]O[/B]pposite over [B]H[/B]ypotenuse
[B]CAH[/B] = [B]C[/B]osine equals [B]A[/B]djacent over [B]H[/B]ypotenuse
[B]TOA [/B]= [B]T[/B]angent equals [B]O[/B]pposite over [B]A[/B]djacent
But what does this mean?
The [B]Hypotenuse[/B] of a right triangle is the longest of the three sides. It's always on the opposite end of the right angle. The other two sides aren't uniquely named.
[t]http://www.mathopenref.com/images/triangle/hypotenuse.gif[/t]
So depending on our situation, we can use one of the three equations to find out all we need to know about a right triangle. All we need is the length of one of the three sides and the degree of one of the two non-right angles. Refer to this diagram (not to scale):
[img]http://s1.postimg.org/vtt3l7jin/sohcahtoa.png[/img]
If we replace those sides with [I]a[/I] and [I]b[/I], with the Hypotenuse being [I]c[/I], with the angle we know being [I]ang[/I], we can use this equation to find the length of side [I]b[/I]. Here is a Lua example:
[lua]
local a = 8
local b -- we're going to find out b. This is our "Opposite" side.
local c = 16
local ang = 30
ang = math.rad( ang ) -- Turn our degrees into radians. This is a requirement for Lua. Don't worry too much about it now.
-- Remember Sine equals Opposite over Hypotenuse.
-- That is, the sine of the angle is equal to the opposite leg's length divided by the Hypotenuse's length.
-- math.sin( ang ) == b / c
-- Here is the same equation, solved for b:
b = math.sin( ang ) * c
-- Lua will calculate the sin of ang, as such:
-- math.sin( math.rad( 30 ) ) = .5
print( b == .5 * 16 )
--Will output true.
[/lua]
Believe it or not, these basic right triangle calculations have [U]SO MANY USES[/U].
Over [I]2200[/I] years ago, mathematicians used these functions to calculate the radius of Earth. It's used literally every second of every day in GPS software (hence the term triangulation). It's used by police to track the location of a phone call. [B]SOH CAH TOA is the foundation of Trigonometry[/B].
[B]PART 2:[/B]
When we investigate the origins of Sine and Cosine, we can learn a thing or two about the fundamental properties of a circle. Consider the following:
[t]http://s29.postimg.org/t7j12mesn/unitcircle.png[/t]
We have a circle with radius 1. In this circle, we have radius line which is tilted 30 degrees (counterclockwise, always counterclockwise) from the circle's right horizontal axis. Because it is a radius line, its length is equal to the radius of the circle, which is 1 in this case.
So what is the length of b? If we recall SOH, we see that [B]Sin( ang ) = Opposite / Hypotenuse[/B]. Plug in our values, and Sin( 30 ) = b / 1.
Seeing as how any number divided by 1 is itself, we can conclude that:
In a circle of radius 1, the [B]Y-value[/B] of a point on a circle relative to the center of the circle is equal to the [B]sine[/B] of the angle.
In a circle of radius 1, the [B]X-value[/B] of a point on a circle relative to the center of the circle is equal to the [B]cosine[/B] of the angle.
That is,
[lua]
y = math.sin( ang )
x = math.cos( ang )
[/lua]
But not all circles are of radius 1. When we have a circle that is larger than radius 1, we just multiply.
[lua]
y = math.sin( ang ) * radius
x = math.cos( ang ) * radius
[/lua]
Furthermore, we've been assuming that our circle is centered at point (0,0). If our circle's center is (100,453), we add.
This is our complete formula:
[lua]
y = math.sin( ang ) * radius + originY
x = math.cos( ang ) * radius + originX
[/lua]
This is useful in GLua for drawing circles, arranging props in circles, and basically any other circle-based code.
Here is an example which draws squares:
[lua]
function PointOnCircle( ang, radius, offX, offY )
ang = math.rad( ang )
local x = math.cos( ang ) * radius + offX
local y = math.sin( ang ) * radius + offY
return x, y
end
local numSquares = 12 --How many squares do we want to draw?
local interval = 360 / numSquares
local centerX, centerY = 200, 500
local radius = 120
hook.Add("HUDPaint","Draw a circle of boxes!", function()
for degrees = 1, 360, interval do --Start at 1, go to 360, and skip forward at even intervals.
local x, y = PointOnCircle( degrees, radius, centerX, centerY )
draw.RoundedBox( 4, x, y, 30, 30, Color(255,255,0) )
end
end)
[/lua]
Result:
[IMG]http://s2.postimg.org/vbrifxju1/boxes.png[/IMG]
WOW! SO USEFUL!
Radial menus, circular health bars, [URL="http://steamcommunity.com/sharedfiles/filedetails/?id=382065862"]chairs arranged around a circular table[/URL], ellipses, sound waves, and [I]MUCH MORE[/I] are possible with Trigonometry.
[B]PART 3:[/B]
The inverse function of a Trigonometric function is called the arc-function.
Arc functions work like so:
sin( [I]a[/I] ) = [I]b[/I] / [I]c[/I]
[I]a[/I] = arcsin( [I]b[/I] / [I]c[/I] )
cos( [I]a[/I] ) = [I]b[/I] / [I]c[/I]
[I]a[/I] = arccos( [I]b[/I] / [I]c[/I] )
These are useful for doing reverse math, for example:
[lua]
-- We know the length of A and B, and we want to find angle THETA, which is adjacent to B
local A = 2
local B = 4
-- sin( ang ) == A / B
-- ang == arcsin( A / B )
local ang = math.asin( A / B )
print(ang) -- Outputs 30; sin( 30 ) == .5 == 2/4 == A/B
[/lua]
These functions are useful if the unknown variable in question is your angle. There is a special Arc-Tangent function for programming called [URL="http://wiki.garrysmod.com/page/math/atan2"]atan2(y,x)[/URL].
Think of tan(ang) as giving the slope - the rise over the run - of a line. So:
[lua]
tan( ang ) = y / x
ang = atan( y / x )
[/lua]
However, when performing y/x, calculating 3/4 gives the same answer as calculating -3/-4. Likewise -3/4 gives the same answer as 3/-4. So we have atan2(y,x) that handles the individual signs correctly and prevents a divide-by-zero/infinity error.
[lua]
ang = atan2( y, x )
[/lua]
atan2's use is to get the angle of a line with a slope [I]m[/I] as in the equation [I]y[/I] = [I]mx[/I] + [I]b[/I]
[t]http://i.stack.imgur.com/xQiWG.png[/t]
If you're looking for a simple way to make radial health bars, use [URL="https://www.dropbox.com/s/dh2nvua6gjmptmi/drawarc.lua?dl=1"]this script[/URL]!
Message me if you have any questions regarding Trigonometry and I'll be glad to help!
[quote][U]TL;DR[/U]
[B]SOH[/B] = [B]S[/B]ine equals [B]O[/B]pposite over [B]H[/B]ypotenuse
[B]CAH[/B] = [B]C[/B]osine equals [B]A[/B]djacent over [B]H[/B]ypotenuse
[B]TOA [/B]= [B]T[/B]angent equals [B]O[/B]pposite over [B]A[/B]djacent
[lua]
ang = math.rad( degrees ) -- Convert degrees to radians.
y = math.sin( ang ) * radius + originY
x = math.cos( ang ) * radius + originX
[/lua]
[lua]
function PointOnCircle( ang, radius, offX, offY )
ang = math.rad( ang )
local x = math.cos( ang ) * radius + offX
local y = math.sin( ang ) * radius + offY
return x, y
end
[/lua]
[lua]
tan( ang ) = y / x -- tangent is the slope of a line
ang = atan2( y, x ) -- atan2 is the angle of a line.
[/lua]
[/quote]
ew, maths
all the wonderful sixth grade math that i forgot four years ago
this is a legitimately helpful thread, put into the glua context
thanks
[editline]9th February 2015[/editline]
like you only went over the basics that we all can quickly pick up, but having a thread to pop into when i'm unsure if something is A or B is nice
Bookmarked - this will be incredibly helpful. 16 years old and never properly covered trig in school. Constantly find myself reading math pages online to solve simple problems in lua :suicide:
you should cover atan2, that's probably my most used trig function besides the obvious sin/cos
Also, for those wondering more about this stuff, and haven't gotten there in school/haven't covered it in a while, Khan Academy has some great videos on this and calculus topics. All that stuff you thought you'd never need to know from school...
[QUOTE=Exploderguy;47110426]ew, maths[/QUOTE]
Programming and math go hand in hand, dude. It's all the same thing - just straight up logic.
I have a few tuts on the subject but nothing going super in-depth on the math aside from some helper-functions about to be released in my dev-base which I've already posted here...
+1 for posting this.
[QUOTE=Revenge282;47110796]All that stuff you thought you'd never need to know from school...[/QUOTE]
If you want to pick up even hobbyist programming you're probably going to need at least a basic grasp on most high school mathematics IMO.
@OP - Great thread, I'm sure you'll save someone a few headaches! :)
[QUOTE=Acecool;47111576]I have a few tuts on the subject but nothing going super in-depth on the math aside from some helper-functions about to be released in my dev-base which I've already posted here...
+1 for posting this.[/QUOTE]
Acecool, you never responded to my accusation of you being a robot on Steam. You're definitely a robot. Even your attempt to "like" this is a program.
[code]+1 for posting( this )[/code]
Sheesh.
[QUOTE=wauterboi;47111902]Acecool, you never responded to my accusation of you being a robot on Steam. You're definitely a robot. Even your attempt to "like" this is a program.
[code]+1 for posting( this )[/code]
Sheesh.[/QUOTE]
He's also constantly in-game on garrys mod. Everytime I sign in, he's playing garrys mod. Same for when I log off.
[QUOTE=Exploderguy;47111921]He's also constantly in-game on garrys mod. Everytime I sign in, he's playing garrys mod. Same for when I log off.[/QUOTE]
That's what happens when you get plugged into the grid, man. You turn into a robot.
Seriously though Acecool makes some cool stuff. Acecool, mind linking to your tutorials?
I wish i was [I]hy on potenuse[/I]
I leave gmod open 24/7 because of my injury.. I am rarely out of bed more than 4 hours per 2 days so any extra time needed to launch, etc.. is annoying. So I keep it up and code when I'm up / answer questions.
[QUOTE=Arizard;47111985]I wish i was [I]hy on potenuse[/I][/QUOTE]
[B][U][I][URL="https://www.youtube.com/watch?v=k1tsGGz-Qw0"]JOE STOP IT! YOU WILL NEVER BE TROY!![/URL][/I][/U][/B]
i feel shameful for living in a world where people need to explain trigonometry in a gimmick game programmation forum
i mean [I]come on[/I]
I would like to strengthen that all trigonometry functions in programming uses [B]Radians [/B]as a measurement and not [B]Degrees[/B], you can use math.deg or math.rad to convert between them.
Another "clue" about trigonometry is that math.sin and math.cos "circles" around. What I mean by that is, if you input an incrementing number the output will keep going up or down, this can be used to for example make blinking text or nice tweens.
[QUOTE=Donkie;47112956]I would like to strengthen that all trigonometry functions in programming uses [B]Radians [/B]as a measurement and not [B]Degrees[/B], you can use math.deg or math.rad to convert between them.
Another "clue" about trigonometry is that math.sin and math.cos "circles" around. What I mean by that is, if you input an incrementing number the output will keep going up or down, this can be used to for example make blinking text or nice tweens.[/QUOTE]
math.deg and math.rad have always fucked me hard, so I use the manual method. How exactly do they work?
For instance, how do I get 2pi radians from 180 degrees, or 180 degrees from 2pi radians using those functions?
[QUOTE=bobbleheadbob;47113205]math.deg and math.rad have always fucked me hard, so I use the manual method. How exactly do they work?
For instance, how do I get 2pi radians from 180 degrees, or 180 degrees from 2pi radians using those functions?[/QUOTE]
Isn't pi rads just 180 degrees?
[lua]local howmanypis = math.rad(225)/math.pi[/lua]
Should spit out 1.25 (which is how many pi)
I'm hungry...
What's so difficult about them? You input radians and get out degrees or vice versa:
math.sin(math.pi) == math.sin(math.rad(180))
[QUOTE=Donkie;47113244]What's so difficult about them? You input radians and get out degrees or vice versa:
math.sin(math.pi) == math.sin(math.rad(180))[/QUOTE]
I don't know why but I've had bad experiences with the functions, but whatever. I updated the examples.
trig is like the only useful thing I took out of high school math. very useful for many things.
[QUOTE=bitches;47110489]all the wonderful sixth grade math that i forgot four years ago[/QUOTE]
We didn't have about this until 10th grade or something :tinfoil:
[QUOTE=Noi;47118410]maybe put this on gmod wiki?[/QUOTE]
[url]http://wiki.garrysmod.com/page/Trigonometry[/url]
Done.
Will be checking this out, This is something I have always known was useful but did not know where to start with it, I really appreciate this man!
You've taught me better than my math teacher at trigonometry, Thanks for the help on it :)
You're the smartest and cutest person I've ever seen in my entire life. :nws::rock::zoid:
[QUOTE=Acecool;47112027]I leave gmod open 24/7 because of my injury.. I am rarely out of bed more than 4 hours per 2 days so any extra time needed to launch, etc.. is annoying. So I keep it up and code when I'm up / answer questions.[/QUOTE]
What happened?
there is a bit of an issue with the example above it does this in game [IMG]http://i.imgur.com/GNGDOQR.png[/IMG]
[QUOTE=xESWxDEATH;47214386]there is a bit of an issue with the example above it does this in game [IMG]http://i.imgur.com/GNGDOQR.png[/IMG][/QUOTE]
I had that issue while making it. You've got like 100000 squares there. I updated the code in the OP to the one I used for the picture. My bad. :downs:
Sorry, you need to Log In to post a reply to this thread.