Пример #1
0
        // Longitude and latitude are in degrees.
        // Output Latitude will be in range [-90, 90].
        // Output Longitude will be in range [-180, 180].
        //
        public void UnprojectPoint(double x, double y, out double latitudeDeg, out double longitudeDeg)
        {
            if (Double.IsNaN(x))
            {
                throw new ArgumentException(Resource.InputCoordinateIsNaN, "x");
            }
            if (Double.IsNaN(y))
            {
                throw new ArgumentException(Resource.InputCoordinateIsNaN, "y");
            }

            double latitude, longitude;

            _projection.Unproject(x, y, out latitude, out longitude);

            if (Double.IsNaN(latitude) || latitude < -Math.PI / 2 || latitude > Math.PI / 2)
            {
                throw new ArgumentOutOfRangeException("latitude", String.Format(CultureInfo.InvariantCulture, Resource.OutputLatitudeIsOutOfRange, latitude));
            }
            if (Double.IsNaN(longitude) || longitude < -Math.PI || longitude > Math.PI)
            {
                throw new ArgumentOutOfRangeException("longitude", String.Format(CultureInfo.InvariantCulture, Resource.OutputLongitudeIsOutOfRange, longitude));
            }

            latitudeDeg  = MathX.Clamp(90, Util.ToDegrees(latitude));
            longitudeDeg = MathX.NormalizeLongitudeDeg(Util.ToDegrees(longitude + _projection.CentralLongitudeRad));
        }
Пример #2
0
        // longitude0, latitude0, parallel1, parallel2
        public AlbersEqualAreaProjection(Dictionary <String, double> parameters)
            : base(parameters)
        {
            double latitude0_rad = InputLatitude("latitude0");
            double parallel1_rad = InputLatitude("parallel1");
            double parallel2_rad = InputLatitude("parallel2");

            double cos_parallel1 = Math.Cos(parallel1_rad);
            double sin_parallel1 = Math.Sin(parallel1_rad);

            _n2 = sin_parallel1 + Math.Sin(parallel2_rad);
            if (Math.Abs(_n2) <= MathX.Tolerance)
            {
                throw new ArgumentOutOfRangeException();
            }

            _n      = _n2 / 2;
            _n_half = _n2 / 4;
            _inv_n2 = 1 / _n2;
            _inv_n  = 2 / _n2;

            _c         = MathX.Square(cos_parallel1) + sin_parallel1 * _n2;
            _c_over_n2 = _c * _inv_n2;

            double a = _c - Math.Sin(latitude0_rad) * _n2;

            if (a < 0)
            {
                throw new ArgumentOutOfRangeException();
            }
            _ro_0 = Math.Sqrt(a) * _inv_n;
        }
        protected internal override void Unproject(double x, double y, out double latitude, out double longitude)
        {
            double ro = Math.Sign(_n) * Math.Sqrt(x * x + MathX.Square(_ro_0 - y));

            // If ro is zero or very small then then latitude will be +-Pi/2 depending on the sign of f.
            latitude  = 2 * Math.Atan(Math.Pow(_f / ro, _nInv)) - Math.PI / 2;
            longitude = MathX.Clamp(Math.PI, Math.Atan2(x, _ro_0 - y) * _nInv);
        }
Пример #4
0
        protected internal override void Unproject(double x, double y, out double latitude, out double longitude)
        {
            double ros = x * x + (_ro_0 - y) * (_ro_0 - y);
            double a   = _c_over_n2 - ros * _n_half;

            if (Double.IsNaN(a) || Math.Abs(a) > 1 + MathX.Tolerance)
            {
                throw new ArgumentOutOfRangeException("x, y");
            }

            latitude  = Math.Asin(MathX.Clamp(1, a));
            longitude = MathX.Clamp(Math.PI, MathX.Atan2(x, _ro_0 - y, "x, y") * _inv_n);
        }
Пример #5
0
        // Longitude and latitude are in degrees.
        // Input Latitude must be in range [-90, 90].
        // Input Longitude must be in range [-15069, 15069].
        //
        public void ProjectPoint(double latitudeDeg, double longitudeDeg, out double x, out double y)
        {
            double latitude  = MathX.InputLat(latitudeDeg, 90, "latitude");
            double longitude = MathX.NormalizeLongitudeRad(MathX.InputLong(longitudeDeg, 15069, "longitude") - _projection.CentralLongitudeRad);

            _projection.Project(latitude, longitude, out x, out y);

            if (Double.IsNaN(x))
            {
                throw new ArgumentOutOfRangeException("x");
            }
            if (Double.IsNaN(y))
            {
                throw new ArgumentOutOfRangeException("y");
            }
        }
