Cuando se usa GPX en Xcode para simular cambios de location, ¿hay alguna forma de controlar la velocidad?

Estoy usando el siguiente file GPX en Xcode 4.2 para simular un cambio de location. Funciona bien, pero no puedo controlar la velocidad del cambio de location. El sello parece no estar funcionando. ¿Alguien tiene una solución para esto?

<?xml version="1.0"?> <gpx version="1.1" creator="Xcode"> <wpt lat="37.331705" lon="-122.030237"></wpt> <wpt lat="37.331705" lon="-122.030337"></wpt> <wpt lat="37.331705" lon="-122.030437"></wpt> <wpt lat="37.331705" lon="-122.030537"></wpt> </gpx> 

No creo (sé) que esto sea posible en el GPX directamente, pero puedes probar el cambio de location con Instruments / Automation.

Usaría un script como:

 var target = UIATarget.localTarget(); target.setLocation(<location); target.delay(5); target.setLocation(...); 

Y así. Tomé este ejemplo del video WWDC11 https://deimos.apple.com/WebObjects/Core.woa/BrowsePrivately/adc.apple.com.8266314619.08266314625.8367850271 (Prueba de tus aplicaciones con conocimiento de location)

Soy consciente de que esto en realidad no te permite definir la velocidad, pero espero que las demoras de alguna manera sirvan de explicación. Quizás eso te ayude.

No creo que puedas hacerlo con files GPX. Pero es fácil con la herramienta de automation dentro de Intruments. Aquí hay uno de los scripts que uso para la testing de mi aplicación y la recostackción de capturas de pantalla:

 var target = UIATarget.localTarget(); // speed is in meters/sec var points = [ {location:{latitude:48.8899,longitude:14.2}, options:{speed:8, altitude:200, horizontalAccuracy:10, verticalAccuracy:15}}, {location:{latitude:48.8899,longitude:14.9}, options:{speed:11, altitude:200, horizontalAccuracy:10, verticalAccuracy:15}}, {location:{latitude:48.8899,longitude:14.6}, options:{speed:12, altitude:200, horizontalAccuracy:10, verticalAccuracy:15}}, {location:{latitude:48.8899,longitude:14.7}, options:{speed:13, altitude:200, horizontalAccuracy:10, verticalAccuracy:15}}, {location:{latitude:49.2,longitude:14.10}, options:{speed:15, altitude:200, horizontalAccuracy:10, verticalAccuracy:15}}, {location:{latitude:49.4,longitude:14.8}, options:{speed:15, altitude:200, horizontalAccuracy:10, verticalAccuracy:15}}, {location:{latitude:48.8899,longitude:14.9}, options:{speed:9, altitude:200, horizontalAccuracy:10, verticalAccuracy:15}}, {location:{latitude:48.8899,longitude:15.1}, options:{speed:8, altitude:200, horizontalAccuracy:10, verticalAccuracy:15}}, {location:{latitude:48.8899,longitude:16.1}, options:{speed:3, altitude:200, horizontalAccuracy:10, verticalAccuracy:15}}, ]; for (var i = 0; i < points.length; i++) { target.setLocationWithOptions(points[i].location,points[i].options); target.captureScreenWithName(i+"_.png"); target.delay(1.0); } 

Creé un tutorial paso a paso sobre cómo usé la simulación de location con Automation and Leaks para capturar capturas de pantalla y encontrar fugas

El soporte de Xcode simula el cambio de velocidad con un file GPX.

Proporcione uno o más waypoints que contengan un par de latitud / longitud. Si proporciona un waypoint, Xcode simulará esa location específica. Si proporciona múltiples waypoints, Xcode simulará una visita de ruta a cada waypoint.

Opcionalmente, proporcione un elemento de time para cada waypoint. Xcode interpolará el movimiento a una velocidad determinada en function del time transcurrido entre cada waypoint. Si no proporciona un elemento de time, entonces Xcode utilizará una velocidad de velocidad fija. Los waypoints deben orderarse por hora en order ascendente.

Escribe así:

 <wpt lat="39.96104510" lon="116.4450860"> <time>2010-01-01T00:00:00Z</time> </wpt> <wpt lat="39.96090940" lon="116.4451400"> <time>2010-01-01T00:00:05Z</time> </wpt> ... <wpt lat="39.96087240" lon="116.4450430"> <time>2010-01-01T00:00:09Z</time> </wpt> 

Acerca de -1 velocidad

