Android开发:百度地图实现路径规划

百度地图实现最简单的路径规划 /*设置目的地开始导航/ if (BaiduNaviManager.isNaviInited()) { routeplanToNavi(); }============================ /** * 路径规划相关 */ 阅读详情

前段时间项目需要做路径规划,简单的研究了下。不过,后来没用到

效果图:

 

 

实现的是从北京西二旗地铁站 到 北京百度科技园的路径规划。这里是固定的,可以根据自己需要改成可输入起止位置

这里面有很多坑,需要一一踩过才知道。

 

记下来,我们来实现功能吧:

至于引入sdk、配置权限等,就不做具体的介绍了,网上或者百度地图官方文档都可以查到。

只许看加粗的主要部分就可以,因为还有其他的功能,所以显得冗余。

1、显示地图页面Activity,我取名叫FiveActivity

package com.example.my;
import android.Manifest;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.graphics.drawable.BitmapDrawable;
import android.os.Build;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.app.ActivityCompat;
import android.support.v7.app.AppCompatActivity;
import android.text.TextUtils;
import android.util.Log;
import android.view.Gravity;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.EditText;
import android.widget.LinearLayout;
import android.widget.PopupWindow;
import android.widget.TextView;
import android.widget.Toast;
import com.baidu.location.BDLocation;
import com.baidu.location.BDLocationListener;
import com.baidu.location.LocationClient;
import com.baidu.location.LocationClientOption;
import com.baidu.mapapi.SDKInitializer;
import com.baidu.mapapi.map.MapView;
import com.baidu.mapapi.model.LatLng;
import com.baidu.mapapi.search.route.BikingRouteLine;
import com.baidu.mapapi.search.route.BikingRoutePlanOption;
import com.baidu.mapapi.search.route.BikingRouteResult;
import com.baidu.mapapi.search.route.DrivingRouteResult;
import com.baidu.mapapi.search.route.IndoorRouteResult;
import com.baidu.mapapi.search.route.MassTransitRouteResult;
import com.baidu.mapapi.search.route.OnGetRoutePlanResultListener;
import com.baidu.mapapi.search.route.PlanNode;
import com.baidu.mapapi.search.route.RoutePlanSearch;
import com.baidu.mapapi.search.route.TransitRouteResult;
import com.baidu.mapapi.search.route.WalkingRouteResult;
import com.baidu.mapapi.utils.DistanceUtil;
import com.example.my.db.LatLngDB;
import com.example.my.util.BikingRouteOverlay;
import com.example.my.util.DragFloatActionButton;
import org.litepal.crud.DataSupport;
import java.lang.ref.WeakReference;
import java.util.ArrayList;
import java.util.List;
import me.bakumon.library.adapter.SimpleBulletinAdapter;
import me.bakumon.library.view.BulletinView;

/**
 * Created by Administrator on 2018/2/6.
 */
public class FiveActivity extends AppCompatActivity {
    private RoutePlanSearch mSearch;
    private MapView mMapView = null;

    BikingRouteOverlay overlay;
    DragFloatActionButton btn_click, btn_refresh, btn_searchDB;
    BulletinView bulletin_view;
    Button btn_start, btn_end;
    private long timeusedinsec;
    private boolean isstop = false;
    TextView tv_time;
    public LocationClient mLocationClient = null;
    private MyLocationListener myListener = new MyLocationListener();
    private MyHandler myHandler;
    private PopupWindow popupWindow;


    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        //在使用SDK各组件之前初始化context信息,传入ApplicationContext
        //注意该方法要再setContentView方法之前实现

        SDKInitializer.initialize(getApplicationContext());
        setContentView(R.layout.activity_five_layout);

