Copy link to clipboard
Copied
I was trying to figure out how to create an accurate GPS location display for an animated path. I got almost everything figured out using some simple math, but the Longitude compensation was giving me problems. Here's the heart of the problem.
Latitude has nearly the same distance of about 69 miles per degree, no matter where you are. Longitude is not as easy. One degree of Longitude is also about 69 miles per degree at the equator, but at the poles, it is zero. As the Latitude increases from 0º to 90º, the distance per degree goes down, but the decrease is not linear because the measurement is on a sphere.
I tried all kinds of trigonometry but failed miserably, so I simplified everything by creating a new layer, offsetting the y Anchor Point value by 1 pixel. I then set up a rotation that matches the 0 to 90º values for Latitude. I then used toWorld to generate a multiplier from 1 to zero from the X position value. Here's the simple expression:
latComp = thisComp.layer("Longetude Factor");
latAngl = latComp.toWorld(anchorPoint)[0]-1-thisComp.width/2;
This gives me a simple way to accurately display distances based on the distance between two GPS locations or the distance traveled by a layer (a dot) following a path drawn on a map.
Does anyone have any idea how to do the same thing mathematically? When the Latitude is 45º, the multiplier should be about .707, so 1º = about 48 miles. I'd love to get this preset to work with just one layer.
Any help would be appreciated. It's been a long time since my Math Analysis and Trig classes. Here's a look at where I am so far:
I'm really out of my lane here, but it seems that if you assume a sphere, and the 69.172 is for the radius at the equator, then the value at other latitudes should be proportional to the radius of the circle at that latitude. So for 30 degrees latitude, say, I would think it would be:
laT = 30;
69.172*Math.sin(degreesToRadians(90-Math.abs(laT)))
Or did you already have that figured out?
Copy link to clipboard
Copied
I don't think there's a simple way to do that, since the Earth isn't even a perfect sphere. Geographers use complex tables and curves to compensate for this stuff. If at all I would imagine you need multiple nested cosine and sine functions with logarithmic inputs, but even then the discrepancies may be too large.
Mylenium
Copy link to clipboard
Copied
If I can get close, it will work. I don't have to be 100% accurate. Just close. I can nail the starting and ending GPS locations. I have the metadata. With the solution I have using the rotating layer, I'm within about 2% of the Google Earth coordinates. I'd just like to get rid of that other layer. I've seen the graphs on the Trig pages, I just can't get the same results as rotating a layer and measuring the difference in the X-axis.
Copy link to clipboard
Copied
I have not got this figured out yet. I would love to eliminate the rotation calculation from the null in my comp to solve the longitude to miles calculations. After setting the Anchor Point of the null to -100, this expression will read the rotation value of the null and calculate the percentage of change in rotation based on the Y position of the null.
// Calculate latitude to miles
ref = thisComp.layer("Rotate Null");
r = ref.rotation;
laT = r.value.toFixed(3);
nFctr = [thisComp.with/2, thisComp.height/2][1];
yVal = ref.toWorld(anchorPoint)[1];
ofSt = yVal - nFctr;
f = ofSt/100;
miLs = 69.172 * f;
Add that calculation to a text layer/Text/Source text property, then add this code, and you get a mile at latitude calculator that is accurate to 2 decimal points.
// Create Text from calculations
if (miLs < 10)
sp = " ";
else
sp = "";
l = laT + "º " + value + " = ";
l + sp + miLs.toFixed(3) + " Miles"
That is accurate enough for my project.
I want to replace the first part of the expression with a few lines of code that would give me the same value for miles to degrees multiplier without looking at another layer's rotation property. I thought something as simple as a Math.tan(r) + something could turn the latitude into an accurate multiplier. There must be a math whiz out there that can figure it out.
Here's what I have so far:
I have also shared a project file if anyone is interested.
Thanks for the help.
Copy link to clipboard
Copied
I'm really out of my lane here, but it seems that if you assume a sphere, and the 69.172 is for the radius at the equator, then the value at other latitudes should be proportional to the radius of the circle at that latitude. So for 30 degrees latitude, say, I would think it would be:
laT = 30;
69.172*Math.sin(degreesToRadians(90-Math.abs(laT)))
Or did you already have that figured out?
Copy link to clipboard
Copied
Thank you, Dan Ebberts, the code is perfect. I kept missing the 90-Math.abs(). Tried a dozen other combinations.
I'll post the project when I get it finalized. Others might find this useful.