使用Google Map中的按钮查找当前位置和用户输入字段之间的距离

时间:2017-02-23 07:05:47

标签: android google-maps

我正在使用一个项目找到两个地方之间的距离,一个是当前位置,另一个是使用自动完成文本视图的用户输入值。

如何使用按钮点击获得正确的距离。没有按钮点击我得到了值。如何实现按钮点击?

output with map click listener

   protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_maps);
    MarkerPoints = new ArrayList<>();
    final AutoCompleteTextView autoCompView = (AutoCompleteTextView) findViewById(R.id.autoCompleteTextView);

    autoCompView.setAdapter(new GooglePlacesAutocompleteAdapter(this, R.layout.list_item));
    autoCompView.setOnItemClickListener(this);
    b1=(Button)findViewById(R.id.search_button);
    b1.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            String location = autoCompView.getText().toString();
            List<Address>addressList = null;

            if (location != null || !location.equals("")) {
                Geocoder geocoder = new Geocoder(MapsActivity.this);
                try {
                    addressList = geocoder.getFromLocationName(location, 1);

                } catch (IOException e) {
                    e.printStackTrace();
                }
                Address address = addressList.get(0);
                LatLng dest = new LatLng(address.getLatitude(), address.getLongitude());
                lat1=String.valueOf(address.getLatitude());
                lon1 = String.valueOf(address.getLongitude());
                Toast.makeText(MapsActivity.this, "new Lati and new longi1 "+dest, Toast.LENGTH_LONG).show();


                mMap.addMarker(new MarkerOptions().position(dest).title("Marker"));
                mMap.animateCamera(CameraUpdateFactory.newLatLng(dest));
               // SendDataToServer(unique_id,lat1,lon1);
                //   mMap.clear();
                findPath(point);

            }



        }
    });

    if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
        checkLocationPermission();
    }
    // Obtain the SupportMapFragment and get notified when the map is ready to be used.
    SupportMapFragment mapFragment = (SupportMapFragment) getSupportFragmentManager()
            .findFragmentById(R.id.map);
    mapFragment.getMapAsync(this);
    sharedpreferences = getSharedPreferences(MyPREFERENCES, Context.MODE_PRIVATE);

}

private void findPath(LatLng point) {
  if (MarkerPoints.size() >= 2) {
        LatLng origin = MarkerPoints.get(0);
        LatLng dest = MarkerPoints.get(1);

        // Getting URL to the Google Directions API
        String url = getUrl(origin, dest);
     //   Log.d("onMapClick", url.toString());
        FetchUrl FetchUrl = new FetchUrl();

        // Start downloading json data from Google Directions API
        FetchUrl.execute(url);
        //move map camera
        mMap.moveCamera(CameraUpdateFactory.newLatLng(origin));
        mMap.animateCamera(CameraUpdateFactory.zoomTo(16));
    }

}

