2013-03-12 5 views
7

ho la seguente configurazione di elementi nella vita reale:calcolate nuove coordinate da vecchi e coordinate x ed y

My setup

Il radar è statico, che significa che ha sempre la stessa posizione. L'A -item può spostarsi e la sua posizione può essere qualunque. Dal radar posso leggere le coordinate x e di A in relazione al radar. Ho scritto le seguenti classi per descrivere la posizione di ciascun elemento:

public class Position { 
    public enum Direction { 
     EAST, WEST, NORTH, SOUTH 
    }; 

    public final Direction latitudeDirection, longitudeDirection; 
    public final float latitude, longitude, altitude; 

    public Position(Direction latitudeDirection, Direction longitudeDirection, 
      float latitude, float longitude, float altitude) { 
     this.latitudeDirection = latitudeDirection; 
     this.longitudeDirection = longitudeDirection; 
     this.latitude = latitude; 
     this.longitude = longitude; 
     this.altitude = altitude; 
    } 

    public Position(float radarX, float radarY) { 
     // TODO: Implement the question here 
     this.altitude = Config.RADAR_POSITION.altitude; 
    } 

} 

class Config { 
    // Position of the radar 
    public static final Position RADAR_POSITION = new Position(
      Position.Direction.NORTH, // Latitude direction 
      Position.Direction.EAST, // Longitude direction 
      55.0f, // Latitude 
      13.0f, // Longitude 
      60.0f); // Altitude 

    // Facing direction of the radar in degrees. 0° is north, advancing 
    // clockwise. 
    public static final float RADAR_FACING_DIRECTION = 10.0f; 
} 

Ora date le coordinate geografiche del radar, le x e y coordinate di A rispetto al radar e la direzione rivolta verso il radar rispetto alla il nord, come posso calcolare le coordinate geografiche assolute di A?

La curvatura della terra non è un problema poiché il valore massimo di x e/o non può essere superiore a un paio di centinaia di metri.

+0

Il tuo problema equivale a ruotare un'immagine di 10 gradi. Ci sono un sacco di letteratura in materia. Una volta ruotati, aggiungi le coordinate della tua origine (il radar). – SJuan76

+0

Ma sarebbe sbagliato. Le coordinate geografiche sono gradi dal centro della terra. Le mie coordinate in riferimento al radar sono solo metri. Non posso aggiungere quei due insieme. – Dimme

+1

Dato che (x, y) è la coordinata corrente 'A'. E se conosci l'angelo (theta) a cui il radar viene ruotato rispetto alla terra, puoi facilmente trovare i nuovi cordinati (xnew, ynew) come: 'xnew = x * cos (theta) - y * sin (theta); ynew = x * sin (theta) + y * cos (theta); ' –

risposta

1

