1. Zanim zaczniesz
Z tego ćwiczenia dowiesz się, jak utworzyć prostą aplikację na Androida, która korzysta z pakietu Navigation SDK w Google Maps Platform, aby nawigować do wstępnie skonfigurowanego miejsca docelowego.
Tak będzie wyglądać Twoja aplikacja po zakończeniu pracy.

Wymagania wstępne
- Znajomość podstaw tworzenia aplikacji na Androida w języku Kotlin
- Znajomość podstawowych pojęć związanych z pakietem Google Maps SDK, takich jak mapy, lokalizacje i współrzędne.
Czego się nauczysz
- Jak utworzyć prostą aplikację na Androida, która korzysta z pakietu Navigation SDK do nawigowania do miejsca docelowego.
- Integracja pakietu SDK do nawigacji z zewnętrznego repozytorium Google Maven
- Jak zarządzać uprawnieniami do lokalizacji i umową użytkownika z warunkami dotyczącymi użytkowników pakietu Navigation SDK
- Inicjowanie pakietu SDK
- Jak ustawić cel podróży i rozpocząć nawigację.
Czego potrzebujesz
- Zainstalowana najnowsza stabilna wersja Androida Studio. Ten codelab został utworzony w Android Studio Jellyfish. Jeśli używasz innej wersji, wygląd i układ interfejsu oraz komponentów mogą się różnić.
- konto Google i projekt z włączonymi płatnościami,
- urządzenie z Androidem w trybie programisty z włączonym debugowaniem USB lub emulator Androida; Niezależnie od tego, którą opcję wybierzesz, musi ona spełniać minimalne wymagania dotyczące pakietu Navigation SDK.
2. Konfiguracja
Jeśli nie masz jeszcze konta Google Cloud Platform i projektu w chmurze z włączonymi płatnościami, skonfiguruj projekt Google Cloud, postępując zgodnie z instrukcjami na stronie Wprowadzenie do Google Maps Platform: https://developers.google.com/maps/gmp-get-started
Wybierz projekt Google Cloud w konsoli.
W konsoli Google Cloud kliknij menu projektu i wybierz projekt, którego chcesz użyć w tym module.

Włączanie Navigation SDK w projekcie
Włącz interfejsy API i pakiety SDK Google Maps Platform wymagane w tym samouczku w Google Cloud Marketplace.
W konsoli Google Cloud otwórz Interfejsy API i usługi > Biblioteka i wyszukaj „Navigation SDK”.
Powinien wyświetlić się 1 wynik wyszukiwania.