        initElement();
        boolean isAllGranted = checkPermissionAllGranted(new String[]{
                Manifest.permission.ACCESS_COARSE_LOCATION,
                Manifest.permission.ACCESS_FINE_LOCATION
        });
        if (isAllGranted) {
            btn_start.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    myHandler.removeMessages(1);
                    myHandler.sendEmptyMessage(1);
                    isstop = false;
                    mLocationClient.start();
                    Toast.makeText(FiveActivity.this, "开始采集坐标", Toast.LENGTH_SHORT).show();
                }
            });
            btn_end.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    isstop = true;
                    mLocationClient.stop();
                    Toast.makeText(FiveActivity.this, "停止采集坐标", Toast.LENGTH_SHORT).show();
                }
            });
        }


        ActivityCompat.requestPermissions(this, new String[]{
                        Manifest.permission.ACCESS_COARSE_LOCATION,
                        Manifest.permission.ACCESS_FINE_LOCATION
                },
                0);
    }


    private void initElement() {
        mSearch = RoutePlanSearch.newInstance();
        mSearch.setOnGetRoutePlanResultListener(listener);
        //获取地图控件引用
        mMapView = (MapView) findViewById(R.id.bmapView);
        btn_click = (DragFloatActionButton) findViewById(R.id.btn_click);
        btn_refresh = (DragFloatActionButton) findViewById(R.id.btn_refresh);
        btn_searchDB = (DragFloatActionButton) findViewById(R.id.btn_searchDB);

        btn_start = findViewById(R.id.btn_start);
        btn_end = findViewById(R.id.btn_end);
        tv_time = findViewById(R.id.tv_time);
        mLocationClient = new LocationClient(getApplicationContext());
        mLocationClient.registerLocationListener(myListener);

        initLocationClientOption();

 

        //点击btn_click 即可实现路径规划

        btn_click.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                setElement();
            }

        });

 

        //可以忽略

        btn_searchDB.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                bottomwindow(view);
            }

        });

 

        //可以忽略

        btn_refresh.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Toast.makeText(FiveActivity.this, "正在清除数据", Toast.LENGTH_SHORT).show();
                List<LatLngDB> latLngDBList = DataSupport.findAll(LatLngDB.class);
                for (LatLngDB latLngDB : latLngDBList) {
                    latLngDB.delete();
                }
                int dbSize = DataSupport.findAll(LatLngDB.class).size();
                List<String> list = new ArrayList<>();
                list.add("坐标库当前数据:" + dbSize + " 条");
                list.add("坐标库当前数据:" + dbSize + " 条");
                bulletin_view.setAdapter(new SimpleBulletinAdapter(FiveActivity.this, list));
                Toast.makeText(FiveActivity.this, "清除数据完成", Toast.LENGTH_SHORT).show();
            }
        });

        myHandler = new MyHandler(this);

        int dbSize = DataSupport.findAll(LatLngDB.class).size();
        bulletin_view = findViewById(R.id.bulletin_view);
        List<String> list = new ArrayList<>();
        list.add("坐标库当前数据:" + dbSize + " 条");
        list.add("坐标库当前数据:" + dbSize + " 条");
        bulletin_view.setAdapter(new SimpleBulletinAdapter(this, list));
    }

    private void initLocationClientOption() {
        LocationClientOption option = new LocationClientOption();
        option.setLocationMode(LocationClientOption.LocationMode.Hight_Accuracy);
        option.setCoorType("bd09ll");
        //可选,设置发起定位请求的间隔,int类型,单位ms
        //如果设置为0,则代表单次定位,即仅定位一次,默认为0
        //如果设置非0,需设置1000ms以上才有效
        option.setScanSpan(1000);
        option.setLocationNotify(true);
        option.setOpenGps(true);
        mLocationClient.setLocOption(option);
    }


    private void setElement() {
        PlanNode stNode = PlanNode.withCityNameAndPlaceName("北京", "西二旗地铁站");
        PlanNode enNode = PlanNode.withCityNameAndPlaceName("北京", "百度科技园");
        mSearch.bikingSearch((new BikingRoutePlanOption())
                .from(stNode)
                .to(enNode));
        overlay = new BikingRouteOverlay(mMapView.getMap());
    }



    OnGetRoutePlanResultListener listener = new OnGetRoutePlanResultListener() {
        @Override
        public void onGetWalkingRouteResult(WalkingRouteResult walkingRouteResult) {
            Toast.makeText(FiveActivity.this, "未定位到数据3", Toast.LENGTH_SHORT).show();
        }


        @Override
        public void onGetTransitRouteResult(TransitRouteResult transitRouteResult) {
            Toast.makeText(FiveActivity.this, "未定位到数据4", Toast.LENGTH_SHORT).show();
        }


        @Override
        public void onGetMassTransitRouteResult(MassTransitRouteResult massTransitRouteResult) {
            Toast.makeText(FiveActivity.this, "未定位到数据5", Toast.LENGTH_SHORT).show();
        }


        @Override
        public void onGetDrivingRouteResult(DrivingRouteResult drivingRouteResult) {
            Toast.makeText(FiveActivity.this, "未定位到数据6", Toast.LENGTH_SHORT).show();
        }


        @Override
        public void onGetIndoorRouteResult(IndoorRouteResult indoorRouteResult) {
            Toast.makeText(FiveActivity.this, "未定位到数据7", Toast.LENGTH_SHORT).show();
        }


        public void onGetBikingRouteResult(BikingRouteResult result) {
            if (result != null) {
                List<BikingRouteLine> routeLineList = result.getRouteLines();
                if (routeLineList != null && !routeLineList.isEmpty() && routeLineList.size() != 0) {
//                    Toast.makeText(FiveActivity.this, routeLineList.get(0).getDistance() + "", Toast.LENGTH_SHORT).show();
                    overlay.removeFromMap();
                    overlay.setData(routeLineList.get(0));
                    overlay.addToMap();
                    overlay.zoomToSpan();
                    String instruction = routeLineList.get(0).getAllStep().get(0).getInstructions();
                    Toast.makeText(FiveActivity.this, routeLineList.get(0).getAllStep().size()
                            + "-------:" + instruction, Toast.LENGTH_SHORT).show();
                } else {
                    Toast.makeText(FiveActivity.this, "未定位到数据2", Toast.LENGTH_SHORT).show();
                }
            } else {
                Toast.makeText(FiveActivity.this, "未定位到数据1", Toast.LENGTH_SHORT).show();
            }
        }
    };





    public class MyLocationListener implements BDLocationListener {
        @Override
        public void onReceiveLocation(BDLocation bdLocation) {
            if (bdLocation != null) {
                double latitude = bdLocation.getLatitude();    //获取纬度信息
                double longitude = bdLocation.getLongitude();    //获取经度信息
                LatLngDB latLngDB = new LatLngDB();
                latLngDB.setLat(latitude);
                latLngDB.setLng(longitude);
                latLngDB.save();
                Log.i("-----", "(" + latitude + "," + longitude + ")");


            }
        }
    }


    public static void startActivity(Context context) {
        Intent intent = new Intent();
        intent.setClass(context, FiveActivity.class);
        context.startActivity(intent);
    }


    private void updateView() {
        timeusedinsec += 1;
        int minute = (int) (timeusedinsec / 60) % 60;
        int second = (int) (timeusedinsec % 60);

        if (minute < 10 && second < 10) {
            tv_time.setText("0" + minute + ":0" + second);
        } else if (minute < 10 && second >= 10) {
            tv_time.setText("0" + minute + ":" + second);
        } else if (minute >= 10 && second < 10) {
            tv_time.setText(minute + ":0" + second);
        } else if (minute >= 10 && second >= 10) {
            tv_time.setText(minute + ":" + second);
        }
    }


    private static class MyHandler extends Handler {
        private WeakReference<FiveActivity> activity;


        public MyHandler(FiveActivity fiveActivity) {
            this.activity = new WeakReference<FiveActivity>(fiveActivity);
        }


        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            FiveActivity fiveActivity = activity.get();
            switch (msg.what) {
                case 1:
                    // 添加更新ui的代码
                    if (!fiveActivity.isstop) {
                        fiveActivity.updateView();
                        fiveActivity.myHandler.sendEmptyMessageDelayed(1, 1000);
                    }
                    break;
                case 0:
                    break;
                case 10:
                    break;
                default:
                    break;
            }
        }
    }


    /**
     * 检查是否有指定的权限
     *
     * @param permissions 权限列表
     * @return 是否有权限
     */
    private boolean checkPermissionAllGranted(String[] permissions) {
        for (String permission : permissions) {
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
                if (getApplicationContext().checkSelfPermission(permission) != PackageManager.PERMISSION_GRANTED) {
                    return false;
                }
            }
        }
        return true;
    }


    @Override
    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
        if (requestCode == 0) {
            boolean isAllGranted = true;
            for (int grant : grantResults) {
                if (grant != PackageManager.PERMISSION_GRANTED) {
                    isAllGranted = false;
                    break;
                }
            }


            if (isAllGranted) {
                btn_start.setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        myHandler.removeMessages(1);
                        myHandler.sendEmptyMessage(1);
                        isstop = false;
                        mLocationClient.start();
                        Toast.makeText(FiveActivity.this, "开始采集坐标", Toast.LENGTH_SHORT).show();
                    }
                });
                btn_end.setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        isstop = true;
                        mLocationClient.stop();
                        Toast.makeText(FiveActivity.this, "停止采集坐标", Toast.LENGTH_SHORT).show();
                    }
                });
            } else {
                Toast.makeText(this, "未授权 ", Toast.LENGTH_SHORT).show();
            }
        }
    }


    /**
     * 创建popupWindow
     *
     * @param view View
     */
    private void bottomwindow(View view) {
        if (popupWindow != null && popupWindow.isShowing()) {
            return;
        }
        LinearLayout layout = (LinearLayout) getLayoutInflater().inflate(R.layout.pop_five_activity_bottom_layout, null);
        popupWindow = new PopupWindow(layout,
                ViewGroup.LayoutParams.MATCH_PARENT,
                ViewGroup.LayoutParams.WRAP_CONTENT);
        //点击空白处时,隐藏掉pop窗口
        popupWindow.setFocusable(true);
        popupWindow.setBackgroundDrawable(new BitmapDrawable());
        //添加弹出、弹入的动画
//        popupWindow.setAnimationStyle(R.style.Popupwindow);
        int[] location = new int[2];
        view.getLocationOnScreen(location);
        popupWindow.showAtLocation(view, Gravity.LEFT | Gravity.BOTTOM, 0, -location[1]);
        //添加按键事件监听
        setButtonListeners(layout);
        //添加pop窗口关闭事件,主要是实现关闭时改变背景的透明度
//        popupWindow.setOnDismissListener(new poponDismissListener());
//        backgroundAlpha(1f);
    }


    private void setButtonListeners(LinearLayout layout) {
        Button btn_cancel = (Button) layout.findViewById(R.id.btn_cancel);
        Button btn_ok = (Button) layout.findViewById(R.id.btn_ok);
        final EditText et_lat = layout.findViewById(R.id.et_lat);
        final EditText et_lng = layout.findViewById(R.id.et_lng);
        final TextView tv_showResult = layout.findViewById(R.id.tv_showResult);


        btn_cancel.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                if (popupWindow != null && popupWindow.isShowing()) {
                    //在此处添加你的按键处理 xxx
                    popupWindow.dismiss();
                }
            }
        });
        btn_ok.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                if (popupWindow != null && popupWindow.isShowing()) {
                    //在此处添加你的按键处理 xxx
                    String lat = et_lat.getText().toString().trim();
                    String lng = et_lng.getText().toString().trim();
                    if (TextUtils.isEmpty(lat) || TextUtils.isEmpty(lng)) {
                        Toast.makeText(FiveActivity.this, "请填写经纬度", Toast.LENGTH_SHORT).show();
                    } else {
                        long startTime = System.currentTimeMillis();
                        Log.i("startTime:", startTime + "");
                        Double resultDistance = 0.0;
                        Double distance;
                        LatLng startPoint = new LatLng(Double.parseDouble(lat), Double.parseDouble(lng));
                        List<LatLngDB> latLngDBList = DataSupport.findAll(LatLngDB.class);
                        int i = 0;
                        for (LatLngDB latLngDB : latLngDBList) {
                            Log.i("次数:", "" + i);
                            i++;
                            //计算p1、p2两点之间的直线距离,单位:米
                            LatLng endPoint = new LatLng(latLngDB.getLat(), latLngDB.getLng());
                            distance = DistanceUtil.getDistance(startPoint, endPoint);
                            Log.i("距离:", "" + distance);
                            if (resultDistance < distance) {
                                resultDistance = distance;
                            }
                        }
                        long endTime = System.currentTimeMillis();
                        Log.i("endTime:", endTime + "");
                        long timeCha = endTime - startTime;
                        Toast.makeText(FiveActivity.this, "---" + timeCha + "ms", Toast.LENGTH_SHORT).show();
                        int minute = (int) (timeCha / 60) % 60;
                        int second = (int) (timeCha % 60);
                        if (minute < 10 && second < 10) {
                            tv_showResult.setText("用时 0" + minute + ":0" + second + ";最远距离:" + resultDistance);
                        } else if (minute < 10 && second >= 10) {
                            tv_showResult.setText("用时 0" + minute + ":" + second + ";最远距离:" + resultDistance);
                        } else if (minute >= 10 && second < 10) {
                            tv_showResult.setText("用时 " + minute + ":0" + second + ";最远距离:" + resultDistance);
                        } else if (minute >= 10 && second >= 10) {
                            tv_showResult.setText("用时 " + minute + ":" + second + ";最远距离:" + resultDistance);
                        }
                    }
                }
            }
        });
    }


    @Override
    protected void onResume() {
        super.onResume();
        //在activity执行onResume时执行mMapView. onResume (),实现地图生命周期管理
        mMapView.onResume();

    }


    @Override
    protected void onPause() {
        super.onPause();
        //在activity执行onPause时执行mMapView. onPause (),实现地图生命周期管理
        mMapView.onPause();

    }


    @Override
    protected void onDestroy() {
        super.onDestroy();
        mSearch.destroy();
        //在activity执行onDestroy时执行mMapView.onDestroy(),实现地图生命周期管理
        mMapView.onDestroy();

        mLocationClient.unRegisterLocationListener(myListener);
    }

}

 

 