penso che dovrebbe essere possibile fare in questo modo: Convertire i x e y coordinate in coordinate polari r e theta, (con il radar come l'origine). Sottrarre la rotazione del radar e riconvertire in coordinate cartesiane. Quindi devi solo convertire in latitudine e longitudine e aggiungere le coordinate del radar.

double r = Math.hypot(radarX, radarY); 
double theta = Math.atan2(radarY, radarX); 
theta -= Math.toRadians(Config.RADAR_FACING_DIRECTION); 
float x = (float) r * Math.cos(theta); 
float y = (float) r * Math.sin(theta); 
longitude = metersToLongitude(Config.RADAR_POSITION, y) + Config.RADAR_POSITION.longitude; 
latitude = metersToLatitude(Config.RADAR_POSITION, x) + Config.RADAR_POSITION.latitude; 

Ho trovato le formule per la lunghezza di un grado di latitudine e longitudine su Wikipedia. Un grado di latitudine è uguale ovunque, ma la longitudine diventa più piccola vicino ai poli.

static float metersToLatitude(Position near, float meters) { 
    return meters/110.6*1000; 
} 

static float metersToLongitude(Position near, float meters) { 
    float lat = Math.toRadians(near.latitude); 
    return meters/
     (111132.954 - 559.822 * Math.cos(2*lat) + 1.175 * Math.cos(4*lat)); 
} 

Purtroppo questo non funziona e non riesco a capire perché.

Se vuoi esprimere le tue coordinate in gradi positivi est/ovest/nord/sud dovrai anche controllare se sono negative e invertirle e la direzione in quel caso.

+0

Grazie. La tua risposta mi ha ispirato. Puoi trovare il codice che ho usato nella mia risposta qui sotto. – Dimme

0

Ruotate tutte le coordinate nel sistema locale del radar -10 ° e sono quindi in grado di aggiungere le coordinate x/y del radar alle coordinate dell'oggetto A.

+0

Come ho detto sopra, sarebbe sbagliato. Le coordinate geografiche sono gradi dal centro della terra. Le mie coordinate in riferimento al radar sono espresse in metri. Non posso aggiungere quei due insieme. – Dimme

+0

Scusa, ho frainteso il testo, fammi pensare di nuovo * g * –

3

A titolo di esempio, è possibile utilizzare le funzioni trigonometriche per creare triangoli per trovare le coordinate di A:

Example of using trigonometric functions

In questo caso, Ax = (y) (cos 10) - (x) (cos 80), e potresti allenarti ad Ay in modo simile.

In questo modo, non si è mai bloccati in gradi, si sta semplicemente lavorando in metri.

La soluzione robusta è il commento di Vishal nel PO, che è stato pubblicato mentre io disegnavo e scansione:

xnew = x * cos(theta) - y * sin(theta); 
ynew = x * sin(theta) + y * cos(theta); 
2

In generale, è possibile utilizzare le seguenti operazioni:

  1. trasformare il vostro radar posizione (lat, lon, height) in terra metrica con messa a terra fissa xyz-system (ECEF)
  2. È possibile quindi utilizzare/combinare qualsiasi argomento di rotazione/argomento/matrice, che descrivono la rotazione del radar e la posizione dell'oggetto, in questa metrica s coordina ystem
  3. xzy indietro trasformano nuova acquisizione di Lat/Lon/h

Ci sono molte le risorse per tali trasformazioni, controllare questo, per esempio: http://www.gmat.unsw.edu.au/snap/gps/clynch_pdfs/coordcvt.pdf

È possibile anche introdurre un sistema di coordinate scena, se necessario (ENU). Qui è una discreta panoramica che descrive la relazione tra UTM, ECEF, ITA e coordinate geodotic (Lat/Lon/h): http://www.dirsig.org/docs/new/coordinates.html

Se avete bisogno di codice di esempio per ECEF da/per conversione geodetici, hanno uno sguardo al codice matlab, http://www.mathworks.de/de/help/map/ref/ecef2geodetic.html, o utilizzare una libreria come GDAL (http://www.gdal.org/)

1

Finalmente l'ho risolto. Il codice è allegato qui sotto. Poiché la risposta di Samuel Edwin Ward è quella che mi ha ispirato, accetterò la sua risposta.

public Position(float radarX, float radarY) { 

    // Convert A's position to distance and bearing in relation to the North 
    double objDistance = (Math.hypot(radarX, radarY)/6367500 /* Mean earth radius */); 
    double objBearing = (Math.atan2(radarY, radarX) + Math.toRadians(Config.RADAR_BEARING)); 

    // Convert the Radar's geographic coordinates to radians 
    double latitudeRadar = Math.toRadians(Config.RADAR_POSITION.latitude); 
    double longitudeRadar = Math.toRadians(Config.RADAR_POSITION.longitude); 

    // Calculate A's geographic coordinates in radians 
    double latitudeObject = Math.asin(Math.sin(latitudeRadar)*Math.cos(objDistance) + 
      Math.cos(latitudeRadar)*Math.sin(objDistance)*Math.cos(objBearing)); 
    double longitudeObject = longitudeRadar + Math.atan2(Math.sin(objBearing)*Math.sin(objDistance)*Math.cos(latitudeRadar), 
      Math.cos(objDistance)-Math.sin(latitudeRadar)*Math.sin(latitudeObject)); 

    // Normalize to -180 ... +180 degrees 
    longitudeObject = (longitudeObject+3*Math.PI) % (2*Math.PI) - Math.PI; 

    // Set the A's coordinates in degrees 
    this.latitude = (float) Math.toDegrees(latitudeObject); 
    this.longitude = (float) Math.toDegrees(longitudeObject); 

    // Set the rest of the arguments 
    this.latitudeDirection = Config.RADAR_POSITION.latitudeDirection; 
    this.longitudeDirection = Config.RADAR_POSITION.longitudeDirection; 
    this.altitude = Config.RADAR_POSITION.altitude; 
} 
+0

Liberarsi dei contatori il prima possibile è davvero luminoso. Perché non ci ho pensato? –

+0

Questo sembra abbastanza accurato, anche se la Terra non è una sfera? –

+0

Se vedi il calcolo della longitudine prende in considerazione la latitudine. Quindi funziona per un ellissoide. – Dimme