Kliknij wynik Navigation SDK, aby otworzyć stronę z informacjami o produkcie. Kliknij przycisk Włącz, aby włączyć pakiet SDK w projekcie.
Powtórz ten proces w przypadku Google Maps SDK na Androida.
Utwórz klucz interfejsu API
Wygeneruj klucz interfejsu API na stronie Dane logowania w konsoli Cloud. Wykonaj czynności opisane w kroku 3 sekcji „Szybki start” w artykule Pierwsze kroki z Google Maps Platform. Wszystkie żądania wysyłane do Google Maps Platform wymagają klucza interfejsu API.
3. Pobieranie przykładowych plików projektu
W tej sekcji opisujemy, jak skonfigurować podstawowy pusty projekt Android Studio, klonując pliki z repozytorium GitHub na potrzeby tego laboratorium. Repozytorium GitHub zawiera wersje kodu modułu przed i po zmianach. Ten przewodnik zaczyna się od pustego szablonu projektu i prowadzi do jego ukończenia. Jeśli utkniesz, możesz użyć gotowego projektu w repozytorium jako materiału referencyjnego.
Sklonuj to repozytorium GitHub, aby uzyskać kod na potrzeby tego ćwiczenia.
git clone https://github.com/googlemaps-samples/codelab-navigation-101-android-kotlin.git
Jeśli nie masz zainstalowanego narzędzia git, kliknij ten przycisk, aby pobrać kod:
Aby jak najszybciej zacząć, w repozytorium znajdziesz w folderze Starter kod startowy, który pomoże Ci w wykonaniu tego ćwiczenia. Projekt początkowy zawiera podstawowy interfejs aplikacji i konfigurację kompilacji, ale nie ma dodanego pakietu Navigation SDK. Dostępny jest też gotowy Solution projekt, jeśli chcesz przejść dalej lub w dowolnym momencie sprawdzić swoje postępy.
Otwórz sklonowane repozytorium w Android Studio
Po sklonowaniu repozytorium lokalnie otwórz folder Starter w Androidzie Studio jako istniejący projekt.
- W oknie Witamy w Android Studio kliknij przycisk Otwórz.
- Przejdź do folderu, w którym zapisano sklonowane repozytorium, i wybierz folder
Starterw folderze najwyższego poziomu „codelab-navigation-101-android-kotlin”. - Sprawdź, czy projekt się kompiluje i działa.
Dodawanie urządzenia wirtualnego lub podłączanie urządzenia
Aby połączyć urządzenie z Androidem z komputerem, postępuj zgodnie z instrukcjami Android Studio dotyczącymi uruchamiania aplikacji na urządzeniu. Możesz też skonfigurować urządzenie wirtualne za pomocą Menedżera urządzenia wirtualnego z Androidem (AVD). Wybierając emulator, pamiętaj, aby wybrać obraz, który zawiera interfejsy API Google.
W Android Studio kliknij opcję menu Uruchom lub ikonę przycisku odtwarzania. Wybierz urządzenie zgodnie z instrukcjami.
4. Dodawanie pakietu Navigation SDK do aplikacji
Dodawanie biblioteki Navigation SDK i klucza interfejsu API do projektu
Aby dodać bibliotekę Navigation SDK do aplikacji, musisz zmodyfikować plik kompilacji na poziomie aplikacji build.gradle.kts, aby pobrać pakiet Navigation SDK z repozytorium Maven i skonfigurować numer wersji.
Utwórz w konfiguracji kompilacji zmienną do przechowywania numeru wersji pakietu Navigation SDK.
Skonfiguruj w build.gradle.kts na poziomie aplikacji zmienną, która będzie zawierać wartość wersji pakietu Navigation SDK używanej w aplikacji. Dzięki temu w przyszłości łatwo będzie można zmienić ją na najnowszą wersję.
Najnowszy numer wersji znajdziesz w informacjach o wersji pakietu Navigation SDK.
val navSdkVersion by extra("6.0.0")
Wartości tej i innych zmiennych możesz też modyfikować w oknie dialogowym, które znajdziesz w sekcji Plik > Struktura projektu > Zmienne:

Dodawanie zależności do konfiguracji kompilacji
Teraz dodaj do sekcji zależności w pliku build.gradle.kts. na poziomie aplikacji tę zależność interfejsu API. Użyta wersja będzie wartością zmiennej ${navSdkVersion}, którą właśnie ustawiono w pliku build.gradle.kts na poziomie aplikacji:
dependencies {
// Include the Google Navigation SDK.
api("com.google.android.libraries.navigation:navigation:${navSdkVersion}")
...
Dodawanie klucza interfejsu API
Zarządzanie kluczem interfejsu API za pomocą wtyczki Gradle obiektów tajnych
Zalecamy używanie wtyczki Gradle obiektów tajnych do bezpiecznego zarządzania kluczem interfejsu API w aplikacji. Wtyczka została dodana do początkowego szablonu projektu jako zależność w pliku build.gradle.kts najwyższego poziomu.
// Top-level build file where you can add configuration options common to all sub-projects/modules.
plugins {
id("com.google.android.libraries.mapsplatform.secrets-gradle-plugin") version "2.0.1" apply false
//... other plugin definitions here
}
Otwórz plik secrets.properties w katalogu najwyższego poziomu, a następnie zastąp YOUR_API_KEY kluczem interfejsu API. Przechowuj klucz w tym pliku, ponieważ secrets.properties jest wykluczony z systemu kontroli wersji.
MAPS_API_KEY=YOUR_API_KEY
Więcej informacji na ten temat znajdziesz w artykule Dodawanie klucza interfejsu API do aplikacji w dokumentacji pakietu Navigation SDK.
Sprawdź zawartość pliku local.defaults.properties
Pusty projekt zawiera też plik local.defaults.properties w katalogu najwyższego poziomu, czyli w tym samym folderze co plik secrets.properties. Otwórz go i sprawdź poniższy kod.
MAPS_API_KEY=DEFAULT_API_KEY
Jest to wartość zapasowa dla właściwości MAPS_API_KEY na wypadek, gdyby właściwość secrets.properties nie została dodana do projektu, aby kompilacje nie kończyły się niepowodzeniem. Nie musisz edytować tego pliku. Jeśli secrets.properties definicja MAPS_API_KEY nie zostanie znaleziona, wartość domyślna spowoduje zatrzymanie działania aplikacji w czasie wykonywania z błędem klucza API.
Sprawdź, czy plik manifestu Androida używa określonego przez Ciebie klucza interfejsu API
Otwórz plik app/src/main/AndroidManifest.xml. Zauważysz, że właściwość MAPS_API_KEY służy do ustawiania klucza interfejsu API aplikacji:
<meta-data
android:name="com.google.android.geo.API_KEY"
android:value="${MAPS_API_KEY}" />
Otwórz plik build.gradle.kts na poziomie aplikacji i znajdź właściwość secrets.
Ustawienie propertiesFileName wtyczki powinno mieć wartość secrets.properties, a wartość defaultPropertiesFileName powinna być równa local.defaults.properties.
secrets {
// Optionally specify a different file name containing your secrets.
// The plugin defaults to "local.properties"
propertiesFileName = "secrets.properties"
// A properties file containing default secret values. This file can be
// checked in version control.
defaultPropertiesFileName = "local.defaults.properties"
}
Zapisz wszystkie pliki i zsynchronizuj projekt z Gradle.
5. Konfigurowanie uprawnień aplikacji i dodawanie podstawowego interfejsu
Prośba o dostęp do dokładnej lokalizacji
Pakiet SDK do nawigacji zależy od sygnałów GPS, więc aplikacja musi poprosić użytkownika o przyznanie dostępu do dokładnych danych o lokalizacji. Dodaj uprawnienie dostępu do dokładnej lokalizacji jako element podrzędny elementu <manifest> w pliku AndroidManifest.xml.
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" >
<uses-permission
android:name="android.permission.ACCESS_FINE_LOCATION"
/>
</manifest>
Więcej informacji o uprawnieniach do lokalizacji na Androidzie znajdziesz w sekcji Request location permissions (Prośba o uprawnienia do lokalizacji) w dokumentacji dla deweloperów aplikacji na Androida.
Aby uruchomić aplikację na urządzeniu z Androidem 14, poproś o dostęp do lokalizacji usługi działającej na pierwszym planie, dodając ten tag uses-permission w tym samym miejscu co uprawnienie dostępu do dokładnej lokalizacji:
<uses-permission android:name="android.permission.FOREGROUND_SERVICE_LOCATION" />
Dodawanie aktywności uruchamiania z podstawowym interfejsem
Podczas uruchamiania aplikacji będzie potrzebny kod, który sprawdzi, czy użytkownik przyznał uprawnienia dostępu do lokalizacji, i obsłuży każdy możliwy scenariusz, w razie potrzeby prosząc o przyznanie uprawnień. Aby to zrobić, dodaj do aplikacji podstawowy interfejs. W tym laboratorium używamy interfejsu, który jest tworzony podczas tworzenia w Androidzie Studio nowej, pustej aktywności Views. Dostosujesz ten kod, aby przed dodaniem kodu do aktywności interfejsu nawigacji sprawdzić dostęp do lokalizacji.
Otwórz plik MainActivity.kt w edytorze kodu i sprawdź kod, który przedstawia podstawowy interfejs.
Wysyłanie prośby o uprawnienia dostępu do lokalizacji w czasie działania
Aplikacja musi wywołać prośbę o dostęp do dokładnej lokalizacji przed zainicjowaniem pakietu Navigation SDK.
Aby to sprawdzanie odbywało się podczas uruchamiania aplikacji, dodaj kod do klasy MainActivity w zastąpionej metodzie onCreate() aktywności.
Poniższy kod sprawdza, czy użytkownik przyznał dostęp do lokalizacji. Jeśli nie, prosi o uprawnienia. Dodaj ten kod w metodzie onCreate().
val permissions =
if (VERSION.SDK_INT >= VERSION_CODES.TIRAMISU) {
arrayOf(permission.ACCESS_FINE_LOCATION, permission.POST_NOTIFICATIONS)
} else {
arrayOf(permission.ACCESS_FINE_LOCATION)
}
if (permissions.any { !checkPermissionGranted(it) }) {
if (permissions.any { shouldShowRequestPermissionRationale(it) }) {
// Display a dialogue explaining the required permissions.
}
val permissionsLauncher =
registerForActivityResult(
RequestMultiplePermissions(),
{ permissionResults ->
if (permissionResults.getOrDefault(permission.ACCESS_FINE_LOCATION, false)) {
onLocationPermissionGranted()
} else {
finish()
}
},
)
permissionsLauncher.launch(permissions)
} else {
android.os.Handler(Looper.getMainLooper()).postDelayed({ onLocationPermissionGranted() }, SPLASH_SCREEN_DELAY_MILLIS)
}
}
private fun checkPermissionGranted(permissionToCheck: String): Boolean =
ContextCompat.checkSelfPermission(this, permissionToCheck) == PackageManager.PERMISSION_GRANTED
Dodaj do klasy MainActivity nową funkcję o nazwie onLocationPermissionGranted, która będzie obsługiwać wynik, gdy użytkownik przyzna uprawnienia do udostępniania lokalizacji. W kolejnych krokach dodamy tutaj kod, który uruchomi nową aktywność nawigacyjną.
private fun onLocationPermissionGranted() {
//code to initialize Navigation SDK will go here
}
Utwórz projekt. Jeśli wystąpią błędy kompilacji, znajdź je i popraw.
Uruchom projekt na nowym urządzeniu wirtualnym. Gdy aplikacja zostanie zainstalowana i uruchomiona, powinno pojawić się okno z prośbą o uprawnienia.
6. Dodawanie interfejsu użytkownika do nawigacji
Interfejs nawigacji możesz dodać na 2 sposoby: SupportNavigationFragment lub NavigationView.
Dla uproszczenia w tym laboratorium używamy znaku NavigationView.
Edytowanie układu
Edytuj res/layout/activity_main.xml, aby dodać układ do widoku NavigationView.
- Otwórz plik i przełącz się na widok kodu.
- Zastąp całą zawartość pliku nowym układem
NavigationViewwRelativeLayout, jak w przykładzie poniżej. Wystarczy prosty układ, ponieważ dodasz tylko widok nawigacji do aplikacji. - Nadaj widokowi NavigationView identyfikator „
@+id/navigation_view”.
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.google.android.libraries.navigation.NavigationView
android:id="@+id/navigation_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
/>
</RelativeLayout>
Konfigurowanie aktywności Nawigacja
W Android Studio otwórz w edytorze plik MainActivity.kt.
Dodaj podstawowy kod konfiguracji, aby zapewnić prawidłowe działanie nawigacji w aplikacji. W pliku MainActivity.kt wprowadź te zmiany:
- Zadeklaruj zmienną w klasie
MainActivity, aby odwoływać się doNavigationView:
private lateinit var navView: NavigationView
- Dodaj do metody
onCreate()kod, aby uzyskać odwołanie doNavigationView:
navView = findViewById(R.id.navigation_view)
navView.onCreate(savedInstanceState)
- Dodaj do metody
onCreate()kod, który zapewni, że ekran pozostanie włączony podczas nawigacji:
// Ensure the screen stays on during nav.
window.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
- Zmodyfikuj kod, który wywołuje
ViewCompat.setOnApplyWindowInsetsListener, aby odwoływał się do identyfikatoraNavigationView.
ViewCompat.setOnApplyWindowInsetsListener(findViewById(R.id.navigation_view)) { v, insets ->
val systemBars = insets.getInsets(WindowInsetsCompat.Type.systemBars())
v.setPadding(systemBars.left, systemBars.top, systemBars.right, systemBars.bottom)
insets
}
- Dodaj do klasy metodę
showToast(), aby wyświetlać użytkownikowi opinie:
private fun showToast(errorMessage: String) {
Toast.makeText(this@MainActivity, errorMessage, Toast.LENGTH_LONG).show()
}
7. Inicjowanie pakietu Navigation SDK
Po zakończeniu podstawowej konfiguracji aktywności Navigation możesz zainicjować pakiet SDK Navigation. Aby to zrobić, dodaj do pliku MainActivity.kt ten kod:
/** Starts the Navigation API, capturing a reference when ready. */
@SuppressLint("MissingPermission")
private fun initializeNavigationApi() {
NavigationApi.getNavigator(
this,
object : NavigatorListener {
override fun onNavigatorReady(navigator: Navigator) {
// store a reference to the Navigator object
mNavigator = navigator
// code to start guidance will go here
}
override fun onError(@NavigationApi.ErrorCode errorCode: Int) {
when (errorCode) {
NavigationApi.ErrorCode.NOT_AUTHORIZED -> {
// Note: If this message is displayed, you may need to check that
// your API_KEY is specified correctly in AndroidManifest.xml
// and is been enabled to access the Navigation API
showToast(
"Error loading Navigation API: Your API key is " +
"invalid or not authorized to use Navigation."
)
}
NavigationApi.ErrorCode.TERMS_NOT_ACCEPTED -> {
showToast(
"Error loading Navigation API: User did not " +
"accept the Navigation Terms of Use."
)
}
else -> showToast("Error loading Navigation API: $errorCode")
}
}
},
)
}
Ten kod tworzy nową metodę o nazwie initializeNavigationApi(). Ta metoda pobiera odwołanie do obiektu Navigator, wywołując metodę NavigationApi.getNavigator(), i implementuje interfejs NavigatorListener do obsługi wywołania zwrotnego.
Zwróć uwagę, że po zainicjowaniu interfejsu Navigation API zostanie wywołana metoda NavigationListener.onNavigatorReady z obiektem Navigator przekazanym jako parametr. Powyższy kod zaktualizuje zadeklarowaną wcześniej zmienną mNavigator za pomocą zainicjowanego obiektu Navigator, który jest przekazywany do tej metody.
Na koniec dodaj wywołanie metody initializeNavigationApi z metody onLocationPermissionGranted.
private fun onLocationPermissionGranted() {
initializeNavigationApi()
}
8. Dodawanie detektorów kluczowych zdarzeń nawigacyjnych
Gdy użytkownicy postępują zgodnie z wskazówkami, pakiet Navigation SDK uruchamia zdarzenia, które mogą powiadamiać aplikację o kluczowych zmianach stanu na trasie, np. gdy użytkownik zmieni trasę lub dotrze do celu. W pliku MainActivity.kt dodaj detektory do obsługi tych zdarzeń:
- W klasie
MainActivityzadeklaruj 2 zmienne, które będą odwoływać się do obiektów detektora zdarzeń:
private var arrivalListener: Navigator.ArrivalListener? = null
private var routeChangedListener: Navigator.RouteChangedListener? = null
- Dodaj metodę
registerNavigationListeners(), aby skonfigurować odbiorniki po zainicjowaniu obiektu Navigator. Ta metoda wywołuje funkcjęNavigator.clearDestinations(), aby zresetowaćNavigationViewpo wywołaniu zdarzenia Arrival:
/**
* Registers a number of example event listeners that show an on screen message when certain
* navigation events occur (e.g. the driver's route changes or the destination is reached).
*/
private fun registerNavigationListeners() {
withNavigatorAsync {
arrivalListener =
Navigator.ArrivalListener { // Show an onscreen message
showToast("User has arrived at the destination!")
mNavigator?.clearDestinations()
}
mNavigator?.addArrivalListener(arrivalListener)
routeChangedListener =
Navigator.RouteChangedListener { // Show an onscreen message when the route changes
showToast("onRouteChanged: the driver's route changed")
}
mNavigator?.addRouteChangedListener(routeChangedListener)
}
}
- Dodaj wywołanie funkcji
registerNavigationListeners()z kodu wywołania zwrotnegoonNavigatorReadyw metodzieinitializeNavigationApi:
override fun onNavigatorReady(navigator: Navigator) {
// store a reference to the Navigator object
mNavigator = navigator
//listen for events en route
registerNavigationListeners()
}
- Skonfiguruj interfejs. Gdy nawigacja jest włączona, możesz kontrolować różne aspekty interfejsu nawigacji. Jedną z ważnych opcji dostosowywania jest pozycja kamery. Dodaj wywołanie metody
setTaskRemovedBehaviourobiektunavigatorzwróconego wonNavigatorReadyw ten sposób: Jeśli aplikacja zostanie przesunięta, wskazówki i powiadomienia zostaną zakończone:
// Disables the guidance notifications and shuts down the app and background service
// when the user dismisses/swipes away the app from Android's recent tasks.
navigator.setTaskRemovedBehavior(Navigator.TaskRemovedBehavior.QUIT_SERVICE)
- Dodaj wywołanie
GoogleMap.followMyLocation, aby określićCameraPerspective. Dostęp doGoogleMapuzyskuje się za pomocą metodyNavigatorView.getMapAsync()w ten sposób:
navView.getMapAsync {
googleMap ->
googleMap.followMyLocation(GoogleMap.CameraPerspective.TILTED)
}
- Aby zapewnić płynne działanie funkcji nawigacji w całym cyklu życia aplikacji, zaimplementuj w klasie
MainActivityte metody:
override fun onSaveInstanceState(savedInstanceState: Bundle) {
super.onSaveInstanceState(savedInstanceState)
navView.onSaveInstanceState(savedInstanceState)
}
override fun onTrimMemory(level: Int) {
super.onTrimMemory(level)
navView.onTrimMemory(level)
}
override fun onStart() {
super.onStart()
navView.onStart()
}
override fun onResume() {
super.onResume()
navView.onResume()
}
override fun onPause() {
navView.onPause()
super.onPause()
}
override fun onConfigurationChanged(configuration: Configuration) {
super.onConfigurationChanged(configuration)
navView.onConfigurationChanged(configuration)
}
override fun onStop() {
navView.onStop()
super.onStop()
}
override fun onDestroy() {
navView.onDestroy()
withNavigatorAsync {
// Unregister event listeners to avoid memory leaks.
if (arrivalListener != null) {
navigator.removeArrivalListener(arrivalListener)
}
if (routeChangedListener != null) {
navigator.removeRouteChangedListener(routeChangedListener)
}
navigator.simulator?.unsetUserLocation()
navigator.cleanup()
}
super.onDestroy()
}
9. Ustaw miejsce docelowe
Możesz teraz ustawić miejsce docelowe i rozpocząć nawigację. W pliku MainActivity.kt wprowadź te zmiany:
- Dodaj nową metodę
navigateToPlace(), która ustawia miejsce docelowe nawigacji i akceptuje parametrplaceId.
/**
* Requests directions from the user's current location to a specific place (provided by the
* Place ID).
*/
private fun navigateToPlace(placeId: String) {
}
- W metodzie
navigateToPlace()użyj metodyWaypoint.builder(), aby utworzyć obiektWaypointna podstawie identyfikatora miejsca przekazanego do metody. ObsłużUnsupportedPlaceIdException, które może zostać zgłoszone w sytuacjach, gdy identyfikator miejsca nie jest przypisany do dokładnego adresu:
val waypoint: Waypoint? =
// Set a destination by using a Place ID (the recommended method)
try {
Waypoint.builder().setPlaceIdString(placeId).build()
} catch (e: Waypoint.UnsupportedPlaceIdException) {
showToast("Place ID was unsupported.")
return
}
- Dodaj do metody
navigateToPlace()ten kod, aby ustawić miejsce docelowe za pomocą punktu na trasie:
val pendingRoute = mNavigator?.setDestination(waypoint)
// Set an action to perform when a route is determined to the destination
pendingRoute?.setOnResultListener { code ->
when (code) {
RouteStatus.OK -> {
// Code to start guidance will go here
}
RouteStatus.ROUTE_CANCELED -> showToast("Route guidance canceled.")
RouteStatus.NO_ROUTE_FOUND,
RouteStatus.NETWORK_ERROR ->
// TODO: Add logic to handle when a route could not be determined
showToast("Error starting guidance: $code")
else -> showToast("Error starting guidance: $code")
}
}
Obiekt Navigator ma metodę setDestinations(), która może przyjmować różne parametry. Najprostszą opcją jest podanie Waypoint. Domyślnie będzie to tryb transportu DRIVING, odpowiedni dla samochodów 4-kołowych. Metoda setDestinations() zwraca obiekt ListenableResultFuture zawierający obiekt RouteStatus. Ikona RouteStatus wskaże, czy znaleziono trasę do miejsca docelowego, i umożliwi Ci obsługę różnych stanów błędów, jeśli nie.
- Wprowadź dodatkowe zmiany w konfiguracji, aby poprawić wrażenia użytkowników nawigacji:
// Hide the toolbar to maximize the navigation UI
supportActionBar?.hide()
// Enable voice audio guidance (through the device speaker)
mNavigator?.setAudioGuidance(Navigator.AudioGuidance.VOICE_ALERTS_AND_GUIDANCE)
// Simulate vehicle progress along the route (for demo/debug builds)
if (BuildConfig.DEBUG) {
mNavigator?.simulator?.simulateLocationsAlongExistingRoute(
SimulationOptions().speedMultiplier(5f)
)
}
Zmiany te obejmują następujące ulepszenia:
- Ukrywanie paska działań, aby zmaksymalizować miejsce na interfejs nawigacji.
- włączenie wskazówek głosowych, które będą odczytywać alerty i wskazówki nawigacji;
- Konfigurowanie symulatora na potrzeby debugowania przez określenie mnożnika prędkości.
- Znajdź identyfikator miejsca, które będzie Twoim miejscem docelowym. Najlepiej, aby znajdował się on w pobliżu lokalizacji użytkownika. Użyj narzędzia Google Maps Platform Place ID Finder lub uzyskaj identyfikator miejsca z wywołania interfejsu Places API.
Jeśli symulujesz nawigację, możesz ustawić lokalizację użytkownika w kodzie lub pobrać ją z podłączonego urządzenia. W tym laboratorium kodowym założymy, że symulujesz lokalizację w Londynie w Wielkiej Brytanii.
- Dodaj do klasy
MainActivityobiekt towarzyszący, aby przechowywać lokalizację początkową i identyfikator miejsca. W ćwiczeniach z programowania użyjemy lokalizacji początkowej w Londynie i identyfikatora miejsca Trafalgar Square:
companion object{
const val TRAFALGAR_SQUARE ="ChIJH-tBOc4EdkgRJ8aJ8P1CUxo" //London, UK
val startLocation = LatLng(51.345678, -0.1234456)
}
- Dodaj wywołanie metody
navigateToPlace()z wywołania zwrotnegoonNavigatorReadyw metodzieinitializeNavigationApii dodaj gałąź logiki, która będzie wykonywana w trybie debugowania i ustawi lokalizację użytkownika:
// Disables the guidance notifications and shuts down the app and background service
// when the user dismisses/swipes away the app from Android's recent tasks.
navigator.setTaskRemovedBehavior(Navigator.TaskRemovedBehavior.QUIT_SERVICE)
mNavigator = navigator
if (BuildConfig.DEBUG) {
mNavigator?.simulator?.setUserLocation(MainActivity.startLocation)
}
//listen for events en route
registerNavigationListeners()
navView.getMapAsync {
googleMap ->
googleMap.followMyLocation(GoogleMap.CameraPerspective.TILTED)
}
//navigate to a destination
navigateToPlace(MainActivity.TRAFALGAR_SQUARE)
10. Tworzenie i uruchamianie kodu
Przy pierwszym uruchomieniu aplikacji musisz przyznać jej uprawnienia do lokalizacji i zaakceptować warunki korzystania z pakietu Navigation SDK.
Uwaga: uruchomienie aplikacji spowoduje wywołanie metody setDestinations(), która po użyciu pierwszych 1000 miejsc docelowych wiąże się z opłatą. Więcej informacji znajdziesz w artykule Wykorzystanie i rozliczenia.


