HERE SDK for Android (Premium Edition)
SDK for Android Developer's Guide

# Turn-by-Turn Navigation for Walking and Driving

Note: [Important] Application developers using the Turn-by-turn Guidance APIs are required to thoroughly test their applications in all expected usage scenarios to ensure safe and correct behavior. Application developers are responsible for warning app users of obligations including but not limited to:
1. Do not follow instructions that may lead to an unsafe or illegal situation.
2. Obey all local laws.
3. Be aware that using a mobile phone or some of its features while driving may be prohibited.
4. Always keep hands free to operate the vehicle while driving.
5. The first priority while driving should be road safety.

SDK for Android supports navigation on pedestrian , truck, and car routes. Using this feature, your app can check the current device position against a calculated route and get just-in-time navigational instructions. Both visual and audio instructions are supported.

SDK for Android can also track the current position and display it on the map without a calculated route.

NavigationManager class is responsible for providing voice and visual instructions to the user while driving or walking. An instance of NavigationManager can be retrieved using NavigationManager.getInstance(). It should be associated with a map with setMap(Map) method before navigation is started.

Navigation can be started in three different modes:
• Simulation Mode - simulate(Route, long) - This mode does not require any GPS data from the device as the position is simulated along the given route.
• Navigation Mode - startNavigation(Route) - This mode takes the calculated route and matches the position against the route. Before using this mode, PositioningManager is required to be running with GPS data.
• Tracking Mode - startTracking() - This mode does not require a calculated route as it only tracks and shows the current position on the map.
Note: Android permission android.permission.ACCESS_FINE_LOCATION is required to use NavigationManager. Otherwise, the class returns Error.POSITIONING_FAILED. In addition, to ensure that the app receives location updates, the user needs to have the Location permission enabled (toggled to "on") during runtime.

The following is an example of performing navigation on a calculated route:



//set the map where the navigation will be performed

// if user wants to start real navigation, submit calculated route
// for more information on calculating a route, see the "Directions" section

Note: During a navigation session it is recommended that you handle gestures by calling NavigationManager.setMapUpdateMode(MapUpdateMode.NONE). This stops the map from moving but it does not affect position indicator movement and voice navigation. To re-enable map movement, call NavigationManager.setMapUpdateMode(MapUpdateMode) with the previous update mode enum, e.g. MapUpdateMode.ROADVIEW.

If you are using Turn-by-Turn Navigation Mode for driving, you can also set HERE SDK to perform guidance (including voice instructions and event callbacks) while the app is in the background. However, unlike the foreground navigation scenario, HERE SDK does not stream map data during background navigation on Android. To properly support background navigation for these devices, HERE SDK requires your app to preload map data (such as for the current city or state) using the MapLoader class.

Important: Starting with Android O (8.0), if your app is running in the background, then the location system service only computes a new location for your app a few times each hour. To avoid this behavior, start a foreground service by following the instructions in the Android documentation.
Important: Starting with Android P (9.0), app that requires use of foreground service must request android.permission.FOREGROUND_SERVICE permission from the user. For more information, please refer to Android Pie behaviour change documentation.

For navigation operation to work properly on application that does NOT use MapView or AndroidXMapFragment, the application needs to do the followings:
1. MapEngine.getInstance().onResume() should be called when the engine is required for headless navigation operations. (For example, you may want to retrieve speed warnings but do not want to draw a map.) This puts the engine in the "active state". MapEngine.getInstance().onPause() puts the engine into a suspended state and release cached in memory data. onResume() and onPause() methods are reference-counted and should be called an equal number of times.
2. Since a map is not displayed with this approach, map data will not be passively downloaded. Instead, the application must first download the required map data through the use of MapLoader or MapDataPrefetcher. Otherwise, navigation operations will not work properly.

Map Matching is automatically enabled in both navigation mode and tracking mode. In simulation mode, the map-matched position is simulated along the route with a user-defined speed.

## Tunnel Extrapolation

Tunnel extrapolation is also performed internally by NavigationManager. It uses the last available position data which contains speed, orientation and GeoCoordinate to estimate the position of your vehicle inside a tunnel. If your application listens to position updates from NavigationManager.PositionListener, there are regular position updates during tunnel extrapolation. However, if your application also listens to the onPositionFixChanged() callback from PositioningManager.OnPositionChangedListener, then it receives this callback signifying a position fix change. (For more information on the OnPositionChangedListener, see Positioning section.) If the road element at position contains the tunnel attribute, it implies that the current location is provided by tunnel extrapolation. Position updates during tunnel extrapolation should be treated the same way as regular updates.

The following sample code demonstrates how to determine if tunnel extrapolation is active:

// At startup, have a member variable position manager setup
// and listening to events
positioningManager = PositioningManager.getInstance();
new WeakReference<PositioningManager.OnPositionChangedListener>(this);
positioningManager.start(LocationMethod.GPS_NETWORK);

......

// upon callback, determine if tunnel extrapolation is active

public void onPositionFixChanged(LocationMethod method, LocationStatus status) {
if (method == LocationMethod.GPS) {
boolean isExtrapolated =
boolean hasGps = status == LocationStatus.AVAILABLE;
}
}


## Natural Guidance

NavigationManager.setNaturalGuidanceMode() method can be used to enable natural guidance. Natural guidance refers to a type of dynamic information available during navigation where route guidance instructions contain contextual elements around a decision point. These contextual elements may include services, cartographic features, traffic signals, and stop signs. Some examples of natural guidance instructions are:
• "Go past the park on your right, then turn left at Anderson school on Bayview street"
• "Go through the traffic light and turn right before the petrol station"
• "Continue on your route passing the dome building on your right"
Three options are available for natural guidance, and they are defined by NavigationManager.NaturalGuidanceMode enumerations. Note that STOP_SIGN, TRAFFIC_LIGHT and JUNCTION can be used together. To disable natural guidance, call setNaturalGuidanceMode(EnumSet<NaturalGuidanceMode>) method with an empty EnumSet.
• TRAFFIC_LIGHT - Natural guidance for traffic lights
• STOP_SIGN - Natural guidance for stop signs
• JUNCTION - Natural guidance for junctions such as landmarks
To use the natural guidance feature, set your voice package to the map display language. Also, to get the best results, use the appropriate voice package for the current location. For example, use the French voice package in the city of Paris. Natural guidance currently supports the following text-to-speech voice packages:
• U.S. English
• U.K. English
• Italian
• Spanish
• German
• French