2、activity_five_layout  xml布局文件,只看自己需要的就行。DragFloatActionButton 悬浮按钮 和 Button按钮可以删除,根据自己需要来写布局文件吧

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <TextView
        android:id="@+id/tv_1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@color/white"
        android:padding="@dimen/margin_10"
        android:text="开始:北京, 西二旗地铁站"
        android:textColor="@color/black" />

    <TextView
        android:id="@+id/tv_2"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@color/white"
        android:padding="@dimen/margin_10"
        android:text="结束:北京, 百度科技园"
        android:textColor="@color/black" />

    <FrameLayout
        android:id="@+id/btn_search"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1">

        <com.baidu.mapapi.map.MapView
            android:id="@+id/bmapView"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:clickable="true" />

        <LinearLayout
            android:layout_width="80dp"
            android:layout_height="130dp"
            android:layout_gravity="bottom|center_horizontal"
            android:orientation="vertical">

            <Button
                android:id="@+id/btn_start"
                android:layout_width="match_parent"
                android:layout_height="@dimen/view_height_35"
                android:layout_margin="@dimen/margin_1"
                android:background="@drawable/content_five_activity_start_button_bg"
                android:padding="@dimen/margin_5"
                android:text="开始采集"
                android:textColor="@color/light_blue"
                android:textStyle="bold" />

            <View
                android:layout_width="match_parent"
                android:layout_height="30dp" />

            <Button
                android:id="@+id/btn_end"
                android:layout_width="match_parent"
                android:layout_height="@dimen/view_height_35"
                android:layout_margin="@dimen/margin_1"
                android:background="@drawable/content_five_activity_stop_button_bg"
                android:padding="@dimen/margin_5"
                android:text="停止采集"
                android:textColor="@color/light_blue"
                android:textStyle="bold" />
        </LinearLayout>

        <com.example.my.util.DragFloatActionButton
            android:id="@+id/btn_click"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="right|center_vertical"
            android:clickable="true"
            android:focusable="true"
            android:src="@android:drawable/ic_menu_directions" />

        <com.example.my.util.DragFloatActionButton
            android:id="@+id/btn_refresh"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="right|center_vertical"
            android:clickable="true"
            android:focusable="true"
            android:src="@android:drawable/ic_menu_revert" />

        <com.example.my.util.DragFloatActionButton
            android:id="@+id/btn_searchDB"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="right|center_vertical"
            android:clickable="true"
            android:focusable="true"
            android:src="@android:drawable/ic_menu_search" />

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_gravity="center_horizontal|top"
            android:orientation="vertical">

            <me.bakumon.library.view.BulletinView
                android:id="@+id/bulletin_view"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:background="#30000000"
                app:bulletinEnterAnim="@anim/bulletin_item_enter"
                app:bulletinInterval="3000"
                app:bulletinLeaveAnim="@anim/bulletin_item_leave" />

            <TextView
                android:id="@+id/tv_time"
                android:layout_width="100dp"
                android:layout_height="25dp"
                android:layout_gravity="center_horizontal"
                android:background="@drawable/content_five_activity_text_bg"
                android:gravity="center"
                android:text="跑秒"
                android:textColor="@color/light_blue"
                android:textStyle="bold" />
        </LinearLayout>

    </FrameLayout>