Ustawianie lokalizacji
Domyślnie emulowane urządzenie może mieć ustawioną lokalizację w kampusie Google w Mountain View w Kalifornii, chyba że lokalizacja została ustawiona w kodzie lub w oknie właściwości emulatora.
Jeśli tak jest, aplikacja może nie znaleźć trasy do skonfigurowanego identyfikatora miejsca (domyślnie jest to Opera w Sydney w Australii). Wskaże to komunikat „Nie znaleziono trasy” wyświetlany przez metodę showToast().

Zakodowanie na stałe lokalizacji początkowej
Aby ustawić inną lokalizację w kodzie, dodaj ten wiersz do metody navigateToPlace() w pliku MainActivity.kt przed wywołaniem funkcji mNavigator.startGuidance():
mNavigator?.simulator?.setUserLocation(startLocation)
Uruchamianie emulatora w wybranej domyślnej lokalizacji
Aby ustawić inną lokalizację w emulatorze urządzenia, uruchom go, jeśli jeszcze nie działa, i kliknij menu z 3 kropkami z etykietką „Rozszerzone ustawienia”. W wyświetlonym oknie znajduje się opcja menu „Lokalizacja”.
Jeśli np. jako miejsce docelowe używasz identyfikatora miejsca Sydney Opera House, wybierz lokalizację w Sydney w Australii. Na przykład wyszukaj „Bondi Beach”, wybierz sugestię i w prawym dolnym rogu okna kliknij „Zapisz lokalizację”. Możesz też kliknąć „Zapisz punkt”, aby dodać lokalizację do zapisanej listy do wykorzystania w przyszłości.

