aboutsummaryrefslogblamecommitdiffstats
path: root/libtellurian.h
blob: be7ec9328eccd041ede9b14700154d64ecdbf2ad (plain) (tree)



















































































































                                                                                                                                                    


                                                              







                                                                         


                                                              





















































































































































































































































































































                                                                                                          
/* See LICENSE file for copyright and license details. */
#ifndef LIBTELLURIAN_H
#define LIBTELLURIAN_H


#if defined(__GNUC__)
# define LIBTELLURIAN_CONST__ __attribute__((__const__, __warn_unused_result__))
# define LIBTELLURIAN_WUR__ __attribute__((__warn_unused_result__))
#else
# define LIBTELLURIAN_CONST__
# define LIBTELLURIAN_WUR__
#endif


/**
 * The Earth's equatorial radius, in meters
 */
#define LIBTELLURIAN_EQUATORIAL_RADIUS 6378137.0 /* a */

/**
 * The Earth's polar radius, in meters
 */
#define LIBTELLURIAN_POLAR_RADIUS 6356752.314245 /* b */

/**
 * The Earth's mean radius (arithmetic mean), in meters
 */
#define LIBTELLURIAN_MEAN_RADIUS 6371008.771415 /* (2a + b) / 3 */

/**
 * The Earth's volumetric radius (geometric mean), in meters
 */
#define LIBTELLURIAN_VOLUMETRIC_RADIUS 6371000.7900090935 /* ∛(a² * b) */

/**
 * The Earth's authalic radius (equal-area mean), in meters
 */
#define LIBTELLURIAN_AUTHALIC_RADIUS 6371007.180918414 /* √(a²/2 + (b² artanh e) / 2e) */

/**
 * The Earth's rectifying radius, in meters
 */
#define LIBTELLURIAN_RECTIFYING_RADIUS 6367449.14582 /* 2π⁻¹∫{0 → ½π} √(a² cos² φ + b² sin² φ) dφ ≅ ∛(½(√a³+√b³))² */

/**
 * The Earth's nominal equatorial radius, in meters
 */
#define LIBTELLURIAN_NOMINAL_EQUATORIAL_RADIUS 6378100.

/**
 * The Earth's nominal polar radius, in meters
 */
#define LIBTELLURIAN_NOMINAL_POLAR_RADIUS 6356800.

/**
 * The Earth's nominal radius, in meters
 */
#define LIBTELLURIAN_NOMINAL_RADIUS LIBTELLURIAN_NOMINAL_EQUATORIAL_RADIUS

/**
 * The Earth's equatorial circumference, in meters
 */
#define LIBTELLURIAN_EQUATORIAL_CIRCUMFERENCE 40075016.68557849 /* 2bπ */

/**
 * The Earth's meridional circumference, in meters
 */
#define LIBTELLURIAN_MERIDIONAL_CIRCUMFERENCE 39940652.74224401 /* 2bπ */

/**
 * The Earth's mean circumference (arithmetic mean), in meters
 */
#define LIBTELLURIAN_MEAN_CIRCUMFERENCE 40030228.70446699 /* 2π(2a + b) / 3 */

/**
 * The Earth's volumetric circumference (geometric mean), in meters
 */
#define LIBTELLURIAN_VOLUMETRIC_CIRCUMFERENCE 40030178.555814676 /* 2π∛(a² * b) */

/**
 * The Earth's authalic circumference (equal-area mean), in meters
 */
#define LIBTELLURIAN_AUTHALIC_CIRCUMFERENCE 40030218.71108221 /* 2π√(a²/2 + (b² artanh e) / 2e) */

/**
 * The Earth's rectifying circumference, in meters
 */
#define LIBTELLURIAN_RECTIFYING_CIRCUMFERENCE 40007862.91722943 /* 4 ∫{0 → ½π} √(a² cos² φ + b² sin² φ) dφ */

/**
 * The Earth's gravity at the equator, in meters per square-second
 */
#define LIBTELLURIAN_EQUATORIAL_GRAVITY 9.7803253359

/**
 * The Earth's gravity at the poles, in meters per square-second
 */
#define LIBTELLURIAN_POLAR_GRAVITY 9.8321849378

/**
 * The Earth's normal gravity at the equator, in meters per square-second
 */
#define LIBTELLURIAN_NORMAL_EQUATORIAL_GRAVITY 9.7803267715

/**
 * The Earth's normal gravity at the poles, in meters per square-second
 */