</LinearLayout>

 

 

3、需要注意的是 BikingRouteOverlay 是需要自己实现的;也可以查看百度路径规划的Demo,有相对应的类。代码如下:

/*
 * Copyright (C) 2016 Baidu, Inc. All Rights Reserved.
 */
package com.example.my.util;
import android.graphics.Color;
import android.os.Bundle;
import android.util.Log;
import com.baidu.mapapi.map.BaiduMap;
import com.baidu.mapapi.map.BitmapDescriptor;
import com.baidu.mapapi.map.BitmapDescriptorFactory;
import com.baidu.mapapi.map.Marker;
import com.baidu.mapapi.map.MarkerOptions;
import com.baidu.mapapi.map.Overlay;
import com.baidu.mapapi.map.OverlayOptions;
import com.baidu.mapapi.map.Polyline;
import com.baidu.mapapi.map.PolylineOptions;
import com.baidu.mapapi.model.LatLng;
import com.baidu.mapapi.search.route.BikingRouteLine;
import java.util.ArrayList;
import java.util.List;


/**
 * 用于显示骑行路线的Overlay
 */
public class BikingRouteOverlay extends OverlayManager {


    private BikingRouteLine mRouteLine = null;


    public BikingRouteOverlay(BaiduMap baiduMap) {
        super(baiduMap);
    }


