1. Zanim zaczniesz
Z tego ćwiczenia w Codelabs dowiesz się, jak zacząć korzystać z Google Maps Platform do tworzenia aplikacji na iOS w języku Swift. Utworzysz aplikację na iOS, która:
- Wczytuje pakiet Maps SDK na iOS i bibliotekę narzędziową pakietu Maps SDK na iOS.
- Wyświetla mapę wyśrodkowaną na Sydney w Australii.
- Wyświetla niestandardowe znaczniki dla 100 punktów w Sydney.
- Implementuje łączenie znaczników w klastry.
- Umożliwia interakcję użytkownika, która po kliknięciu znacznika ponownie wyśrodkowuje mapę i rysuje na niej okrąg.
Wymagania wstępne
- Podstawowa wiedza na temat języka Swift i tworzenia aplikacji na iOS.
Jakie zadania wykonasz
- Wczytaj pakiet Maps SDK na iOS i bibliotekę narzędziową Google Maps SDK na iOS.
- Wczytaj mapę.
- Używaj znaczników, znaczników niestandardowych i grupowania znaczników.
- Korzystaj z systemu zdarzeń pakietu Maps SDK na iOS, aby obsługiwać interakcje użytkowników.
- Sterowanie kamerą mapy za pomocą kodu.
- Rysuj na mapie.
Czego potrzebujesz
Aby ukończyć to ćwiczenie, potrzebujesz tych kont, usług i narzędzi:
- Xcode 12.0 lub nowszy z pakietem SDK w wersji 12.0 lub nowszej.
- Zainstalowano Cocoapods.
- Konto Google Cloud Platform z włączonymi płatnościami (patrz następny krok).
- Projekt w konsoli Google Cloud z włączonym pakietem Maps SDK na iOS (patrz następny krok).
2. Konfiguracja
Aby wykonać krok włączenia poniżej, musisz włączyć Maps SDK na iOS.
Konfigurowanie Google Maps Platform
Jeśli nie masz jeszcze konta Google Cloud Platform i projektu z włączonymi płatnościami, zapoznaj się z przewodnikiem Pierwsze kroki z Google Maps Platform, aby utworzyć konto rozliczeniowe i projekt.
- W konsoli Google Cloud kliknij menu projektu i wybierz projekt, którego chcesz użyć w tym samouczku.
- Włącz interfejsy API i pakiety SDK Google Maps Platform wymagane w tym samouczku w Google Cloud Marketplace. Aby to zrobić, wykonaj czynności opisane w tym filmie lub tej dokumentacji.
- Wygeneruj klucz interfejsu API na stronie Dane logowania w konsoli Cloud. Możesz wykonać czynności opisane w tym filmie lub tej dokumentacji. Wszystkie żądania wysyłane do Google Maps Platform wymagają klucza interfejsu API.
Krótkie wprowadzenie
Aby jak najszybciej rozpocząć pracę, przygotowaliśmy kod początkowy, który pomoże Ci w tym samouczku.
- Sklonuj repozytorium, jeśli masz zainstalowany program
git
.
git clone https://github.com/googlemaps/codelab-maps-platform-101-swift.git
Możesz też kliknąć Podaj mi kod, aby pobrać kod źródłowy.
- Po pobraniu kodu otwórz projekt StarterApp w katalogu
/starter
. Ten projekt zawiera podstawową strukturę plików potrzebną do ukończenia ćwiczenia. Wszystko, czego potrzebujesz do pracy, znajduje się w katalogu/starter/StarterApp
.
Aby zobaczyć działający pełny kod rozwiązania, wyświetl ukończony kod w katalogu /solution/SolutionApp
.
3. Instalowanie pakietu Maps SDK na iOS
Pierwszym krokiem w korzystaniu z pakietu Maps SDK na iOS jest zainstalowanie wymaganych zależności. Ten proces składa się z 2 etapów: zainstalowania pakietu Maps SDK na iOS i biblioteki narzędziowej pakietu Maps SDK na iOS z menedżera zależności Cocoapods oraz podania klucza interfejsu API do pakietu SDK.
- Dodaj pakiet Maps SDK na iOS i bibliotekę narzędziową pakietu Maps SDK na iOS do
Podfile
.
W tym samouczku wykorzystujemy zarówno pakiet Maps SDK na iOS, który zapewnia wszystkie podstawowe funkcje Map Google, jak i bibliotekę narzędziową Maps iOS, która udostępnia różne narzędzia do wzbogacania mapy, w tym grupowanie znaczników.
Aby rozpocząć, otwórz w Xcode (lub w ulubionym edytorze tekstu) plik Podfile
i zaktualizuj go, aby zawierał zależności pakietu Maps SDK na iOS i biblioteki narzędziowej pod komentarzem # Pods for StarterApp
:
pod 'GoogleMaps', '6.1.0' pod 'Google-Maps-iOS-Utils', '3.4.0'
Najnowszą wersję pakietu SDK i wskazówki dotyczące jego obsługi znajdziesz w dokumentacji wersji pakietu Maps SDK na iOS.
Twój Podfile
powinien wyglądać tak:
source 'https://github.com/CocoaPods/Specs.git' platform :ios, '12.0' target 'StarterApp' do # Comment the next line if you don't want to use dynamic frameworks use_frameworks! # Pods for StarterApp pod 'GoogleMaps', '6.1.0' pod 'Google-Maps-iOS-Utils', '3.4.0' end
- Zainstaluj pody pakietu Maps SDK na iOS i biblioteki narzędziowej pakietu Maps SDK na iOS.
Aby zainstalować zależności, uruchom polecenie pod install
w katalogu /starter
z poziomu wiersza poleceń. Cocoapods automatycznie pobiera zależności i tworzy StarterApp.xcworkspace
.
- Po zainstalowaniu zależności uruchom polecenie
open StarterApp.xcworkspace
w katalogu/starter
, aby otworzyć plik w Xcode, a następnie uruchom aplikację w symulatorze iPhone'a, naciskającCommand+R
. Jeśli wszystko jest skonfigurowane prawidłowo, symulator uruchomi się i wyświetli czarny ekran. Nie martw się, nic jeszcze nie zostało utworzone, więc to normalne. - Zaimportuj pakiet SDK w
AppDelegate.swift
.
Po zainstalowaniu zależności musisz podać klucz interfejsu API w pakiecie SDK. Pierwszym krokiem jest zaimportowanie pakietu Maps SDK na iOS jako zależności. W tym celu umieść poniższy kod pod instrukcją import UIKit
import:
import GoogleMaps
- Przekaż klucz interfejsu API do pakietu SDK na iOS, wywołując
provideAPIKey
wGMSServices
wapplication: didFinishLaunchingWithOptions:
.
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
GMSServices.provideAPIKey("YOUR_API_KEY")
return true
}
Zaktualizowany plik AppDelegate.swift
powinien teraz wyglądać tak:
import UIKit
import GoogleMaps
@main
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
GMSServices.provideAPIKey("YOUR_API_KEY")
return true
}
}
Zastąp YOUR_API_KEY
kluczem interfejsu API utworzonym w konsoli Cloud Console.
Gdy masz już zainstalowane zależności i klucz interfejsu API, możesz zacząć wywoływać pakiet Maps SDK na iOS.
4. Wyświetlanie mapy
Czas wyświetlić pierwszą mapę.
Najczęściej używaną częścią pakietu Maps SDK na iOS jest klasa GMSMapView
, która udostępnia wiele metod umożliwiających tworzenie instancji mapy i manipulowanie nimi. Aby to zrobić:
- Otwórz pokój
ViewController.swift
.
W tym miejscu wykonasz pozostałą część ćwiczenia. Zauważ, że zdarzenia cyklu życia loadView
i viewDidLoad
kontrolera widoku są już dla Ciebie przygotowane.
- Zaimportuj pakiet Maps SDK na iOS, dodając ten wiersz na początku pliku:
import GoogleMaps
- Zadeklaruj zmienną instancji
ViewController
, aby przechowywaćGMSMapView
.
Instancja GMSMapView
to główny obiekt, z którym będziesz pracować w tym laboratorium, i będziesz się do niego odwoływać oraz wykonywać na nim działania w różnych metodach cyklu życia kontrolera widoku. Aby udostępnić tę wartość, zaktualizuj implementację ViewController
, deklarując zmienną instancji do jej przechowywania:
class ViewController: UIViewController {
private var mapView: GMSMapView!
...
}
- W
loadView
utwórz instancjęGMSCameraPosition
.
GMSCameraPosition
określa, gdzie mapa jest wyśrodkowana, i poziom powiększenia, który jest wyświetlany. Ten kod wywołuje metodę cameraWithLatitude:longitude:zoom:
, aby wyśrodkować mapę na Sydney w Australii przy szerokości geograficznej –33, 86 i długości geograficznej 151, 20 oraz poziomie powiększenia 12:
let camera:GMSCameraPosition = GMSCameraPosition.camera(withLatitude: -33.86, longitude: 151.20, zoom: 12)
- W
loadView
utwórz instancjęGMSMapView
, aby utworzyć instancję mapy.
Aby utworzyć nową instancję mapy, wywołaj funkcję GMSMapView(frame: CGRect, camera: GMSCameraPosition)
. Zwróć uwagę, że ramka jest ustawiona na CGRect.zero
, czyli zmienną globalną z biblioteki CGGeometry
iOS, która określa ramkę o szerokości 0 i wysokości 0, znajdującą się w kontrolerze widoku w pozycji (0,0). Kamera zostanie ustawiona w utworzonej przed chwilą pozycji.
Następnie, aby wyświetlić mapę, ustaw widok główny kontrolera widoku na mapView
, co spowoduje wyświetlenie mapy na pełnym ekranie.
mapView = GMSMapView(frame: .zero, camera: camera)
self.view = mapView
- Ustaw
GMSMapViewDelegate
na kontroler widoku.
Po wdrożeniu delegat widoku mapy umożliwia obsługę zdarzeń pochodzących z interakcji użytkownika z instancją GMSMapView
, co będzie potrzebne później.
Najpierw zaktualizuj interfejs ViewController
, aby był zgodny z protokołem GMSMapViewDelegate:
class ViewController: UIViewController, GMSMapViewDelegate
Następnie dodaj ten wiersz w funkcji loadView
, aby ustawić GMSMapViewDelegate
na ViewController
.
mapView.delegate = self
Teraz ponownie załaduj aplikację w symulatorze iOS (Command+R
). Mapa powinna wyglądać tak jak na tym zrzucie ekranu:
Ilustracja 1. Aplikacja na iOS wyświetlająca Mapę Google.
Podsumowując, w tym kroku utworzyliśmy instancję GMSMapView
, aby wyświetlić mapę wyśrodkowaną na Sydney w Australii.
Plik ViewController.swift
powinien teraz wyglądać tak:
import UIKit
import GoogleMaps
class ViewController: UIViewController, GMSMapViewDelegate {
private var mapView: GMSMapView!
override func loadView() {
// Load the map at set latitude/longitude and zoom level
let camera:GMSCameraPosition = GMSCameraPosition.camera(withLatitude: -33.86, longitude: 151.20, zoom: 11)
mapView = GMSMapView(frame: .zero, camera: camera)
self.view = mapView
mapView.delegate = self
}
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
}
}
5. Nadawanie stylu mapie (opcjonalnie)
Styl mapy możesz dostosować za pomocą definiowania stylów map w Google Cloud.
Tworzenie identyfikatora mapy
Jeśli nie masz jeszcze identyfikatora mapy powiązanego ze stylem mapy, zapoznaj się z przewodnikiem Identyfikatory mapy i wykonaj te czynności:
- Utwórz identyfikator mapy.
- powiązać identyfikator mapy ze stylem mapy.
Dodawanie identyfikatora mapy do aplikacji
Aby użyć identyfikatora mapy utworzonego w poprzednim kroku, otwórz plik ViewController.swift
i w metodzie loadView
utwórz obiekt GMSMapID
i podaj mu identyfikator mapy. Następnie zmodyfikuj instancję GMSMapView
, podając obiekt GMSMapID
jako parametr.
ViewController.swift
override func loadView() {
// Load the map at set latitude/longitude and zoom level
let camera:GMSCameraPosition = GMSCameraPosition.camera(withLatitude: -33.86, longitude: 151.20, zoom: 11)
let mapID = GMSMapID(identifier: "YOUR_MAP_ID")
mapView = GMSMapView(frame: .zero, mapID: mapID, camera: camera)
self.view = mapView
mapView.delegate = self
}
Gdy to zrobisz, uruchom aplikację, aby zobaczyć mapę w wybranym stylu.
6. Dodawanie znaczników do mapy
Deweloperzy korzystają z pakietu Maps SDK na iOS na wiele sposobów, ale umieszczanie znaczników na mapie jest zdecydowanie najpopularniejsze. Znaczniki wskazują konkretne punkty na mapie i są powszechnym elementem interfejsu do obsługi interakcji użytkownika. Jeśli korzystasz już z Map Google, prawdopodobnie znasz domyślny znacznik, który wygląda jak czerwone pinezki na ilustracji 2:
Rysunek 2. Mapa z czerwonymi znacznikami.
Ten krok pokazuje, jak użyć klasy GMSMarker
, aby umieścić znaczniki na mapie.
Pamiętaj, że markerów nie można umieszczać na mapie, dopóki nie zostanie ona wczytana z poprzedniego kroku w zdarzeniu cyklu życia loadView
kontrolera widoku. Wykonaj te czynności w zdarzeniu cyklu życia viewDidLoad
, które jest wywoływane po wczytaniu widoku (i mapy).
- Określ obiekt
CLLocationCoordinate2D
.
CLLocationCoordinate2D
to struktura udostępniana przez bibliotekę CoreLocation w iOS, która określa lokalizację geograficzną na podstawie szerokości i długości geograficznej. Aby rozpocząć tworzenie pierwszego markera, zdefiniuj obiekt CLLocationCoordinate2D
i ustaw szerokość i długość geograficzną na środek mapy. Współrzędne środka mapy są dostępne w widoku mapy za pomocą właściwości camera.target.latitude
i camera.target.longitude
.
// Add a single marker with a custom icon
let mapCenter = CLLocationCoordinate2DMake(mapView.camera.target.latitude, mapView.camera.target.longitude)
- Utwórz instancję
GMSMarker
.
Pakiet Maps SDK na iOS udostępnia klasę GMSMarker
. Każda instancja GMSMarker
reprezentuje pojedynczy znacznik na mapie i jest tworzona przez wywołanie funkcji markerWithPosition:
oraz przekazanie jej obiektu CLLocationCoordinate2D
, aby poinformować pakiet SDK, gdzie umieścić znacznik na mapie.
let marker = GMSMarker(position: mapCenter)
- Ustaw niestandardową ikonę markera.
Domyślny czerwony znacznik w Mapach Google jest świetny, ale dostosowywanie mapy też jest fajne. Na szczęście używanie niestandardowego znacznika jest proste dzięki pakietowi Maps SDK na iOS. Zauważ, że projekt StarterApp zawiera obraz o nazwie „custom_pin.png”, którego możesz użyć, ale możesz też użyć dowolnego innego obrazu.
Aby ustawić niestandardowy znacznik, ustaw właściwość icon
znacznika na instancję UIImage
.
marker.icon = UIImage(named: "custom_pin.png")
- Wyświetl znacznik na mapie.
Znacznik zostanie utworzony, ale nie będzie jeszcze widoczny na mapie. Aby to zrobić, ustaw właściwość map
instancji GMSMarker
na instancję GMSMapView
.
marker.map = mapView
Teraz ponownie załaduj aplikację i zobacz swoją pierwszą mapę ze znacznikiem, tak jak na rysunku 3.
Ilustracja 3. Aplikacja na iOS z Mapami Google i czerwonym znacznikiem na środku.
Podsumowując, w tej sekcji utworzyliśmy instancję klasy GMSMarker i zastosowaliśmy ją do widoku mapy, aby wyświetlić na niej znacznik. Zaktualizowane zdarzenie cyklu życia viewDidLoad w ViewController.swift
powinno teraz wyglądać tak:
override func viewDidLoad() {
super.viewDidLoad()
// Add a single marker with a custom icon
let mapCenter = CLLocationCoordinate2DMake(mapView.camera.target.latitude, mapView.camera.target.longitude)
let marker = GMSMarker(position: mapCenter)
marker.icon = UIImage(named: "custom_pin.png")
marker.map = mapView
}
7. Włączanie klastrowania znaczników
Jeśli używasz wielu znaczników lub są one blisko siebie, mogą się nakładać lub być zbyt blisko siebie, co pogarsza komfort użytkownika. Jeśli np. 2 markery znajdują się bardzo blisko siebie, może to wyglądać tak jak na rysunku 4:
Rysunek 4. Dwa markery znajdujące się bardzo blisko siebie.
W takiej sytuacji przydaje się grupowanie znaczników. Kolejną często stosowaną funkcją jest grupowanie znaczników, które łączy pobliskie znaczniki w jedną ikonę zmieniającą się w zależności od poziomu powiększenia, jak pokazano na rysunku 5:
Rysunek 5. Przykład znaczników zgrupowanych w jedną ikonę.
Algorytm klastrowania znaczników dzieli widoczny obszar mapy na siatkę, a następnie grupuje ikony znajdujące się w tej samej komórce. Zespół Google Maps Platform stworzył przydatną bibliotekę narzędziową o otwartym kodzie źródłowym o nazwie Google Maps SDK for iOS Utility Library, która m.in. automatycznie obsługuje grupowanie znaczników. Więcej informacji o grupowaniu znaczników znajdziesz w dokumentacji Google Maps Platform. Możesz też sprawdzić źródło biblioteki narzędziowej iOS na GitHub.
- Dodaj do mapy więcej znaczników.
Aby zobaczyć działanie klastrowania znaczników, musisz mieć na mapie wiele znaczników. Aby to uprościć, użyj generatora znaczników dostępnego w projekcie początkowym w MarkerGenerator.swift
.
Aby dodać do mapy określoną liczbę znaczników, wywołaj funkcję MarkerGenerator(near:count:).markerArray
w metodzie viewDidLoad
kontrolera widoku poniżej kodu z poprzedniego kroku. Metoda tworzy liczbę markerów określoną w parametrze count
w losowych lokalizacjach wokół współrzędnych podanych w obiekcie CLLocationCoordinate2D
. W takim przypadku możesz przekazać do niego utworzoną wcześniej zmienną mapCenter
. Markery są zwracane w obiekcie [GMSMarker]
.
// Generate many markers
let markerArray = MarkerGenerator(near: mapCenter, count: 100).markerArray
Możesz sprawdzić, jak wygląda taka liczba znaczników, dodając te wiersze po definicji markerArray
, a następnie uruchamiając aplikację. Przed przejściem do kolejnych kroków, w których do zarządzania wyświetlaniem znaczników używany jest moduł Marker Clusterer, pamiętaj, aby zakomentować te wiersze:
// Comment the following code out if using the marker clusterer
// to manage markers instead.
for marker in markerArray {
marker.map = mapView
}
- Zaimportuj bibliotekę narzędziową pakietu Google Maps SDK na iOS.
Aby dodać bibliotekę narzędziową Map Google na iOS jako zależność do projektu, dodaj ten kod do listy zależności u góry pliku ViewController.swift
:
import GoogleMapsUtils
- Skonfiguruj klaster znaczników.
Aby użyć klastrowania znaczników, musisz podać 3 elementy, które określają sposób jego działania: algorytm klastrowania, generator ikon i renderowanie. Algorytm określa sposób grupowania znaczników, np. odległość między znacznikami, które mają być uwzględnione w tym samym klastrze. Generator ikon udostępnia ikony klastrów, które mają być używane na różnych poziomach powiększenia. Moduł renderujący odpowiada za renderowanie ikon klastrów na mapie.
Jeśli wolisz, możesz je wszystkie napisać od zera. Biblioteka narzędziowa Map na iOS udostępnia domyślne implementacje, które przyspieszają ten proces. Dodaj te wiersze:
// Set up the cluster manager with a supplied icon generator and renderer.
let algorithm = GMUNonHierarchicalDistanceBasedAlgorithm()
let iconGenerator = GMUDefaultClusterIconGenerator()
let renderer = GMUDefaultClusterRenderer(mapView: mapView, clusterIconGenerator: iconGenerator)
- Utwórz instancję
GMUClusterManager
.
GMUClusterManager
to klasa, która implementuje grupowanie znaczników przy użyciu określonego przez Ciebie algorytmu, generatora ikon i renderera. Aby utworzyć moduł renderujący i udostępnić go widokowi mapy, najpierw dodaj zmienną instancji do implementacji ViewController
, aby przechowywać instancję menedżera klastrów:
class ViewController: UIViewController, GMSMapViewDelegate {
private var mapView: GMSMapView!
private var clusterManager: GMUClusterManager!
}
Następnie utwórz instancję GMUClusterManager
w zdarzeniu cyklu życia viewDidLoad
:
clusterManager = GMUClusterManager(map: mapView, algorithm: algorithm, renderer: renderer)
- Dodaj znaczniki i uruchom narzędzie do klastrowania znaczników.
Po skonfigurowaniu instancji klastrowania znaczników przekaż do menedżera klastrów tablicę znaczników do klastrowania, wywołując add(items:)
, a następnie uruchom klastrowanie, wywołując cluster
.
clusterManager.setMapDelegate(self)
clusterManager.add(markerArray)
clusterManager.cluster()
Ponownie załaduj aplikację. Powinno się w niej teraz wyświetlać wiele znaczników zgrupowanych w sposób podobny do tego na ilustracji 6. Wypróbuj różne poziomy powiększenia, zsuwając i rozsuwając palce na mapie, aby zobaczyć, jak klastry znaczników dostosowują się do powiększania i pomniejszania.
Rysunek 6. Aplikacja na iOS z Mapami Google i zgrupowanymi znacznikami.
Podsumowując, w tym kroku skonfigurowaliśmy instancję narzędzia do klastrowania znaczników z biblioteki narzędziowej pakietu Google Maps SDK na iOS, a następnie użyliśmy jej do klastrowania 100 znaczników na mapie. viewDidLoad
Zdarzenie związane z cyklem życia w ViewController.swift
powinno teraz wyglądać tak:
override func viewDidLoad() {
super.viewDidLoad()
// Add a single marker with a custom icon
let mapCenter = CLLocationCoordinate2DMake(mapView.camera.target.latitude, mapView.camera.target.longitude)
let marker = GMSMarker(position: mapCenter)
marker.icon = UIImage(named: "custom_pin.png")
marker.map = mapView
// Generate many markers
let markerArray = MarkerGenerator(near: mapCenter, count: 100).markerArray
// Comment the following code out if using the marker clusterer
// to manage markers instead.
// for marker in markerArray {
// marker.map = mapView
// }
// Set up the cluster manager with a supplied icon generator and renderer.
let algorithm = GMUNonHierarchicalDistanceBasedAlgorithm()
let iconGenerator = GMUDefaultClusterIconGenerator()
let renderer = GMUDefaultClusterRenderer(mapView: mapView, clusterIconGenerator: iconGenerator)
clusterManager = GMUClusterManager(map: mapView, algorithm: algorithm, renderer: renderer)
clusterManager.setMapDelegate(self)
clusterManager.add(markerArray)
clusterManager.cluster()
}
8. Dodawanie interakcji użytkownika
Masz teraz świetnie wyglądającą mapę, która wyświetla znaczniki i korzysta z grupowania znaczników. W tym kroku dodasz dodatkową obsługę interakcji użytkownika za pomocą zmiennej GMSMapViewDelegate
, którą wcześniej ustawiono na kontroler widoku, aby poprawić wygodę korzystania z mapy.
Pakiet Maps SDK na iOS udostępnia kompleksowy system zdarzeń, który jest implementowany za pomocą delegata widoku mapy. Zawiera on obsługę zdarzeń, która umożliwia wykonywanie kodu, gdy zachodzą różne interakcje użytkownika. Na przykład delegat MapView zawiera metody, które umożliwiają wywoływanie kodu w przypadku interakcji, takich jak kliknięcie mapy i znaczników przez użytkownika, przesuwanie widoku mapy, powiększanie i pomniejszanie oraz inne.
W tym kroku programowo przesuwasz mapę, aby wyśrodkować dowolny znacznik, który kliknie użytkownik.
- Zaimplementuj odbiornik kliknięć markera.
mapView(_:didTap:)
jest wywoływana za każdym razem, gdy użytkownik kliknie jeden z utworzonych wcześniej znaczników, oraz za każdym razem, gdy kliknie klaster znaczników (wewnętrznie klastry znaczników są implementowane jako instancja GMSMarker
).
Aby zaimplementować odbiornik zdarzeń, zacznij od jego utworzenia u dołu pliku ViewController.swift
przed zamykającym nawiasem klamrowym.
func mapView(_ mapView: GMSMapView, didTap marker: GMSMarker) -> Bool {
return false
}
Zwróć uwagę, że metoda zwraca wartość false
. Dzięki temu pakiet SDK na iOS będzie nadal wykonywać domyślne działanie GMSMarker
, np. po wykonaniu kodu obsługi zdarzeń wyświetlać okno informacyjne, jeśli jest ono skonfigurowane.
- Obsłuż zdarzenie kliknięcia i animuj kamerę, aby wyśrodkować mapę po kliknięciu znacznika lub klastra znaczników.
Gdy wywoływana jest funkcja mapView(_:didTap:)
, przekazuje ona instancję elementu GMSMarker
, który został kliknięty, dzięki czemu możesz obsłużyć ją w kodzie. Możesz użyć tej instancji, aby wyśrodkować mapę, wywołując animate(toLocation:)
w widoku mapy z poziomu procedury obsługi zdarzeń i przekazując jej pozycję instancji znacznika z właściwości position
.
// Animate to the marker
mapView.animate(toLocation: marker.position)
- Powiększanie klastra znaczników po jego dotknięciu.
Częstym wzorcem UX jest powiększanie klastrów znaczników po kliknięciu. Dzięki temu użytkownicy mogą wyświetlać zgrupowane markery, ponieważ klaster rozszerza się przy mniejszych poziomach powiększenia.
Jak wspomnieliśmy wcześniej, ikona klastra znaczników to w rzeczywistości implementacja GMSMarker
z niestandardową ikoną. Jak więc sprawdzić, czy kliknięto znacznik czy klaster znaczników? Gdy menedżer klastrowania znaczników tworzy nową ikonę klastra, implementuje instancję GMSMarker
, aby była zgodna z protokołem o nazwie GMUCluster.
. Możesz użyć warunku, aby sprawdzić, czy znacznik przekazany do funkcji obsługi zdarzeń jest zgodny z tym protokołem.
Gdy programowo wykryjesz, że kliknięto klaster, możesz wywołać metodę animate(toZoom:)
w instancji widoku mapy i ustawić poziom powiększenia na bieżący poziom powiększenia plus jeden. Bieżący poziom powiększenia jest dostępny w instancji mapView we właściwości camera.zoom
.
Zwróć też uwagę, jak poniższy kod zwraca wartość true
. Informuje to moduł obsługi zdarzeń, że obsługa zdarzenia została zakończona i nie należy wykonywać w nim żadnego dalszego kodu. Jednym z powodów jest zapobieganie wykonywaniu przez obiekt bazowy GMSMarker
pozostałych domyślnych działań, takich jak wyświetlanie okna informacyjnego, co nie miałoby większego sensu w przypadku kliknięcia ikony klastra.
// If the tap was on a marker cluster, zoom in on the cluster
if let _ = marker.userData as? GMUCluster {
mapView.animate(toZoom: mapView.camera.zoom + 1)
return true
}
Teraz ponownie załaduj aplikację i kliknij kilka znaczników i klastrów znaczników. Gdy dotkniesz jednego z nich, mapa zostanie wyśrodkowana na tym elemencie. Gdy klikniesz klaster znaczników, mapa powiększy się o 1 poziom, a klaster znaczników rozwinie się, aby wyświetlić zgrupowane pod nim znaczniki.
Podsumowując, w tym kroku zaimplementowaliśmy detektor kliknięć znacznika i obsłużyliśmy zdarzenie, aby wyśrodkować widok na klikniętym elemencie i powiększyć go, jeśli jest to ikona klastra znaczników.
Metoda mapView(_:didTap:)
powinna wyglądać tak:
func mapView(_ mapView: GMSMapView, didTap marker: GMSMarker) -> Bool {
// Animate to the marker
mapView.animate(toLocation: marker.position)
// If the tap was on a marker cluster, zoom in on the cluster
if let _ = marker.userData as? GMUCluster {
mapView.animate(toZoom: mapView.camera.zoom + 1)
return true
}
return false
}
9. Rysowanie na mapie
Do tej pory utworzyliśmy mapę Sydney, na której znajduje się 100 losowych znaczników i która obsługuje interakcje użytkownika. W ostatnim kroku tego laboratorium kodowania użyjesz funkcji rysowania pakietu Maps SDK na iOS, aby dodać do mapy przydatną funkcję.
Wyobraź sobie, że z tej mapy będą korzystać użytkownicy, którzy chcą zwiedzić Sydney. Przydatną funkcją byłoby wizualizowanie promienia wokół znacznika po jego kliknięciu. Dzięki temu użytkownik może szybko sprawdzić, jakie inne miejsca docelowe znajdują się w pobliżu klikniętego znacznika.
Pakiet SDK na iOS zawiera zestaw funkcji do rysowania na mapie kształtów, takich jak kwadraty, wielokąty, linie i okręgi. W tym kroku wyrenderujesz okrąg, aby po kliknięciu znacznika wyświetlić promień 800 metrów (około pół mili).
- Dodaj zmienną instancji
circle
do implementacji elementu ViewController.
Ta zmienna instancji służy do zapisywania ostatnio narysowanego okręgu, aby można go było usunąć przed narysowaniem kolejnego. W końcu nie byłoby to zbyt pomocne dla użytkownika i nie wyglądałoby dobrze, gdyby każdy kliknięty znacznik miał narysowane wokół niego kółko.
Aby to zrobić, zaktualizuj implementację ViewController
w ten sposób:
class ViewController: UIViewController, GMSMapViewDelegate {
private var mapView: GMSMapView!
private var clusterManager: GMUClusterManager!
private var circle: GMSCircle? = nil
...
}
- Narysuj okrąg po kliknięciu znacznika.
U dołu metody mapView(_:didTap:)
, tuż nad instrukcją return false
, dodaj pokazany tu kod, aby utworzyć instancję klasy GMSCircle
pakietu SDK na iOS, która narysuje nowe koło o promieniu 800 metrów. W tym celu wywołaj metodę GMSCircle(position:radius:)
i przekaż jej pozycję klikniętego znacznika, tak jak podczas ponownego wyśrodkowywania mapy.
// Draw a new circle around the tapped marker
circle = GMSCircle(position: marker.position, radius: 800)
- Dostosuj styl okręgu.
Domyślnie tag GMSCircle
rysuje okrąg z czarną kreską i przezroczystym wypełnieniem. To działa w przypadku wyświetlania promienia, ale nie wygląda zbyt dobrze i jest trochę trudne do zobaczenia. Następnie nadaj okręgowi kolor wypełnienia, aby poprawić styl, przypisując UIColor
do właściwości fillColor
okręgu. Kod widoczny poniżej dodaje szare wypełnienie z 50-procentową przezroczystością:
circle?.fillColor = UIColor(red: 0.67, green: 0.67, blue: 0.67, alpha: 0.5)
- Wyświetl okrąg na mapie.
Podobnie jak w przypadku tworzenia znaczników, utworzenie instancji GMSCircle
nie powoduje, że pojawi się ona na mapie. Aby to zrobić, przypisz instancję widoku mapy do właściwości map
okręgu.
circle?.map = mapView
- Usuń wszystkie wcześniej wyrenderowane okręgi.
Jak wspomnieliśmy wcześniej, ciągłe dodawanie okręgów do mapy nie byłoby zbyt wygodne dla użytkowników. Aby usunąć okrąg wyrenderowany przez poprzednie zdarzenie kliknięcia, ustaw właściwość map
elementu circle
na nil
u góry elementu mapView(_:didTap:)
.
// Clear previous circles
circle?.map = nil
Załaduj ponownie aplikację i kliknij znacznik. Po kliknięciu markera powinien pojawić się nowy okrąg, a wcześniej wyrenderowany okrąg powinien zostać usunięty (jak pokazano na rysunku 7).
Rysunek 7. Okrąg narysowany wokół klikniętego znacznika.
Podsumowując, w tym kroku użyliśmy klasy GMSCircle
, aby renderować okrąg za każdym razem, gdy klikniesz znacznik.
Metoda mapView(_:didTap:)
powinna wyglądać tak:
func mapView(_ mapView: GMSMapView, didTap marker: GMSMarker) -> Bool {
// Clear previous circles
circle?.map = nil
// Animate to the marker
mapView.animate(toLocation: marker.position)
// If the tap was on a marker cluster, zoom in on the cluster
if let _ = marker.userData as? GMUCluster {
mapView.animate(toZoom: mapView.camera.zoom + 1)
return true
}
// Draw a new circle around the tapped marker
circle = GMSCircle(position: marker.position, radius: 800)
circle?.fillColor = UIColor(red: 0.67, green: 0.67, blue: 0.67, alpha: 0.5)
circle?.map = mapView
return false
}
10. Gratulacje
Udało Ci się utworzyć aplikację na iOS z interaktywną mapą Google.
Czego się dowiedziałeś
- Wczytywanie i konfigurowanie pakietu Maps SDK na iOS oraz biblioteki narzędziowej Google Maps SDK na iOS
- Wczytywanie mapy
- Stylizowanie mapy
- Używanie znaczników, znaczników niestandardowych i grupowania znaczników
- system zdarzeń, który umożliwia interakcję użytkownika;
- Sterowanie kamerą na mapie w sposób automatyczny
- Rysowanie na mapie
Co dalej?
- Aby znaleźć więcej inspiracji, przejrzyj lub utwórz rozwidlenie
maps-sdk-for-ios-samples
repozytorium GitHub z przykładami i wersjami demonstracyjnymi. - Skorzystaj z większej liczby ćwiczeń z programowania w Swift, aby tworzyć aplikacje na iOS za pomocą Google Maps Platform
- Pomóż nam tworzyć treści, które będą dla Ciebie najbardziej przydatne, i wypełnij poniższą ankietę:
Jakie inne codelaby chcesz zobaczyć?
Nie możesz znaleźć warsztatów, które Cię najbardziej interesują? Zgłoś problem tutaj