mapbox / mapbox-navigation-android Goto Github PK
View Code? Open in Web Editor NEWMapbox Navigation SDK for Android
Home Page: https://docs.mapbox.com/android/navigation/overview/
License: Other
Mapbox Navigation SDK for Android
Home Page: https://docs.mapbox.com/android/navigation/overview/
License: Other
the constant found on this line needs to be switched out for the options.get...
method.
Hey,
I'm using your pretty cool MockLocationEngine from the demo project. I noticed that the myLocationEnabled state is resettet after the LocationEngine is set (@ mapbox-android-navigation:0.2.0).
If I use only this code, the myLocation-Dot at the map doesn't move (even if I had set myLocationEnabled to true and MyLocationTracking.TRACKING_FOLLOW).
mapboxMap.setLocationSource(mockLocationEngine);
With the additional line
mapboxMap.setMyLocationEnabled(true);
everything work well.
But: In both cases the onMyLocationChange-Listener receives the update from MockLocationEngine
Similar to how we have created a module for RxJava specific support in Mapbox-Java, we should consider doing the same for the navigation SDK.
I can't seem to get the navigation to start from a fragment.
All is fine on the routing front, draws the route. But it seems that the line below is where nothing happens:
navigation.startNavigation(route);
No Errors, nothing back from the navigation listeners.
Here is my code
package au.com.gardenbagsbrisbane.gardenbagsdriver.fragment;
import android.content.Context;
import android.graphics.Color;
import android.location.Location;
import android.net.Uri;
import android.os.Bundle;
import android.app.Fragment;
import android.support.annotation.NonNull;
import android.support.design.widget.BaseTransientBottomBar;
import android.support.design.widget.FloatingActionButton;
import android.support.design.widget.Snackbar;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.Toast;
import au.com.gardenbagsbrisbane.gardenbagsdriver.R;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import timber.log.Timber;
import com.mapbox.mapboxsdk.Mapbox;
import com.mapbox.mapboxsdk.annotations.Marker;
import com.mapbox.mapboxsdk.annotations.MarkerOptions;
import com.mapbox.mapboxsdk.annotations.Polyline;
import com.mapbox.mapboxsdk.annotations.PolylineOptions;
import com.mapbox.mapboxsdk.camera.CameraUpdateFactory;
import com.mapbox.mapboxsdk.constants.MyLocationTracking;
import com.mapbox.mapboxsdk.constants.Style;
import com.mapbox.mapboxsdk.geometry.LatLng;
import com.mapbox.mapboxsdk.location.LocationSource;
import com.mapbox.mapboxsdk.maps.MapView;
import com.mapbox.mapboxsdk.maps.MapboxMap;
import com.mapbox.mapboxsdk.maps.OnMapReadyCallback;
import com.mapbox.services.Constants;
import com.mapbox.services.android.navigation.v5.MapboxNavigation;
import com.mapbox.services.android.navigation.v5.NavigationConstants;
import com.mapbox.services.android.navigation.v5.RouteProgress;
import com.mapbox.services.android.navigation.v5.listeners.AlertLevelChangeListener;
import com.mapbox.services.android.navigation.v5.listeners.NavigationEventListener;
import com.mapbox.services.android.navigation.v5.listeners.OffRouteListener;
import com.mapbox.services.android.navigation.v5.listeners.ProgressChangeListener;
import com.mapbox.services.android.telemetry.location.LocationEngine;
import com.mapbox.services.android.telemetry.location.LocationEngineListener;
import com.mapbox.services.android.telemetry.location.LocationEnginePriority;
import com.mapbox.services.android.telemetry.permissions.PermissionsListener;
import com.mapbox.services.android.telemetry.permissions.PermissionsManager;
import com.mapbox.services.api.directions.v5.models.DirectionsResponse;
import com.mapbox.services.api.directions.v5.models.DirectionsRoute;
import com.mapbox.services.commons.geojson.LineString;
import com.mapbox.services.commons.models.Position;
import java.util.ArrayList;
import java.util.List;
/**
* A simple {@link Fragment} subclass.
* Activities that contain this fragment must implement the
* {@link HomeFragment.OnFragmentInteractionListener} interface
* to handle interaction events.
* Use the {@link HomeFragment#newInstance} factory method to
* create an instance of this fragment.
*/
public class HomeFragment extends Fragment implements PermissionsListener, OnMapReadyCallback,MapboxMap.OnMapClickListener,
ProgressChangeListener, NavigationEventListener, AlertLevelChangeListener, OffRouteListener {
// TODO: Rename parameter arguments, choose names that match
// the fragment initialization parameters, e.g. ARG_ITEM_NUMBER
private static final String ARG_PARAM1 = "param1";
private static final String ARG_PARAM2 = "param2";
private MapView mapView = null;
private MapboxMap map;
private FloatingActionButton floatingActionButton;
private LocationEngineListener locationEngineListener;
private PermissionsManager permissionsManager;
private Marker destinationMarker;
// Navigation related variables
private LocationEngine locationEngine;
private MapboxNavigation navigation;
private FloatingActionButton startRouteButton;
private DirectionsRoute route;
private Position destination;
private Polyline routeLine;
// TODO: Rename and change types of parameters
private String mParam1;
private String mParam2;
private OnFragmentInteractionListener mListener;
public HomeFragment() {
// Required empty public constructor
}
/**
* Use this factory method to create a new instance of
* this fragment using the provided parameters.
*
* @param param1 Parameter 1.
* @param param2 Parameter 2.
* @return A new instance of fragment HomeFragment.
*/
// TODO: Rename and change types and number of parameters
public static HomeFragment newInstance(String param1, String param2) {
HomeFragment fragment = new HomeFragment();
Bundle args = new Bundle();
args.putString(ARG_PARAM1, param1);
args.putString(ARG_PARAM2, param2);
fragment.setArguments(args);
return fragment;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if (getArguments() != null) {
mParam1 = getArguments().getString(ARG_PARAM1);
mParam2 = getArguments().getString(ARG_PARAM2);
}
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
Mapbox.getInstance(getActivity(), getString(R.string.access_token));
View layout = inflater.inflate(R.layout.fragment_home, container, false);
mapView = (MapView) layout.findViewById(R.id.mapboxMapView);
mapView.onCreate(savedInstanceState);
mapView.getMapAsync(this);
//locationEngine.activate();
locationEngine = LocationSource.getLocationEngine(getActivity());
navigation = new MapboxNavigation(getActivity(), Mapbox.getAccessToken());
locationEngine.setInterval(0);
locationEngine.setSmallestDisplacement(3.0f);
locationEngine.setPriority(LocationEnginePriority.HIGH_ACCURACY);
locationEngine.setFastestInterval(1000);
navigation.setLocationEngine(locationEngine);
floatingActionButton = (FloatingActionButton) layout.findViewById(R.id.location_toggle_fab);
floatingActionButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (map != null) {
toggleGps(!map.isMyLocationEnabled());
}
}
});
startRouteButton = (FloatingActionButton) layout.findViewById(R.id.startRouteButton);
startRouteButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (navigation != null && route != null) {
// Hide the start button
startRouteButton.setVisibility(View.INVISIBLE);
// Attach all of our navigation listeners.
navigation.addNavigationEventListener(HomeFragment.this);
navigation.addProgressChangeListener(HomeFragment.this);
navigation.addAlertLevelChangeListener(HomeFragment.this);
// Adjust location engine to force a gps reading every second. This isn't required but gives an overall
// better navigation experience for users. The updating only occurs if the user moves 3 meters or further
// from the last update.
navigation.startNavigation(route);
}
else
{
Timber.e("No valid navigation object or route");
}
}
});
return layout;
}
// TODO: Rename method, update argument and hook method into UI event
public void onButtonPressed(Uri uri) {
if (mListener != null) {
mListener.onFragmentInteraction(uri);
}
}
@Override
public void onMapReady(MapboxMap mapboxMap) {
map = mapboxMap;
map.setOnMapClickListener(HomeFragment.this);
Snackbar.make(mapView, "Tap map to place destination", BaseTransientBottomBar.LENGTH_LONG).show();
map.moveCamera(CameraUpdateFactory.zoomBy(12));
if (PermissionsManager.areLocationPermissionsGranted(getActivity())) {
mapboxMap.setMyLocationEnabled(true);
mapboxMap.getTrackingSettings().setMyLocationTrackingMode(MyLocationTracking.TRACKING_FOLLOW);
}
}
@Override
public void onMapClick(@NonNull LatLng point) {
if (destinationMarker != null) {
map.removeMarker(destinationMarker);
}
destinationMarker = map.addMarker(new MarkerOptions().position(point));
startRouteButton.setVisibility(View.VISIBLE);
destination = Position.fromCoordinates(point.getLongitude(), point.getLatitude());
calculateRoute();
}
private void drawRouteLine(DirectionsRoute route) {
List<Position> positions = LineString.fromPolyline(route.getGeometry(), Constants.PRECISION_6).getCoordinates();
List<LatLng> latLngs = new ArrayList<>();
for (Position position : positions) {
latLngs.add(new LatLng(position.getLatitude(), position.getLongitude()));
}
// Remove old route if currently being shown on map.
if (routeLine != null) {
map.removePolyline(routeLine);
}
routeLine = map.addPolyline(new PolylineOptions()
.addAll(latLngs)
.color(Color.parseColor("#56b881"))
.width(5f));
}
private void calculateRoute() {
Location userLocation = map.getMyLocation();
if (userLocation == null) {
Timber.d("calculateRoute: User location is null, therefore, origin can't be set.");
return;
}
Position origin = (Position.fromCoordinates(userLocation.getLongitude(), userLocation.getLatitude()));
navigation.getRoute(origin, destination, new Callback<DirectionsResponse>() {
@Override
public void onResponse(Call<DirectionsResponse> call, Response<DirectionsResponse> response) {
DirectionsRoute route = response.body().getRoutes().get(0);
HomeFragment.this.route = route;
drawRouteLine(route);
navigation.addNavigationEventListener(HomeFragment.this);
navigation.addProgressChangeListener(HomeFragment.this);
navigation.addAlertLevelChangeListener(HomeFragment.this);
// Adjust location engine to force a gps reading every second. This isn't required but gives an overall
// better navigation experience for users. The updating only occurs if the user moves 3 meters or further
// from the last update.
navigation.startNavigation(route);
}
@Override
public void onFailure(Call<DirectionsResponse> call, Throwable throwable) {
Timber.e("onFailure: navigation.getRoute()", throwable);
}
});
}
/*
* Navigation listeners
*/
@Override
public void onRunning(boolean running) {
if (running) {
Timber.d("onRunning: Started");
} else {
Timber.d("onRunning: Stopped");
}
}
@Override
public void onProgressChange(Location location, RouteProgress routeProgress) {
Timber.d("onProgressChange: fraction of route traveled: %f", routeProgress.getFractionTraveled());
}
@Override
public void onAlertLevelChange(int alertLevel, RouteProgress routeProgress) {
switch (alertLevel) {
case NavigationConstants.HIGH_ALERT_LEVEL:
Toast.makeText(getActivity(), "HIGH", Toast.LENGTH_LONG).show();
break;
case NavigationConstants.MEDIUM_ALERT_LEVEL:
Toast.makeText(getActivity(), "MEDIUM", Toast.LENGTH_LONG).show();
break;
case NavigationConstants.LOW_ALERT_LEVEL:
Toast.makeText(getActivity(), "LOW", Toast.LENGTH_LONG).show();
break;
case NavigationConstants.ARRIVE_ALERT_LEVEL:
Toast.makeText(getActivity(), "ARRIVE", Toast.LENGTH_LONG).show();
break;
case NavigationConstants.DEPART_ALERT_LEVEL:
Toast.makeText(getActivity(), "DEPART", Toast.LENGTH_LONG).show();
break;
default:
case NavigationConstants.NONE_ALERT_LEVEL:
Toast.makeText(getActivity(), "NONE", Toast.LENGTH_LONG).show();
break;
}
}
@Override
public void userOffRoute(Location location) {
Position newOrigin = Position.fromCoordinates(location.getLongitude(), location.getLatitude());
navigation.updateRoute(newOrigin, destination, new Callback<DirectionsResponse>() {
@Override
public void onResponse(Call<DirectionsResponse> call, Response<DirectionsResponse> response) {
DirectionsRoute route = response.body().getRoutes().get(0);
HomeFragment.this.route = route;
// Remove old route line from map and draw the new one.
map.removePolyline(routeLine);
drawRouteLine(route);
}
@Override
public void onFailure(Call<DirectionsResponse> call, Throwable throwable) {
Timber.e("onFailure: navigation.getRoute()", throwable);
}
});
}
/*
* Activity lifecycle methods
*/
@Override
public void onAttach(Context context) {
super.onAttach(context);
if (context instanceof OnFragmentInteractionListener) {
mListener = (OnFragmentInteractionListener) context;
} else {
throw new RuntimeException(context.toString()
+ " must implement OnFragmentInteractionListener");
}
}
@Override
public void onStart() {
super.onStart();
mapView.onStart();
}
@Override
public void onDetach() {
super.onDetach();
mListener = null;
}
@Override
public void onPause() {
super.onPause();
mapView.onPause();
}
@Override
public void onStop() {
super.onStop();
mapView.onStop();
navigation.onStop();
}
@Override
public void onResume() {
super.onResume();
mapView.onResume();
}
@Override
public void onDestroy() {
super.onDestroy();
mapView.onDestroy();
if (locationEngineListener != null) {
locationEngine.removeLocationEngineListener(locationEngineListener);
}
// Remove all navigation listeners
navigation.removeAlertLevelChangeListener(this);
navigation.removeNavigationEventListener(this);
navigation.removeProgressChangeListener(this);
navigation.removeOffRouteListener(this);
// End the navigation session
navigation.endNavigation();
}
@Override
public void onLowMemory() {
super.onLowMemory();
mapView.onLowMemory();
}
@Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
mapView.onSaveInstanceState(outState);
}
private void toggleGps(boolean enableGps) {
if (enableGps) {
// Check if user has granted location permission
permissionsManager = new PermissionsManager(this);
if (!PermissionsManager.areLocationPermissionsGranted(getActivity())) {
Log.v("GPS","Requesting permissions");
permissionsManager.requestLocationPermissions(getActivity());
} else {
enableLocation(true);
}
} else {
enableLocation(false);
}
}
private void enableLocation(boolean enabled) {
if (enabled) {
// If we have the last location of the user, we can move the camera to that position.
Location lastLocation = locationEngine.getLastLocation();
if (lastLocation != null) {
map.moveCamera(CameraUpdateFactory.newLatLngZoom(new LatLng(lastLocation), 16));
}
locationEngineListener = new LocationEngineListener() {
@Override
public void onConnected() {
// No action needed here.
}
@Override
public void onLocationChanged(Location location) {
if (location != null) {
// Move the map camera to where the user location is and then remove the
// listener so the camera isn't constantly updating when the user location
// changes. When the user disables and then enables the location again, this
// listener is registered again and will adjust the camera once again.
map.moveCamera(CameraUpdateFactory.newLatLngZoom(new LatLng(location), 16));
locationEngine.removeLocationEngineListener(this);
}
}
};
locationEngine.addLocationEngineListener(locationEngineListener);
floatingActionButton.setImageResource(R.drawable.ic_location_disabled_24dp);
} else {
floatingActionButton.setImageResource(R.drawable.ic_my_location_24dp);
}
// Enable or disable the location layer on the map
map.setMyLocationEnabled(enabled);
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
permissionsManager.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
@Override
public void onExplanationNeeded(List<String> permissionsToExplain) {
Toast.makeText(getActivity(), "This app needs location permissions in order to show its functionality.",
Toast.LENGTH_LONG).show();
}
@Override
public void onPermissionResult(boolean granted) {
if (granted) {
enableLocation(true);
} else {
Toast.makeText(getActivity(), "You didn't grant location permissions.",
Toast.LENGTH_LONG).show();
getActivity().finish();
}
}
/**
* This interface must be implemented by activities that contain this
* fragment to allow an interaction in this fragment to be communicated
* to the activity and potentially other fragments contained in that
* activity.
* <p>
* See the Android Training lesson <a href=
* "http://developer.android.com/training/basics/fragments/communicating.html"
* >Communicating with Other Fragments</a> for more information.
*/
public interface OnFragmentInteractionListener {
// TODO: Update argument type and name
void onFragmentInteraction(Uri uri);
}
}
In order to be able to release the first version of the Mapbox Navigation SDK for Android as a standalone project, the following things need to happen:
cc: @cammace @danesfeder
Original ticket opened by @Guardiola31337 in MAS mapbox/mapbox-java#436.
handler
could be null
which would make the app to crash.
Following snippet will fix the issue.
if (handler != null) {
handler.postDelayed(new LocationUpdateRunnable(), UPDATE_INTERVAL_MS);
}
Hi, i have implemented a simple navigation UI, from the information that "RouteProgress" object gives. this is how i create "MapboxDirection" object:
return new MapboxDirections.Builder()
.setOverview(DirectionsCriteria.OVERVIEW_FULL)
.setSteps(true)
.setAccessToken(getString(R.string.mapbox_access_token))
.setCoordinates(coords)
.setProfile(DirectionsCriteria.PROFILE_DRIVING)
.build();
coords are a list of coordinates, where the first element in the list is my current location, the last element is the destination, and <21 points in between are waypoints (not stopovers). But the RouteProgress + onAlertLevelChange seems to think that when i come to my second coordinate (from my current location to first waypoint), that the trip is over and i get "You have arrived at your destination" in routeProgress.getCurrentLegProgress().getUpComingStep().getManeuver().getInstruction()
and the routeProgress.getCurrentLegProgress().getDistanceRemaining()
is 0. But routeProgress.getDistanceRemaining()
and the duration of the whole routeProgress is still there. I also get ARRIVE_ALERT_LEVEL in onAlertLevelChange, at the second coordinate.So how do i make the navigation advance the route leg, without actually stopping navigatint after the fist waypoint.
Sometimes while running the demo app and the Navigation example it crashes after you have started a route. Does not happen all the time. I tried 5-10 times without a crash yesterday but later I got 5 crashes in a row.
Tested on Google Pixel XL running 7.1.2 and navigation 0.1.
E java.lang.NullPointerException: Attempt to invoke virtual method 'double com.mapbox.services.android.navigation.v5.MapboxNavigationOptions.getMinimumHighAlertDistance()' on a null object reference
E at com.mapbox.services.android.navigation.v5.LocationUpdatedThread.monitorStepProgress(LocationUpdatedThread.java:158)
Should make sure options are not null for that entire method. Seeing that options is used later in that method (monitorStepProgress)
as well.
Currently, OSRM text instructions aren't being exposed inside the navigation sdk.
Causing a crash on Firebase, temporarily fixed it in the testapp activity, this might need to be fixed in mapbox-java too @zugaldia?
Hello,
Is there a drop in controller that can has been implemented for android just like the one in the iOS repository here? https://github.com/mapbox/mapbox-navigation-ios
I would like to use map box and I just want to know if there is already one in the works before I start doing any heavy lifting.
Hey,
I don't know if this is a navigation issue or a general mapbox-java issue.
My setup on a Google Nexus 6 with Android 6.0 is:
compile ('com.mapbox.mapboxsdk:mapbox-android-sdk:5.1.0-beta.2@aar') {
transitive = true
exclude module: 'lost'
exclude module: 'mapbox-java-geojson'
exclude module: 'mapbox-android-telemetry'
}
compile('com.mapbox.mapboxsdk:mapbox-android-services:2.1.0@aar') {
transitive = true
}
compile 'com.mapbox.mapboxsdk:mapbox-android-navigation:0.2.0'
If the user has allowed the smartphone to locate himself, everything work fine (app permissions for localisation are granted).
But if he disables the localisation, and I run the following code, the app crashes after I activate the location engine:
LocationEngine locationEngine = LocationSource.getLocationEngine(context);
locationEngine.activate();
05-24 15:35:21.661 15330-15330/? W/System.err: java.lang.AbstractMethodError: abstract method "void com.mapzen.android.lost.api.LocationListener.onProviderDisabled(java.lang.String)"
05-24 15:35:21.662 15330-15330/? W/System.err: at com.mapzen.android.lost.internal.LostClientManager.reportProviderDisabled(LostClientManager.java:205)
05-24 15:35:21.662 15330-15330/? W/System.err: at com.mapzen.android.lost.internal.FusedLocationProviderServiceImpl.reportProviderDisabled(FusedLocationProviderServiceImpl.java:145)
05-24 15:35:21.662 15330-15330/? W/System.err: at com.mapzen.android.lost.internal.FusionEngine.onProviderDisabled(FusionEngine.java:214)
05-24 15:35:21.662 15330-15330/? W/System.err: at android.location.LocationManager$ListenerTransport._handleMessage(LocationManager.java:310)
05-24 15:35:21.662 15330-15330/? W/System.err: at android.location.LocationManager$ListenerTransport.-wrap0(LocationManager.java)
05-24 15:35:21.662 15330-15330/? W/System.err: at android.location.LocationManager$ListenerTransport$1.handleMessage(LocationManager.java:242)
05-24 15:35:21.662 15330-15330/? W/System.err: at android.os.Handler.dispatchMessage(Handler.java:102)
05-24 15:35:21.662 15330-15330/? W/System.err: at android.os.Looper.loop(Looper.java:154)
05-24 15:35:21.662 15330-15330/? W/System.err: at android.app.ActivityThread.main(ActivityThread.java:6077)
05-24 15:35:21.662 15330-15330/? W/System.err: at java.lang.reflect.Method.invoke(Native Method)
05-24 15:35:21.662 15330-15330/? W/System.err: at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:865)
05-24 15:35:21.662 15330-15330/? W/System.err: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:755)
Best regards,
Patrick
Currently, the navigation example in the testapps using mock location engine, a separate activity should be created using the LOST location provider.
iOS added the ability for different profiles such as biking for a navigation session.
Breakup monitorStepProgress method into smaller, more testable, methods and easier readability. Currently it is a direct port from the Swift function found here. Tagging @bsudekum and @1ec5 since this could potentially break parity with the iOS SDK.
cc: @zugaldia @danesfeder
While our other SDK testapps generate the access token file, we currently have to do this manually in the nav testapp.
cc: @Guardiola31337
Now that RouteProgress has moved to an Android project, we can take advantage of the annotations to further ensure parameters, methods, classes, etc. are correct.
Hey,
is there a plan to add different route calculation parameters?
For example:
car
bicycle
pedestrian
fastes route
shortest route
language (for maneuver instructions)
Best regards,
Patrick
I'm having issues running the test application. OnCreate in each activity fails to load when setting the view.
setContentView(R.layout.activity_navigation_activity);
android.view.InflateException: Binary XML file line #12: Binary XML file line #12: Error inflating class com.mapbox.mapboxsdk.maps.MapView
I'm at a loss to what the issue is, as I'm running the entire project cloned.
Thanks for any help!
Useful for many reasons but hasn't been implemented since mapbox/mapbox-java#450 hasn't been decided yet.
Original ticket: mapbox/mapbox-java#233
For routeUtils, we should allow the user to specify which units they want to use for distance values. Currently we are just using the default value.
This ticket tracks the release of Mapbox Android Navigation SDK v0.3.0
. The leading feature in this release are listed below:
0.3.0
milestone0.3.0
in gradle.properties
0.3.0
artifact to Maven Central0.4.0-SNAPSHOT
CHANGELOG.md
v0.3.0
in GitHubREADME.md
/android-docs
/cc: @mapbox/navigation
Following in the footsteps of the Map SDK, we should switch CI to use CircleCi instead of Bitrise
Once #1 lands, and before we publish the first release, we need to integrate this project with our CI system.
cc: @danesfeder
when I click start route, no thing happen the navigation not work why, there is no error
The following files contain translatable messages that should be localized at Transifex:
https://github.com/mapbox/mapbox-navigation-android/blob/master/navigation/app/src/main/res/values/strings.xml
https://github.com/mapbox/mapbox-navigation-android/blob/master/navigation/libandroid-navigation/src/main/res/values/strings.xml
We’ll want to set up a separate project under the Mapbox organization. Though Transifex mostly supports drawing in resources from multiple repositories, the tx
client works best when a Transifex project is hooked up to a single repository. For convenience, we can share the same translation teams as the iOS navigation SDK and the map SDKs.
make prepare-osrm
already pulls in translations from the OSRM Text Instructions project on Transifex, so guidance instructions should already be localized as long as we’re using TextInstructions
wherever we need to display an instruction.
Once #1 lands, and before we publish the first release, we need to add Maven functionality (for both local and remote installs).
Sometimes, maneuver completion announcements can happen prematurely.
An example of a driver that's told to make a left turn:
He arrives at the light and stops at the intersection. While he's stationary and waiting for the light to turn, the SDK considers the maneuver complete (presumably because the GPS location moved around slightly) and gives him the next instruction as if he's continued driving. Despite the announcement, the confused user is still waiting for the light to turn green.
@1ec5 proposed a more sophisticated model for determining maneuver state:
Ultimately, we may need to model maneuvers as a state machine rather than reevaluating turn completion factors from scratch on every location update.
Android version of mapbox/mapbox-navigation-ios#222
cc @cammace
This ticket tracks the release of Mapbox Android Navigation SDK v0.3.1
. This release brings many improvements to the RouteProgress objects and significantly increases performance.
0.3.1
milestone0.3.1
in gradle.properties
0.3.1
artifact to Maven Central0.4.0-SNAPSHOT
CHANGELOG.md
v0.3.1
in GitHubREADME.md
/android-docs
In order to better control when location updates occur, a Kalman filter can be used to force location updates between real GPS updates.
cc: @zugaldia
Occasionally during rerouting, the SDK will return a maneuver that's too close to the user's current location and can lead to a missed turn and frequent + repeated re-routing.
If the user was driving 70km/h along a road and missed a left turn, the navigation SDK would trigger a re-route and receive a directions response requiring another left turn or U-turn almost immediately. At the high speed the user was traveling, the immediacy of the maneuver would be too much to act on, and the user would miss the turn and trigger another re-route, and so on.
As a first pass suggestion by @danpat, we can validate that a re-route is reasonable before presenting to the user:
- Request the re-route and get back the new response from the Directions API.
- Examine the first step. If it's not too quick, display the re-route to the user.
If it is "too quick" (threshold to be determined), use the intersections object to predict the driver's probable path past the "too quick turn", and request another route from the Directions API that starts somewhere past the "too quick" turn.
cc @cammace
Once mapbox/mapbox-java#476 merges, use this implementation instead.
Introduce the MapboxNavigationOptions
to allow developers to set their own constant values if needed.
cc: @zugaldia @danesfeder
RouteUtils is no longer needed and can be removed in favor of placing the logic directly where it is needed.
The current implementation can be significantly improved; we offer the option to consider the user's bearing when first creating a route but not when rerouting. Additionally, the rerouting should find the user's future position x time in the future (using dead reckoning). Potentially lower the off-route threshold when already detected off-route at first.
When a navigation session begins, we take the instance of the locationEngine passed in and force the updating to happen more frequently. After a nav session, the locationEngine is automatically set to a lower battery consumption settings but this isn't necessarily what the developer had before they started navigating. Perhaps this is an API we should include in locationEngine, thoughts @zugaldia?
We don't allow much customization for the notification currently being offered in the SDK, we should add a default notification but also allow devs to pass in their own notifications or even disable the notifications.
The NavigationService onProgressChance can be used for updating the notification.
Hi guys, first of all, thanks for the great work on this, I'm testing it right now and it's really cool.
It seems like the url to the Javadoc is wrong on the documentation page:
https://www.mapbox.com/android-docs/navigation/latest/getting-started/#api-reference
Thanks.
Hello MapBox !
Platform: Android
Mapbox SDK version: 4.2.2
I need to find a route for cycling users so my app is on Cycling profile, but this profile allow parking and private roads.
For now I use Driving profile to avoid these problems, but one way roads and cycling ways are not allowed in this mode.
Do someone have to solve this problem or someones know how to deal with it ?
Arrival Point before parking's exit :
05-19 17:51:08.972 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 17.0
05-19 17:51:08.972 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 2.6673089788901962
05-19 17:51:09.912 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:51:09.912 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.120464490039302
05-19 17:51:11.899 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:51:11.899 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.1952861108700281
05-19 17:51:12.935 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:51:12.935 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.5276582018307443
05-19 17:51:14.946 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 16.0
05-19 17:51:14.947 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.2958761817742823
05-19 17:51:15.942 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 17.0
05-19 17:51:15.942 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.4639976027921042
05-19 17:51:17.951 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 17.0
05-19 17:51:17.951 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.234808416569313
05-19 17:51:18.921 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 17.0
05-19 17:51:18.921 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.6589061440476407
05-19 17:51:19.967 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 17.0
05-19 17:51:19.968 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.869655409333431
05-19 17:51:21.933 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 17.0
05-19 17:51:21.933 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 2.536247410736636
05-19 17:51:22.937 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 18.0
05-19 17:51:22.937 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.8308895608109472
05-19 17:51:24.951 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 19.0
05-19 17:51:24.952 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 0.0947097615169983
05-19 17:51:25.928 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 19.0
05-19 17:51:25.929 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.9738245111823365
05-19 17:51:27.919 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 16.0
05-19 17:51:27.920 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 20.92935250395903
05-19 17:51:28.953 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 16.0
05-19 17:51:28.953 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 3.5069682564933435
05-19 17:51:29.947 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 17.0
05-19 17:51:29.947 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 0.6968343303512787
05-19 17:51:31.956 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 16.0
05-19 17:51:31.957 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.2075432097227468
05-19 17:51:32.939 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 17.0
05-19 17:51:32.939 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 2.25326750154043
05-19 17:51:33.954 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 16.0
05-19 17:51:33.954 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 2.312485607613608
05-19 17:51:35.916 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:51:35.917 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.987098264973477
05-19 17:51:36.931 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 16.0
05-19 17:51:36.931 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 2.500876545599369
05-19 17:51:38.958 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:51:38.959 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.5835084095561727
05-19 17:51:39.955 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:51:39.956 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 0.8516772133033655
05-19 17:51:41.913 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:51:41.913 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 0.2026728075728913
05-19 17:51:44.943 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 13.0
05-19 17:51:44.943 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.0697906741340788
05-19 17:51:51.925 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:51:51.926 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 2.1633341236735872
05-19 17:51:53.923 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:51:53.923 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.2343921140133707
05-19 17:51:54.936 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:51:54.936 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 2.027983113197057
05-19 17:51:56.927 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:51:56.927 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 1.131519942450051
05-19 17:51:57.950 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:51:57.951 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 2.4655416279968385
05-19 17:51:59.933 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:51:59.934 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 20.048194106846864
05-19 17:52:00.940 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:52:00.941 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 28.4654527885577
05-19 17:52:01.928 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:52:01.929 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 35.45609534346335
05-19 17:52:02.929 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:52:02.929 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 41.77779286188603
05-19 17:52:04.900 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:52:04.900 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 53.97655449822273
05-19 17:52:05.915 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:52:05.916 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 58.65807539566811
05-19 17:52:06.907 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:52:06.907 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 64.57468121131893
05-19 17:52:07.911 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:52:07.911 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 71.80579155317197
05-19 17:52:08.913 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:52:08.913 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 80.0539120875666
05-19 17:52:09.912 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 14.0
05-19 17:52:09.913 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 88.99351645981768
05-19 17:52:10.923 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:52:10.923 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 97.53616789572308
05-19 17:52:12.933 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:52:12.933 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 115.82413171385913
05-19 17:52:13.929 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 15.0
05-19 17:52:13.929 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 127.29867994638687
05-19 17:52:15.905 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: radius: 16.0
05-19 17:52:15.906 5159-5159/com.mapbox.services.android.navigation.testapp I/System.out: true position: 148.64584220141234
Is there, and/or will there be a separate Activity with a mapview with some style, that would take 'Route' object and show built in navigation with distance,estimated time, next maneuver etc. UI. iOS has NavigationViewController (MBNavigationViewController) that can be easily presented.
Platform: Android 7.1.2
SDK version: Latest SNAPSHOT
RerouteActivity.java
60
on this line-87.6910, 41.8542
)I thought this was specific to the mock engine but actually if I'm right this could happen in real life if car is going fast and GPS signal is slow I guess.
Navigation should end nicely
App crash with an NPE
Hey,
is there a way to get instructions in another language? If not, do you plan to include it?
Best regards,
Patrick
The background handler thread can be removed and logic can be calculated directly in the NavigationService
object. The NavigationService however, needs to be running on a separate thread to keep performance intact
cc: @zugaldia @danesfeder
How could i use sdk navigation to create a navigation inside an indoor map? Let me explain better, I need to create a navigation application for internal locations that shows the route and navigates from one place to another. To make the location of the user without using the gps, I will use qr codes scattered throughout the building to give me the exact location of the user and then show the route and make the navigation to the destination. But I'm not sure if it's possible to do this using the mapbox, since it's geared towards external applications.
I need to create something like this:
I would be grateful if anyone could help me.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.