World Ocean Simulation System (WOSS) library
coordinates-definitions.h
Go to the documentation of this file.
1/* WOSS - World Ocean Simulation System -
2 *
3 * Copyright (C) 2009 2025 Federico Guerra
4 * and regents of the SIGNET lab, University of Padova
5 *
6 * Author: Federico Guerra - WOSS@guerra-tlc.com
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation;
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 */
21
22
33#ifndef WOSS_COORDINATES_DEFINITIONS_H
34#define WOSS_COORDINATES_DEFINITIONS_H
35
36
37#include <cmath>
38#include <iostream>
39#include <cassert>
40#include <utility>
41#include <vector>
42#include <ostream>
43
44namespace woss {
45
46 class Coord;
47 class CoordZ;
48
52 using UtmZoneChar = char;
53
58 using CoordZVector = std::vector< CoordZ >;
59
63 using Marsden = int;
64
70 using MarsdenCoord = std::pair< int, int >;
71
75 using CoordVector = std::vector< Coord >;
76
80 using MarsdenVector = std::vector< Marsden >;
81
85 using MarsdenCoordVector = std::vector< MarsdenCoord >;
86
90 static constexpr inline double COORD_NOT_SET_VALUE = -2000.0;
91
98 class Coord {
99
100 public:
101
102 static constexpr double COORD_MIN_LATITUDE = -90.0;
103
104 static constexpr double COORD_MAX_LATITUDE = 90.0;
105
106 static constexpr double COORD_MIN_LONGITUDE = -180.0;
107
108 static constexpr double COORD_MAX_LONGITUDE = 180.0;
109
110 static constexpr double EARTH_RADIUS = 6371000.0;
111
113 static constexpr double EARTH_SEMIMAJOR_AXIS = 6378137.0;
114
116 static constexpr double EARTH_GRS80_POLAR_RADIUS = 6356752.3141;
117
119 static constexpr double EARTH_WGS84_POLAR_RADIUS= 6356752.314245;
120
122 static constexpr double EARTH_GRS80_ECCENTRICITY = 0.0818191910428158;
123
125 static constexpr double EARTH_WGS84_ECCENTRICITY = 0.0818191908426215;
126
132 constexpr Coord( double lat = COORD_NOT_SET_VALUE, double lon = COORD_NOT_SET_VALUE );
133
134 constexpr Coord( const Coord& copy ) = default;
135
136 constexpr Coord( Coord&& tmp ) = default;
137
142 constexpr void setLatitude( double lat ) { latitude = lat; updateMarsdenCoord(); }
143
148 constexpr void setLongitude( double lon ) { longitude = lon; updateMarsdenCoord(); }
149
156
161 constexpr double getLatitude() const { return latitude; }
162
167 constexpr double getLongitude() const { return longitude; }
168
173 constexpr int getMarsdenSquare() const { return marsden_square; }
174
179 constexpr int getMarsdenOneDegreeSquare() const { return marsden_one_degree; }
180
185 constexpr MarsdenCoord getMarsdenCoord() const { return( std::make_pair( marsden_square, marsden_one_degree) ); }
186
192 constexpr double getInitialBearing( const Coord& destination ) const;
193
199 constexpr double getFinalBearing( const Coord& destination ) const;
200
207 constexpr double getGreatCircleDistance( const Coord& destination, double depth = 0 ) const ;
208
218 static constexpr Coord getCoordFromBearing( const Coord& start_coord, double bearing, double distance, double depth = 0.0 );
219
229 static constexpr Coord getCoordAlongGreatCircle( const Coord& start_coord, const Coord& end_coord, double distance, double depth = 0.0 );
230
239 static constexpr Coord getCoordFromUtmWgs84( double easting, double northing, double utm_zone_number, UtmZoneChar utm_zone_char );
240
246 constexpr Coord& operator=( const Coord& copy ) = default;
247
253 constexpr Coord& operator=( Coord&& tmp ) = default;
254
261 friend constexpr Coord operator+( const Coord& left , const Coord& right );
262
269 friend constexpr Coord operator-( const Coord& left , const Coord& right );
270
277 friend constexpr Coord& operator+=( Coord& left, const Coord& right );
278
285 friend constexpr Coord& operator-=( Coord& left, const Coord& right );
286
293 friend constexpr bool operator==( const Coord& left, const Coord& right );
294
301 friend constexpr bool operator!=( const Coord& left, const Coord& right );
302
309 friend constexpr bool operator>( const Coord& left, const Coord& right );
310
317 friend constexpr bool operator<( const Coord& left, const Coord& right );
318
325 friend constexpr bool operator>=( const Coord& left, const Coord& right );
326
333 friend constexpr bool operator<=( const Coord& left, const Coord& right );
334
341 friend std::ostream& operator<<( std::ostream& os, const Coord& instance );
342
343 protected:
344
348 double latitude;
349
353 double longitude;
354
359
364
368 constexpr void updateMarsdenCoord();
369
375 static constexpr bool isValidUtmZoneChar( UtmZoneChar utm_zone_char );
376 };
377
378
384 class CoordZ : public Coord {
385
386 public:
387
388 static constexpr double COORDZ_MIN_DEPTH = 0.0;
389
398 {
399 COORDZ_SPHERE = 0,
402 };
403
410 public:
411
415 constexpr CartCoords();
416
424 constexpr CartCoords(double in_x, double in_y, double in_z, CoordZSpheroidType in_type);
425
430 constexpr double getX() const { return x; }
431
436 constexpr double getY() const { return y; }
437
442 constexpr double getZ() const { return z; }
443
448 constexpr CoordZSpheroidType getType() const { return type; }
449
456 friend std::ostream& operator<<( std::ostream& os, const CartCoords& instance );
457
458 protected:
459
460 double x;
461
462 double y;
463
464 double z;
465
467 };
468
475 constexpr CoordZ( double lat = COORD_NOT_SET_VALUE, double lon = COORD_NOT_SET_VALUE, double z = COORD_NOT_SET_VALUE );
476
482 explicit constexpr CoordZ( const Coord& coords, double depth = COORD_NOT_SET_VALUE );
483
484 constexpr CoordZ( const CoordZ& copy ) = default;
485
486 constexpr CoordZ( CoordZ&& tmp ) = default;
487
492 constexpr void setDepth( double d ) { depth = d; }
493
498 constexpr double getDepth() const { return depth; }
499
505 constexpr CartCoords getCartCoords(CoordZSpheroidType type = CoordZSpheroidType::COORDZ_SPHERE) const;
506
513
520
527
532 constexpr double getSphericalRho() const;
533
538 constexpr double getSphericalTheta() const;
539
544 constexpr double getSphericalPhi() const;
545
551 constexpr double getCartDistance( const CoordZ& coords, CoordZSpheroidType type = CoordZSpheroidType::COORDZ_SPHERE ) const;
552
557 constexpr double getCartRelZenith( const CoordZ& coords ) const;
558
563 constexpr double getCartRelAzimuth( const CoordZ& coords ) const;
564
573 static constexpr CoordZ getCoordZAlongCartLine( const CoordZ& start, const CoordZ& end, double distance );
574
584 static constexpr CoordZ getCoordZAlongGreatCircle( const CoordZ& start, const CoordZ& end, double distance );
585
594 static constexpr CoordZ getCoordZFromCartesianCoords( double x, double y, double z, CoordZSpheroidType type = CoordZSpheroidType::COORDZ_SPHERE);
595
601 static constexpr CoordZ getCoordZFromCartesianCoords( const CartCoords& cart_coords );
602
610 static constexpr CoordZ getCoordZFromSphericalCoords( double rho, double theta, double phi);
611
616 constexpr bool isValid() const { return( Coord::isValid() && depth >= COORDZ_MIN_DEPTH ); }
617
623 constexpr CoordZ& operator=( const CoordZ& coordz ) = default;
624
630 constexpr CoordZ& operator=( CoordZ&& coordz ) = default;
631
638 friend constexpr CoordZ operator+( const CoordZ& left , const CoordZ& right );
639
646 friend constexpr CoordZ operator-( const CoordZ& left , const CoordZ& right );
647
654 friend constexpr CoordZ& operator+=( CoordZ& left, const CoordZ& right );
655
662 friend constexpr CoordZ& operator-=( CoordZ& left, const CoordZ& right );
663
670 friend constexpr bool operator==( const CoordZ& left , const CoordZ& right ) ;
671
678 friend constexpr bool operator!=( const CoordZ& left , const CoordZ& right ) ;
679
686 friend constexpr bool operator>( const CoordZ& left , const CoordZ& right ) ;
687
694 friend constexpr bool operator<( const CoordZ& left , const CoordZ& right ) ;
695
702 friend constexpr bool operator>=( const CoordZ& left , const CoordZ& right ) ;
703
710 friend constexpr bool operator<=( const CoordZ& left , const CoordZ& right ) ;
711
718 friend std::ostream& operator<<( std::ostream& os, const CoordZ& instance );
719
720 protected:
721
725 double depth;
726 };
727
728 class UtmWgs84 {
729
730 public:
731
738 constexpr UtmWgs84(int utmZone = COORD_NOT_SET_VALUE, double east = COORD_NOT_SET_VALUE, double north = COORD_NOT_SET_VALUE);
739
740 constexpr int getZone() const;
741
742 constexpr double getEasting() const;
743
744 constexpr double getNorthing() const;
745
746 constexpr bool isValid() const;
747
755 static constexpr UtmWgs84 getUtmWgs84FromCoord(const Coord& coords);
756
763 friend std::ostream& operator<<( std::ostream& os, const UtmWgs84& instance );
764
765 protected:
766
767 int zone;
769 double easting;
771 double northing;
772 };
773
774
782 template < class CompUser, class T = Coord >
784
785 public:
786
795 bool operator()( const T& x, const T& y ) const {
796 if ( CompUser::getSpaceSampling() <= 0.0 )
797 return operator<(x,y);
798 if ( x.getGreatCircleDistance(y) <= CompUser::getSpaceSampling() )
799 return false;
800 return operator<(x,y);
801 }
802
803 };
804
805
813 template < class CompUser >
814 class CoordComparator< CompUser, CoordZ > {
815
816 public:
817
826 bool operator()( const CoordZ& x, const CoordZ& y ) const {
827 if ( CompUser::getSpaceSampling() <= 0.0 )
828 return operator<(x,y);
829 if ( x.getCartDistance(y) <= CompUser::getSpaceSampling() )
830 return false;
831 return operator<(x,y);
832 }
833
834 };
835
836
837 // inline functions
838
839 inline constexpr Coord::Coord( double lat, double lon )
840 : latitude(lat),
841 longitude(lon),
842 marsden_square(COORD_NOT_SET_VALUE),
843 marsden_one_degree(COORD_NOT_SET_VALUE)
844 {
846 }
847
848
849 inline constexpr void Coord::updateMarsdenCoord() {
850 if( isValid() == false ) {
851 marsden_one_degree = COORD_NOT_SET_VALUE;
852 marsden_square = COORD_NOT_SET_VALUE;
853 return;
854 }
855
856 double lat = latitude;
857 double lon = longitude;
858
859 marsden_one_degree =(int)( (std::floor(std::abs(lat)) - std::floor(std::abs(lat)/10.0)*10.0)*10.0 + (std::floor(std::abs(lon)) - std::floor(std::abs(lon)/10.0)*10.0));
860
861 if (( lat >= 0.0) && (lat < 80.0) ) {
862 if (lon > 0.0)
863 lon -= 360.0;
864 lon = std::abs(lon);
865 int quoz_lat = (int)std::floor(lat / 10.0);
866 int quoz_long = (int)std::ceil(lon / 10.0);
867 // marsden square's longitude should be in range (N, N+10]
868 double rem_lon = std::fmod(lon, 10.0);
869 if (rem_lon == 0)
870 quoz_long += 1;
871
872 marsden_square = quoz_lat * 36 + quoz_long;
873 }
874 else if (lat >= 80.0) {
875 if (lon > 0.0)
876 lon -= 360.0;
877 lon = std::abs(lon);
878 int quoz_long = (int)std::ceil(lon / 10.0);
879 // marsden square's longitude should be in range (N, N+10]
880 double rem_lon = std::fmod(lon, 10.0);
881 if (rem_lon == 0)
882 quoz_long += 1;
883 marsden_square = 900 + quoz_long;
884 }
885 else {
886 if (lon > 0.0)
887 lon -= 360.0;
888 lon = std::abs(lon);
889 lat = std::abs(lat);
890 int quoz_lat = (int)std::floor(lat / 10.0);
891 int quoz_long = (int)std::floor(lon / 10.0);
892
893 // marsden square of S latitude should be in range (N, N+10]
894 double rem_lat = std::fmod(lat, 10.0);
895 if (rem_lat == 0)
896 quoz_lat -= 1;
897
898 marsden_square = 300 + quoz_lat * 36 + quoz_long;
899 }
900 }
901
902
903 inline constexpr Coord Coord::getCoordFromBearing( const Coord& destination, double bearing, double distance, double depth ) {
904 assert( destination.isValid() );
905
906 double lat1 = destination.latitude * M_PI / 180.0;
907 double lon1 = destination.longitude * M_PI / 180.0;
908 double lat2 = std::asin( std::sin(lat1) * std::cos(distance/(EARTH_RADIUS-depth))
909 + std::cos(lat1) * std::sin(distance/(EARTH_RADIUS-depth)) * std::cos(bearing) );
910 double lon2 = lon1 + std::atan2(std::sin(bearing) * std::sin(distance/(EARTH_RADIUS-depth)) * std::cos(lat1),
911 std::cos(distance/(EARTH_RADIUS-depth)) - std::sin(lat1) * std::sin(lat2));
912
913 double ret_lat = lat2 * 180.0 / M_PI;
914 double ret_long = lon2 * 180.0 / M_PI;
915
916 ret_long = std::fmod((ret_long + 540.0), 360.0) - 180.0;
917
918 if (ret_lat > 90.0)
919 ret_lat -= 180.0;
920
921 return( Coord(ret_lat, ret_long) );
922 }
923
924
925 inline constexpr double Coord::getInitialBearing( const Coord& destination ) const {
926 assert( destination.isValid() );
927
928 double lat1 = latitude * M_PI / 180.0;
929 double lat2 = destination.latitude * M_PI / 180.0;
930 double dLon = (destination.longitude - longitude) * M_PI / 180.0;
931
932 double y = std::sin(dLon) * std::cos(lat2);
933 double x = std::cos(lat1)* std::sin(lat2) - std::sin(lat1)* std::cos(lat2) * std::cos(dLon);
934
935 double bearing = std::atan2(y, x);
936 // normalize to 0 -> 360
937 bearing += 2.0 * M_PI;
938 bearing = std::fmod(bearing, 2.0 * M_PI);
939
940 return bearing;
941 }
942
943
944 inline constexpr double Coord::getFinalBearing( const Coord& destination ) const {
945 double init_bear = destination.getInitialBearing(*this);
946
947 double fin_bear = init_bear + M_PI;
948 fin_bear = std::fmod(fin_bear, 2.0 * M_PI);
949
950 return fin_bear;
951 }
952
953
954 inline constexpr double Coord::getGreatCircleDistance( const Coord& destination, double depth ) const {
955 assert( destination.isValid() );
956
957 double dLat = (destination.latitude - latitude) * M_PI / 180.0;
958 double dLon = (destination.longitude - longitude) * M_PI / 180.0;
959 double lat1 = latitude * M_PI / 180.0;
960 double lat2 = destination.latitude * M_PI / 180.0;
961
962 double a = std::sin(dLat/2.0) * std::sin(dLat/2.0) +
963 std::cos(lat1) * std::cos(lat2) *
964 std::sin(dLon/2.0) * std::sin(dLon/2.0);
965
966 double c = 2.0 * std::atan2(std::sqrt(a), std::sqrt(1.0-a));
967
968 return((EARTH_RADIUS - depth) * c);
969 }
970
971
972 inline constexpr bool Coord::isValidUtmZoneChar( UtmZoneChar utm_zone_char ) {
973 if ( ( (utm_zone_char >= 'C') && ( utm_zone_char <= 'X' ) && (utm_zone_char != 'I')
974 && (utm_zone_char != 'O') )
975 || ( (utm_zone_char >= 'c') && ( utm_zone_char <= 'x' ) && (utm_zone_char != 'i')
976 && (utm_zone_char != 'o') ) )
977 return true;
978
979 return false;
980 }
981
982
983 inline constexpr Coord Coord::getCoordFromUtmWgs84( double easting, double northing, double utm_zone_number, UtmZoneChar utm_zone_char) {
984 if ( !isValidUtmZoneChar(utm_zone_char) ) {
985 std::cerr << "Coord::getCoordFromUtmWgs84() easting = " << easting << "; northing = " << northing
986 << "; utm zone = " << utm_zone_number << "; utm zone char = " << utm_zone_char
987 << "; WARNING, invalid input parameters!!" << std::endl;
988 }
989#if 0
990 std::cout << "Coord::getCoordFromUtmWgs84() easting = " << easting << "; northing = " << northing
991 << "; utm zone = " << utm_zone_number << "; utm zone char = " << utm_zone_char
992 << "; zone int = " << (unsigned int) utm_zone_char << "; c = " << (unsigned int) 'c'
993 << "; m = " << (unsigned int) 'm' << "; C = " << (unsigned int) 'C' << "; M = "
994 << (unsigned int) 'M' << std::endl;
995#endif
996 bool is_hemis_north = true;
997
998 if ( ((utm_zone_char < 'M') && (utm_zone_char >= 'C'))
999 || ((utm_zone_char < 'm') && (utm_zone_char >= 'c')) ) {
1000 is_hemis_north = false;
1001 }
1002
1003 // Equatorial radius
1004 double sa = EARTH_SEMIMAJOR_AXIS;
1005 // Polar radius
1006 double sb = EARTH_WGS84_POLAR_RADIUS;
1007
1008 double e2 = std::pow( ( std::pow(sa, 2.0) - std::pow(sb, 2.0) ), 0.5 ) / sb;
1009 double e2square = std::pow( e2, 2.0);
1010 double c = std::pow( sa, 2.0 ) / sb;
1011
1012 // Conventional easting (not referred to standard meridian)
1013 double X = easting - 500000.0;
1014
1015 // Standard northing shift if the UTM zone is in the southern emispèhere
1016 double Y = 0.0;
1017
1018 if ( is_hemis_north == false )
1019 Y = northing - 10000000.0;
1020 else
1021 Y = northing;
1022
1023 // UTM zone
1024 double S = ( ( utm_zone_number * 6.0 ) - 183.0 );
1025 double lat = Y / ( 6366197.724 * 0.9996 ) ;
1026
1027 double v = ( c / std::pow( ( 1.0 + ( e2square * std::pow( std::cos(lat), 2.0 ) ) ), 0.5 ) ) * 0.9996;
1028
1029 double a = X / v ;
1030
1031 double a1 = std::sin( 2.0 * lat ) ;
1032 double a2 = a1 * std::pow( std::cos(lat), 2.0);
1033
1034 double j2 = lat + a1/2.0 ;
1035 double j4 = ( 3.0 * j2 + a2 ) / 4.0 ;
1036 double j6 = ( 5.0 * j4 + a2 * std::pow( std::cos(lat), 2.0 ) ) / 3.0;
1037
1038 double alpha = 3.0/4.0 * e2square ;
1039 double beta = 5.0/3.0 * std::pow( alpha, 2.0 );
1040 double gamma = 35.0/27.0 * std::pow( alpha, 3.0 );
1041
1042 double Bm = 0.9996 * c * ( lat - alpha * j2 + beta * j4 - gamma * j6 );
1043 double b = ( Y - Bm ) / v ;
1044 double Epsi = e2square * std::pow( a, 2.0 ) / 2.0 * std::pow( std::cos(lat), 2.0 );
1045 double Epss = a * ( 1.0 - Epsi / 3.0 );
1046 double nab = b * ( 1.0 - Epsi ) + lat;
1047
1048 double Delt = std::atan( std::sinh(Epss) / std::cos(nab) );
1049 double TaO = std::atan( std::cos(Delt) * std::tan(nab) );
1050
1051 double longitude = Delt * 180.0 / M_PI + S;
1052 double latitude = ( lat + ( 1.0 + e2square * std::pow( std::cos(lat), 2.0 ) - 3.0/2.0 * e2square * std::sin(lat) * std::cos(lat) * ( TaO - lat ) ) * ( TaO - lat ) ) * 180.0 / M_PI;
1053
1054#if 0
1055 std::cout << "Coord::getCoordFromUtmWgs84() latitude = " << latitude
1056 << "; longitude = " << longitude << std::endl;
1057#endif //
1058 return Coord(latitude, longitude);
1059 }
1060
1061
1062 inline constexpr Coord Coord::getCoordAlongGreatCircle( const Coord& start_coord, const Coord& end_coord, double distance, double depth ) {
1063 return Coord::getCoordFromBearing( start_coord, start_coord.getInitialBearing(end_coord), distance, depth );
1064 }
1065
1066
1067 inline constexpr CoordZ::CoordZ(double lat, double lon, double d)
1068 : Coord(lat,lon),
1069 depth(d)
1070 {
1071
1072 }
1073
1074
1075 inline constexpr CoordZ::CoordZ(const Coord& coords, double d)
1076 : Coord(coords),
1077 depth(d)
1078 {
1079
1080 }
1081
1082
1084 : x(0.0),
1085 y(0.0),
1086 z(0.0),
1087 type(CoordZSpheroidType::COORDZ_SPHERE)
1088 {
1089 }
1090
1091
1092 inline constexpr CoordZ::CartCoords::CartCoords(double in_x, double in_y, double in_z, CoordZSpheroidType in_type)
1093 : x(in_x),
1094 y(in_y),
1095 z(in_z),
1096 type(in_type)
1097 {
1098 }
1099
1101 double latitudeRadians = M_PI / 180.0 * latitude;
1102 double longitudeRadians = M_PI / 180.0 * longitude;
1103 double a = 0.0; // semi-major axis of earth
1104 double e = 0.0; // first eccentricity of earth
1105 double altitude = -1.0 * depth;
1106
1108 a = EARTH_RADIUS;
1109 e = 0.0;
1110 }
1111 else if (type == CoordZSpheroidType::COORDZ_GRS80) {
1114 }
1115 else { // if type == WGS84
1118 }
1119
1120 // radius of curvature
1121 double Rn = a / (std::sqrt(1.0 - std::pow(e, 2.0) * std::pow(std::sin(latitudeRadians), 2.0)));
1122 double x = (Rn + altitude) * std::cos(latitudeRadians) * std::cos(longitudeRadians);
1123 double y = (Rn + altitude) * std::cos(latitudeRadians) * std::sin(longitudeRadians);
1124 double z = ((1 - std::pow (e, 2.0)) * Rn + altitude) * std::sin(latitudeRadians);
1125
1126 return CoordZ::CartCoords(x, y, z, type);
1127 }
1128
1129 inline constexpr double CoordZ::getCartX( CoordZSpheroidType type ) const {
1130 return getCartCoords(type).getX();
1131 }
1132
1133
1134 inline constexpr double CoordZ::getCartY( CoordZSpheroidType type ) const {
1135 return getCartCoords(type).getY();
1136 }
1137
1138
1139 inline constexpr double CoordZ::getCartZ( CoordZSpheroidType type ) const {
1140 return getCartCoords(type).getZ();
1141 }
1142
1143
1144 inline constexpr double CoordZ::getSphericalRho() const {
1145 return EARTH_RADIUS - depth;
1146 }
1147
1148
1149 inline constexpr double CoordZ::getSphericalTheta() const {
1150 return 90.0 - latitude;
1151 }
1152
1153
1154 inline constexpr double CoordZ::getSphericalPhi() const {
1155 return longitude;
1156 }
1157
1158
1159 inline constexpr double CoordZ::getCartDistance( const CoordZ& coords, CoordZSpheroidType type ) const {
1160 assert( coords.isValid() );
1161
1162 CartCoords my_cart_coords = getCartCoords(type);
1163 CartCoords input_cart_coords = coords.getCartCoords(type);
1164
1165 return std::sqrt( std::pow((my_cart_coords.getX() - input_cart_coords.getX()), 2.0)
1166 + std::pow((my_cart_coords.getY() - input_cart_coords.getY()), 2.0)
1167 + std::pow((my_cart_coords.getZ() - input_cart_coords.getZ()), 2.0));
1168 }
1169
1170
1171 inline constexpr double CoordZ::getCartRelAzimuth( const CoordZ& coords ) const {
1172 assert( coords.isValid() );
1173
1176
1177 return(std::atan2((input_cart_coords.getY() - my_cart_coords.getY()), (input_cart_coords.getX() - my_cart_coords.getX())));
1178 }
1179
1180
1181 inline constexpr double CoordZ::getCartRelZenith( const CoordZ& coords ) const {
1182 assert( coords.isValid() );
1183
1186
1187 return acos((input_cart_coords.getZ() - my_cart_coords.getZ()) / getCartDistance(coords));
1188 }
1189
1190
1191 inline constexpr Coord& operator+=( Coord& left, const Coord& right ) {
1192 if( !( left.isValid() && right.isValid() ) ) {
1193 left.latitude = COORD_NOT_SET_VALUE;
1194 left.longitude = COORD_NOT_SET_VALUE;
1195 }
1196 left.latitude += right.latitude;
1197 left.longitude += right.longitude;
1198 return left;
1199 }
1200
1201
1202 inline constexpr Coord& operator-=( Coord& left, const Coord& right ) {
1203 if( !( left.isValid() && right.isValid() ) ) {
1204 left.latitude = COORD_NOT_SET_VALUE;
1205 left.longitude = COORD_NOT_SET_VALUE;
1206 }
1207 left.latitude -= right.latitude;
1208 left.longitude -= right.longitude;
1209 return left;
1210 }
1211
1212
1213 inline constexpr Coord operator+( const Coord& left , const Coord& right ) {
1214 if( !( left.isValid() && right.isValid() ) )
1215 return Coord();
1216 return( Coord( (left.latitude + right.latitude), (left.longitude + right.longitude) ) );
1217 }
1218
1219
1220 inline constexpr Coord operator-( const Coord& left , const Coord& right ) {
1221 if( !( left.isValid() && right.isValid() ) )
1222 return Coord();
1223 return( Coord( (left.latitude - right.latitude), (left.longitude - right.longitude) ) );
1224 }
1225
1226
1227 inline constexpr bool operator==( const Coord& left , const Coord& right ) {
1228 if ( &left == &right )
1229 return true;
1230 return( left.latitude == right.latitude && left.longitude == right.longitude );
1231 }
1232
1233
1234 inline constexpr bool operator!=( const Coord& left , const Coord& right ) {
1235 if ( &left == &right )
1236 return false;
1237 return( left.latitude != right.latitude || left.longitude != right.longitude );
1238 }
1239
1240
1241 inline constexpr bool operator>( const Coord& left , const Coord& right ) {
1242 if ( &left == &right )
1243 return false;
1244 return( ( left.latitude > right.latitude ) || ( ( left.latitude == right.latitude ) && ( left.longitude > right.longitude ) ) );
1245 }
1246
1247
1248 inline constexpr bool operator<( const Coord& left , const Coord& right ) {
1249 if ( &left == &right )
1250 return false;
1251 return( ( left.latitude < right.latitude ) || ( ( left.latitude == right.latitude ) && ( left.longitude < right.longitude ) ) );
1252 }
1253
1254
1255 inline constexpr bool operator>=( const Coord& left , const Coord& right ) {
1256 if ( left == right )
1257 return true;
1258 return( left > right );
1259 }
1260
1261
1262 inline constexpr bool operator<=( const Coord& left , const Coord& right ) {
1263 if ( left == right )
1264 return true;
1265 return( left < right );
1266 }
1267
1268
1269 inline std::ostream& operator<<(std::ostream& os, const Coord& x) {
1270 os << "Latitude = " << x.latitude << "; Longitude = " << x.longitude
1271 << "; Marsden square = " << x.marsden_square
1272 << "; Marsden One Degree square = " << x.marsden_one_degree;
1273 return os;
1274 }
1275
1276
1277 inline std::ostream& operator<<( std::ostream& os, const CoordZ::CartCoords& instance ) {
1278 os << "X = " << instance.x << "; Y = " << instance.y << "; Z = " << instance.z << "; type = " << static_cast<int>(instance.type);
1279 return os;
1280 }
1281
1282
1283 inline constexpr bool operator==( const CoordZ& left, const CoordZ& right ) {
1284 if ( &left == &right )
1285 return true;
1286 return( left.latitude == right.latitude && left.longitude == right.longitude && left.depth == right.depth );
1287 }
1288
1289
1290 inline constexpr bool operator!=( const CoordZ& left, const CoordZ& right ) {
1291 if ( &left == &right )
1292 return false;
1293 return( left.latitude != right.latitude || left.longitude != right.longitude || left.depth != right.depth );
1294 }
1295
1296
1297 inline constexpr bool operator>( const CoordZ& left, const CoordZ& right ) {
1298 if ( &left == &right )
1299 return false;
1300
1301 return( ( left.latitude > right.latitude ) || ( ( left.latitude == right.latitude ) && ( left.longitude > right.longitude ) )
1302 || ( ( left.latitude == right.latitude ) && ( left.longitude == right.longitude ) && ( left.depth > right.depth ) ) );
1303 }
1304
1305
1306 inline constexpr bool operator<( const CoordZ& left, const CoordZ& right ) {
1307 if ( &left == &right )
1308 return false;
1309 return ( ( left.latitude < right.latitude ) || ( ( left.latitude == right.latitude ) && ( left.longitude < right.longitude ) )
1310 || ( ( left.latitude == right.latitude ) && ( left.longitude == right.longitude ) && ( left.depth < right.depth ) ) );
1311 }
1312
1313
1314 inline constexpr bool operator>=( const CoordZ& left, const CoordZ& right ) {
1315 if ( left == right )
1316 return true;
1317 return( left > right );
1318 }
1319
1320
1321 inline constexpr bool operator<=( const CoordZ& left, const CoordZ& right ) {
1322 if ( left == right )
1323 return true;
1324 return( left < right );
1325 }
1326
1327
1328 inline constexpr CoordZ& operator+=( CoordZ& left, const CoordZ& right ) {
1329 if( !( left.isValid() && right.isValid() ) ) {
1330 left.latitude = COORD_NOT_SET_VALUE;
1331 left.longitude = COORD_NOT_SET_VALUE;
1332 left.depth = COORD_NOT_SET_VALUE;
1333 }
1334 left.latitude += right.latitude;
1335 left.longitude += right.longitude;
1336 left.depth += right.depth;
1337 return left;
1338 }
1339
1340 inline constexpr CoordZ& operator-=( CoordZ& left, const CoordZ& right ) {
1341 if( !( left.isValid() && right.isValid() ) ) {
1342 left.latitude = COORD_NOT_SET_VALUE;
1343 left.longitude = COORD_NOT_SET_VALUE;
1344 left.depth = COORD_NOT_SET_VALUE;
1345 }
1346 left.latitude -= right.latitude;
1347 left.longitude -= right.longitude;
1348 left.depth -= right.depth;
1349 return left;
1350 }
1351
1352 inline std::ostream& operator<<( std::ostream& os, const CoordZ& instance ) {
1353 os << "Latitude = " << instance.latitude << "; Longitude = " << instance.longitude << "; Depth = " << instance.depth
1354 << "; Marsden square = " << instance.marsden_square
1355 << "; Marsden One Degree square = " << instance.marsden_one_degree;
1356 return os;
1357 }
1358
1359 constexpr CoordZ CoordZ::getCoordZAlongGreatCircle( const CoordZ& start, const CoordZ& end, double distance ) {
1360 double start_depth = start.getDepth();
1361 double end_depth = end.getDepth();
1362 double total_distance = start.getGreatCircleDistance( end, start_depth );
1363
1364 if ( total_distance == 0.0 && start_depth != end_depth ) {
1365 total_distance = std::abs(end_depth - start_depth);
1366 assert( distance < total_distance );
1367
1368 return( CoordZ( static_cast<Coord>(start), distance ) );
1369 }
1370
1371 double delta_depth = end_depth - start_depth;
1372 double curr_depth = start_depth + distance / total_distance * delta_depth;
1373
1374 return( CoordZ( Coord::getCoordAlongGreatCircle( start, end, distance , start_depth ) , curr_depth ) );
1375 }
1376
1377 constexpr CoordZ CoordZ::getCoordZAlongCartLine( const CoordZ& start, const CoordZ& end, double distance ) {
1379 double Xsorg_ = sorg_cart_coords.getX();
1380 double Ysorg_ = sorg_cart_coords.getY();
1381 double Zsorg_ = sorg_cart_coords.getZ();
1382
1383 double azimut = start.getCartRelAzimuth( end );
1384 double polar = start.getCartRelZenith( end );
1385
1386 double x_fin = Xsorg_ + distance * std::cos(azimut) * std::sin(polar);
1387 double y_fin = Ysorg_ + distance * std::sin(azimut) * std::sin(polar);
1388 double z_fin = Zsorg_ + distance * std::cos(polar);
1389
1390#if 0
1392 double Xdest_ = end_cart_coords.getX();
1393 double Ydest_ = end_cart_coords.getY();
1394 double Zdest_ = end_cart_coords.getZ();
1395
1396 std::cout << std::endl;
1397 std::cout << "x_fin = " << x_fin << "; Xdest_ = " << Xdest_ << "; diff = " << (x_fin - Xdest_) << std::endl;
1398 std::cout << "y_fin = " << y_fin << "; Ydest_ = " << Ydest_ << "; diff = " << (y_fin - Ydest_) << std::endl;
1399 std::cout << "z_fin = " << z_fin << "; Zdest_ = " << Zdest_ << "; diff = " << (z_fin - Zdest_) << std::endl;
1400
1401 std::cout << std::endl;
1402 std::cout << "x_fin = " << x_fin << "; Xsorg_ = " << Xsorg_ << "; diff = " << (x_fin - Xsorg_) << std::endl;
1403 std::cout << "y_fin = " << y_fin << "; Ysorg_ = " << Ysorg_ << "; diff = " << (y_fin - Ysorg_) << std::endl;
1404 std::cout << "z_fin = " << z_fin << "; Zsorg_ = " << Zsorg_ << "; diff = " << (z_fin - Zsorg_) << std::endl;
1405
1406 std::cout << std::endl;
1407 std::cout << "Xdest_ = " << Xdest_ << "; Xsorg_ = " << Xsorg_ << "; diff = " << (Xdest_ - Xsorg_) << std::endl;
1408 std::cout << "Ydest_ = " << Ydest_ << "; Ysorg_ = " << Ysorg_ << "; diff = " << (Ydest_ - Ysorg_) << std::endl;
1409 std::cout << "Zdest_ = " << Zdest_ << "; Zsorg_ = " << Zsorg_ << "; diff = " << (Zdest_ - Zsorg_) << std::endl;
1410#endif //
1411
1412 double lat = 90.0 - 180.0 / M_PI * acos( z_fin / std::sqrt( std::pow(x_fin,2.0) + std::pow(y_fin,2.0) + std::pow(z_fin,2.0) ) );
1413 double lon = 180.0 / M_PI * std::atan2( y_fin, x_fin );
1414 double depth = std::sqrt( std::pow(x_fin,2.0) + std::pow(y_fin,2.0) + std::pow(z_fin,2.0) ) - EARTH_RADIUS;
1415
1416#if 0
1417 std::cout << "lat = " << lat << std::endl;
1418 std::cout << "long = " << lon << std::endl;
1419 std::cout << "depth = " << depth << std::endl;
1420#endif //
1421
1422 return CoordZ( lat, lon, std::abs(depth) );
1423 }
1424
1425 inline constexpr CoordZ CoordZ::getCoordZFromCartesianCoords( const CartCoords& cart_coords ) {
1426 return CoordZ::getCoordZFromCartesianCoords( cart_coords.getX(), cart_coords.getY(), cart_coords.getZ(), cart_coords.getType() );
1427 }
1428
1429 inline constexpr CoordZ CoordZ::getCoordZFromCartesianCoords( double x, double y, double z, CoordZSpheroidType type ) {
1430 double polarRadius = 0.0;
1431 double equatorRadius = 0.0;
1432 double e2Param = 0.0;
1433
1435 equatorRadius = EARTH_RADIUS;
1436 e2Param = 0.0;
1437 }
1438 else if (type == CoordZSpheroidType::COORDZ_GRS80) {
1439 polarRadius = EARTH_GRS80_POLAR_RADIUS;// GRS80 ellipsoide
1440 equatorRadius = EARTH_SEMIMAJOR_AXIS;
1441 e2Param = ( std::pow(equatorRadius, 2.0) - std::pow(polarRadius, 2.0) ) / std::pow(equatorRadius, 2.0);
1442 }
1443 else { // if type == COORDZ_WGS84
1444 polarRadius = EARTH_WGS84_POLAR_RADIUS;// WGS84 ellipsoide
1445 equatorRadius = EARTH_SEMIMAJOR_AXIS;
1446 e2Param = ( std::pow(equatorRadius, 2.0) - std::pow(polarRadius, 2.0) ) / std::pow(equatorRadius, 2.0);
1447 }
1448
1449 double latitude = COORD_NOT_SET_VALUE;
1450 double longitude = COORD_NOT_SET_VALUE;
1451 double altitude = COORD_NOT_SET_VALUE;
1452
1453 // distance from the position point (P) to earth center point (origin O)
1454 double op = std::sqrt( x*x + y*y + z*z );
1455
1456 if ( op > 0.0 ) {
1457 // longitude calculation
1458 double lon2 = std::atan(y / x);
1459
1460 // scale longitude between -PI and PI (-180.0 and 180.0 in degrees)
1461 if ( x != 0.0 || y != 0.0 ) {
1462 longitude = std::atan(y/x) * 180.0/M_PI;
1463
1464 if ( x < 0.0 ) {
1465 if ( y > 0.0) {
1466 longitude = 180.0 + longitude;
1467 lon2 = lon2 - M_PI;
1468 }
1469 else {
1470 longitude = -180.0 + longitude;
1471 lon2 = M_PI + lon2;
1472 }
1473 }
1474 }
1475
1476 // Geocentric latitude
1477 double latG = std::atan(z / (std::sqrt( x*x + y*y )));
1478
1479 // Geocentric latitude (of point Q, Q is intersection point of segment OP and reference ellipsoid)
1480 double latQ = std::atan(z / ( (1.0 - e2Param ) * (std::sqrt( x*x + y*y ))) );
1481
1482 // calculate radius of the curvature
1483 double rCurvature = ( equatorRadius / std::sqrt(1.0 - e2Param * std::sin(latQ) * std::sin(latQ)) );
1484
1485 // x, y, z of point Q
1486 double xQ = rCurvature * std::cos(latQ) * std::cos(lon2);
1487 double yQ = rCurvature * std::cos(latQ) * std::sin(lon2);
1488 double zQ = rCurvature * (1.0 - e2Param) * std::sin(latQ);
1489
1490 // distance OQ
1491 double oq = std::sqrt( xQ*xQ + yQ*yQ + zQ*zQ );
1492
1493 // distance PQ is OP - OQ
1494 double pq = op - oq;
1495
1496 // length of the normal segment from point P of line (PO) to point T.
1497 // T is intersection point of linen the PO normal and ellipsoid normal from point Q.
1498 double tp = pq * std::sin(latG - latQ);
1499
1500 double lat_radians = latQ + tp / op * std::cos(latQ - latG);
1501 latitude = lat_radians*180.0/M_PI;
1502
1503 altitude = pq * std::cos(latQ - latG);
1504#if 0
1505 std::cout << "lat new = " << latitude << std::endl;
1506 std::cout << "lon new = " << longitude << std::endl;
1507 std::cout << "alt new = " << altitude << std::endl;
1508#endif //
1509 }
1510
1511 return CoordZ( latitude, longitude, std::abs(altitude) );
1512 }
1513
1514 constexpr CoordZ CoordZ::getCoordZFromSphericalCoords( double rho, double theta, double phi ) {
1515 // we want to be underwater!
1516 assert(rho <= EARTH_RADIUS);
1517
1518 return CoordZ( (90.0 - theta), phi, std::abs(EARTH_RADIUS - rho) );
1519 }
1520
1521 inline constexpr CoordZ operator+( const CoordZ& left , const CoordZ& right ) {
1522 if( !( left.isValid() && right.isValid() ) )
1523 return CoordZ();
1524 return( CoordZ( left.latitude + right.latitude, left.longitude + right.longitude, left.depth + right.depth ) );
1525 }
1526
1527 inline constexpr CoordZ operator-( const CoordZ& left , const CoordZ& right ) {
1528 if( !( left.isValid() && right.isValid() ) )
1529 return CoordZ();
1530 return( CoordZ( left.latitude - right.latitude, left.longitude - right.longitude, left.depth - right.depth ) );
1531 }
1532
1533 inline constexpr int UtmWgs84::getZone() const {
1534 return zone;
1535 }
1536
1537 inline constexpr double UtmWgs84::getEasting() const {
1538 return easting;
1539 }
1540
1541 inline constexpr double UtmWgs84::getNorthing() const {
1542 return northing;
1543 }
1544
1545 inline constexpr bool UtmWgs84::isValid() const {
1546 return ((zone != COORD_NOT_SET_VALUE) && (easting != COORD_NOT_SET_VALUE) && (northing != COORD_NOT_SET_VALUE));
1547 }
1548
1549 inline std::ostream& operator<<( std::ostream& os, const UtmWgs84& instance ) {
1550 os << "Zone = " << instance.zone << "; Easting = " << instance.easting << "; Northing = " << instance.northing;
1551 return os;
1552 }
1553
1554
1555 inline constexpr UtmWgs84::UtmWgs84(int utmZone, double east, double north)
1556 : zone(utmZone),
1557 easting(east),
1558 northing(north)
1559 {
1560 }
1561
1562 inline constexpr UtmWgs84 UtmWgs84::getUtmWgs84FromCoord(const Coord& coords) {
1563 double latitude = coords.getLatitude();
1564 double longitude = coords.getLongitude();
1565 double falseEasting = 500000.0;
1566 double falseNorthing = 10000000.0;
1567
1568 int zone = std::floor((longitude + 180.0)/6.0) + 1;
1569 double lambda0 = ((zone-1)*6.0 - 180.0 + 3.0)*M_PI / 180.0;//central meridian
1570 double phi = latitude*M_PI/180.0;
1571 double lambda = longitude*M_PI/180.0 - lambda0;
1572
1573 double a = Coord::EARTH_SEMIMAJOR_AXIS;
1574 double f = 1/298.2572215381486;
1575
1576 double k0 = 0.9996;
1577
1578 double e = std::sqrt(f*(2.0-f));
1579 double n = f/(2.0-f);
1580 double n2 = std::pow(n,2.0);
1581 double n3 = std::pow(n,3.0);
1582 double n4 = std::pow(n,4.0);
1583 double n5 = std::pow(n,5.0);
1584 double n6 = std::pow(n,6.0);
1585
1586 double cosLambda = std::cos(lambda);
1587 double sinLambda = std::sin(lambda);
1588
1589 double tau = std::tan(phi);
1590 double sigma = std::sinh(e*atanh(e*tau / std::sqrt(1.0+std::pow(tau,2.0)) ));
1591
1592 double tau_prime = tau*std::sqrt(1.0 + std::pow(sigma,2.0)) - sigma*std::sqrt(1.0 + std::pow(tau,2.0));
1593
1594 double epsilon_prime = std::atan2(tau_prime, cosLambda);
1595 double eta_prime = std::asinh(sinLambda/ std::sqrt( std::pow(tau_prime,2.0) + std::pow(cosLambda,2.0)));
1596
1597 double A = a/(1.0+n) * (1.0 + 1.0/4.0*n2 + 1.0/64.0*n4 + 1.0/256.0*n6);
1598 double alpha[] = {0.0,
1599 1.0/2.0*n - 2.0/3.0*n2 + 5.0/16.0*n3 + 41.0/180.0*n4 -127.0/288.0*n5 + 7891.0/37800.0*n6,
1600 13.0/48.0*n2 - 3.0/5.0*n3 + 557.0/1440.0*n4 + 281.0/630.0*n5 - 1983433.0/1935360.0*n6,
1601 61.0/240.0*n3 - 103.0/140.0*n4 + 15061.0/26880.0*n5 + 167603.0/181440.0*n6,
1602 49561.0/161280.0*n4 - 179.0/168*n5 + 6601661.0/7257600.0*n6,
1603 34729.0/80640.0*n5 - 3418889.0/1995840.0*n6,
1604 212378941.0/319334400.0*n6};
1605 double epsilon = epsilon_prime;
1606
1607 for(int j = 1; j<=6; j++) {
1608 epsilon += alpha[j]*std::sin(2.0*j*epsilon_prime)*std::cosh(2.0*j*eta_prime);
1609 }
1610
1611 double eta = eta_prime;
1612 for(int j = 1; j<=6; j++) {
1613 eta += alpha[j]*std::cos(2.0*j*epsilon_prime)*std::sinh(2.0*j*eta_prime);
1614 }
1615
1616 double x = k0*A*eta;
1617 double y = k0*A*epsilon;
1618
1619 x = x + falseEasting;
1620
1621 if(y<0.0)
1622 y = y + falseNorthing;
1623
1624 return UtmWgs84(zone,x,y);
1625 }
1626}
1627
1628#endif /* WOSS_COORDINATES_DEFINITIONS_H */
1629
bool operator()(const CoordZ &x, const CoordZ &y) const
Definition coordinates-definitions.h:826
Function object for partial ordering of coordinates.
Definition coordinates-definitions.h:783
bool operator()(const T &x, const T &y) const
Definition coordinates-definitions.h:795
Class that represents cartesian coordinates.
Definition coordinates-definitions.h:409
double x
Definition coordinates-definitions.h:460
constexpr double getY() const
Definition coordinates-definitions.h:436
double z
Y-asis value in meters.
Definition coordinates-definitions.h:464
constexpr double getX() const
Definition coordinates-definitions.h:430
CoordZSpheroidType type
Z-asis value in meters.
Definition coordinates-definitions.h:466
double y
X-asis value in meters.
Definition coordinates-definitions.h:462
friend std::ostream & operator<<(std::ostream &os, const CartCoords &instance)
Definition coordinates-definitions.h:1277
constexpr CoordZSpheroidType getType() const
Definition coordinates-definitions.h:448
constexpr double getZ() const
Definition coordinates-definitions.h:442
constexpr CartCoords()
Definition coordinates-definitions.h:1083
3D-Coordinates (lat, long, depth) class definitions and functions library
Definition coordinates-definitions.h:384
constexpr bool isValid() const
Definition coordinates-definitions.h:616
constexpr double getSphericalTheta() const
Definition coordinates-definitions.h:1149
friend constexpr CoordZ & operator+=(CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1328
constexpr CoordZ(CoordZ &&tmp)=default
static constexpr CoordZ getCoordZFromCartesianCoords(double x, double y, double z, CoordZSpheroidType type=CoordZSpheroidType::COORDZ_SPHERE)
Definition coordinates-definitions.h:1429
friend constexpr bool operator>=(const CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1314
friend std::ostream & operator<<(std::ostream &os, const CoordZ &instance)
Definition coordinates-definitions.h:1352
friend constexpr bool operator==(const CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1283
static constexpr CoordZ getCoordZAlongGreatCircle(const CoordZ &start, const CoordZ &end, double distance)
Definition coordinates-definitions.h:1359
constexpr double getCartX(CoordZSpheroidType type=CoordZSpheroidType::COORDZ_SPHERE) const
Definition coordinates-definitions.h:1129
constexpr double getCartZ(CoordZSpheroidType type=CoordZSpheroidType::COORDZ_SPHERE) const
Definition coordinates-definitions.h:1139
constexpr double getCartDistance(const CoordZ &coords, CoordZSpheroidType type=CoordZSpheroidType::COORDZ_SPHERE) const
Definition coordinates-definitions.h:1159
constexpr CoordZ(const CoordZ &copy)=default
constexpr double getSphericalPhi() const
Definition coordinates-definitions.h:1154
constexpr double getSphericalRho() const
Definition coordinates-definitions.h:1144
friend constexpr CoordZ operator+(const CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1521
constexpr void setDepth(double d)
Definition coordinates-definitions.h:492
constexpr CoordZ & operator=(const CoordZ &coordz)=default
CoordZSpheroidType
Spheroid model to use.
Definition coordinates-definitions.h:398
constexpr CoordZ(double lat=COORD_NOT_SET_VALUE, double lon=COORD_NOT_SET_VALUE, double z=COORD_NOT_SET_VALUE)
Definition coordinates-definitions.h:1067
constexpr CoordZ & operator=(CoordZ &&coordz)=default
friend constexpr bool operator!=(const CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1290
constexpr double getCartRelZenith(const CoordZ &coords) const
Definition coordinates-definitions.h:1181
static constexpr CoordZ getCoordZFromSphericalCoords(double rho, double theta, double phi)
Definition coordinates-definitions.h:1514
friend constexpr CoordZ operator-(const CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1527
constexpr double getCartY(CoordZSpheroidType type=CoordZSpheroidType::COORDZ_SPHERE) const
Definition coordinates-definitions.h:1134
friend constexpr bool operator<(const CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1306
constexpr double getDepth() const
Definition coordinates-definitions.h:498
friend constexpr bool operator<=(const CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1321
friend constexpr CoordZ & operator-=(CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1340
double depth
Definition coordinates-definitions.h:725
constexpr double getCartRelAzimuth(const CoordZ &coords) const
Definition coordinates-definitions.h:1171
constexpr CartCoords getCartCoords(CoordZSpheroidType type=CoordZSpheroidType::COORDZ_SPHERE) const
Definition coordinates-definitions.h:1100
static constexpr CoordZ getCoordZAlongCartLine(const CoordZ &start, const CoordZ &end, double distance)
Definition coordinates-definitions.h:1377
static constexpr double COORDZ_MIN_DEPTH
Minimum valid depth.
Definition coordinates-definitions.h:388
friend constexpr bool operator>(const CoordZ &left, const CoordZ &right)
Definition coordinates-definitions.h:1297
Coordinates (lat, long) class definitions and functions library.
Definition coordinates-definitions.h:98
static constexpr double COORD_MAX_LATITUDE
Maximum valid Latitude.
Definition coordinates-definitions.h:104
constexpr double getInitialBearing(const Coord &destination) const
Definition coordinates-definitions.h:925
friend constexpr bool operator<=(const Coord &left, const Coord &right)
Definition coordinates-definitions.h:1262
static constexpr double EARTH_GRS80_ECCENTRICITY
Earth's first eccentricity as defined by GRS80.
Definition coordinates-definitions.h:122
static constexpr double EARTH_GRS80_POLAR_RADIUS
Earth's semi-major axis in meters as defined by GRS80.
Definition coordinates-definitions.h:116
constexpr void setLongitude(double lon)
Definition coordinates-definitions.h:148
constexpr int getMarsdenOneDegreeSquare() const
Definition coordinates-definitions.h:179
constexpr int getMarsdenSquare() const
Definition coordinates-definitions.h:173
static constexpr double COORD_MAX_LONGITUDE
Maximum valid Longitude.
Definition coordinates-definitions.h:108
friend constexpr bool operator!=(const Coord &left, const Coord &right)
Definition coordinates-definitions.h:1234
constexpr double getGreatCircleDistance(const Coord &destination, double depth=0) const
Definition coordinates-definitions.h:954
static constexpr double EARTH_WGS84_ECCENTRICITY
Earth's first eccentricity as defined by WGS84.
Definition coordinates-definitions.h:125
constexpr void setLatitude(double lat)
Definition coordinates-definitions.h:142
friend constexpr Coord operator+(const Coord &left, const Coord &right)
Definition coordinates-definitions.h:1213
friend constexpr bool operator<(const Coord &left, const Coord &right)
Definition coordinates-definitions.h:1248
friend constexpr Coord operator-(const Coord &left, const Coord &right)
Definition coordinates-definitions.h:1220
constexpr Coord & operator=(const Coord &copy)=default
double latitude
Definition coordinates-definitions.h:348
static constexpr double COORD_MIN_LATITUDE
Minimum valid Latitude.
Definition coordinates-definitions.h:102
friend constexpr Coord & operator-=(Coord &left, const Coord &right)
Definition coordinates-definitions.h:1202
constexpr Coord(Coord &&tmp)=default
static constexpr Coord getCoordFromBearing(const Coord &start_coord, double bearing, double distance, double depth=0.0)
Definition coordinates-definitions.h:903
constexpr Coord(const Coord &copy)=default
double longitude
Definition coordinates-definitions.h:353
constexpr bool isValid() const
Definition coordinates-definitions.h:154
constexpr double getFinalBearing(const Coord &destination) const
Definition coordinates-definitions.h:944
friend constexpr bool operator>(const Coord &left, const Coord &right)
Definition coordinates-definitions.h:1241
constexpr void updateMarsdenCoord()
Definition coordinates-definitions.h:849
static constexpr double EARTH_RADIUS
Mean earth radius in meters.
Definition coordinates-definitions.h:110
static constexpr double EARTH_SEMIMAJOR_AXIS
Earth's semi-major axis in meters as defined by both GRS80 and WGS84.
Definition coordinates-definitions.h:113
friend constexpr bool operator==(const Coord &left, const Coord &right)
Definition coordinates-definitions.h:1227
static constexpr bool isValidUtmZoneChar(UtmZoneChar utm_zone_char)
Definition coordinates-definitions.h:972
friend constexpr Coord & operator+=(Coord &left, const Coord &right)
Definition coordinates-definitions.h:1191
static constexpr Coord getCoordFromUtmWgs84(double easting, double northing, double utm_zone_number, UtmZoneChar utm_zone_char)
Definition coordinates-definitions.h:983
static constexpr double EARTH_WGS84_POLAR_RADIUS
Earth's polar radius in meters as defined by WGS84.
Definition coordinates-definitions.h:119
int marsden_one_degree
Definition coordinates-definitions.h:363
constexpr MarsdenCoord getMarsdenCoord() const
Definition coordinates-definitions.h:185
int marsden_square
Definition coordinates-definitions.h:358
friend constexpr bool operator>=(const Coord &left, const Coord &right)
Definition coordinates-definitions.h:1255
constexpr Coord(double lat=COORD_NOT_SET_VALUE, double lon=COORD_NOT_SET_VALUE)
Definition coordinates-definitions.h:839
constexpr Coord & operator=(Coord &&tmp)=default
static constexpr double COORD_MIN_LONGITUDE
Minimum valid Longitude.
Definition coordinates-definitions.h:106
friend std::ostream & operator<<(std::ostream &os, const Coord &instance)
Definition coordinates-definitions.h:1269
constexpr double getLongitude() const
Definition coordinates-definitions.h:167
static constexpr Coord getCoordAlongGreatCircle(const Coord &start_coord, const Coord &end_coord, double distance, double depth=0.0)
Definition coordinates-definitions.h:1062
constexpr double getLatitude() const
Definition coordinates-definitions.h:161
Definition coordinates-definitions.h:728
constexpr UtmWgs84(int utmZone=COORD_NOT_SET_VALUE, double east=COORD_NOT_SET_VALUE, double north=COORD_NOT_SET_VALUE)
Definition coordinates-definitions.h:1555
constexpr double getNorthing() const
Definition coordinates-definitions.h:1541
double northing
Definition coordinates-definitions.h:771
constexpr int getZone() const
Definition coordinates-definitions.h:1533
static constexpr UtmWgs84 getUtmWgs84FromCoord(const Coord &coords)
Definition coordinates-definitions.h:1562
constexpr double getEasting() const
Definition coordinates-definitions.h:1537
int zone
Definition coordinates-definitions.h:767
friend std::ostream & operator<<(std::ostream &os, const UtmWgs84 &instance)
Definition coordinates-definitions.h:1549
constexpr bool isValid() const
Definition coordinates-definitions.h:1545
double easting
Definition coordinates-definitions.h:769
Definition ac-toolbox-arr-asc-reader.h:44
std::pair< int, int > MarsdenCoord
Definition coordinates-definitions.h:70
constexpr bool operator<(const Coord &left, const Coord &right)
Definition coordinates-definitions.h:1248
std::vector< Coord > CoordVector
Definition coordinates-definitions.h:75
std::vector< CoordZ > CoordZVector
Definition coordinates-definitions.h:58
std::vector< MarsdenCoord > MarsdenCoordVector
Definition coordinates-definitions.h:85
char UtmZoneChar
Definition coordinates-definitions.h:52
int Marsden
Definition coordinates-definitions.h:63
std::vector< Marsden > MarsdenVector
Definition coordinates-definitions.h:80