    /**
     * 设置路线数据。
     *
     * @param line
     *            路线数据
     */
    public void setData(BikingRouteLine line) {
        mRouteLine = line;
    }


    @Override
    public final List<OverlayOptions> getOverlayOptions() {
        if (mRouteLine == null) {
            return null;
        }


        List<OverlayOptions> overlayList = new ArrayList<OverlayOptions>();
        if (mRouteLine.getAllStep() != null
                && mRouteLine.getAllStep().size() > 0) {
            for (BikingRouteLine.BikingStep step : mRouteLine.getAllStep()) {
                Bundle b = new Bundle();
                b.putInt("index", mRouteLine.getAllStep().indexOf(step));
                if (step.getEntrance() != null) {
                    overlayList.add((new MarkerOptions())
                            .position(step.getEntrance().getLocation())
                                    .rotate((360 - step.getDirection()))
                                            .zIndex(10)
                                                    .anchor(0.5f, 0.5f)
                                                            .extraInfo(b)
                                                                    .icon(BitmapDescriptorFactory
                                                                            .fromAssetWithDpi("Icon_line_node.png")));
                }


                // 最后路段绘制出口点
                if (mRouteLine.getAllStep().indexOf(step) == (mRouteLine
                        .getAllStep().size() - 1) && step.getExit() != null) {
                    overlayList.add((new MarkerOptions())
                            .position(step.getExit().getLocation())
                                    .anchor(0.5f, 0.5f)
                                            .zIndex(10)
                                                    .icon(BitmapDescriptorFactory
                                                            .fromAssetWithDpi("Icon_line_node.png")));
                }
            }
        }
        // starting
        if (mRouteLine.getStarting() != null) {
            overlayList.add((new MarkerOptions())
                    .position(mRouteLine.getStarting().getLocation())
                            .icon(getStartMarker() != null ? getStartMarker() :
                                    BitmapDescriptorFactory
                                            .fromAssetWithDpi("Icon_start.png")).zIndex(10));
        }
        // terminal
        if (mRouteLine.getTerminal() != null) {
            overlayList
                    .add((new MarkerOptions())
                            .position(mRouteLine.getTerminal().getLocation())
                                    .icon(getTerminalMarker() != null ? getTerminalMarker() :
                                            BitmapDescriptorFactory
                                                    .fromAssetWithDpi("Icon_end.png"))
                                                            .zIndex(10));
        }


        // poly line list
        if (mRouteLine.getAllStep() != null
                && mRouteLine.getAllStep().size() > 0) {
            LatLng lastStepLastPoint = null;
            for (BikingRouteLine.BikingStep step : mRouteLine.getAllStep()) {
                List<LatLng> watPoints = step.getWayPoints();
                if (watPoints != null) {
                    List<LatLng> points = new ArrayList<LatLng>();
                    if (lastStepLastPoint != null) {
                        points.add(lastStepLastPoint);
                    }
                    points.addAll(watPoints);
                    overlayList.add(new PolylineOptions().points(points).width(10)
                            .color(getLineColor() != 0 ? getLineColor() : Color.argb(178, 0, 78, 255)).zIndex(0));
                    lastStepLastPoint = watPoints.get(watPoints.size() - 1);
                }
            }
        }
        return overlayList;
    }


