Example #1
0
        private void LineInit(Geodesic g,
                              double lat1, double lon1,
                              double azi1, double salp1, double calp1,
                              int caps)
        {
            _a  = g._a;
            _f  = g._f;
            _b  = g._b;
            _c2 = g._c2;
            _f1 = g._f1;
            // Always allow latitude and azimuth and unrolling the longitude
            _caps = caps | GeodesicMask.LATITUDE | GeodesicMask.AZIMUTH |
                    GeodesicMask.LONG_UNROLL;

            _lat1 = GeoMath.LatFix(lat1);
            _lon1 = lon1;
            _azi1 = azi1; _salp1 = salp1; _calp1 = calp1;
            double cbet1, sbet1;

            {
                Pair p = GeoMath.Sincosd(GeoMath.AngRound(_lat1));
                sbet1 = _f1 * p.First; cbet1 = p.Second;
            }
            // Ensure cbet1 = +epsilon at poles
            {
                Pair p = GeoMath.Norm(sbet1, cbet1);
                sbet1 = p.First; cbet1 = Math.Max(Geodesic.tiny_, p.Second);
            }
            _dn1 = Math.Sqrt(1 + g._ep2 * GeoMath.Sq(sbet1));

            // Evaluate alp0 from sin(alp1) * cos(bet1) = sin(alp0),
            _salp0 = _salp1 * cbet1; // alp0 in [0, pi/2 - |bet1|]
                                     // Alt: calp0 = hypot(sbet1, calp1 * cbet1).  The following
                                     // is slightly better (consider the case salp1 = 0).
            _calp0 = GeoMath.Hypot(_calp1, _salp1 * sbet1);
            // Evaluate sig with tan(bet1) = tan(sig1) * cos(alp1).
            // sig = 0 is nearest northward crossing of equator.
            // With bet1 = 0, alp1 = pi/2, we have sig1 = 0 (equatorial line).
            // With bet1 =  pi/2, alp1 = -pi, sig1 =  pi/2
            // With bet1 = -pi/2, alp1 =  0 , sig1 = -pi/2
            // Evaluate omg1 with tan(omg1) = sin(alp0) * tan(sig1).
            // With alp0 in (0, pi/2], quadrants for sig and omg coincide.
            // No atan2(0,0) ambiguity at poles since cbet1 = +epsilon.
            // With alp0 = 0, omg1 = 0 for alp1 = 0, omg1 = pi for alp1 = pi.
            _ssig1 = sbet1; _somg1 = _salp0 * sbet1;
            _csig1 = _comg1 = sbet1 != 0 || _calp1 != 0 ? cbet1 * _calp1 : 1;
            {
                Pair p = GeoMath.Norm(_ssig1, _csig1);
                _ssig1 = p.First; _csig1 = p.Second;
            } // sig1 in (-pi, pi]
              // GeoMath.norm(_somg1, _comg1); -- don't need to normalize!

            _k2 = GeoMath.Sq(_calp0) * g._ep2;
            double eps = _k2 / (2 * (1 + Math.Sqrt(1 + _k2)) + _k2);

            if ((_caps & GeodesicMask.CAP_C1) != 0)
            {
                _A1m1 = Geodesic.A1m1f(eps);
                _C1a  = new double[nC1_ + 1];
                Geodesic.C1f(eps, _C1a);
                _B11 = Geodesic.SinCosSeries(true, _ssig1, _csig1, _C1a);
                double s = Math.Sin(_B11), c = Math.Cos(_B11);
                // tau1 = sig1 + B11
                _stau1 = _ssig1 * c + _csig1 * s;
                _ctau1 = _csig1 * c - _ssig1 * s;
                // Not necessary because C1pa reverts C1a
                //    _B11 = -SinCosSeries(true, _stau1, _ctau1, _C1pa, nC1p_);
            }

            if ((_caps & GeodesicMask.CAP_C1p) != 0)
            {
                _C1pa = new double[nC1p_ + 1];
                Geodesic.C1pf(eps, _C1pa);
            }

            if ((_caps & GeodesicMask.CAP_C2) != 0)
            {
                _C2a  = new double[nC2_ + 1];
                _A2m1 = Geodesic.A2m1f(eps);
                Geodesic.C2f(eps, _C2a);
                _B21 = Geodesic.SinCosSeries(true, _ssig1, _csig1, _C2a);
            }

            if ((_caps & GeodesicMask.CAP_C3) != 0)
            {
                _C3a = new double[nC3_];
                g.C3f(eps, _C3a);
                _A3c = -_f *_salp0 *g.A3f(eps);

                _B31 = Geodesic.SinCosSeries(true, _ssig1, _csig1, _C3a);
            }

            if ((_caps & GeodesicMask.CAP_C4) != 0)
            {
                _C4a = new double[nC4_];
                g.C4f(eps, _C4a);
                // Multiplier = a^2 * e^2 * cos(alpha0) * sin(alpha0)
                _A4  = GeoMath.Sq(_a) * _calp0 * _salp0 * g._e2;
                _B41 = Geodesic.SinCosSeries(false, _ssig1, _csig1, _C4a);
            }
        }