java多段线未显示在两个位置之间,但显示时间和距离
注意:很抱歉我的英语不好,因为英语不是我的母语,我已经用谷歌翻译了强>
我正在开发一个Android地图应用程序,用户可以在其中找到他们朋友的当前位置。为了存储当前位置,我使用Firebase实时数据库。在Lalit Singh之前的帮助下,它现在显示了时间和距离,但仍然没有更新两个不同位置之间的多段线。我的更新代码如下
地图活性。java(我从fire base获取好友位置,并调用更新的时间、距离和多段线方法)
public void proceed(final View view) { DatabaseReference ref = FirebaseDatabase.getInstance().getReference().child("Email"); ref.addValueEventListener(new ValueEventListener() { @Override public void onDataChange(DataSnapshot dataSnapshot) { for (DataSnapshot dataSnapshot1 : dataSnapshot.getChildren()) { UserInformation details = dataSnapshot1.getValue(UserInformation.class); if (mMap != null) { mMap.clear(); } MarkerOptions markerOptions = new MarkerOptions(); LatLng latLng1 = new LatLng(details.getLatitude(), details.getLongitude()); markerOptions.position(latLng1); markerOptions.title(String.valueOf(latLng1)); mMap.addMarker(markerOptions).setIcon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_GREEN)); mMap.setMapType(GoogleMap.MAP_TYPE_HYBRID); mMap.moveCamera(CameraUpdateFactory.newLatLng(latLng1)); mMap.animateCamera(CameraUpdateFactory.zoomTo(14)); distance_task.getDirectionsUrl(latLng1, markerOptions.getPosition()); distance_task.setLoadListener(new CalculateDistanceTime.taskCompleteListener() { @Override public void taskCompleted(String[] time_distance) { text1.setText(time_distance[0]); //Distance text2.setText(time_distance[1]); //Time } }); String url = getDirectionsUrl(latLng1, markerOptions.getPosition()); DownloadTask downloadTask = new DownloadTask(); downloadTask.execute(url); } } @Override public void onCancelled(DatabaseError databaseError) { } }); }
计算待机时间。java(添加了新类)
class CalculateDistanceTime { private taskCompleteListener mTaskListener; private Context mContext; CalculateDistanceTime(Context context) { mContext = context; } void setLoadListener(taskCompleteListener taskListener) { mTaskListener = taskListener; } void getDirectionsUrl(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; DownloadTask downloadTask = new DownloadTask(); // Start downloading json data from Google Directions API downloadTask.execute(url); } private String downloadUrl(String strUrl) throws IOException { String data = ""; HttpURLConnection urlConnection; 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 try (InputStream iStream = urlConnection.getInputStream()) { BufferedReader br = new BufferedReader(new InputStreamReader(iStream)); StringBuilder sb = new StringBuilder(); String line; while ((line = br.readLine()) != null) { sb.append(line); } data = sb.toString(); br.close(); } catch (Exception e) { Log.d("Excp. while downloading", e.toString()); } finally { urlConnection.disconnect(); } return data; } interface taskCompleteListener { void taskCompleted(String[] time_distance); } private class DownloadTask extends AsyncTask<String, Void, String> { // Downloading data in non-ui thread @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]); } catch (Exception e) { Log.d("Background Task", e.toString()); } return data; } // Executes in UI thread, after the execution of // doInBackground() @Override protected void onPostExecute(String result) { super.onPostExecute(result); ParserTask parserTask = new ParserTask(); // Invokes the thread for parsing the JSON data parserTask.execute(result); } } private class ParserTask extends AsyncTask<String, Integer, List<HashMap<String, String>>> { // Parsing the data in non-ui thread @Override protected List<HashMap<String, String>> doInBackground(String... jsonData) { JSONObject jObject; List<HashMap<String, String>> routes = null; try { jObject = new JSONObject(jsonData[0]); DistanceTimeParser parser = new DistanceTimeParser(); // Starts parsing data routes = parser.parse(jObject); } catch (Exception e) { e.printStackTrace(); } return routes; } // Executes in UI thread, after the parsing process @Override protected void onPostExecute(List<HashMap<String, String>> result) { String duration_distance = ""; if (result.size() < 1) { Log.e("Error : ", "No Points found"); return; } String[] date_dist = new String[2]; // Traversing through all the routes for (int i = 0; i < result.size(); i++) { // Fetching i-th route HashMap<String, String> tmpData = result.get(i); Set<String> key = tmpData.keySet(); Iterator it = key.iterator(); while (it.hasNext()) { String hmKey = (String) it.next(); duration_distance = tmpData.get(hmKey); System.out.println("Key: " + hmKey + " & Data: " + duration_distance); it.remove(); // avoids a ConcurrentModificationException } date_dist[i] = duration_distance; } mTaskListener.taskCompleted(date_dist); } } }
距离时间分析器。java(添加了新类)
public class DistanceTimeParser { public List<HashMap<String, String>> parse(JSONObject jObject) { List<HashMap<String, String>> routes = new ArrayList<HashMap<String, String>>(); JSONArray jRoutes = null; JSONArray jLegs = null; JSONObject jDistance = null; JSONObject jDuration = null; try { jRoutes = jObject.getJSONArray("routes"); jLegs = ((JSONObject) jRoutes.get(0)).getJSONArray("legs"); List<HashMap<String, String>> path = new ArrayList<HashMap<String, String>>(); /** Getting distance from the json data */ jDistance = ((JSONObject) jLegs.get(0)).getJSONObject("distance"); HashMap<String, String> hmDistance = new HashMap<String, String>(); hmDistance.put("distance", jDistance.getString("text")); /** Getting duration from the json data */ jDuration = ((JSONObject) jLegs.get(0)).getJSONObject("duration"); HashMap<String, String> hmDuration = new HashMap<String, String>(); hmDuration.put("duration", jDuration.getString("text")); routes.add(hmDistance); routes.add(hmDuration); } catch (JSONException e) { e.printStackTrace(); } catch (Exception e) { } return routes; } }
DirectionsJSONParser。java(添加了新类)
public class DirectionsJSONParser { List<List<HashMap<String,String>>> parse(JSONObject jObject){ List<List<HashMap<String, String>>> routes = new ArrayList<>() ; JSONArray jRoutes ; JSONArray jLegs ; JSONArray jSteps ; try { jRoutes = jObject.getJSONArray("routes"); for(int i=0;i<jRoutes.length();i++){ jLegs = ( (JSONObject)jRoutes.get(i)).getJSONArray("legs"); List path = new ArrayList<>(); 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<>(); hm.put("lat", Double.toString((list.get(l)).latitude) ); hm.put("lng", Double.toString((list.get(l)).longitude) ); path.add(hm); } } routes.add(path); } } } catch (JSONException e) { e.printStackTrace(); }catch (Exception ignored){ } return routes; } private List<LatLng> decodePoly(String encoded) { List<LatLng> poly = new ArrayList<>(); 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; } }
这4种方法添加到mapsActivity中。爪哇
private String getDirectionsUrl(LatLng origin, LatLng dest) { String str_origin = "origin=" + origin.latitude + "," + origin.longitude; String str_dest = "destination=" + dest.latitude + "," + dest.longitude; String sensor = "sensor=false"; String parameters = str_origin + "&" + str_dest + "&" + sensor; String output = "json"; return "https://maps.googleapis.com/maps/api/directions/" + output + "?" + parameters; } @SuppressLint("NewApi") public static String downloadUrl(String strUrl) throws IOException { String data = ""; HttpURLConnection urlConnection; 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 try (InputStream iStream = urlConnection.getInputStream()) { BufferedReader br = new BufferedReader(new InputStreamReader(iStream)); StringBuilder sb = new StringBuilder(); String line; while ((line = br.readLine()) != null) { sb.append(line); } data = sb.toString(); br.close(); } catch (Exception e) { Log.d("Exception while down", e.toString()); } finally { urlConnection.disconnect(); } return data; } private class DownloadTask extends AsyncTask<String, Void, String> { // Downloading data in non-ui thread @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]); } catch (Exception e) { Log.d("Background Task", e.toString()); } return data; } // Executes in UI thread, after the execution of // doInBackground() @Override protected void onPostExecute(String result) { super.onPostExecute(result); ParserTask parserTask = new ParserTask(); // Invokes the thread for parsing the JSON data parserTask.execute(result); } } private class ParserTask extends AsyncTask<String, Integer, List<List<HashMap<String, String>>>> { @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]); DirectionsJSONParser parser = new DirectionsJSONParser(); // Starts parsing data routes = parser.parse(jObject); } catch (Exception e) { e.printStackTrace(); } return routes; } @Override protected void onPostExecute(List<List<HashMap<String, String>>> result) { ArrayList<LatLng> points = new ArrayList<>(); PolylineOptions lineOptions = new PolylineOptions(); for (int i = 0; i < result.size(); i++) { List<HashMap<String, String>> path = result.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); } lineOptions.addAll(points); lineOptions.width(10); lineOptions.color(Color.WHITE); mMap.addPolyline(lineOptions); } } }
地图活性。java(我在地图中的当前位置)
@Override public void onLocationChanged(Location location) { Log.d("onLocationChanged", "entered"); mLastLocation = location; DateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss"); dateFormat.setTimeZone(TimeZone.getTimeZone("UTC")); Date date = new Date(); mLastUpdateTime = ((dateFormat.format(date).toString())); saveToFirebase(); if (mCurrLocationMarker != null) { mCurrLocationMarker.remove(); } latitude = location.getLatitude(); longitude = location.getLongitude(); LatLng latLng = new LatLng(location.getLatitude(), location.getLongitude()); MarkerOptions markerOptions = new MarkerOptions(); markerOptions.position(latLng); markerOptions.draggable(false); markerOptions.title("Current Position"); markerOptions.icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_MAGENTA)); mCurrLocationMarker = mMap.addMarker(markerOptions); //move map camera mMap.moveCamera(CameraUpdateFactory.newLatLng(latLng)); mMap.animateCamera(CameraUpdateFactory.zoomTo(11)); Toast.makeText(MapsActivity.this, "Your Current Location", Toast.LENGTH_LONG).show(); //stop location updates if (mGoogleApiClient != null) { LocationServices.FusedLocationApi.removeLocationUpdates(mGoogleApiClient, this); Log.d("onLocationChanged", "Removing Location Updates"); } }
保存在Fire Base方法中的数据
public void saveToFirebase() { DatabaseReference ref = FirebaseDatabase.getInstance().getReference().child("Email").push(); String email = FirebaseAuth.getInstance().getCurrentUser().getEmail(); UserInformation userInformation = new UserInformation(email, mLastLocation.getLatitude(), mLastLocation.getLongitude()); ref.setValue(userInformation); }
# 1 楼答案
添加以下代码并替换为图形多段线代码,使用
在需要绘制方向的地方使用上述代码,
origin
&dest
是LatLng对象,例如下面以下是获取方向的方法:
在这之后,使用下面的课程
# 2 楼答案
我假设你需要路线、距离和时间。 首先创建这三个类
计算待机时间。爪哇
距离时间分析器。爪哇
DirectionsJSONParser。爪哇
在简单地复制这三个文件之后。 对于任何MapsActivity,您都可以执行以下操作
在这一点上,您可以在任何活动中使用下面的代码,而在每个活动中,上面的代码都将保持不变(方向图)
创建一个全局变量
CalculateDistanceTime distance_task;
在
onCreate
中将其初始化为distance_task = new CalculateDistanceTime(this);
在MapsActivity中发布这4种方法。爪哇
此时,您已经拥有了所有需要的代码
现在使用下面的代码传递你的位置和朋友的位置的latlngs,你将得到时间距离和路线:
要显示距离和时间,必须创建两个
TextView
(请参见上文的文本1和文本2)