La velocidad del object CoreLocation siempre será -1 durante la simulación. Una posible solución es save una última location y luego calcular la velocidad nosotros mismos. Código de muestra:

 CLLocationSpeed speed = location.speed; if (speed < 0) { // A negative value indicates an invalid speed. Try calculate manually. CLLocation *lastLocation = self.lastLocation; NSTimeInterval time = [location.timestamp timeIntervalSinceDate:lastLocation.timestamp]; if (time <= 0) { // If there are several location manager work at the same time, an outdated cache location may returns and should be ignonetworking. return; } CLLocationDistance distanceFromLast = [lastLocation distanceFromLocation:location]; if (distanceFromLast < DISTANCE_THRESHOLD || time < DURATION_THRESHOLD) { // Optional, dont calculate if two location are too close. This may avoid gets unreasonable value. return; } speed = distanceFromLast/time; self.lastLocation = location; } 

Si no desea tratar con el automatizador, puede hacerlo funcionar solo con un file GPX. El truco es crear un montón de puntos.

Por ejemplo, en lugar de crear solo 2 puntos para pasar de A a B, cree un montón de puntos intermedios entre ellos. Esto funciona porque el simulador de location lleva un time constante para viajar de un punto a otro, sin importar la distancia entre los dos puntos.

En lugar de tener que crear un grupo de puntos manualmente, puede usar el siguiente código.

Instrucciones:

  1. Pegue el código a continuación, ajustando la constante kDesinetworkingSpeed ​​a su gusto.
  2. Agregue UITapGestureRecognizer a su vista de map, vinculándolo a mapViewTapped:
  3. Agregue botones que llamen startRecordingPoints y stopRecordingPoints.
  4. Ejecuta la aplicación.
  5. Toque el button startRecordingPoints.
  6. Toque donde debe comenzar la ruta.
  7. Toque otra location en el map. Esto generará X cantidad de puntos entre el último nodo y el nuevo nodo para que aparezca moverse a la velocidad que desee.
  8. Repite el paso anterior tantas veces como quieras.
  9. Presione detener la grabación.
  10. Copie la salida de la console.
  11. Archivo> Nuevo file …
  12. Elija Recurso> Archivo GPX
  13. Pegue el contenido y guarde el file.
  14. Toque la flecha de location en el depurador y elija su file GPX.
  15. ¡Siéntate y observa cómo se actualiza la location exactamente a la velocidad que deseas!

Código:

 @property (strong, nonatomic) CLLocation *lastRecordedPoint; @property (strong, nonatomic) NSMutableString *recordingOutput; ... - (IBAction)mapViewTapped:(UITapGestureRecognizer *)sender { if (sender.state != UIGestureRecognizerStateEnded || !self.recordingOutput) { return; } CLLocationCoordinate2D coord = [self.mapView convertPoint:[sender locationInView:self.mapView] toCoordinateFromView:self.mapView]; [self recordPoint:coord]; } - (void)recordPoint:(CLLocationCoordinate2D)newPoint { const CGFloat kAppleTravelTime = 2; // the default time it takes to travel from one point to another const CGFloat kDesinetworkingSpeed = 6; // meters per sec const CGFloat kDesinetworkingDistanceBetweenPoints = kDesinetworkingSpeed * kAppleTravelTime; NSString * const kFormatString = @" <wpt lat=\"%f\" lon=\"%f\"></wpt>\n"; CLLocation *newLocation = [[CLLocation alloc] initWithLatitude:newPoint.latitude longitude:newPoint.longitude]; NSInteger numberOfPoints = 1; if (self.lastRecordedPoint) { CLLocationDistance distance = [self.lastRecordedPoint distanceFromLocation:newLocation]; numberOfPoints = MAX(round(distance / kDesinetworkingDistanceBetweenPoints), 1); CGFloat deltaLatitude = newPoint.latitude - self.lastRecordedPoint.coordinate.latitude; CGFloat deltaLongitude = newPoint.longitude - self.lastRecordedPoint.coordinate.longitude; for (NSInteger i = 0; i < numberOfPoints; i++) { CLLocationDegrees latitude = self.lastRecordedPoint.coordinate.latitude + (numberOfPoints/distance * deltaLatitude) * (i+1); CLLocationDegrees longitude = self.lastRecordedPoint.coordinate.longitude + (numberOfPoints/distance * deltaLongitude) * (i+1); [self.recordingOutput appendFormat:kFormatString, latitude, longitude]; } } else { [self.recordingOutput appendFormat:kFormatString, newPoint.latitude, newPoint.longitude]; } NSLog(@"Recorded %ld point(s) to: %f,%f", (long)numberOfPoints, newPoint.latitude, newPoint.longitude); self.lastRecordedPoint = newLocation; } - (void)startRecordingPoints { NSLog(@"Started recording points. Tap anywhere on the map to begin recording points."); self.recordingOutput = [NSMutableString string]; [self.recordingOutput appendString:@"<?xml version=\"1.0\"?>\n<gpx version=\"1.1\" creator=\"Xcode\">\n"]; self.lastRecordedPoint = nil; } - (void)stopRecordingPoints { [self.recordingOutput appendString:@"</gpx>"]; NSLog(@"Done recording, here is your gpx file: \n%@", self.recordingOutput); self.recordingOutput = nil; } 

Descargo de responsabilidad: kAppleTravelTime = 2 es solo una suposition. Si tiene un valor más preciso, publíquelo en un comentario.

También hay un método que le permite pasar la velocidad y algunas otras properties:

 target.setLocationWithOptions({latitude: 46.546928, longitude: 11.867127}, {altitude: 200.0, speed: 5}); 

(Verifique este AppleDoc para más detalles)

Todavía puede ver su NSLog en la aplicación de console (/Applications/Utilities/Console.app). Simplemente agregue un filter para get los resultados adecuados.