#define LIBTELLURIAN_NORMAL_POLAR_GRAVITY 9.8321863685

/**
 * The Earth's mass, in kilograms
 */
#define LIBTELLURIAN_MASS_OF_EARTH 5.972168e24


/**
 * Calculate the distance of the nominal sea level (geocentric
 * radius), for some point on the Earth's surface, from the
 * centre of the Earth
 * 
 * @param   latitude  GPS latitude coordinate, in degrees
 * @return            The geocentric altitude of the sea level, in meters
 */
LIBTELLURIAN_CONST__
double libtellurian_sea_level(double latitude);

/**
 * Calculate the distance of the nominal sea level (geocentric
 * radius), for some point on the Earth's surface, from the
 * centre of the Earth
 * 
 * @param   latitude  GPS latitude coordinate, in radians
 * @return            The geocentric altitude of the sea level, in meters
 */
LIBTELLURIAN_CONST__
double libtellurian_sea_level_radians(double latitude);

/**
 * Calculate the distance between two points on the Earth's surface
 * 
 * This function is gives an approximate value using
 * a sphere as a model for the Earth
 * 
 * @param   latitude1   GPS latitude coordinate for the first point, in degrees
 * @param   longitude1  GPS longitude coordinate for the first point, in degrees
 * @param   latitude2   GPS latitude coordinate for the second point, in degrees
 * @param   longitude2  GPS longitude coordinate for the second point, in degrees
 * @return              Approximate distance between the two points
 */
LIBTELLURIAN_CONST__
double libtellurian_coarse_distance(double latitude1, double longitude1,
                                    double latitude2, double longitude2);

/**
 * Calculate the distance between two points on the Earth's surface
 * 
 * This function is gives an approximate value using
 * a sphere as a model for the Earth
 * 
 * @param   latitude1   GPS latitude coordinate for the first point, in radians
 * @param   longitude1  GPS longitude coordinate for the first point, in radians
 * @param   latitude2   GPS latitude coordinate for the second point, in radians
 * @param   longitude2  GPS longitude coordinate for the second point, in radians
 * @return              Approximate distance between the two points
 */
LIBTELLURIAN_CONST__
double libtellurian_coarse_distance_radians(double latitude1, double longitude1,
                                            double latitude2, double longitude2);

/**
 * Calculate the distance and azimuths between two points on the Earth's surface
 * 
 * This function is gives good approximate values
 * using an oblate spheroid as a model for the Earth
 * 
 * @param   latitude1     GPS latitude coordinate for the first point, in degrees
 * @param   longitude1    GPS longitude coordinate for the first point, in degrees
 * @param   latitude2     GPS latitude coordinate for the second point, in degrees
 * @param   longitude2    GPS longitude coordinate for the second point, in degrees
 * @param   azimuth1_out  Output parameter for the forward azimuth, in degrees,
 *                        at the first point; or `NULL`
 * @param   azimuth2_out  Output parameter for the forward azimuth, in degrees,
 *                        at the second point; or `NULL`
 * @return                Approximate distance between the two points
 * 
 * Calculating the the forward azimuths is not free, but it
 * is cheap to compute them (especially the first one) when
 * most of the computations for the distance have been
 * performed. If you have no need for an azimuth you can set
 * the corresponding output parameter to `NULL`, and the
 * function will not compute it.
 */
LIBTELLURIAN_WUR__
double libtellurian_distance(double latitude1, double longitude1,
                             double latitude2, double longitude2,
                             double *azimuth1_out, double *azimuth2_out);

/**
 * Calculate the distance and azimuths between two points on the Earth's surface
 * 
 * This function is gives good approximate values
 * using an oblate spheroid as a model for the Earth
 * 
 * @param   latitude1     GPS latitude coordinate for the first point, in radians
 * @param   longitude1    GPS longitude coordinate for the first point, in radians
 * @param   latitude2     GPS latitude coordinate for the second point, in radians
 * @param   longitude2    GPS longitude coordinate for the second point, in radians
 * @param   azimuth1_out  Output parameter for the forward azimuth, in radians,
 *                        at the first point; or `NULL`
 * @param   azimuth2_out  Output parameter for the forward azimuth, in radians,
 *                        at the second point; or `NULL`
 * @return                Approximate distance between the two points
 * 
 * Calculating the the forward azimuths is not free, but it
 * is cheap to compute them (especially the first one) when
 * most of the computations for the distance have been
 * performed. If you have no need for an azimuth you can set
 * the corresponding output parameter to `NULL`, and the
 * function will not compute it.
 */
