Mostafa Mohamed Raafat Mostafa Mohamed Raafat - 1 year ago 823
Swift Question

How to implement auto-complete for address using Apple Map Kit

I want to auto-complete the address for the user as same as what google api provides in this link:

How can i implement the same functionality using apple map kit?

I have tried to use the Geo Coder, i wrote this for example:

@IBAction func SubmitGeoCode(sender: AnyObject) {

let address = "1 Mart"

let coder = CLGeocoder()

coder.geocodeAddressString(address) { (placemarks, error) -> Void in

for placemark in placemarks!{

let lines = placemark.addressDictionary?["FormattedAddressLines"] as? [String]

for addressline in lines!



However the results are very dissapointing.

Any Apple APIs available to implement such functionality, or should i head for google api ?

Thank you

Answer Source

In iOS 9.3 a new class called MKLocalSearchCompleter was introduced, this allows the creation of an autocomplete solution, you simply pass in the queryFragment as below:

var searchCompleter = MKLocalSearchCompleter()
searchCompleter.delegate = self
var searchResults = [MKLocalSearchCompletion]()

searchCompleter.queryFragment = searchField.text!

Then handle the results of the query using the MKLocalSearchCompleterDelegate:

extension SearchViewController: MKLocalSearchCompleterDelegate {

    func completerDidUpdateResults(completer: MKLocalSearchCompleter) {
        searchResults = completer.results

    func completer(completer: MKLocalSearchCompleter, didFailWithError error: NSError) {
        // handle error

And display the address results in an appropriate format:

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
    let searchResult = searchResults[indexPath.row]
    let cell = UITableViewCell(style: .Subtitle, reuseIdentifier: nil)
    cell.textLabel?.text = searchResult.title
    cell.detailTextLabel?.text = searchResult.subtitle
    return cell

You can then use a MKLocalCompletion object to instantiate a MKLocalSearchRequest, thus gaining access to the MKPlacemark and all other useful data:

let searchRequest = MKLocalSearchRequest(completion: completion!)
let search = MKLocalSearch(request: searchRequest)
search.startWithCompletionHandler { (response, error) in
    let coordinate = response?.mapItems[0].placemark.coordinate