chromium/third_party/s2cellid/src/s2/s1angle.h

// Copyright 2005 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS-IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//

// Author: [email protected] (Eric Veach)

// Needed on Windows to get |M_PI| from math.h.
#ifdef _WIN32
#define _USE_MATH_DEFINES
#endif

#ifndef S2_S1ANGLE_H_
#define S2_S1ANGLE_H_

#include <math.h>
#include <limits>
#include <ostream>
#include <type_traits>

#include "s2/_fpcontractoff.h"
#include "s2/util/math/mathutil.h"
#include "s2/util/math/vector.h"

class S2LatLng;
// Avoid circular include of s2.h.
// This must be a typedef rather than a type alias declaration because of SWIG.
S2Point;

// This class represents a one-dimensional angle (as opposed to a
// two-dimensional solid angle).  It has methods for converting angles to
// or from radians, degrees, and the E5/E6/E7 representations (i.e. degrees
// multiplied by 1e5/1e6/1e7 and rounded to the nearest integer).
//
// The internal representation is a double-precision value in radians, so
// conversion to and from radians is exact.  Conversions between E5, E6, E7,
// and Degrees are not always exact; for example, Degrees(3.1) is different
// from E6(3100000) or E7(310000000).  However, the following properties are
// guaranteed for any integer "n", provided that "n" is in the input range of
// both functions:
//
//     Degrees(n) == E6(1000000 * n)
//     Degrees(n) == E7(10000000 * n)
//          E6(n) == E7(10 * n)
//
// The corresponding properties are *not* true for E5, so if you use E5 then
// don't test for exact equality when comparing to other formats such as
// Degrees or E7.
//
// The following conversions between degrees and radians are exact:
//
//          Degrees(180) == Radians(M_PI)
//       Degrees(45 * k) == Radians(k * M_PI / 4)  for k == 0..8
//
// These identities also hold when the arguments are scaled up or down by any
// power of 2.  Some similar identities are also true, for example,
// Degrees(60) == Radians(M_PI / 3), but be aware that this type of identity
// does not hold in general.  For example, Degrees(3) != Radians(M_PI / 60).
//
// Similarly, the conversion to radians means that Angle::Degrees(x).degrees()
// does not always equal "x".  For example,
//
//         S1Angle::Degrees(45 * k).degrees() == 45 * k      for k == 0..8
//   but       S1Angle::Degrees(60).degrees() != 60.
//
// This means that when testing for equality, you should allow for numerical
// errors (EXPECT_DOUBLE_EQ) or convert to discrete E5/E6/E7 values first.
//
// CAVEAT: All of the above properties depend on "double" being the usual
// 64-bit IEEE 754 type (which is true on almost all modern platforms).
//
// This class is intended to be copied by value as desired.  It uses
// the default copy constructor and assignment operator.
class S1Angle {};

//////////////////   Implementation details follow   ////////////////////

inline constexpr S1Angle S1Angle::Infinity() {}

inline constexpr S1Angle S1Angle::Zero() {}

inline constexpr double S1Angle::radians() const {}

inline constexpr double S1Angle::degrees() const {}

// Note that the E5, E6, and E7 conversion involve two multiplications rather
// than one.  This is mainly for backwards compatibility (changing this would
// break many tests), but it does have the nice side effect that conversions
// between Degrees, E6, and E7 are exact when the arguments are integers.

inline int32_t S1Angle::e5() const {}

inline int32_t S1Angle::e6() const {}

inline int32_t S1Angle::e7() const {}

inline S1Angle S1Angle::abs() const {}

inline bool operator==(S1Angle x, S1Angle y) {}

inline bool operator!=(S1Angle x, S1Angle y) {}

inline bool operator<(S1Angle x, S1Angle y) {}

inline bool operator>(S1Angle x, S1Angle y) {}

inline bool operator<=(S1Angle x, S1Angle y) {}

inline bool operator>=(S1Angle x, S1Angle y) {}

inline S1Angle operator-(S1Angle a) {}

inline S1Angle operator+(S1Angle a, S1Angle b) {}

inline S1Angle operator-(S1Angle a, S1Angle b) {}

inline S1Angle operator*(double m, S1Angle a) {}

inline S1Angle operator*(S1Angle a, double m) {}

inline S1Angle operator/(S1Angle a, double m) {}

inline double operator/(S1Angle a, S1Angle b) {}

inline S1Angle& S1Angle::operator+=(S1Angle a) {}

inline S1Angle& S1Angle::operator-=(S1Angle a) {}

inline S1Angle& S1Angle::operator*=(double m) {}

inline S1Angle& S1Angle::operator/=(double m) {}

inline double sin(S1Angle a) {}

inline double cos(S1Angle a) {}

inline double tan(S1Angle a) {}

inline constexpr S1Angle S1Angle::Radians(double radians) {}

inline constexpr S1Angle S1Angle::Degrees(double degrees) {}

inline constexpr S1Angle S1Angle::E5(int32_t e5) {}

inline constexpr S1Angle S1Angle::E6(int32_t e6) {}

inline constexpr S1Angle S1Angle::E7(int32_t e7) {}

inline constexpr S1Angle S1Angle::UnsignedE6(uint32_t e6) {}

inline constexpr S1Angle S1Angle::UnsignedE7(uint32_t e7) {}

// Writes the angle in degrees with 7 digits of precision after the
// decimal point, e.g. "17.3745904".
std::ostream& operator<<(std::ostream& os, S1Angle a);

#endif  // S2_S1ANGLE_H_