Here are the guts of the gravity example:
pushMatrix()
translate(WIDTH/2, HEIGHT/2)
grav = vec2(Gravity.x * 300, Gravity.y * 300)
line(0, 0, grav.x, grav.y)
-- Arrowhead
down = vec2(1, 0)
orient = down:angleBetween(grav)
pushMatrix()
resetMatrix()
translate(WIDTH/2,HEIGHT/2)
translate(grav.x,grav.y)
rotate(math.deg(orient))
line(0, 0, -25, -20)
line(0, 0, -25, 20)
popMatrix()
The first pushmatrix() saves the current state of translate/rotate/scale so we can come back to it later with popmatrix() It’s not necessary in the demo, but it’s good practice if you expect your code to be reused - it lets you clean up after yourself, and by writing code with transform/rotate/scale you can avoid what can turn into some very nasty math.
A note: The complexity here comes from needing to be able to calculate the rotation for the arrow head - if you just wanted to draw a line, the x and y from gravity is enough.
Anyway - the next line saves gravity.x and y as a vector. The line after draws the shaft of the arrow.
To draw the arrowhead, we will draw a rotated V shape. To figure out how much to rotate, we need to calculate the angle between our gravity vector and a fixed vector we call down. These two lines set up down, and then figure out the angle between down and grav.
Next, the transform matrix is reset to the default (not necessary here, but again good practice), and the arrowhead is drawn by moving first to the center, then to the other end of the line, then rotating. The actual v is drawn, then the matrix is popped to put us back where we were.
That’s about it - simple gravity is looking at gravity, establishing the angle and rotating, the proceeding assuming gravity is just straight down.