    /**
     * 覆写此方法以改变默认起点图标
     *
     * @return 起点图标
     */
    public BitmapDescriptor getStartMarker() {
        return null;
    }
    public int getLineColor() {
        return 0;
    }
    /**
     * 覆写此方法以改变默认终点图标
     *
     * @return 终点图标
     */
    public BitmapDescriptor getTerminalMarker() {
        return null;
    }


    /**
     * 处理点击事件
     *
     * @param i
     *            被点击的step在
     *            {@link BikingRouteLine#getAllStep()}
     *            中的索引
     * @return 是否处理了该点击事件
     */
    public boolean onRouteNodeClick(int i) {
        if (mRouteLine.getAllStep() != null
                && mRouteLine.getAllStep().get(i) != null) {
            Log.i("baidumapsdk", "BikingRouteOverlay onRouteNodeClick");
        }
        return false;
    }


    @Override
    public final boolean onMarkerClick(Marker marker) {
        for (Overlay mMarker : mOverlayList) {
            if (mMarker instanceof Marker && mMarker.equals(marker)) {
                if (marker.getExtraInfo() != null) {
                    onRouteNodeClick(marker.getExtraInfo().getInt("index"));
                }
            }
        }
        return true;
    }


    @Override
    public boolean onPolylineClick(Polyline polyline) {
        // TODO Auto-generated method stub
        return false;
    }

}

4、到这里基本可以实现路径规划了,我这里地址是写的固定的,根据自己需要,可以改成输入框

 

 

 

 

