© Jeffrey Linwood 2020
J. LinwoodBuild Location Apps on iOS with Swifthttps://doi.org/10.1007/978-1-4842-6083-8_7

7. Displaying a Map with the Google Maps SDK

Jeffrey Linwood1 
(1)
Austin, TX, USA
 

Apple’s MapKit framework isn’t the only solution for mapping applications on iOS. Other providers offer mapping and routing technologies, including Google, Mapbox, Bing Maps by Microsoft, and ESRI’s ArcGIS. In this chapter, as well as the following chapters, we are going to work with the Google Maps SDK for iOS. For applications on multiple platforms, you can use Google Maps on the Web, Android, and iOS. This can provide consistency across your application. You may also want to use imagery from Google in your map or use Google’s driving directions or place information.

This chapter contains all of the steps needed to work with Google Maps in an iOS app. The following chapters will build on the project we create in this chapter.

Using the Google Maps Platform

Working with the Google Maps SDK is similar to working with Apple’s MapKit framework, but there are a few differences. The first difference is that you will need to sign up with the Google Maps Platform. The second is that you will need to download the Google Maps library and integrate it into your Xcode project.

Find out more about the Google Maps Platform at https://cloud.google.com/maps-platform/.

Google Maps has pricing and billing associated with its features, unlike Apple’s Maps. At the time of writing (early 2020), Google offers $200/month (USD) of free credits for each user across Maps, Routes, and Places. In addition, at the time of writing, displaying maps inside a mobile application is free. These pricing offers could change at any time or be different outside the United States, so please check the pricing before signing up for the service.

Installing the Google Maps SDK for iOS library

Create a new iOS project in Xcode, named GoogleMapsApp, as a Single View Application with storyboards and Swift – similar to our other projects so far.