private void drawMarker(LatLng point) {
    MarkerPoints.add(point);

    // Creating MarkerOptions
    MarkerOptions options = new MarkerOptions();

    // Setting the position of the marker
    options.position(point);
  private String getUrl(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;
}

/**
 * A method to download json data from url
 */
private String downloadUrl(String strUrl) throws IOException {
    String data = "";
    InputStream iStream = null;
    HttpURLConnection urlConnection = null;
    try {
        URL url = new URL(strUrl);

        // Creating an http connection to communicate with url
        urlConnection = (HttpURLConnection) url.openConnection();

        // Connecting to url
        urlConnection.connect();

        // Reading data from url
        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();
        Log.d("downloadUrl", data.toString());
        br.close();

    } catch (Exception e) {
        Log.d("Exception", e.toString());
    } finally {
        iStream.close();
        urlConnection.disconnect();
    }
    return data;
}

// Fetches data from url passed
private class FetchUrl extends AsyncTask<String, Void, String> {

    @Override
    protected String doInBackground(String... url) {

        // For storing data from web service
        String data = "";

        try {
            // Fetching the data from web service
            data = downloadUrl(url[0]);
            Log.d("Background Task data", data.toString());
        } catch (Exception e) {
            Log.d("Background Task", e.toString());
        }
        return data;
    }

    @Override
    protected void onPostExecute(String result) {
        super.onPostExecute(result);

        ParserTask parserTask = new ParserTask();

        // Invokes the thread for parsing the JSON data
        parserTask.execute(result);

    }
}

/**
 * A class to parse the Google Places in JSON format
 */
private class ParserTask extends AsyncTask<String, Integer, List<List<HashMap<String, String>>>> {

    // Parsing the data in non-ui thread
    @Override
    protected List<List<HashMap<String, String>>> doInBackground(String... jsonData) {

        JSONObject jObject;
        List<List<HashMap<String, String>>> routes = null;

        try {
            jObject = new JSONObject(jsonData[0]);
            Log.d("ParserTask",jsonData[0].toString());
            DataParser parser = new DataParser();
            Log.d("ParserTask", parser.toString());

            // Starts parsing data
            routes = parser.parse(jObject);
            Log.d("ParserTask","Executing routes");
            Log.d("ParserTask",routes.toString());

        } catch (Exception e) {
            Log.d("ParserTask",e.toString());
            e.printStackTrace();
        }
        return routes;
    }

    // Executes in UI thread, after the parsing process
    @Override
    protected void onPostExecute(List<List<HashMap<String, String>>> result) {
        ArrayList<LatLng> points;
        PolylineOptions lineOptions = null;
        String distance = "";
        String duration = "";

        // Traversing through all the routes
        for (int i = 0; i < result.size(); i++) {
            points = new ArrayList<>();
            lineOptions = new PolylineOptions();

            // Fetching i-th route
            List<HashMap<String, String>> path = result.get(i);

            // Fetching all the points in i-th route
            for (int j = 0; j < path.size(); j++) {
                HashMap<String, String> point = path.get(j);

                if(j==0){    // Get distance from the list
                    distance = (String)point.get("distance");
                    continue;
                }else if(j==1){ // Get duration from the list
                    duration = (String)point.get("duration");
                    continue;
                }

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

                points.add(position);
            }

            // Adding all the points in the route to LineOptions
            lineOptions.addAll(points);
            lineOptions.width(10);
            lineOptions.color(Color.RED);

            Log.d("onPostExecute","onPostExecute lineoptions decoded");
            tvDistanceDuration.setText("Distance:"+distance + ", Duration:"+duration);
        }

        // Drawing polyline in the Google Map for the i-th route
        if(lineOptions != null) {
            mMap.addPolyline(lineOptions);
        }
        else {
            Log.d("onPostExecute","without Polylines drawn");
        }
    }

2 个答案:

答案 0 :(得分:0)

如果您知道两个位置的纬度和经度,那么您可以轻松计算两个位置之间的距离。有关详细信息,请访问http://www.geodatasource.com/developers/java

以下是如何在android中完成的。

在某个类

中创建如下的方法
private static double distance(double lat1, double lon1, double lat2, double lon2, String unit) {
        double theta = lon1 - lon2;
        double dist = Math.sin(deg2rad(lat1)) * Math.sin(deg2rad(lat2)) + Math.cos(deg2rad(lat1)) * Math.cos(deg2rad(lat2)) * Math.cos(deg2rad(theta));
        dist = Math.acos(dist);
        dist = rad2deg(dist);
        dist = dist * 60 * 1.1515;
        if (unit == "K") {
            dist = dist * 1.609344;
        } else if (unit == "N") {
            dist = dist * 0.8684;
        }

        return (dist);
    }

    /*:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::*/
    /*::    This function converts decimal degrees to radians                        :*/
    /*:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::*/
    private static double deg2rad(double deg) {
        return (deg * Math.PI / 180.0);
    }

    /*:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::*/
    /*::    This function converts radians to decimal degrees                        :*/
    /*:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::*/
    private static double rad2deg(double rad) {
        return (rad * 180 / Math.PI);
    }

然后您可以使用distance方法

例如,距离是Helper Class的静态方法,然后

int distance = Helper.distance(lat1,lon1,lat2,lon2,"K")使用&#34; K&#34;公里&#34; N&#34;为了

我希望这会以某种方式帮助你。

答案 1 :(得分:0)

这是我用来获取从用户位置到所选位置的距离和时间旅行的方法。将其添加到AsyncTask

下方
public void getDistAndDuration(JSONObject jObj){
    try{
        JSONArray array = jObj.getJSONArray("routes");
        JSONObject rou = array.getJSONObject(0);
        JSONArray legs = rou.getJSONArray("legs");
        JSONObject steps = legs.getJSONObject(0);
        JSONObject distance = steps.getJSONObject("distance");
        JSONObject duration = steps.getJSONObject("duration");
        final String textDist = distance.getString("text");
        final String textDur = duration.getString("text");

        Log.i("DISTANCE", ""+textDist);
        Log.i("TIME", ""+textDur);

    }catch(Exception e){
        e.printStackTrace();
    }
}

使用ParserTask方法在doInBackground中调用此方法,如下所示:

@Override
protected List<List<HashMap<String, String>>> doInBackground(String... jsonData) {

    JSONObject jObject;
    List<List<HashMap<String, String>>> routes = null;

    try {
        jObject = new JSONObject(jsonData[0]);

        ////////// HERE //////////////
        getDistAndDuration(jObject);
        //////////////////////////////

        Log.d("ParserTask",jsonData[0].toString());
        DataParser parser = new DataParser();
        Log.d("ParserTask", parser.toString());

        // Starts parsing data
        routes = parser.parse(jObject);
        Log.d("ParserTask","Executing routes");
        Log.d("ParserTask",routes.toString());

    } catch (Exception e) {
        Log.d("ParserTask",e.toString());
        e.printStackTrace();
    }
    return routes;
}

如果您只想点击按钮上的距离,请在全局范围内声明jObject,并在按钮的点击监听器中调用getDistAndDuration(JSONObject jObj)。请先致电AsyncTask后再拨打电话。

希望有所帮助:)