3

I want my application to know if the user is inside a particular area. I've been learning about geofences but I don't want the device to be constantly checking if it's entering or leaving an area, I just want to know if it's on it at that concrete moment. Plus, I've reading that geofencing has (it seems) low accuracy, and I need more than cellular tower precision.
So the idea is to do this using the "standard" kind of location, but I don't know how to, given a new current location, check if it's inside a (circular, rectangular, polygonal?) area.
It maybe has to be done using pure mathematics, checking if the altitude is between 2 parameters, and so for the longitude? Is there a simpler way?

Thanks!

David
  • 99
  • 2
  • 11

3 Answers3

1

Use CLLocations's distanceFromLocation

http://developer.apple.com/library/ios/#DOCUMENTATION/CoreLocation/Reference/CLLocation_Class/CLLocation/CLLocation.html

Josh Knauer
  • 1,744
  • 2
  • 17
  • 29
  • 1
    Ok, that would work for a circular area. What if I wanted to define a polygonal area? Basically, checking if the device is circulating through a path, or it's outside it (considering the path 10 meters wide, for example). Thanks for replying! – David May 16 '12 at 17:14
  • 1
    There's no built in stuff in iOS to determine if a point is inside a polygon. You can use basic "point in poly" algorithms with lat/lon coordinates, but because of the way that geographic projections work they are not reliable at larger scales. I've never used it, but ShapeKit http://github.com/mweisman/ShapeKit looks like it might do what you need. – Josh Knauer May 16 '12 at 17:35
  • I think I'll do it with `distanceFromLocation` and several if's&else's, so I'll be able to detect intersections. For my purpose, it should work fine. Thanks anyway for the help! :) – David May 16 '12 at 18:26
1

Here's my Swift code for Jordan Curve Theorem. Simply provide an array of CLLocationCoordinate2D which can make squares, polygons, anything really.

More in depth answer I translated this from: How can I determine whether a 2D Point is within a Polygon?

Original website: PNPOLY - Point Inclusion in Polygon Test W. Randolph Franklin (WRF)

extension CLLocationCoordinate2D {

    func liesInsideRegion(region:[CLLocationCoordinate2D]) -> Bool {

        var liesInside = false
        var i = 0
        var j = region.count-1

        while i < region.count {

            guard let iCoordinate = region[safe:i] else {break}
            guard let jCoordinate = region[safe:j] else {break}

            if (iCoordinate.latitude > self.latitude) != (jCoordinate.latitude > self.latitude) {
                if self.longitude < (iCoordinate.longitude - jCoordinate.longitude) * (self.latitude - iCoordinate.latitude) / (jCoordinate.latitude-iCoordinate.latitude) + iCoordinate.longitude {
                    liesInside = !liesInside
                    }
            }

            i += 1
            j = i+1
        }

        return liesInside
    }

}

Edit

Safe array item

extension MutableCollection {
    subscript (safe index: Index) -> Iterator.Element? {
        get {
            guard startIndex <= index && index < endIndex else { return nil }
            return self[index]
        }
        set(newValue) {
            guard startIndex <= index && index < endIndex else { print("Index out of range."); return }
            guard let newValue = newValue else { print("Cannot remove out of bounds items"); return }
            self[index] = newValue
        }
    }
}
Magoo
  • 2,552
  • 1
  • 23
  • 43
  • Thanks for the algorithm Swift translation, could you explain what is the meaning of the "safe" variable in your algorithm ? Do I have to set it to 0 ? – michael-martinez Feb 27 '19 at 23:07
  • Ah I made a wrapper for array so that it can return optional at index... let me add it for you – Magoo Feb 28 '19 at 07:15
  • Thanks a lot for the explanation ! – michael-martinez Feb 28 '19 at 11:24
  • Hi, @Magoo Thanks for the answer. I think this solution is for "Convex" not for "Not convex" polygons. Right? – Yuan Fu Mar 17 '20 at 01:20
  • I think Jordan Curve Theorm works for any... it works by checking how many times the x intersects .... https://www.maths.ed.ac.uk/~v1ranick/jordan/cr.pdf – Magoo Mar 19 '20 at 04:49
  • Potentially if mine doesn't work for concave polygons something is wrong. When I made it, it was for the regions of Australia, the poly data was relatively detailed and i'm sure some parts were concave when i tested the borders. – Magoo Mar 19 '20 at 04:50
0

If you're using Google Map SDK and want to check if a point is inside a polygon, you can try to use GMSGeometryContainsLocation. @Magoo 's answer works well if the polygon is not convex. But if it's concave, then the method from @Magoo didn't help.

if GMSGeometryContainsLocation(point, polygon, true) {
    print("Inside this polygon.")
} else {
    print("outside this polygon")
}

Here is the reference: https://developers.google.com/maps/documentation/ios-sdk/reference/group___geometry_utils#gaba958d3776d49213404af249419d0ffd

Yuan Fu
  • 310
  • 2
  • 14