Android百度地图开发定位和路线导航 在写之前要先加入百度地图sdk的jar包从百度地图开发者官网上就能下载 百度地图sdk下载 而其中用到的一些与定位和路线规划有关的包可以在事例中查看导入 首先是xml的布局文件,其中editText的background是采用的自定义的样式,而在edittext前面的小点是用来美化界面的,可以直接删除 &amp;amp;amp;amp;lt;?xml version=&amp;amp;amp;quot;1.0&amp;amp;amp;quot; encoding=&amp 阅读详情

相关推荐

百度地图SDK for Android【路径规划】

1路径服务简介         路径规划实际上是一种特殊的检索服务,因此,在使用路径规划服务之前首先要对检索相关的方法进行初始化,具体介绍请参考检索服务部分中的第一章节。         注意:在使用检索服务时,请明确唯一的起点和终点,否则将不能搜到您所需结果;当起点或终点信息不唯一时,SDK会为您返回一个起点/终点列表,您可通过选择列表中的信息来完成起点/终点的唯一选择,然后再进行路径搜索。

百度LBS开放平台 1万+

Android 记录遇到好的框架或是炫酷的控件,附上github

StatusLayoutManager:切换不同的数据状态布局,包含加载中、空数据和出错状态。 github地址:https://github.com/Bakumon/StatusLayoutManager?utm_source=androidweekly&amp;utm_medium=website   SmartTable github地址:https://github.com/hua...

L_Sharon的博客 679

安卓开发实战:用百度地图API实现GPS轨迹模拟骑行(附完整源码)

本文详细介绍了在安卓开发中,如何利用百度地图API实现GPS轨迹模拟骑行功能。内容涵盖从核心原理、轨迹数据获取与坐标系转换,到构建平滑模拟引擎及与百度地图SDK集成的完整实战流程,并提供了可复用的完整源码,帮助开发者快速为应用添加演示或测试用的模拟定位模块。

weixin_29218509的博客 928

小白和你一起做百度地图的“路径规划”

百度地图的“路径规划” 1.路径服务简介   路径规划实际上是一种特殊的检索服务,因此,在使用路径规划服务之前首先要对检索相关的方法进行初始化,具体介绍请参考检索服务部分中的第一章节。   注意:在使用检索服务时,请明确唯一的起点和终点,否则将不能搜到您所需结果;当起点或终点信息不唯一时,SDK会为您返回一个起点/终点列表,您可通过选择列表中的信息来完成起点/终点的唯

u012482178的专栏 2912

Android集成百度地图实现定位与路径规划

为了提高用户交互体验,我们还需要处理用户在地图上的点击事件。例如,用户可能会点击地图上的某个位置以设定路线的起点或终点。// 给地图视图添加点击事件监听器@Override// 处理地图点击事件,例如添加标记或开始路径规划});在地图上添加自定义标注或标记,可以为用户提供更加丰富和具体的信息。例如,用户点击某个位置后,可以添加一个标记点。// 创建一个标注点.position(new LatLng(latitude, longitude)) // 设置标注点的位置// 设置图标。

weixin_42402664的博客 1465

百度地图Android开发应用实战案例

百度地图提供了丰富的交互控件,如缩放控件、定位控件等,这些控件可以帮助用户更好地与地图进行交互。开发者可以在初始化地图的时候启用这些控件,并根据自己的应用需求进行自定义。// 启用缩放控件// 启用指南针控件自定义控件通常需要覆盖或修改控件的样式,这可以通过重写控件的XML布局文件来完成,也可以通过编程方式直接在代码中修改控件属性。例如,开发者可以改变控件的背景颜色、图标等,以匹配应用的主题风格。// 通过编程方式自定义定位按钮的图标。

weixin_42610010的博客 1305

python调用百度地图实现路径规划提取坐标点

利用python调用百度地图API,进行路径规划,返回将路径上的坐标点(gps经纬度坐标)

weixin_52999035的博客 4128

实现安卓调用百度地图功能的全面指南

在当今移动互联网时代,地理位置服务已成为各类应用不可或缺的功能。百度地图API作为一款功能强大的地图服务平台,它允许开发者将其地图服务集成到自己的应用中,实现地图展示、路径规划、地理定位等功能。本章将简要介绍百度地图API的基本概念、特点以及集成方法,为深入探索百度地图SDK的高级功能打下基础。百度地图API是百度地图提供的可编程接口,通过这些接口,开发者可以方便地在自己的应用中加入地图服务,进行位置信息的查询、展示、路径规划等操作。它的主要特点包括跨平台支持、丰富的地图数据、多样化的功能接口。

weixin_42588877的博客 1280

Android应用开发中的百度地图路径规划技术合集