LIBTELLURIAN_WUR__
double libtellurian_distance_radians(double latitude1, double longitude1,
                                     double latitude2, double longitude2,
                                     double *azimuth1_out, double *azimuth2_out);

/**
 * Calculate the azimuths between two points on the Earth's surface
 * 
 * This function is gives good approximate values
 * using an oblate spheroid as a model for the Earth
 * 
 * @param  latitude1     GPS latitude coordinate for the first point, in degrees
 * @param  longitude1    GPS longitude coordinate for the first point, in degrees
 * @param  latitude2     GPS latitude coordinate for the second point, in degrees
 * @param  longitude2    GPS longitude coordinate for the second point, in degrees
 * @param  azimuth1_out  Output parameter for the forward azimuth, in degrees,
 *                       at the first point; or `NULL`
 * @param  azimuth2_out  Output parameter for the forward azimuth, in degrees,
 *                       at the second point; or `NULL`
 * 
 * This function is identical to libtellurian_distance`
 * except it does not compute the distance between the
 * points
 */
void libtellurian_azimuth(double latitude1, double longitude1,
                          double latitude2, double longitude2,
                          double *azimuth1_out, double *azimuth2_out);

/**
 * Calculate the azimuths between two points on the Earth's surface
 * 
 * This function is gives good approximate values
 * using an oblate spheroid as a model for the Earth
 * 
 * @param  latitude1     GPS latitude coordinate for the first point, in radians
 * @param  longitude1    GPS longitude coordinate for the first point, in radians
 * @param  latitude2     GPS latitude coordinate for the second point, in radians
 * @param  longitude2    GPS longitude coordinate for the second point, in radians
 * @param  azimuth1_out  Output parameter for the forward azimuth, in radians,
 *                       at the first point; or `NULL`
 * @param  azimuth2_out  Output parameter for the forward azimuth, in radians,
 *                       at the second point; or `NULL`
 * 
 * 
 * This function is identical to libtellurian_distance_radians`
 * except it does not compute the distance between the points
 */
void libtellurian_azimuth_radians(double latitude1, double longitude1,
                                  double latitude2, double longitude2,
                                  double *azimuth1_out, double *azimuth2_out);

/**
 * Calculate the location that is some distance away,
 * in some direction, from some point
 * 
 * @param  latitude1       GPS latitude coordinate for the starting point, in degrees
 * @param  longitude1      GPS longitude coordinate for the starting point, in degrees
 * @param  azimuth1        The direction to travel, in degrees
 * @param  distance        The distance to travel, in meters
 * @param  latitude2_out   Output parameter for the end point's GPS latitude
 *                         coordinate, in degrees; or `NULL`
 * @param  longitude2_out  Output parameter for the end point's GPS longitude
 *                         coordinate, in degrees; or `NULL`
 * @param  azimuth2_out    Output parameter for the direction from the end point
 *                         to the starting point, in degrees; or `NULL`
 */
void libtellurian_end_point(double latitude1, double longitude1, double azimuth1, double distance,
                            double *latitude2_out, double *longitude2_out, double *azimuth2_out);

/**
 * Calculate the location that is some distance away,
 * in some direction, from some point
 * 
 * @param  latitude1       GPS latitude coordinate for the starting point, in radians
 * @param  longitude1      GPS longitude coordinate for the starting point, in radians
 * @param  azimuth1        The direction to travel, in radians
 * @param  distance        The distance to travel, in meters
 * @param  latitude2_out   Output parameter for the end point's GPS latitude
 *                         coordinate, in radians; or `NULL`
 * @param  longitude2_out  Output parameter for the end point's GPS longitude
 *                         coordinate, in radians; or `NULL`
 * @param  azimuth2_out    Output parameter for the direction from the end point
 *                         to the starting point, in radians; or `NULL`
 */
void libtellurian_end_point_radians(double latitude1, double longitude1, double azimuth1, double distance,
                                    double *latitude2_out, double *longitude2_out, double *azimuth2_out);

/**
 * Calculate the normal gravity for some point on
 * the Earth's surface, where the Earth's is model
 * as an oblate spheroid
 * 
 * @param   latitude  GPS latitude coordinate, in degrees
 * @return            The normal gravity, in meters per square-second
 */