Google Maps for iOS has two different paths for installation. One way is to do a manual installation, following the step-by-step directions on the Google Maps installation page (https://developers.google.com/maps/documentation/ios-sdk/start#step_2_install_the_sdk). This is fairly involved and probably only worthwhile if you cannot use the second path, which uses the CocoaPods dependency manager.

CocoaPods is a dependency manager for iOS applications, similar to Homebrew for the Mac or Node Package Manager (NPM) for JavaScript. Instead of downloading libraries into your Xcode project and adding them manually, CocoaPods lets you declare which libraries your application uses, along with the versions, and then downloads and installs those libraries for you. This makes it much easier to upgrade frameworks and will help avoid issues where some libraries are incompatible with each other.

If you don’t have CocoaPods installed on your system, it is distributed as a Ruby gem. You will need to install CocoaPods onto your Mac with this command:
sudo gem install cocoapods

Next, use the command line to navigate to the directory that contains your new Xcode project.

In that directory, type the following command to create a CocoaPods Podfile. Podfiles contain the dependencies for your project:
pod init
Now look in that directory, and view the Podfile that pod init just created. It should look something similar to Listing 7-1.
# Uncomment the next line to define a global platform for your project
# platform :ios, '9.0'
target 'GoogleMapsApp' do
  # Comment the next line if you don't want to use dynamic frameworks
  use_frameworks!
  # Pods for GoogleMapsApp
end
Listing 7-1

New CocoaPods Podfile for the Google Maps App

So far, none of this has anything to do with Google Maps yet. We are going to add the GoogleMaps library as a dependency to our Podfile. Underneath the # Pods for GoogleMapsApp line, add the GoogleMaps pod. With the addition, your Podfile file should look like Listing 7-2.
target 'GoogleMapsApp' do
  # Comment the next line if you don't want to use dynamic frameworks
  use_frameworks!
  # Pods for GoogleMapsApp
  pod 'GoogleMaps'
end
Listing 7-2

CocoaPods Podfile with the GoogleMaps dependency

Now that the dependency is in place, CocoaPods can download the latest version of the Google Maps SDK for us and set it up in our iOS application.

Run the following command from the command line in the same directory that you ran pod init:
pod install

CocoaPods will install the GoogleMaps dependency, and it will also create an Xcode workspace for your application. This workspace will contain two targets – one for your application and one for the downloaded dependencies (called pods). You will need to open GoogleMapsApp.xcworkspace now, not GoogleMapsApp.xcodeproj, to build your application.

With CocoaPods you can pin the version of Google Maps to a specific version (at the time of writing, 3.7.0), using semantic versioning. See the CocoaPods documentation at https://cocoapods.org/ for more on how to use CocoaPods and Podfiles.

Go ahead and open the workspace in Xcode. Try running the iOS application (GoogleMapsApp) on the Simulator or on your device. You will not see anything but a blank white screen, but if there are any compilation errors or other issues, this is a good time to debug them. For the next step, we will set up the Google Maps API Key, so that we can start to use Google’s Maps, Routing, and Places services.

Setting up a Google Maps API Key

Before we go any further, you will need a Google Maps API Key. Sign up at https://cloud.google.com/maps-platform.

When you enable the Google Maps Platform, check off the box for Maps, as shown in Figure 7-1.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig1_HTML.jpg
Figure 7-1

Enable the Google Maps Platform and select a product

Click CONTINUE. On the next screen (Figure 7-2), create a new project named First Maps Project.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig2_HTML.jpg
Figure 7-2

Create a new project for Google Cloud

You will also need to set up a billing account for Google Maps, along with a credit card that Google can charge for usage over the free quota.

After that process, Google will ask if you want to enable the Google Maps Platform for your new project, as shown in Figure 7-3. Go ahead and click NEXT.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig3_HTML.jpg
Figure 7-3

Enable Google Maps Platform APIs

You will want to enable the Maps SDK for iOS – other platforms and services are available through the same interface.

If you are having trouble getting an API Key for the Maps SDK, there are alternative directions on Google’s website: https://developers.google.com/maps/documentation/ios-sdk/get-api-key.

Last, you will want to create an API key. Under the APIs section of the web interface, find Maps SDK for iOS. Select the Credentials tab, and then click the link for Credentials in APIs & Services. On that screen, select the CREATE CREDENTIALS button, as shown in Figure 7-4, and then choose API key from the drop-down menu that appears.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig4_HTML.jpg
Figure 7-4

Create Credentials for Google Maps Project

The portal will create a new API Key for you, as seen in Figure 7-5. You will have access to this key in the future, so you do not need to save it right away. What you do need to do is to restrict usage of this key to just your application. This will keep others from using your API key in their projects, which would affect your billing.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig5_HTML.jpg
Figure 7-5

The Google Maps API Key creation dialog box

Choose the RESTRICT KEY button on the dialog box in Figure 7-5. The Restrictions page appears (Figure 7-6), with several selections to choose from. Restrict this key to iOS apps. Add an iOS bundle identifier for your application. For this project, the bundle identifier would be com.buildingmobileapps.GoogleMapsApp. Your bundle identifier may be different based on your organization.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig6_HTML.jpg
Figure 7-6

Restrict the use of a Google Maps API Key

Be sure to press the DONE button after adding your bundle identifier and then the Save button to persist your changes. After saving, you should see that restriction appear next to your iOS key, as in Figure 7-7.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig7_HTML.jpg
Figure 7-7

Restricted iOS Maps Key

Now that you have created an API key, you have restricted its use to your iOS app, and you have the Google Maps library integrated with your project, the next step is to provide the API key inside your iOS application.

Including the API Key in your application

Before you use any Google Maps services (such as Maps, Routing, or Places), you need to register your API Key with the Google Maps SDK. If you do not do this, your application will receive a runtime error from the SDK.

The easiest way to make sure that Google Maps always has the API key before using any services is to provide the API Key in the application(_ didFinishLaunchingWithOptions:) method in AppDelegate.swift, as shown in Listing 7-3. You will need to import the GoogleMaps framework and make a call to GMSServices.provideAPIKey(). What follows is a code listing for AppDelegate.swift with the required changes. Replace API-KEY with the API Key you created in the Google Cloud Console.
import UIKit
import GoogleMaps
@UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
        // Override point for customization after application launch.
        GMSServices.provideAPIKey("API-KEY")
        return true
    }
}
Listing 7-3