本章围绕公交查询与换乘方案设计,详细介绍了公交网络建模、百度地图API调用、路径计算与优化等内容。通过图搜索算法与实际公交数据的结合,构建了完整的公交路径规划系统。后续章节将在此基础上进一步探讨步行导航与地图融合的应用场景。

weixin_42613018的博客 804

基于百度地图API的安卓定位软件开发实战

随着移动互联网的快速发展,基于位置的服务(LBS)已成为各类应用的核心功能之一。安卓系统提供了强大的定位能力,结合百度地图API,开发者可以快速构建具备高精度定位、地图展示和路径规划等功能的应用程序。本章将从安卓定位的基本概念入手,介绍其在实际开发中的应用场景,并逐步引导读者完成百度地图API的账号申请、密钥获取及SDK集成流程,为后续章节的深入开发打下坚实基础。

weixin_33245447的博客 1095

Android安卓百度地图定位+导航+路径规划实现APP(源码+APK) 毕业设计

百度地图实时定位+导航路径规划的实现APP 本科生毕业设计:《一种智能停车系统的设计》,成都信息工程大学,2018 1、简单实时定位效果如图,打开即可用 2、高级功能:已实现车辆的自动识别(二维码扫描识别功能)、车位计时、充值缴费(模拟)、地图自动引导(路线规划功能)。登录注册(包含自动登录) 等功能。基于B/S架构的java web网络结构模式,采用了百度地图和LBS云服务器的设计...

u011752195的博客 8617

百度地图路径规划

基于安卓系统的百度地图开发,实现路径规划功能。

百度地图SDK for Android【Demo路径规划】

今天我将给大家分享路径规划接口的使用。        首先,我们要构建一个最基本的地图应用,具体介绍请参考:百度地图SDK for Android【Demo地图展示】        自此基础之上,我们对工程做一定的修改,即可实现一个最基本的路径规划应用。        第一步,修改布局文件,添加用于输入起点、终点的输入框已经执行路径规划操作的按钮。代码如下所示: <RelativeLayo

百度LBS开放平台 2万+

百度地图定位和路径规划

基于百度地图的路径规划和定位,在地图上显示定位点。

保姆级教程:在mmdetection中手动计算并可视化P、R、F1值(附完整代码)

本文提供了一份详细的mmdetection教程,指导开发者如何手动计算并可视化精确率(P)、召回率(R)和F1值。通过完整的代码示例和清晰的步骤说明,帮助用户深入理解目标检测模型的性能评估方法,特别适合需要精细分析模型表现的计算机视觉研究人员和工程师。

weixin_29038303的博客 399

Android 百度地图之路径规划

我集成了百度地图驾车路径规划,但总是不规划,下面我来简单说说吧。 首先就是按照百度官方文档按步骤复制粘贴对应的代码到自己工程。 百度地图驾车路径规划网址:https://lbsyun.baidu.com/index.php?title=androidsdk/guide/route/drive 说说要注意的点:第二步有红体字,下载demo,然后复制需要的类到你的项目。 注意坑,下面我要说坑了,我花了2天才搞定。坑就是你要把demo中的assets文件夹直接复制到你的项目。那么问题来了,文件夹放哪里呢?

yijiaodingqiankun的博客 1210

【AI蛋白预测实战】零门槛在Colab上运行AlphaFold2全流程解析

本文为零基础用户提供了在谷歌Colab平台上运行AlphaFold2进行蛋白质结构预测的完整实战指南。通过ColabFold项目,用户无需本地高性能硬件,即可免费利用云端GPU完成从序列输入到3D结构生成和结果可视化的全流程,大幅降低了AI蛋白预测的技术门槛。

mqtt6iot的博客 912

安卓百度地图之步行路径规划

使用的是百度地图的API,地址是:androidsdk | 百度地图API SDK步骤一:配置build.gradle步骤二:创建路线规划检索实例步骤三:创建路线规划检索结果监听器全部代码:

u014388322的专栏 1280

记一次在JAVA中客户端使用axis调用webservice服务端出现的异常:Unmarshalling Error: For input string: ""

在使axis调用webservice服务端,参照网上给的demo: Call call = (Call) service.createCall(); call.setTargetEndpointAddress(endpoint);//设置服务请求路径 QName qn = new QName(name); call.setOperationName(qn); call.addParamet

kry1201的专栏 8080

单片机:实现FFT快速傅里叶变换算法(附完整源码)

单片机:实现FFT快速傅里叶变换算法(附完整源码)

希望我的博客,能帮上你解决学习中工作中所遇到的问题 1099
上一篇: Android开发:PopupWindow实现底部弹出框
下一篇: Android开发:去除标题栏的方法
android157
博客等级 码龄9年 193粉丝 95原创
评论 9
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值