Jeśli jako miejsce docelowe ustawisz inny identyfikator miejsca, wybierz lokalizację w pobliżu, aby symulowana trasa była realistyczna i nie za długa, co ułatwi debugowanie.
Uruchom ponownie aplikację. Powinna teraz przejść do miejsca docelowego.

11. Gratulacje!
To koniec tego ćwiczenia. Gratulacje – dotarliśmy do celu! Pozdrawiamy :-)

12. Możesz zrobić jeszcze więcej
Jeśli chcesz dalej rozwijać swoją aplikację, zapoznaj się z poniższymi tematami, aby znaleźć inspirację.
- Nasłuchiwanie większej liczby zdarzeń nawigacyjnych Dodaj kod, aby wyświetlać wiadomość, gdy kierowca zmieni trasę lub gdy dotrze na miejsce.
- Dostosowywanie interfejsu nawigacji
- Jeśli chcesz podjąć większe wyzwanie, spróbuj dodać kontrolkę selektora miejsca z interfejsu Places API, aby umożliwić użytkownikowi ustawienie miejsca docelowego. Wskazówka: przykładowe aplikacje pakietu Navigation SDK w serwisie GitHub zawierają przykładową implementację.
- Zapobiegaj potencjalnym problemom z asynchronicznym wywoływaniem obiektów Navigator i GoogleMap, stosując podejście użyte w aplikacjach demonstracyjnych pakietu Navigation SDK w GitHubie. W bardziej złożonych scenariuszach aplikacji te obiekty mogą nie być jeszcze zainicjowane w momencie uruchomienia kodu. Wskazówka: aby szybko wdrożyć tę funkcję, możesz dodać klasę InitializedNavScope na końcu pliku MainActivity.kt.