GNSS-SDR  0.0.19
An Open Source GNSS Software Defined Receiver
geofunctions.h
Go to the documentation of this file.
1 /*!
2  * \file geofunctions.h
3  * \brief A set of coordinate transformations functions and helpers,
4  * some of them migrated from MATLAB, for geographic information systems.
5  * \author Javier Arribas, 2018. jarribas(at)cttc.es
6  *
7  *
8  * -----------------------------------------------------------------------------
9  *
10  * GNSS-SDR is a Global Navigation Satellite System software-defined receiver.
11  * This file is part of GNSS-SDR.
12  *
13  * Copyright (C) 2010-2020 (see AUTHORS file for a list of contributors)
14  * SPDX-License-Identifier: GPL-3.0-or-later
15  *
16  * -----------------------------------------------------------------------------
17  */
18 
19 #ifndef GNSS_SDR_GEOFUNCTIONS_H
20 #define GNSS_SDR_GEOFUNCTIONS_H
21 
22 #if ARMA_NO_BOUND_CHECKING
23 #define ARMA_NO_DEBUG 1
24 #endif
25 
26 #include <armadillo>
27 
28 /** \addtogroup Algorithms_Library
29  * \{ */
30 /** \addtogroup Algorithm_libs algorithms_libs
31  * \{ */
32 
33 
34 arma::mat Skew_symmetric(const arma::vec &a); //!< Calculates skew-symmetric matrix
35 
36 double WGS84_g0(double Lat_rad);
37 
38 double WGS84_geocentric_radius(double Lat_geodetic_rad);
39 
40 /*!
41  * \brief Transformation of vector dx into topocentric coordinate
42  * system with origin at x
43  * Inputs:
44  * x - vector origin coordinates (in ECEF system [X; Y; Z;])
45  * dx - vector ([dX; dY; dZ;]).
46  *
47  * Outputs:
48  * D - vector length. Units like the input
49  * Az - azimuth from north positive clockwise, degrees
50  * El - elevation angle, degrees
51  *
52  * Based on a Matlab function by Kai Borre
53  */
54 int topocent(double *Az, double *El, double *D, const arma::vec &x, const arma::vec &dx);
55 
56 /*!
57  * \brief Subroutine to calculate geodetic coordinates latitude, longitude,
58  * height given Cartesian coordinates X,Y,Z, and reference ellipsoid
59  * values semi-major axis (a) and the inverse of flattening (finv).
60  *
61  * The output units of angular quantities will be in decimal degrees
62  * (15.5 degrees not 15 deg 30 min). The output units of h will be the
63  * same as the units of X,Y,Z,a.
64  *
65  * Inputs:
66  * a - semi-major axis of the reference ellipsoid
67  * finv - inverse of flattening of the reference ellipsoid
68  * X,Y,Z - Cartesian coordinates
69  *
70  * Outputs:
71  * dphi - latitude
72  * dlambda - longitude
73  * h - height above reference ellipsoid
74  *
75  * Based in a Matlab function by Kai Borre
76  */
77 int togeod(double *dphi, double *dlambda, double *h, double a, double finv, double X, double Y, double Z);
78 
79 arma::vec Gravity_ECEF(const arma::vec &r_eb_e); //!< Calculates acceleration due to gravity resolved about ECEF-frame
80 
81 /*!
82  * \brief Conversion of Cartesian coordinates (X,Y,Z) to geographical
83  * coordinates (latitude, longitude, h) on a selected reference ellipsoid.
84  *
85  * Choices of Reference Ellipsoid for Geographical Coordinates
86  * 0. International Ellipsoid 1924
87  * 1. International Ellipsoid 1967
88  * 2. World Geodetic System 1972
89  * 3. Geodetic Reference System 1980
90  * 4. World Geodetic System 1984
91  */
92 arma::vec cart2geo(const arma::vec &XYZ, int elipsoid_selection);
93 
94 arma::vec LLH_to_deg(const arma::vec &LLH);
95 
96 double degtorad(double angleInDegrees);
97 
98 double radtodeg(double angleInRadians);
99 
100 double mstoknotsh(double MetersPerSeconds);
101 
102 double mstokph(double MetersPerSeconds);
103 
104 arma::vec CTM_to_Euler(const arma::mat &C);
105 
106 arma::mat Euler_to_CTM(const arma::vec &eul);
107 
108 void ECEF_to_Geo(const arma::vec &r_eb_e, const arma::vec &v_eb_e, const arma::mat &C_b_e, arma::vec &LLH, arma::vec &v_eb_n, arma::mat &C_b_n);
109 
110 
111 /*!
112  * \brief From Geographic to ECEF coordinates
113  *
114  * Inputs:
115  * LLH latitude (rad), longitude (rad), height (m)
116  * v_eb_n velocity of body frame w.r.t. ECEF frame, resolved along
117  * north, east, and down (m/s)
118  * C_b_n body-to-NED coordinate transformation matrix
119  *
120  * Outputs:
121  * r_eb_e Cartesian position of body frame w.r.t. ECEF frame, resolved
122  * along ECEF-frame axes (m)
123  * v_eb_e velocity of body frame w.r.t. ECEF frame, resolved along
124  * ECEF-frame axes (m/s)
125  * C_b_e body-to-ECEF-frame coordinate transformation matrix
126  *
127  */
128 void Geo_to_ECEF(const arma::vec &LLH, const arma::vec &v_eb_n, const arma::mat &C_b_n, arma::vec &r_eb_e, arma::vec &v_eb_e, arma::mat &C_b_e);
129 
130 
131 /*!
132  * \brief Converts curvilinear to Cartesian position and velocity
133  * resolving axes from NED to ECEF
134  * This function created 11/4/2012 by Paul Groves
135  *
136  * Inputs:
137  * L_b latitude (rad)
138  * lambda_b longitude (rad)
139  * h_b height (m)
140  * v_eb_n velocity of body frame w.r.t. ECEF frame, resolved along
141  * north, east, and down (m/s)
142  *
143  * Outputs:
144  * r_eb_e Cartesian position of body frame w.r.t. ECEF frame, resolved
145  * along ECEF-frame axes (m)
146  * v_eb_e velocity of body frame w.r.t. ECEF frame, resolved along
147  * ECEF-frame axes (m/s)
148  */
149 void pv_Geo_to_ECEF(double L_b, double lambda_b, double h_b, const arma::vec &v_eb_n, arma::vec &r_eb_e, arma::vec &v_eb_e);
150 
151 
152 /*!
153  * \brief The Haversine formula determines the great-circle distance between two points on a sphere given their longitudes and latitudes.
154  */
155 double great_circle_distance(double lat1, double lon1, double lat2, double lon2);
156 
157 
158 /*!
159  * \brief Transformation of ECEF (X,Y,Z) to (E,N,U) in UTM, zone 'zone'.
160  */
161 void cart2utm(const arma::vec &r_eb_e, int zone, arma::vec &r_enu);
162 
163 
164 /*!
165  * \brief Function finds the UTM zone number for given longitude and latitude.
166  */
167 int findUtmZone(double latitude_deg, double longitude_deg);
168 
169 
170 /*!
171  * \brief Clenshaw summation of sinus of argument.
172  */
173 double clsin(const arma::colvec &ar, int degree, double argument);
174 
175 
176 /*!
177  * \brief Clenshaw summation of sinus with complex argument.
178  */
179 void clksin(const arma::colvec &ar, int degree, double arg_real, double arg_imag, double *re, double *im);
180 
181 
182 /** \} */
183 /** \} */
184 #endif // GNSS_SDR_GEOFUNCTIONS_H
double great_circle_distance(double lat1, double lon1, double lat2, double lon2)
The Haversine formula determines the great-circle distance between two points on a sphere given their...
void cart2utm(const arma::vec &r_eb_e, int zone, arma::vec &r_enu)
Transformation of ECEF (X,Y,Z) to (E,N,U) in UTM, zone &#39;zone&#39;.
int findUtmZone(double latitude_deg, double longitude_deg)
Function finds the UTM zone number for given longitude and latitude.
double clsin(const arma::colvec &ar, int degree, double argument)
Clenshaw summation of sinus of argument.
int topocent(double *Az, double *El, double *D, const arma::vec &x, const arma::vec &dx)
Transformation of vector dx into topocentric coordinate system with origin at x Inputs: x - vector or...
arma::vec cart2geo(const arma::vec &XYZ, int elipsoid_selection)
Conversion of Cartesian coordinates (X,Y,Z) to geographical coordinates (latitude, longitude, h) on a selected reference ellipsoid.
arma::mat Skew_symmetric(const arma::vec &a)
Calculates skew-symmetric matrix.
void Geo_to_ECEF(const arma::vec &LLH, const arma::vec &v_eb_n, const arma::mat &C_b_n, arma::vec &r_eb_e, arma::vec &v_eb_e, arma::mat &C_b_e)
From Geographic to ECEF coordinates.
arma::vec Gravity_ECEF(const arma::vec &r_eb_e)
Calculates acceleration due to gravity resolved about ECEF-frame.
void clksin(const arma::colvec &ar, int degree, double arg_real, double arg_imag, double *re, double *im)
Clenshaw summation of sinus with complex argument.
int togeod(double *dphi, double *dlambda, double *h, double a, double finv, double X, double Y, double Z)
Subroutine to calculate geodetic coordinates latitude, longitude, height given Cartesian coordinates ...
void pv_Geo_to_ECEF(double L_b, double lambda_b, double h_b, const arma::vec &v_eb_n, arma::vec &r_eb_e, arma::vec &v_eb_e)
Converts curvilinear to Cartesian position and velocity resolving axes from NED to ECEF This function...