Jake O'Toole Jake O'Toole - 1 month ago 26
iOS Question

Display information in UITableView from Firebase based on location Swift




I am building an app in Swift and I have a quick question.

When the user enters a certain location, (e.g. shop) I want it to display a list of items saved in Firebase Database in a UITableView (can vary in different locations).

I've done a bit of location stuff in Swift before but nothing like this.

Help would be much appreciated!

Thanks so much,
Jake.




{
"venues" : {
"CrokePark" : {
"beverages" : {
"drink1" : "Coca-Cola",
"drink2" : "Fanta",
"drink3" : "Dr. Pepper"
},
"orders" : {
"Fanta" : {
"addedByUser" : "test2@test.com",
"completed" : false,
"name" : "Aaron"
},
"Coca-Cola" : {
"addedByUser" : "test@test.com",
"completed" : false,
"name" : "Jake"
}
}
}
}
}

Answer

In order to achieve what you're looking for, you'd generally want to have the exact location i.e. (latitude, longitude), of the cafe stored in your database. So your venue structure would look as such

"venues" : {
"CrokePark" : {
  "latitude": 37.335556, // this is a double
  "longitude": -122.009167 // this is a double
  "beverages" : {
    "drink1" : "Coca-Cola",
    "drink2" : "Fanta",
    "drink3" : "Dr. Pepper"
  }

With the location you have to worry of retrieval at this point. Generally speaking, you'd want to notify the user when they are a certain radius; r, from the venue. Two methods come in mind

Lousy Battery Draining Method

Always get an update of their current location, query the database to see if their current location is within r. If yes, notify them then stop getting their location and querying Firebase.

This method is the easiest to implement but you sincerely have got to have a serious issue with your users should you opt for it.

Slightly Improved

  1. Make a SINGLE query for the user's current location. Let's call this let currentLocation = CLLocation2D()
  2. Make a SINGLE query to Firebase checking for all locations possibly within r; you can even tell FrB to sort them for you, then cache the results. Because of memory limitations you may limit the number of results to say 10. The point is to avoid keeping all the Firebase data in memory at once especially if its going to be massive. Let's call this let possibleDestinations = []
  3. Start a timer. This is dependent on whether your user is on foot or not. If on foot then a 5-10 minute timer is pretty reasonable. If not then you might want a 1-3 minute timer instead.
  4. When timer == expired roll back to Step 1
    • Is currentLocation equal or close to any address in possibleDestinations
      1. If yes; then our user is definitely headed towards one of the addresses we already have, then timer.invalidate() and present the info of the venue from possibleDestinations
      2. If no; probably the user has switched their course, then repeat from Step 2

Obviously the second method is more complex than the first one but its more user-friendly; in terms of battery consumption, and efficient.

Side Note:

  1. I made the latitude and longitude nodes store Double respectively so as you can simply pass them into the CLLocationDegrees constructor. More info

  2. Since you seem to be relatively new to the Core Location API, I'd recommend you create a side project first and learn how to perform geo-fencing before integrating it into your application. Current Location Tutorial. Geofencing Tutorial.