How to get the radial distance to the boundary given a point in ITK? - itk

I'm loading a 3D CT model and doing thinning algorithms on it. Now I'd like to calculate how much thinning the algorithms do. How can I know the distances between skeleton points and their nearest/farthest boundary points?

Compute the distance transform of the skeleton points and boundary points (stored as a binary mask). Your answer lies therin.

Related

Plotting lineArcs with turf.js that don't match up with their surrounding geodesic strings

Background
We are supplied with some AIXM data (an XML based superset of GML) which describes polygon areas on a map as a mix of GeodesicStrings (a list of coordinates) and ArcByCentrePoints (a centre point coordinate with a radius, start bearing and end bearing). We are taking this data and converting it into a simple list of coordinates that we then display using a Google maps polyline.
Problem
When we plot a shape with an arc, the start and end points of the arc usually don't match up with the end point of the preceding line and the start point of the subsequent line. It looks as if the radial distance is out by an amount which doesn't appear to be proportional to the radius. See screenshot: interestingly the smaller arc at the top seems fine but the larger arc is inset.
We're pretty sure the data is correct because it looks fine when we use a third party tool to visualise it, so we're doing something wrong.
Implementation
We are using the turf.js library to convert the arc description into a set of points using their lineArc function. Internally this utilises their destination function which "uses the Haversine formula to account for global curvature". We combine these generated points, in the correct sequence, with the points taken directly from the preceding and subsequent GeodesicString elements to give us our final polygon.
Data
Input: Fragment of AIXM (GML) describing polygon
Output: Resulting list of points
Help!
I'm aware this question is light on code but I hope I've described the problem adequately and that some kind person with more GIS knowledge than me (>0) might be able to point me in the right direction. Thanks :)
I've given a couple of presentations on debugging and one of the things I say is that you should keep an open mind and shouldn't get too fixated on a possible cause of a bug because you can waste a lot of time tracking down a false lead.
Sadly in this case I didn't take my own advice. I was so obsessed with the idea that the problem arose from a complex cause, such as issues with the implementation of the Haversine formula, that I overlooked the far simpler answer. My code was taking a string representation of the radius, including the units (e.g. nautical miles or meters) and converting it into kilometres. Sadly I was using parseInt rather than parseFloat as part of this and so instantly losing precision. It was a simple as that - a schoolboy error.
Big thanks to Stefano Borghi, a maintainer of Turf JS, for all his help with this and for helping me see the wood for the trees.

grid of 10km * 10 km from centroids

I have a point layer which are the centroids of each cell of a grid. Each cells is of 10km per 10 km. How can I recreate this grid from the centroids and the cell size?
I have to say that I am a newbie in gis things.
Thanks
Have a look at this question - you're effectively asking for what Matthew didn't want, which is the simpler version. Make a circular buffer around each centroid, and convert that to a square with Feature Envelope to Polygon. (or possibly Minimum Bounding Geometry, depending on your licence level)
For the record, this kind of question is better suited to GIS.SE, since it's not technically a programming question.

Calculate 3D coordinates from 2D Image plane accounting for perspective without direct access to view/projection matrix

First time asking a question on the stack exchange, hopefully this is the right place.
I can't seem to develop a close enough approximation algorithm for my situation as I'm not exactly the best in terms of 3D math.
I have a 3d environment in which I can access the position and rotation of any object, including my camera, as well as run trace lines from any two points to get distances between a point and a point of collision. I also have my camera's field of view. I do not have any form of access to the world/view/projection matrices however.
I also have a collection of 2d images that are basically a set of screenshots of the 3d environment from the camera, each collection is from the same point and angle and the average set is taken at about an average of a 60 degree angle down from the horizon.
I have been able to get to the point of using "registration point entities" that can be placed in the 3d world that represent the corners of the 2d image, and then when a point is picked on the 2d image it is read as a coordinate with range 0-1, which is then interpolated between the 3d positions of the registration points. This seems to work well, but only if the image is a perfect top down angle. When the camera is tilted and another dimension of perspective is introduced, the results become more grossly inaccurate as there no compensation for this perspective.
I don't need to be able to calculate the height of a point, say a window on a sky scraper, but at least the coordinate at the base of the image plane, or which if I extend a line out from my image from a specified image space point I need at least the point that the line will intersect with the ground if there was nothing in the way.
All of the material I found about this says to just deproject the point using the world/view/projection matrices, which I find straightforward in itself except I don't have access to these matrices, just data I can collect at screenshot time and other algorithms use complex maths I simply don't grasp yet.
One end goal of this would be able to place markers in the 3d environment where a user clicks in the image, while not being able to run a simple deprojection from the user's view.
Any help would be appreciated, thanks.
Edit: Herp derp, while my implementation for doing so is a bit odd due to the limitations of my situation, the solution essentially boiled down to ananthonline's answer about simply recalculating the view/projection matrices.
Between position, rotation and FOV of the camera, could you not calculate the View/Projection matrices of the camera (songho.ca/opengl/gl_projectionmatrix.html) - thus allowing you to unproject known 3D points?

Radius of multiple latitude/longitude points

