Android谷歌地图在两点之间绘制一条路径 [英] Android Google Maps draw a path between two points

查看:92
本文介绍了Android谷歌地图在两点之间绘制一条路径的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想绘制两点之间的路径,并计算从A移动到B需要多长时间。我认为这对于Google Maps API来说是微不足道的任务。



我发现的所有内容都是 PolyUtil api / utility /rel =nofollow noreferrer>文档,不知道如何使用它。



我做了什么?



里面 MapsActivity onMapReady中方法我试图创建一个编码路径:

 列表< LatLng> latLngList = new ArrayList<>(); 
latLngList.add(new LatLng(56.952503,24.083719));
latLngList.add(new LatLng(55.877526,26.533898));

字符串encodedPath = PolyUtil.encode(latLngList);

但下一步是什么?如何在地图上绘制此路径?如何计算这两点之间的车/步行距离?

解决方案

路径是点的序列。其中一个解决方案是向谷歌地图API发出HTTP请求,指定您的两个位置作为参数,并取回描述在两点之间建立路径所需的点的JSON。需要执行的代码如下所示:


  1. 获取调用Google Maps API的方向URL
  2. ol>


      private String getMapsApiDirectionsUrl(LatLng origin,LatLng dest){
    //路由的起源
    String str_origin =origin =+ origin.latitude +,+ origin.longitude;

    //路线
    的目的地String str_dest =destination =+ dest.latitude +,+ dest.longitude;


    //启用传感器
    String sensor =sensor = false;

    //将参数构建到Web服务
    字符串参数= str_origin +&+ str_dest +&+ sensor;

    //输出格式
    字符串输出=json;

    //将网址构建到网络服务
    String url =https://maps.googleapis.com/maps/api/directions/\"+output+\"?\"+parameters;


    return url;


    $ / code $ / pre
    $ /


    1. 在后台执行URL调用

        private class ReadTask extends AsyncTask< String,Void ,String> {

      @Override
      protected String doInBackground(String ... url){
      // TODO自动生成的方法存根
      String data =;
      尝试{
      MapHttpConnection http = new MapHttpConnection();
      data = http.readUr(url [0]);

      $ b $ catch(Exception e){
      // TODO:处理异常
      Log.d(Background Task,e.toString());
      }
      返回数据;
      }

      @Override
      protected void onPostExecute(String result){
      super.onPostExecute(result);
      new ParserTask()。execute(result);
      }

      }





      public class MapHttpConnection {
    public String readUr(String mapsApiDirectionsUrl)throws IOException {
    String data =;
    InputStream istream = null;
    HttpURLConnection urlConnection = null;
    尝试{
    URL url = new URL(mapsApiDirectionsUrl);
    urlConnection =(HttpURLConnection)url.openConnection();
    urlConnection.connect();
    istream = urlConnection.getInputStream();
    BufferedReader br = new BufferedReader(new InputStreamReader(istream));
    StringBuffer sb = new StringBuffer();
    String line =; ((line = br.readLine())!= null){
    sb.append(line);
    while
    }
    data = sb.toString();
    br.close();


    $ b catch(Exception e){
    Log.d(读取url时的异常,e.toString());
    } finally {
    istream.close();
    urlConnection.disconnect();
    }
    返回数据;


    $ b $ / code $ / pre
    $ /


    1. 创建Parser类以将数据从 JSON 解析为指针列表

        public class PathJSONParser {

      public List< List< HashMap< String,String>>> parse(JSONObject jObject){
      List< List< HashMap< String,String>>> routes = new ArrayList< List< HashMap< String,String>>>();
      JSONArray jRoutes = null;
      JSONArray jLegs = null;
      JSONArray jSteps = null;
      尝试{
      jRoutes = jObject.getJSONArray(routes);
      for(int i = 0; i< jRoutes.length(); i ++){
      jLegs =((JSONObject)jRoutes.get(i))。getJSONArray(legs);
      List< HashMap< String,String>> path = new ArrayList< HashMap< String,String>>(); $ j $ b $ for(int j = 0; j jSteps =((JSONObject)jLegs.get(j))。getJSONArray(steps);
      for(int k = 0; k< jSteps.length(); k ++){
      String polyline =;
      polyline =(String)((JSONObject)((JSONObject)jSteps.get(k))。get(polyline))。get(points);
      列表< LatLng> list = decodePoly(polyline);
      for(int l = 0; l< list.size(); l ++){
      HashMap< String,String> hm = new HashMap< String,String>();
      hm.put(lat,
      Double.toString(((LatLng)list.get(l))。latitude));
      hm.put(lng,
      Double.toString(((LatLng)list.get(l))。longitude));
      path.add(hm);
      }
      }
      routes.add(path);



      $ b catch(Exception e){
      e.printStackTrace();
      }
      返回路线;

      }

      私人列表< LatLng> decodePoly(字符串编码){
      List< LatLng> poly = new ArrayList< LatLng>();
      int index = 0,len = encoded.length();
      int lat = 0,lng = 0;

      while(index< len){
      int b,shift = 0,result = 0;
      do {
      b = encoded.charAt(index ++) - 63;
      result | =(b& 0x1f)<<转移;
      shift + = 5;
      } while(b> = 0x20);
      int dlat =((result& 1)!= 0?〜(result>> 1):( result>> 1));
      lat + = dlat;

      shift = 0;
      结果= 0;
      do {
      b = encoded.charAt(index ++) - 63;
      result | =(b& 0x1f)<<转移;
      shift + = 5;
      } while(b> = 0x20);
      int dlng =((result& 1)!= 0?〜(result>> 1):(result>> 1));
      lng + = dlng;

      LatLng p = new LatLng((((double)lat / 1E5)),
      (((double)lng / 1E5)));
      poly.add(p);
      }
      返回poly;
      }}


    2. 使用另一个线程扩展性能





    3.   private class ParserTask扩展AsyncTask< String,Integer,List< List< HashMap< String,String>>>> {
      @Override
      protected List< List< HashMap< String,String>>> doInBackground(
      String ... jsonData){
      // TODO自动生成的方法存根
      JSONObject jObject;
      List< List< HashMap< String,String>>> routes = null;
      尝试{
      jObject = new JSONObject(jsonData [0]);
      PathJSONParser parser = new PathJSONParser();
      routes = parser.parse(jObject);


      } catch(Exception e){
      e.printStackTrace();
      }
      返回路线;

      $ b @Override
      protected void onPostExecute(List< List< HashMap< String,String>>> routes){
      ArrayList< LatLng> points = null;
      PolylineOptions polyLineOptions = null;

      //遍历路由
      for(int i = 0; i< routes.size(); i ++){
      points = new ArrayList< LatLng>();
      polyLineOptions = new PolylineOptions();
      List< HashMap< String,String>> path = routes.get(i);

      for(int j = 0; j< path.size(); j ++){
      HashMap< String,String> point = path.get(j);

      double lat = Double.parseDouble(point.get(lat));
      double lng = Double.parseDouble(point.get(lng));
      LatLng position = new LatLng(lat,lng);

      points.add(position);
      }

      polyLineOptions.addAll(points);
      polyLineOptions.width(4);
      polyLineOptions.color(Color.BLUE);
      }

      googleMap.addPolyline(polyLineOptions);

      }}





      1. 当您想获得两点的路径时




        String url = getMapsApiDirectionsUrl(latlngOne,latlngTwo); 
      ReadTask downloadTask = new ReadTask();
      //开始从Google Directions API下载json数据
      downloadTask.execute(url);


      计算积分之间的距离

        float [] results = new float [1]; 
      Location.distanceBetween(latLongA.latitude,latLongB.longitude,
      latLongB.latitude,latLongB.longitude,
      results);

      结果将以米为单位

      I would like to draw a path between two points and calculate how much time it will take to move from A to B. I have thought that it is trivial task for Google Maps API.

      Everything that I found is small snippet about PolyUtil in documentation and nothing about how to use it.

      What I did ?

      Inside MapsActivity in onMapReady method I'm trying to create an encoded path:

      List<LatLng> latLngList = new ArrayList<>();
      latLngList.add(new LatLng(56.952503, 24.083719));
      latLngList.add(new LatLng(55.877526, 26.533898));
      
      String encodedPath = PolyUtil.encode(latLngList);
      

      But what is the next ? How to draw this path on map ? How to calculate car/walking distance between this points ?

      解决方案

      Path is sequence of point . One of the solution is to make HTTP request to Google maps API specifying your two locations as parameters and get back JSON describing the points required to make the path between the two points. Require code to do that are listed below :

      1. Get direction URL require to call Google Maps API

      private String  getMapsApiDirectionsUrl(LatLng origin,LatLng dest) {
         // Origin of route
       String str_origin = "origin="+origin.latitude+","+origin.longitude;
      
       // Destination of route
       String str_dest = "destination="+dest.latitude+","+dest.longitude;        
      
      
       // Sensor enabled
       String sensor = "sensor=false";            
      
       // Building the parameters to the web service
       String parameters = str_origin+"&"+str_dest+"&"+sensor;
      
       // Output format
       String output = "json";
      
       // Building the url to the web service
       String url = "https://maps.googleapis.com/maps/api/directions/"+output+"?"+parameters;
      
      
       return url;
      
      }
      

      1. Do the URL call in background

        private class ReadTask extends AsyncTask<String, Void , String> {
        
        @Override
        protected String doInBackground(String... url) {
            // TODO Auto-generated method stub
            String data = "";
            try {
                MapHttpConnection http = new MapHttpConnection();
                data = http.readUr(url[0]);
        
        
            } catch (Exception e) {
                // TODO: handle exception
                Log.d("Background Task", e.toString());
            }
            return data;
        }
        
        @Override
        protected void onPostExecute(String result) {
            super.onPostExecute(result);
            new ParserTask().execute(result);
        }
        
        }
        

        public class MapHttpConnection {
        public String readUr(String mapsApiDirectionsUrl) throws IOException{
            String data = "";
            InputStream istream = null;
            HttpURLConnection urlConnection = null;
            try {
                URL url = new URL(mapsApiDirectionsUrl);
                urlConnection = (HttpURLConnection) url.openConnection();
                urlConnection.connect();
                istream = urlConnection.getInputStream();
                BufferedReader br = new BufferedReader(new InputStreamReader(istream));
                StringBuffer sb = new StringBuffer();
                String line ="";
                while ((line = br.readLine()) != null) {
                    sb.append(line);
                }
                data = sb.toString();
                br.close();
      
      
            }
            catch (Exception e) {
                Log.d("Exception while reading url", e.toString());
            } finally {
                istream.close();
                urlConnection.disconnect();
            }
            return data;
      
        }
      }
      

      1. Create Parser class to parse the data from JSON to List of pointes

        public class PathJSONParser {
        
        public List<List<HashMap<String, String>>> parse(JSONObject jObject) {
            List<List<HashMap<String, String>>> routes = new ArrayList<List<HashMap<String,String>>>();
            JSONArray jRoutes = null;
            JSONArray jLegs = null;
            JSONArray jSteps = null;
            try {
                jRoutes = jObject.getJSONArray("routes");
                for (int i=0 ; i < jRoutes.length() ; i ++) {
                    jLegs = ((JSONObject) jRoutes.get(i)).getJSONArray("legs");
                    List<HashMap<String, String>> path = new ArrayList<HashMap<String,String>>();
                    for(int j = 0 ; j < jLegs.length() ; j++) {
                        jSteps = ((JSONObject) jLegs.get(j)).getJSONArray("steps");
                        for(int k = 0 ; k < jSteps.length() ; k ++) {
                            String polyline = "";
                            polyline = (String) ((JSONObject) ((JSONObject) jSteps.get(k)).get("polyline")).get("points");
                            List<LatLng> list = decodePoly(polyline);
                            for(int l = 0 ; l < list.size() ; l ++){
                                HashMap<String, String> hm = new HashMap<String, String>();
                                hm.put("lat",
                                        Double.toString(((LatLng) list.get(l)).latitude));
                                hm.put("lng",
                                        Double.toString(((LatLng) list.get(l)).longitude));
                                path.add(hm);
                            }
                        }
                        routes.add(path);
                    }
        
                }
        
            } catch (Exception e) {
                e.printStackTrace();
            }
            return routes;
        
        }
        
        private List<LatLng> decodePoly(String encoded) {
            List<LatLng> poly = new ArrayList<LatLng>();
            int index = 0, len = encoded.length();
            int lat = 0, lng = 0;
        
            while (index < len) {
                int b, shift = 0, result = 0;
                do {
                    b = encoded.charAt(index++) - 63;
                    result |= (b & 0x1f) << shift;
                    shift += 5;
                } while (b >= 0x20);
                int dlat = ((result & 1) != 0 ? ~(result >> 1) : (result >> 1));
                lat += dlat;
        
                shift = 0;
                result = 0;
                do {
                    b = encoded.charAt(index++) - 63;
                    result |= (b & 0x1f) << shift;
                    shift += 5;
                } while (b >= 0x20);
                int dlng = ((result & 1) != 0 ? ~(result >> 1) : (result >> 1));
                lng += dlng;
        
                LatLng p = new LatLng((((double) lat / 1E5)),
                        (((double) lng / 1E5)));
                poly.add(p);
            }
            return poly;
        }}
        

      2. Do the parse using another Thread to expand performance

      private class ParserTask extends AsyncTask<String,Integer, List<List<HashMap<String , String >>>> {
        @Override
        protected List<List<HashMap<String, String>>> doInBackground(
                String... jsonData) {
            // TODO Auto-generated method stub
            JSONObject jObject;
            List<List<HashMap<String, String>>> routes = null;
            try {
                jObject = new JSONObject(jsonData[0]);
                PathJSONParser parser = new PathJSONParser();
                routes = parser.parse(jObject);
      
      
            } catch (Exception e) {
                e.printStackTrace();
            }
            return routes;
        }
      
        @Override
        protected void onPostExecute(List<List<HashMap<String, String>>> routes) {
            ArrayList<LatLng> points = null;
            PolylineOptions polyLineOptions = null;
      
            // traversing through routes
            for (int i = 0; i < routes.size(); i++) {
                points = new ArrayList<LatLng>();
                polyLineOptions = new PolylineOptions();
                List<HashMap<String, String>> path = routes.get(i);
      
                for (int j = 0; j < path.size(); j++) {
                    HashMap<String, String> point = path.get(j);
      
                    double lat = Double.parseDouble(point.get("lat"));
                    double lng = Double.parseDouble(point.get("lng"));
                    LatLng position = new LatLng(lat, lng);
      
                    points.add(position);
                }
      
                polyLineOptions.addAll(points);
                polyLineOptions.width(4);
                polyLineOptions.color(Color.BLUE);
            }
      
            googleMap.addPolyline(polyLineOptions);
      
        }}
      

      1. When you want to get the path of two point

       String url = getMapsApiDirectionsUrl(latlngOne, latlngTwo);                    
          ReadTask downloadTask = new ReadTask();       
          // Start downloading json data from Google Directions API
          downloadTask.execute(url);
      

      To calculate distance between points

      float[] results = new float[1];
      Location.distanceBetween(latLongA.latitude, latLongB.longitude,
                               latLongB.latitude, latLongB.longitude,
                               results); 
      

      the results will be in meters

      这篇关于Android谷歌地图在两点之间绘制一条路径的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