void Spice::ComputeSolarLongitude(double et) { NaifStatus::CheckErrors(); if (iString(Target()).UpCase() == "SKY") { p_solarLongitude = -999.0; return; } if (p_bodyRotation->IsCached()) return; double tipm[3][3], npole[3]; char frameName[32]; SpiceInt frameCode; SpiceBoolean found; cidfrm_c (p_spkBodyCode, sizeof(frameName), &frameCode, frameName, &found); if ( found ) { pxform_c("J2000",frameName,et,tipm); } else { tipbod_c("J2000",p_spkBodyCode,et,tipm); } for (int i=0; i<3; i++) { npole[i] = tipm[2][i]; } double state[6], lt; spkez_c(p_spkBodyCode,et,"J2000","NONE",10,state,<); double uavel[3]; ucrss_c(state,&state[3],uavel); double x[3], y[3], z[3]; vequ_c(uavel,z); ucrss_c(npole,z,x); ucrss_c(z,x,y); double trans[3][3]; for (int i=0; i<3; i++) { trans[0][i] = x[i]; trans[1][i] = y[i]; trans[2][i] = z[i]; } spkez_c(10,et,"J2000","LT+S",p_spkBodyCode,state,<); double pos[3]; mxv_c(trans,state,pos); double radius, ls, lat; reclat_c(pos,&radius,&ls,&lat); ls *= 180.0 / Isis::PI; if (ls < 0.0) ls += 360.0; else if (ls > 360.0) ls -= 360.0; p_solarLongitude = ls; NaifStatus::CheckErrors(); }
/** * Returns the sub-solar latitude/longitude in universal coordinates (0-360 * positive east, ocentric) * * @param lat Sub-solar latitude * * @param lon Sub-solar longitude */ void Spice::SubSolarPoint (double &lat, double &lon) { NaifStatus::CheckErrors(); if (p_et == -DBL_MAX) { std::string msg = "You must call SetEphemerisTime first"; throw iException::Message(iException::Programmer,msg,_FILEINFO_); } SpiceDouble uuB[3],dist; unorm_c (p_uB,uuB,&dist); SpiceDouble a = p_radii[0]; SpiceDouble b = p_radii[1]; SpiceDouble c = p_radii[2]; SpiceDouble originB[3]; originB[0] = originB[1] = originB[2] = 0.0; SpiceBoolean found; SpiceDouble subB[3]; surfpt_c (originB,uuB,a,b,c,subB,&found); SpiceDouble mylon,mylat; reclat_c (subB,&a,&mylon,&mylat); lat = mylat * 180.0 / Isis::PI; lon = mylon * 180.0 / Isis::PI; if (lon < 0.0) lon += 360.0; NaifStatus::CheckErrors(); }
/** * Returns the sub-spacecraft latitude/longitude in universal coordinates * (0-360 positive east, ocentric) * * @param lat Sub-spacecraft latitude * * @param lon Sub-spacecraft longitude */ void Spice::SubSpacecraftPoint (double &lat, double &lon) { NaifStatus::CheckErrors(); if (p_et == -DBL_MAX) { std::string msg = "You must call SetEphemerisTime first"; throw iException::Message(iException::Programmer,msg,_FILEINFO_); } SpiceDouble usB[3],dist; std::vector<double> vsB = p_bodyRotation->ReferenceVector(p_instrumentPosition->Coordinate()); SpiceDouble sB[3]; sB[0] = vsB[0]; sB[1] = vsB[1]; sB[2] = vsB[2]; unorm_c (sB,usB,&dist); SpiceDouble a = p_radii[0]; SpiceDouble b = p_radii[1]; SpiceDouble c = p_radii[2]; SpiceDouble originB[3]; originB[0] = originB[1] = originB[2] = 0.0; SpiceBoolean found; SpiceDouble subB[3]; surfpt_c (originB,usB,a,b,c,subB,&found); SpiceDouble mylon,mylat; reclat_c (subB,&a,&mylon,&mylat); lat = mylat * 180.0 / Isis::PI; lon = mylon * 180.0 / Isis::PI; if (lon < 0.0) lon += 360.0; NaifStatus::CheckErrors(); }
static VALUE reclat(VALUE self, VALUE rectangular_point) { double radius, longitude, latitude; reclat_c(NM_STORAGE_DENSE(rectangular_point)->elements, &radius, &longitude, &latitude); return rb_ary_new3(3, DBL2NUM(radius), DBL2NUM(longitude), DBL2NUM(latitude)); }
//FUNCTION : getLonLat int getLonLat(SpiceDouble **earth_pos, SpiceDouble lon[], SpiceDouble lat[], int n) { SpiceInt i; SpiceDouble radius; SpiceDouble longitude; SpiceDouble latitude; for (i = 0; i < n; i++) { reclat_c(earth_pos[i], &radius, &longitude, &latitude); lon[i] = longitude; lat[i] = latitude; } return 0; }
/** Compute ground position from slant range * * @param ux Slant range distance * @param uy Doppler shift (always 0.0) * @param uz Not used * * @return conversion was successful */ bool RadarGroundMap::SetFocalPlane(const double ux, const double uy, double uz) { SpiceRotation *bodyFrame = p_camera->BodyRotation(); SpicePosition *spaceCraft = p_camera->InstrumentPosition(); // Get spacecraft position and velocity to create a state vector std::vector<double> Ssc(6); // Load the state into Ssc vequ_c ( (SpiceDouble *) &(spaceCraft->Coordinate()[0]), &Ssc[0]); vequ_c ( (SpiceDouble *) &(spaceCraft->Velocity()[0]), &Ssc[3]); // Rotate state vector to body-fixed std::vector<double> bfSsc(6); bfSsc = bodyFrame->ReferenceVector(Ssc); // Extract body-fixed position and velocity std::vector<double> Vsc(3); std::vector<double> Xsc(3); vequ_c ( &bfSsc[0], (SpiceDouble *) &(Xsc[0]) ); vequ_c ( &bfSsc[3], (SpiceDouble *) &(Vsc[0]) ); // Compute intrack, crosstrack, and radial coordinate SpiceDouble i[3]; vhat_c (&Vsc[0],i); SpiceDouble c[3]; SpiceDouble dp; dp = vdot_c(&Xsc[0],i); SpiceDouble p[3],q[3]; vscl_c(dp,i,p); vsub_c(&Xsc[0],p,q); vhat_c(q,c); SpiceDouble r[3]; vcrss_c(i,c,r); // What is the initial guess for R double radii[3]; p_camera->Radii(radii); SpiceDouble R = radii[0]; SpiceDouble lastR = DBL_MAX; SpiceDouble rlat; SpiceDouble rlon; SpiceDouble lat = DBL_MAX; SpiceDouble lon = DBL_MAX; double slantRangeSqr = (ux * p_rangeSigma) / 1000.; slantRangeSqr = slantRangeSqr*slantRangeSqr; SpiceDouble X[3]; int iter = 0; do { double normXsc = vnorm_c(&Xsc[0]); double alpha = (R*R - slantRangeSqr - normXsc*normXsc) / (2.0 * vdot_c(&Xsc[0],c)); double arg = slantRangeSqr - alpha*alpha; if (arg < 0.0) return false; double beta = sqrt(arg); if (p_lookDirection == Radar::Left) beta *= -1.0; SpiceDouble alphac[3],betar[3]; vscl_c(alpha,c,alphac); vscl_c(beta,r,betar); vadd_c(alphac,betar,alphac); vadd_c(&Xsc[0],alphac,X); // Convert X to lat,lon lastR = R; reclat_c(X,&R,&lon,&lat); rlat = lat*180.0/Isis::PI; rlon = lon*180.0/Isis::PI; R = GetRadius(rlat,rlon); iter++; } while (fabs(R-lastR) > p_tolerance && iter < 30); if (fabs(R-lastR) > p_tolerance) return false; lat = lat*180.0/Isis::PI; lon = lon*180.0/Isis::PI; while (lon < 0.0) lon += 360.0; // Compute body fixed look direction std::vector<double> lookB; lookB.resize(3); lookB[0] = X[0] - Xsc[0]; lookB[1] = X[1] - Xsc[1]; lookB[2] = X[2] - Xsc[2]; std::vector<double> lookJ = bodyFrame->J2000Vector(lookB); SpiceRotation *cameraFrame = p_camera->InstrumentRotation(); std::vector<double> lookC = cameraFrame->ReferenceVector(lookJ); SpiceDouble unitLookC[3]; vhat_c(&lookC[0],unitLookC); p_camera->SetLookDirection(unitLookC); return p_camera->Sensor::SetUniversalGround(lat,lon); }
void recrad_c ( ConstSpiceDouble rectan[3], SpiceDouble * range, SpiceDouble * ra, SpiceDouble * dec ) /* -Brief_I/O VARIABLE I/O DESCRIPTION -------- --- -------------------------------------------------- rectan I Rectangular coordinates of a point. range O Distance of the point from the origin. ra O Right ascension in radians. dec O Declination in radians. -Detailed_Input rectan The rectangular coordinates of a point. -Detailed_Output range is the distance of the point `rectan' from the origin. The units associated with `range' are those associated with the input `rectan'. ra is the right ascension of `rectan'. This is the angular distance measured toward the east from the prime meridian to the meridian containing the input point. The direction of increasing right ascension is from the +X axis towards the +Y axis. `ra' is output in radians. The range of `ra' is [0, 2*pi]. dec is the declination of `rectan'. This is the angle from the XY plane of the ray from the origin through the point. `dec' is output in radians. The range of `dec' is [-pi/2, pi/2]. -Parameters None. -Exceptions Error free. 1) If the X and Y components of `rectan' are both zero, the right ascension is set to zero. 2) If `rectan' is the zero vector, right ascension and declination are both set to zero. -Files None. -Particulars None. -Examples The following code fragment converts right ascension and declination from the B1950 reference frame to the J2000 frame. #include "SpiceUsr.h" SpiceDouble ra; SpiceDouble dec; SpiceDouble r; SpiceDouble mtrans [ 3 ][ 3 ]; SpiceDouble v1950 [ 3 ]; SpiceDouble v2000 [ 3 ]; /. Convert RA and DEC to a 3-vector expressed in the B1950 frame. ./ radrec_c ( 1.0, ra, dec, v1950 ); /. We use the CSPICE routine pxform_c to obtain the transformation matrix for converting vectors between the B1950 and J2000 reference frames. Since both frames are inertial, the input time value we supply to pxform_c is arbitrary. We choose zero seconds past the J2000 epoch as the input value. ./ pxform_c ( "B1950", "J2000", 0.0, mtrans ); /. Transform the vector to the J2000 frame. ./ mxv_c ( mtrans, v1950, v2000 ); /. Find the RA and DEC of the J2000-relative vector. ./ recrad_c ( v2000, &r, &ra, &dec ); -Restrictions None. -Author_and_Institution N.J. Bachman (JPL) H.A. Neilan (JPL) E.D. Wright (JPL) -Literature_References None. -Version -CSPICE Version 1.1.2, 30-JUL-2003 (NJB) Various header corrections were made. -CSPICE Version 1.1.0, 22-OCT-1998 (NJB) Made input vector const. -CSPICE Version 1.0.0, 08-FEB-1998 (EDW) -Index_Entries rectangular coordinates to ra and dec rectangular to right_ascension and declination -& */ { /* Begin recrad_c */ /* Call reclat_c to perform the conversion to angular terms. */ reclat_c ( rectan, range, ra, dec ); /* Right ascension is always in the domain [0, 2Pi]. Rectan_c returns ra in the domain [ -Pi, Pi ]. If ra is negative, add 2 Pi to map the value to the correct domain */ if ( *ra < 0. ) { *ra = *ra + twopi_c(); } } /* End recrad_c */