Partial version of AppDelegate.swift with Maps API Key

Now that you have an API key in place, it’s time to move on to the fun part – displaying Google Maps within your app!

Displaying Google Maps with a map view

There are a couple of different ways we can add a map view (GMSMapView) to our iOS application. We can add it as a subview programmatically, we can add it to the storyboard as a UIView, and then change the custom class, or we can replace the view of the view controller with a map.

Displaying the map view on the storyboard is the easiest way. Simply drag a UIView onto the storyboard, and then change the custom class to be GMSMapView, as shown in Figure 7-8.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig8_HTML.jpg
Figure 7-8

Adding the Google map view to a storyboard

Add constraints to the map view that it stretches from edge to edge (don’t worry about the safe areas unless you want to). Now run the application in the Simulator – you should see a map like Figure 7-9 show up in your app!
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig9_HTML.jpg
Figure 7-9

Basic Google Maps running in the Simulator

Now, there is one final step for you to make this mapping application complete. Clicking or tapping the Google logo in the bottom left corner of the map needs to open up the Google Maps iOS app or the Google Chrome browser for iOS, if they are loaded onto the phone. If the end user doesn’t have them, it will open up in Safari. We will need to allow our app to query for the proper URL schemes.

Allowing the Google Maps and Chrome URL schemes

The Google Maps SDK for iOS will attempt to open up either the Google Maps app or the Google Chrome app after someone taps on the Google logo in the lower left-hand corner of the map. The SDK will check to see if those apps are installed on the user’s phone before opening them. The fallback is to open up the URL in Safari.

The first versions of iOS let any application check to see if any other application was installed on the phone. Unfortunately, this capability was abused, so Apple restricted the use of this permission. Any application bundle identifiers that you would like to check need to be specifically declared in the Info.plist file.

Add a row to the Info.plist. The key will be LSApplicationQueriesSchemes. There is not a corresponding entry in the drop-down that appears, so you will need to type the name in exactly. Change the type from String to Array. Now you can add any URL schemes that the app is going to query to the array. Here are the two for Google Maps and Google Chrome:
  • comgooglemaps

  • googlechromes

Your completed Info.plist file should look something similar to Figure 7-10.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig10_HTML.jpg
Figure 7-10

The Info.plist file with the required URL query schemes

Now that all of the required information is set up, we can move on to changing the way the map view displays information.

Changing display options on the map view

If we want to change display options on the map view, we will need to do so from code. Using the Assistant view in Xcode, create an outlet on your ViewController class for the Google map view, and name it mapView, as seen in Figure 7-11.
../images/485790_1_En_7_Chapter/485790_1_En_7_Fig11_HTML.jpg
Figure 7-11

Creating an outlet for the Google Maps map view

The outlet property should look like this:
@IBOutlet weak var mapView: GMSMapView!
You will also need to add the import statement for the GoogleMaps framework to the top of the ViewController class:
import GoogleMaps
Now run your iOS application, just to make sure that nothing is broken. You should not see any changes yet. Let’s go ahead and change the location of the map. Using Google Maps, we would create a camera position and then animate the map view to the new position. Add the following lines to your viewDidLoad() method:
let camera = GMSCameraPosition.camera(
  withLatitude: 30.25,
  longitude: -97.7,
  zoom: 7)
mapView.animate(to: camera)
Replace the latitude and longitude with a coordinate of your choosing if you would like to view something other than Austin, Texas! Your final ViewController class should look something like Listing 7-4.
import UIKit
import GoogleMaps
class ViewController: UIViewController {
    @IBOutlet weak var mapView: GMSMapView!
    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view.
        let camera = GMSCameraPosition.camera(
          withLatitude: 30.25,
          longitude: -97.7,
          zoom: 7)
        mapView.animate(to: camera)
    }
}
Listing 7-4

Complete ViewController class for Google Maps

Now that we have the basics for working with the Google Maps SDK on iOS, we can move on to more advanced topics, such as changing the type of map to satellite, terrain, or hybrid, adding map markers, or giving driving directions. We will reuse the Xcode project we built in this chapter to avoid having to repeat all of the setup and installation instructions.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.222.196.175