5

Biorąc pod uwagę aktualne dane o lokalizacji poruszającego się urządzenia w krótkim okresie czasu, w jaki sposób mogę uzyskać dłuższą parę dalej wzdłuż tej drogi, powiedzmy, 2 mile, a nawet lepiej, 5 minut jazdy samochodem?Jak mogę ekstrapolować dalej wzdłuż drogi?

Widzę, że mogę korzystać z Google's Roads API, aby przyciągnąć się do drogi, biorąc pod uwagę długą/długą parę https://developers.google.com/maps/documentation/roads/snap, ale to tylko w pewnym sensie doprowadza mnie do tego.

To będzie w aplikacji na Androida.

+0

nie google kierunki API ma jakieś rozwiązanie tego https: //developers.google.com/maps/documentation/directions/intro#Waypoints – commonSenseCode

+0

Nie, że mogę zobaczyć – Ken

+0

Myślę, że szukasz tego https://developer.android.com/reference/android/telephony/TelephonyManager.html#getCellLocation() –

Odpowiedz

5

Biorąc trasa reprezentowana jako List<LatLng>, ta funkcja oblicza punkt na trasie, wynikającego z przejazdu distance metrów od origin na tej trasie (za pomocą Google Maps API Utility Library zrobić kilka obliczeń):

private LatLng extrapolate(List<LatLng> path, LatLng origin, float distance) { 
    LatLng extrapolated = null; 

    if (!PolyUtil.isLocationOnPath(origin, path, false, 1)) { // If the location is not on path non geodesic, 1 meter tolerance 
     return null; 
    } 

    float accDistance = 0f; 
    boolean foundStart = false; 
    List<LatLng> segment = new ArrayList<>(); 

    for (int i = 0; i < path.size() - 1; i++) { 
     LatLng segmentStart = path.get(i); 
     LatLng segmentEnd = path.get(i + 1); 

     segment.clear(); 
     segment.add(segmentStart); 
     segment.add(segmentEnd); 

     double currentDistance = 0d; 

     if (!foundStart) { 
      if (PolyUtil.isLocationOnPath(origin, segment, false, 1)) { 
       foundStart = true; 

       currentDistance = SphericalUtil.computeDistanceBetween(origin, segmentEnd); 

       if (currentDistance > distance) { 
        double heading = SphericalUtil.computeHeading(origin, segmentEnd); 
        extrapolated = SphericalUtil.computeOffset(origin, distance - accDistance, heading); 
        break; 
       } 
      } 
     } else { 
      currentDistance = SphericalUtil.computeDistanceBetween(segmentStart, segmentEnd); 

      if (currentDistance + accDistance > distance) { 
       double heading = SphericalUtil.computeHeading(segmentStart, segmentEnd); 
       extrapolated = SphericalUtil.computeOffset(segmentStart, distance - accDistance, heading); 
       break; 
      } 
     } 

     accDistance += currentDistance; 
    } 

    return extrapolated; 
} 

Oto Niektóre testy:

List<LatLng> route = new ArrayList<>(); 
route.add(new LatLng(40, 4)); 
route.add(new LatLng(40.1, 4)); 
route.add(new LatLng(40.1, 4.1)); 
route.add(new LatLng(40.2, 4.1)); 
route.add(new LatLng(40.2, 4.2)); 
route.add(new LatLng(40.3, 4.2)); 
route.add(new LatLng(40.3, 4.3)); 

LatLng origin; 
LatLng extrapolated; 

origin = new LatLng(40.1, 4.05); 
extrapolated = extrapolate(route, origin, 30000); 
Log.e("Extrapolated1", "" + extrapolated); // lat/lng: (40.25517043951189,4.2) 

origin = new LatLng(40.05, 4); 
extrapolated = extrapolate(route, origin, 100); 
Log.e("Extrapolated2", "" + extrapolated); // lat/lng: (40.05089932033549,4.0) 

origin = new LatLng(40.05, 4); 
extrapolated = extrapolate(route, origin, 50000); 
Log.e("Extrapolated3", "" + extrapolated); // lat/lng: (40.300010207449226,4.261348349980259) 

origin = new LatLng(40.05, 4); 
extrapolated = extrapolate(route, origin, 100000); 
Log.e("Extrapolated4", "" + extrapolated); // null (result out of the route) 
+0

Świetna odpowiedź! Niestety nie mam trasy. Zmieniłem to pytanie, aby to wyjaśnić. – Ken

+1

Będę edytować moją odpowiedź, jeśli znajdę coś, co pasuje do twoich potrzeb, ale zachowam tę metodę na wypadek, gdyby to pomogło innym, nie masz nic przeciwko – antonio