Turfjs / turf

A modular geospatial engine written in JavaScript and TypeScript
https://turfjs.org/
MIT License
9.35k stars 941 forks source link

area for large polygons near poles #1558

Open rob4acre opened 5 years ago

rob4acre commented 5 years ago

I created a geojson polygon which extends over an 8th of the Earth's surface (I think).

https://gist.github.com/rob4acre/725d7b05c266cb429e1e5a1515232a4a

I then used the area module on this to compute the area. I got the result

31950493337238.19 m2 = 31950493.33723819 km2

The area of the Earth's surface should be 510064471.91 km2 , an eighth of this (which is what i think my polygon is) is 63758058.98875 km2

The area computed with the area module is not the same as my calculated value above, in fact it's half. I don't think it's my math that's the problem, but apologies in advance if this is the case!

Rob

stebogit commented 5 years ago

@rob4acre your polygon represents a triangle on the map, so a 16th of the surface of the flat (Mercator) map:

screen shot 2018-12-20 at 11 44 33 pm

@turf/area looks like projects the feature onto the spherical surface first (see notes). In fact (good to know) if you calculate the area of the full 8th of the map (the full rectangle) it will return a number similar to what you expected:

var p = turf.polygon([ [[0, 0], [0, 90], [90, 90], [90, 0], [0, 0]] ]);
var a = turf.area(p); // 63900986674476.38 (m2)

Does that make sense? 🤔

rob4acre commented 5 years ago

@stebogit I chose this simple wedge as it was easy to calculate the area manually.

After reading the notes, it seems like the area is calculated geodesically (is that a word) so perhaps this is an edge case. It might be good to put the notes into the documentation for the module.

Also, a colleague pointed out that some modules in turf do seem to use spherical geometry and mention this in the docs, namely midpoint

Takes two points and returns a point midway between them. The midpoint is calculated geodesically, meaning the curvature of the earth is taken into account.

rob4acre commented 5 years ago

@stebogit If you do

var p = turf.polygon([ [[0, 0], [0, 89.99], [90, 0], [0, 0]] ]);
var a = turf.area(p); // 31945627122347.24 (m2)

This suggests that its not the coordinate at the pole that is causing a problem...

morganherlocker commented 5 years ago

Also, a colleague pointed out that some modules in turf do seem to use spherical geometry and mention this in the docs, namely midpoint

We do use geodesic calculations where possible. Many algorithms are considerably harder to implement with full geodesic accuracy, so this is not entirely consistent. Documenting this per function is a good idea. That said, there could also be a bug here, which will need investigation.