LIBTELLURIAN_CONST__
double libtellurian_normal_gravity(double latitude);

/**
 * Calculate the normal gravity for some point on
 * the Earth's surface, where the Earth's is model
 * as an oblate spheroid
 * 
 * @param   latitude  GPS latitude coordinate, in radians
 * @return            The normal gravity, in meters per square-second
 */
LIBTELLURIAN_CONST__
double libtellurian_normal_gravity_radians(double latitude);

/**
 * Calculate the gravity adjusted for the elevation
 * above the altitude where the gravity is measure
 * 
 * Altitudes above circa 100000 meters is out of range
 * for this function (that would be in outer space)
 * 
 * @param   gravity   The gravity at sea level, in meters per square-second
 * @param   latitude  GPS latitude coordinate, in degrees
 * @param   altitude  Elevation above the gravity's measurement point, in meters
 * @return            The height-adjusted gravity, in meters per square-second
 */
LIBTELLURIAN_CONST__
double libtellurian_elevated_gravity(double gravity, double latitude, double altitude);

/**
 * Calculate the gravity adjusted for the elevation
 * above the altitude where the gravity is measure
 * 
 * Altitudes above circa 100000 meters is out of range
 * for this function (that would be in outer space)
 * 
 * @param   gravity   The gravity at sea level, in meters per square-second
 * @param   latitude  GPS latitude coordinate, in radians
 * @param   altitude  Elevation above the gravity's measurement point, in meters
 * @return            The height-adjusted gravity, in meters per square-second
 */
LIBTELLURIAN_CONST__
double libtellurian_elevated_gravity_radians(double gravity, double latitude, double altitude);

/**
 * Calculate the Earth's meridan radius of curvature at some latitude
 * 
 * @param   latitude  GPS latitude coordinate, in degrees
 * @return            The meridan radius of curvature, in meters (for radians!)
 */
LIBTELLURIAN_CONST__
double libtellurian_meridan_radius(double latitude);

/**
 * Calculate the Earth's meridan radius of curvature at some latitude
 * 
 * @param   latitude  GPS latitude coordinate, in radians
 * @return            The meridan radius of curvature, in meters (for radians)
 */
LIBTELLURIAN_CONST__
double libtellurian_meridan_radius_radians(double latitude);

/**
 * Calculate the Earth's transverse radius of curvature at some latitude
 * 
 * @param   latitude  GPS latitude coordinate, in degrees
 * @return            The transverse radius of curvature, in meters (for radians!)
 */
LIBTELLURIAN_CONST__
double libtellurian_transverse_radius(double latitude);

/**
 * Calculate the Earth's transverse radius of curvature at some latitude
 * 
 * @param   latitude  GPS latitude coordinate, in radians
 * @return            The transverse radius of curvature, in meters (for radians)
 */
LIBTELLURIAN_CONST__
double libtellurian_transverse_radius_radians(double latitude);

/**
 * Calculate the Earth's azimuthal radius of curvature
 * at some latitude for some azimuth
 * 
 * @param   latitude  GPS latitude coordinate, in degrees
 * @param   azimuth   The azimuth, in degrees
 * @return            The transverse radius of curvature, in meters (for radians!)
 */
LIBTELLURIAN_CONST__
double libtellurian_azimuthal_radius(double latitude, double azimuth);

/**
 * Calculate the Earth's azimuthal radius of curvature
 * at some latitude for some azimuth
 * 
 * @param   latitude  GPS latitude coordinate, in radians
 * @param   azimuth   The azimuth, in radians
 * @return            The transverse radius of curvature, in meters (for radians)
 */
LIBTELLURIAN_CONST__
double libtellurian_azimuthal_radius_radians(double latitude, double azimuth);

/**
 * Calculate the Earth's Gaussian radius of curvature at some latitude
 * 
 * @param   latitude  GPS latitude coordinate, in degrees
 * @return            The Gaussian radius of curvature, in meters (for radians!)
 */
LIBTELLURIAN_CONST__
double libtellurian_gaussian_radius(double latitude);

/**
 * Calculate the Earth's Gaussian radius of curvature at some latitude
 * 
 * @param   latitude  GPS latitude coordinate, in radians
 * @return            The Gaussian radius of curvature, in meters (for radians)
 */
LIBTELLURIAN_CONST__
double libtellurian_gaussian_radius_radians(double latitude);


#undef LIBTELLURIAN_CONST__
#undef LIBTELLURIAN_WUR__

#endif