Пример #6
0
        protected internal override void Project(double latitude, double longitude, out double x, out double y)
        {
            double sin_lat = Math.Sin(latitude);
            double cos_lat = Math.Cos(latitude);

            double sin_long = Math.Sin(longitude);
            double cos_long = Math.Cos(longitude);

            double a = _sin_fi_p * sin_lat - _cos_fi_p * cos_lat * sin_long;             // sin_fi_p

            if (Double.IsNaN(a) || Math.Abs(a) > 1)
            {
                throw new ArgumentOutOfRangeException("latitude, longitude");
            }

            x = MathX.Atan2(sin_lat / cos_lat * _cos_fi_p + sin_long * _sin_fi_p, cos_long, "latitude, longitude");
            y = MathX.Clamp(MaxY, Math.Log((1 + a) / (1 - a)) / 2);             // protect againt +-Infinity
        }
Пример #7
0
        protected internal override void Unproject(double x, double y, out double latitude, out double longitude)
        {
            double sin_x = Math.Sin(x);
            double cos_x = Math.Cos(x);

            double sinh_y = Math.Sinh(y);
            double cosh_y = Math.Cosh(y);

            // cosh_y >= 1 by definition
            double a = (_sin_fi_p * sinh_y + _cos_fi_p * sin_x) / cosh_y;

            if (Math.Abs(a) > 1)
            {
                throw new ArgumentOutOfRangeException("x, y");
            }

            latitude  = Math.Asin(a);
            longitude = MathX.Atan2(_sin_fi_p * sin_x - _cos_fi_p * sinh_y, cos_x, "x, y");
        }
 protected internal override void Unproject(double x, double y, out double latitude, out double longitude)
 {
     if (x >= MaxX)
     {
         latitude  = 0;
         longitude = Math.PI / 2;
     }
     else if (x <= -MaxX)
     {
         latitude  = 0;
         longitude = -Math.PI / 2;
     }
     else
     {
         // 1 <= cosh(x) <= cosh(MaxX)
         latitude = Math.Asin(Math.Sin(y) / Math.Cosh(x));
         // In case of x=0 and y=+-Pi/2: latitude will be +-90 and longtude will be 0
         longitude = MathX.Atan2(Math.Sinh(x), Math.Cos(y));
     }
 }
        // x will be in range [-MaxX, MaxX]
        // y will be in range [-Pi, Pi]
        protected internal override void Project(double latitude, double longitude, out double x, out double y)
        {
            // North pole
            if (latitude >= Math.PI / 2 - MathX.Tolerance)
            {
                x = 0;
                y = Math.PI / 2;
                return;
            }

            // South pole
            if (latitude <= -Math.PI / 2 + MathX.Tolerance)
            {
                x = 0;
                y = -Math.PI / 2;
                return;
            }

            if (Math.Abs(latitude) <= MathX.Tolerance)
            {
                // East of India
                if (Math.Abs(longitude - Math.PI / 2) <= MathX.Tolerance)
                {
                    x = MaxX;
                    y = 0;
                    return;
                }
                // West of South America
                if (Math.Abs(longitude + Math.PI / 2) <= MathX.Tolerance)
                {
                    x = -MaxX;
                    y = 0;
                    return;
                }
            }

            double b = Math.Cos(latitude) * Math.Sin(longitude);

            x = MathX.Clamp(MaxX, Math.Log((1 + b) / (1 - b)) / 2);
            y = Math.Atan2(Math.Tan(latitude), Math.Cos(longitude));
        }
Пример #10
0
 protected internal double InputLongitude(string name, double max)
 {
     return(MathX.InputLong(_parameters[name], max, name));
 }
 protected internal override void Project(double latitude, double longitude, out double x, out double y)
 {
     x = longitude;
     y = MathX.Clamp(MaxY, Math.Log(Math.Tan(Math.PI / 4 + latitude / 2)));             // protect againt +-Infinity
 }