You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过MapboxNavigation对象启动带UI导航并实现OffRouteListener?

如何用MapboxNavigation对象启动带UI的导航会话并监听OffRoute事件

你碰到的问题很典型——MapboxNavigation#startNavigation()本身只是启动后台导航计算会话,负责处理路线跟踪、偏离检测这些核心逻辑,但它完全不负责渲染导航UI(比如地图、转向提示、进度条这些视觉元素)。这就是为什么你调用这个方法后看不到任何界面的原因。

下面给你两种可行的解决方案,你可以根据自己的需求选择:

方案1:继续用NavigationLauncher启动默认UI,同时添加监听器

如果你想保留Mapbox官方的默认导航UI(就是之前用NavigationLauncher.startNavigation()启动的那个界面),同时添加OffRouteListener这类监听器,可以这么做:

  • 首先还是用NavigationLauncher启动导航,同时设置回调来监听导航状态:

    NavigationLauncherOptions options = NavigationLauncherOptions.builder()
        .directionsRoute(directionsRoute)
        .shouldSimulateRoute(false)
        .build();
    
    NavigationLauncher.startNavigation(MainActivity.this, options, new NavigationLauncher.Callback() {
        @Override
        public void onNavigationFinished() {
            // 导航结束后的清理工作
        }
    
        @Override
        public void onNavigationCanceled() {
            // 导航取消后的处理
        }
    });
    
  • 导航启动后,通过MapboxNavigationProvider获取全局的导航实例,然后添加监听器:

    // 建议在导航启动后的合适时机调用,比如在回调里或者延迟一点执行
    MapboxNavigation mapboxNavigation = MapboxNavigationProvider.retrieve();
    if (mapboxNavigation != null) {
        // 保存这个监听器实例,方便后续移除
        OffRouteListener offRouteListener = location -> {
            // 这里写偏离路线后的逻辑,比如提示用户、触发重新规划
            Log.d("Navigation", "当前已偏离路线,位置:" + location.getLatitude() + ", " + location.getLongitude());
        };
        mapboxNavigation.addOffRouteListener(offRouteListener);
    }
    
  • 别忘了在页面销毁时移除监听器并销毁实例,避免内存泄漏:

    @Override
    protected void onDestroy() {
        super.onDestroy();
        MapboxNavigation mapboxNavigation = MapboxNavigationProvider.retrieve();
        if (mapboxNavigation != null) {
            mapboxNavigation.removeOffRouteListener(offRouteListener);
            mapboxNavigation.onDestroy();
        }
    }
    

方案2:使用NavigationView自定义导航UI(更灵活)

如果你想完全自定义导航界面,或者需要更直接地控制MapboxNavigation实例,可以把NavigationView嵌入到自己的Activity布局中,替代NavigationLauncher:

  1. 先在布局文件里添加NavigationView:

    <com.mapbox.navigation.ui.NavigationView
        android:id="@+id/navigationView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        app:mapbox_navigation_view_routing_profile="driving"/>
    
  2. 在Activity中初始化并启动导航:

    private MapboxNavigation mapboxNavigation;
    private NavigationView navigationView;
    private OffRouteListener offRouteListener;
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    
        navigationView = findViewById(R.id.navigationView);
        // 获取NavigationView绑定的MapboxNavigation实例
        mapboxNavigation = navigationView.retrieveMapboxNavigation();
    
        // 创建并添加偏离路线监听器
        offRouteListener = location -> {
            // 处理偏离逻辑
        };
        mapboxNavigation.addOffRouteListener(offRouteListener);
    
        // 启动导航,NavigationView会自动渲染导航UI
        mapboxNavigation.startNavigation(directionsRoute);
    }
    
    @Override
    protected void onDestroy() {
        super.onDestroy();
        if (mapboxNavigation != null) {
            mapboxNavigation.removeOffRouteListener(offRouteListener);
            mapboxNavigation.onDestroy();
        }
        navigationView.onDestroy();
    }
    

这种方式的好处是你可以自由定制导航界面的布局和交互,同时直接掌控MapboxNavigation实例,方便添加各种监听器和自定义逻辑。

简单总结:

  • 要保留官方默认UI,选方案1最省心;
  • 要自定义界面或深度控制,选方案2更合适。

内容的提问来源于stack exchange,提问作者qwlice

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.06 18:12:41