I have a program that takes as input an array of lat/long points. I need to perform a check on that array to ensure that all of the points are within a certain radius. So, for example, the maximum radius I will allow is 100 miles. Given an array of lat/long (coming from a MySQL database, could be 10 points could be 10000) I need to figure out if they will all fit in a circle with radius of 100 miles.
Kinda stumped on how to approach this. Any help would be greatly appreciated.
Find the smallest circle containing all points, and compare its radius to 100.
It's easiest way for me to solve this is by converting the coordinates to (X,Y,Z), then finding the distance along a sphere.
Assuming Earth is a sphere (totally untrue) with radius R...
X = R * cos(long) * cos(lat)
Y = R * sin(long) * cos(lat)
Z = R * sin(lat)
At this point, you can approximate the distance between the points using the extension of the pythagorean theorem for threespace:
dist = sqrt((x1-x2)^2 + (y1-y2)^2 + (z1-z2)^2)
But to find the actual distance along the surface, you're going to need to know the angle subtended by the two points from the origin (center of the Earth).
Representing your locations as vectors V1 = (X1, Y1, Z1) and V2 = (X2, Y2, Z2), the angle is:
angle = arcsin((V1 x V2) / (|V1||V2|)), where x is the cross-product.
The distance is then:
dist = (Earth's circumference) * angle / (2 * pi)
Of course, this doesn't take into account changes in elevation or the fact that the Earth is wider at the equator.
Apologies for not writing my math in LaTeX.
The answer below involves pretending that the earth is a perfect sphere, which should give a more accurate answer than treating the earth as a flat plane.
To figure out the radius of a set of lat/lon points, you must first ensure that your set of points is "hemispherical", ie. all the points can fit into some arbitrary half of your perfect sphere.
Check out Section 3 in the paper "Optimal algorithms for some proximity problems on the Gaussian sphere with applications" by Gupta and Saluja. I don't have a specific link, but I believe that you can find a copy online for free. This paper is not sufficient to implement a solution. You'll also need Appendix 1 in "Approximating Centroids for the Maximum Intersection of Spherical Polygons" by Ha and Yoo.
I wouldn't use Megiddo's algorithm for doing the linear programming part of the hemisphericity testing. Instead, use Seidel's algorithm for solving Linear Programming problems, described in "Small-Dimensional Linear Programming and Convex Hulls Made Easy" by Raimund Seidel. Also see "Seidel’s Randomized Linear Programming Algorithm" by Kurt Mehlhorn and Section 9.4 from "Real-Time Collision Detection" by Christer Ericson.
Once you have determined that your points are hemispherical, move on to Section 4 of the paper by Gupta and Saluja. This part shows how to actually get the "smallest enclosing circle" for the points.
To do the required quadratic programming, see the paper "A Randomized Algorithm for Solving Quadratic Programs" by N.D. Botkin. This tutorial is helpful, but the paper uses (1/2)x^T G x - g^T x and the web tutorial uses (1/2)x^T H x + c^T x. One adds the terms and the other subtracts, leading to sign-related problems. Also see this example 2D QP problem. A hint: if you're using C++, the Eigen library is very good.
This method is a little more complicated than some of the 2D methods above, but it should give you more accurate results than just ignoring the curvature of the earth completely. This method also has O(n) time complexity, which is likely asymptotically optimal.
Note: The method described above may not handle duplicate data well, so you may want to check for duplicate lat/lon points before finding the smallest enclosing circle.
Check out the answers to this question. It gives a way to measure the distance between any two (lat,long) points. Then use a smallest enclosing circle algorithm.
I suspect that finding a smallest enclosing circle may be difficult enough on a plane, so to eliminate the subtleties of working with latitude and longitude and spherical geometry, you should probably consider mapping your points to the XY plane. That will introduce some amount of distortion, but if your intended scale is 100 miles you can probably live with that. Once you have a circle and its center on the XY plane, you can always map back to the terrestial sphere and re-check your distances.

How do I find the center of a number of geographic points?

If I have a series of points as longitude and latitude, how would I calculate the center of all of those points?
Geomidpoint covers 3 different methods for calculating this.
Several people have answered to take the mean of the latitudes and longitudes. This is sort of the right idea, but means are more complicated on the sphere.
The latitude/longitude representation is essentially artificial and has discontinuities (at the poles, and opposite the prime meridian if you aren't careful), so it taking means in it doesn't seem likely (to me) to have a sensible geometric interpretation. I think you need to do something like averaging vectors in earth-centered coordinates, and then normalizing the result to put it back on the sphere.
I hope someone with more experience in these matters can comment more concretely.
Don't just take averages.
You can convert to 3d coordinates, then take the average (of x,y, and z coords), then project it back onto the sphere and turn that back into lat/long.
The wikipedia page on spherical coordinates has conversion algorithms.
First off, you need to define which centre you're interested in. Take these two points:
A. .B
The centre is easy, it's halfway between them. Now add a third point:
A. C. .B
Is the centre still halfway between A and B or is it weighted towards A because of C? So is the centre the point nearest to all points or just the points on the enclosing polygon?
Also, as it's long/lat you're dealing with the points are on a surface of a sphere so the distance between long 0 and long 90 degrees is much greater at lat 0 than at lat 45 degrees.
You're probably looking for the centroid of the simple polygon defined by the points. There is information on how to calculate it for various geometries in that article.
Wolfram Alpha will do this for you if you ask the question in the following form:
centroid of polygon with vertices: (X, Y), (X, Y), (X, Y), (X, Y), (X, Y), etc.
Just remember to convert each "(X, Y)" into decimal form first.
Wolfram Alpha will return the answer in decimal form, which you can then copy and paste into Google Earth.
See Moe's answer, although if your points are distributed across the globe, you'll have to be satisfied that your center tends towards the Prime Meridian and not the International Date Line.