Point() support more spatial reference systems?


(Snellad1) #1

Hi,

I'd like to import and process spatial survey data in NAD83, WGS84, and NAD27 coordinate reference systems.

In the US, geo related surveys use NAD83, and used to use NAD27, as it provides static positioning with respect to the continent that does not change with tectonic plate activity. Over time, WGS84 and NAD83 diverge, by a few centimeters per year.

Further, I also have a requirement to process coordinates in US State Plane coordinate system [Northing, Easting, Zone] using NAD83.

The survey data I have has centimeter precision, reported in US State Plane NAD83 (GRS 80 Ellipsoid). I'd like to calculate positional differences (in millimeters or meters), display lat / lons in Google Maps, convert between NAD83 and WGS84.

This is a good Reference for State Plane conversions: http://www.earthpoint.us/StatePlane.aspx

Any advice on how to implement this would be greatly appreciated.

Maybe can I ask that point() function supports additional SRIDs?


(Craig Taverner) #2

The current support for WGS84 and Cartesian should be interpreted as meaning 'geographic' and 'cartesian', which also means that you could, for example, place data for any other geographic CRS into WGS84 points, and for any projected CRS into Cartesian points. This is only possible because we currently have no support for conversion between CRS, and so the differences between the two will not matter as long as all points claiming to be WGS84 are in only one geographic coordinate system. This, of course, can lead to future problems if we add support for conversions and all your data is now claiming (falsely) to be in WGS84, and errors will be introduced by any attempt to convert it to some other CRS.

We would like to introduce more CRS in future, but it is not yet clear when such support will be added.

Also, since you are interested in high accuracy, it should be noted that the current calculation for distances in WGS84 is not very accurate. As described in the documentation at https://neo4j.com/docs/developer-manual/current/cypher/functions/spatial/#functions-distance, we use a spherical approximation for the distance function. This is likely to be improved in the future to use the correct ellipsoid. But for now you might need to evaluate whether you feel the built-in distance function is accurate enough for your case.

There are ways for you to work around both the CRS and distance function issues. You could add additional properties to nodes that have your points, clarifying the real CRS, and write your own distance function that uses the correct ellipsoid. Your function could also deal with points from different CRS, by looking at the two points additional properties and adjusting the calculation accordingly. If you take this route, and Neo4j supports additional CRS and improved distance functions in future, you could refactor your data to port all points into the correct CRS at that time.


(Snellad1) #3

Thanks @craig.taverner. I'll implement your last suggestion and refactor to native Neo4j functions if/when they become supported.

NAD83(2011), NAD27, and WGS84 CRS support in Neo4j would be very useful.
Additionally, support for the following coordinate types would also be very useful: LLH (Lat/Lon/Height), SPC (State Plane Coordinates), and UTM (Universal Transverse Mercator Coordinates).

Thank you.


(Craig Taverner) #4

Hi @snellad1. Thanks for the feedback. I would like to know a bit more about what you would like to see with additional CRS support. While it would be relatively simple to simply add more CRS as legal attributes to the Point objects, the only real impact this will have on behaviour is that points of different CRS will no longer be indexed in the same space filling curve, and will therefor become incomparable. So, for example, if you define an MBR using min and max corner points in WGS84, and then search for all points in that MBR, only WGS84 points will be returned, never any NAD83 or other. This is because the Cypher predicate for MBR (or for distance) is also a type predicate. Another way of seeing this is that two points in different CRS are considered to be of different types, and cannot be compared. Mostly this is desirable behaviour.

So I was wondering if your request for more CRS implied a number of additional functions as well, like explicit conversions between different CRS? So, for example, if you wanted to find all NAD83 points within an MBR defined in WGS84, you could type WHERE toCRS(min,'nad83') < n.location < toCRS(max,'nad83')? The toCRS function would be entirely new, and also require that Neo4j not only save the CRS id to the points, but actually know a lot more about all CRS supported than it knows today in order to be able to perform the conversions.