Adding Navigation
Start course
3h 18m

In this course, we're going to build a Foursquare Clone using Parse. Parse provides you with a great tool to work in cloud servers and you will learn the advantages and disadvantages that come with it.

Intended Audience

This course is designed for anyone who wants to:

  • Learn about iOS development and coding
  • Move into a career as an iOS developer
  • Master Swift skills


To get the most out of this course, you should have some basic knowledge of iOS.


Hi, within this lecture we're going to add a navigation by using the detailDisclosure button in our annotation, and we know how to do that from the Travel Book app. Remember what we have to do?

We have to call for view for annotation to customize our annotations. But as you can see, we cannot call view for annotation right now because we haven't made our details ViewController a delegate of our MapView, right? So, let's do that, let's come over here and let's say that MKMapView. This one MapViewDelegate. And remember we used to say, CLLocationmanagerDelegate as well, but I believe in our case we're not going to use this because we're not getting the user location at this point. So, afterwards if we need this, we may have to add it later on, but right now I just need this details.MapView.delegate itself.

Once I do that I can come down and I can call for view for annotation. So, let's call for view for a notation. Here we go we are looking for this function, and in here we're going to check to see we're going to actually customize the annotations that we have, but I don't want to deal with location annotations of the currentUser. So, remember how we do that, we actually begin to check to see if annotation, this one, okay, this annotation is MKUserLocation annotation. So, I'm going to return nil if that's the case. And later on I'm going to create an annotation and remember how we do that. This is giving us an error because it expects us to return an annotation which we will later on. I'm going to create this annotation and I'm going to call this pinView, aand this will be mapView.dequeue.ReusableAnnotationView, and this will ask us to give an identifier. And actually we're going to use this identifier more than one time. So, I'm going to create a reuse ID here call it pin and give this reuse ideas an identifier. And then I'm going to check to see if this pinView is nil or not. If it's nil then we're going to give it some annotation to it, we're going to create our annotation here for real. So, this will be an MKpinPointAnnotationView. This will ask us to give it an annotation and an identifier, the annotation is this one, and the identifier is the identifier that we have created. So, give it some reuse ID. And then later on we have to say pinView.canShowCall out. So, this means that we can actually show the button that we're about to show on the right hand side. So, if we don't do that even though we added it won't display it. So, let me create that button that we have been talking about. So, the type of this button will be disclosure, detailDisclosure. Okay, so it will display something with I like in an information button, okay? And we're going to add this to be a rightCalloutAccessoryView to our pinView, okay? So, that it will display the button in the rightCalloutAccessory, else if pin is actually not nil then pinView annotation is the annotation that is given to me. So, that's it, I'm referring to this annotation by the way. I'm going to return this pinView so that I have my customized annotation. So, if you haven't watched the map section, I believe you should go and watch for a refresher because I'm explaining everything in details in that section. And again I'm going to call for accessory control tapped and this specifies what will happen once we click on that button over here. We have created that button, remember? So, this defines what will happen whether you use that tabs on that button. So, what we want to happen is to open a navigation actually. And in order to open that navigation, remember we need something called placeMarks. And in order to get that placeMarks object we need to have a reverse geolocation operation. And in order all of this thing to happen we have to create a location to begin with. So, under this callout accessory control tapped function we're going to control, we're going to actually create a location first. So, we have our chosen latitude and longitude here, right? So, I'm going to check to see if self.chosenLongitude is not 0.0. So, we have some values and if self.chosenLatitude again is not 0.0. So, I can come over here and I can create a location, and at this point it doesn't make sense to have this value 0.0, but again, to be on the safe side, I believe we can just do it. After we check this, I'm going to create this requestLocation, okay?

So, this request location will be a CLLocation. So, this is not a CLLocationCoordinates2D and you will see why in a minute, and again this will ask us to give some latitude and longitude, so this will be chosenLatitude and this will be chosenLongitude, okay? And after we give this, after we create this requestLocation, then we're going to use this CLGeocoder that I was talking about. So, this actually converts placeNames to coordinates or vice versa. So, I'm going to do a reverse GeocodeLocation this one, and this should in fact ask before a requestLocation, a CLLocation, and I cannot see it right now because, I misspelled it. I have to add this parenthesis over here and say a reverseGeocodeLocation here this one. As you can see it asks us to create a CLLocation and it gives us a completion handler. So, that's the one I want, let me give request location and hit 'Enter.' Here you go, we have our placemark array. So, let's call this placemarks an error. So, I'm going to cast my placemarks array as a placemark variable so that I will make it not optional by doing that. So, after that I'm going to check to see if placemark.count is actually greater than zero, meaning that I have something inside my array so that I can create my MKPlaceMark object. So, this will be MKPlaceMark, okay? So, this is a description of the chosen location, it will ask me for a placemark. So, this one and I'm going to get this from placemark zero. So, first element of my placemark object, and then I need a MapItem because that's what we need to open in navigations and it will drive from, it will be coming from this mkPlaceMark and this one, that mkPlaceMark that I have created. Later on I'm just going to use this mapItem and we can give it a name if we want to display in the navigation as well and we can get this name from our detailsNameLabel, right? So, detailsNameLabel.text so that we can see the name in the navigation as well. And actually now I can just come over here and say mapItem.openInMaps, but it will ask us to give some specific launch options, let's take care of that as well. Let's create launch options. So, first we have to give some key and the key is MKLaunchOptionsDirectionsModeKey, and the value that I'm looking for is ModeD riving, so MKLaunchOptionsDirectionsModeDriving, so this will by default show me how to get there by car. So, let me give these launch options and let me try this. So, let us surround this in our simulator, okay? And let us try to go to James restaurant, and if I click on here you will see the disclosure button. This is the detailDisclosure button as you can see. Now if I tapped on this, if I tap on this actually, this will get called callout accessory control tapped, and it will bring me into a navigation in which I will get my current location to the destination location navigation. So, this is showing drive by default and here you go, that's all we wanted. Again we are using MapItem to open in maps, so and we're checking to see if the location is not empty and we're creating a requestLocation because this will ask us to give us some MKMapItem, and in this MKMapItem we need some placemarks and in order to get this placemarks we have to create this placemarks array. And in order to create this placemarks array, we have to have this reverse Geocode location. And in order to have this requestLocation, we have to make sure this latitude and longitude is not empty. That's why we are doing all of this. Now, I believe we are okay right now. We can go ahead and test to see if our app is really working by adding new places.


About the Author
Learning Paths

Atil is an instructor at Bogazici University, where he graduated back in 2010. He is also co-founder of Academy Club, which provides training, and Pera Games, which operates in the mobile gaming industry.

Covered Topics