• Skip to content
  • Skip to link menu
KDE 3.5 API Reference
  • KDE API Reference
  • API Reference
  • Sitemap
  • Contact Us
 

kstars

ksmoon.cpp

Go to the documentation of this file.
00001 /***************************************************************************
00002                           ksmoon.cpp  -  K Desktop Planetarium
00003                              -------------------
00004     begin                : Sun Aug 26 2001
00005     copyright            : (C) 2001 by Jason Harris
00006     email                : kstars@30doradus.org
00007  ***************************************************************************/
00008 
00009 /***************************************************************************
00010  *                                                                         *
00011  *   This program is free software; you can redistribute it and/or modify  *
00012  *   it under the terms of the GNU General Public License as published by  *
00013  *   the Free Software Foundation; either version 2 of the License, or     *
00014  *   (at your option) any later version.                                   *
00015  *                                                                         *
00016  ***************************************************************************/
00017 
00018 #include <stdlib.h>
00019 #include <math.h>
00020 
00021 #include <qfile.h>
00022 
00023 #include "ksnumbers.h"
00024 #include "ksutils.h"
00025 #include "kssun.h"
00026 #include "ksmoon.h"
00027 #include "kstarsdata.h"
00028 
00029 KSMoon::KSMoon(KStarsData *kd)
00030  : KSPlanetBase( kd, I18N_NOOP("Moon"), "", 3474.8 /*diameter in km*/ ) {
00031     BData.setAutoDelete(true);
00032     LRData.setAutoDelete(true);
00033 }
00034 
00035 KSMoon::~KSMoon() {
00036 }
00037 
00038 bool KSMoon::data_loaded = false;
00039 QPtrList<KSMoon::MoonLRData> KSMoon::LRData;
00040 QPtrList<KSMoon::MoonBData> KSMoon::BData;
00041 
00042 bool KSMoon::loadData() {
00043     if (data_loaded) return true;
00044 
00045     QString line;
00046     QFile f;
00047     int nd, nm, nm1, nf;
00048     double Li, Ri, Bi; //coefficients of the sums
00049 
00050     if ( KSUtils::openDataFile( f, "moonLR.dat" ) ) {
00051         QTextStream stream( &f );
00052         while ( !stream.eof() ) {
00053             line = stream.readLine();
00054             QTextIStream instream( &line );
00055             instream >> nd >> nm >> nm1 >> nf >> Li >> Ri;
00056             LRData.append(new MoonLRData(nd, nm, nm1, nf, Li, Ri));
00057         }
00058         f.close();
00059     } else
00060         return false;
00061 
00062 
00063     if ( KSUtils::openDataFile( f, "moonB.dat" ) ) {
00064         QTextStream stream( &f );
00065         while ( !stream.eof() ) {
00066             line = stream.readLine();
00067             QTextIStream instream( &line );
00068             instream >> nd >> nm >> nm1 >> nf >> Bi;
00069             BData.append(new MoonBData(nd, nm, nm1, nf, Bi));
00070         }
00071         f.close();
00072     }
00073 
00074     data_loaded = true;
00075     return true;
00076 }
00077 
00078 bool KSMoon::findGeocentricPosition( const KSNumbers *num, const KSPlanetBase* ) {
00079     //Algorithms in this subroutine are taken from Chapter 45 of "Astronomical Algorithms"
00080   //by Jean Meeus (1991, Willmann-Bell, Inc. ISBN 0-943396-35-2.  http://www.willbell.com/math/mc1.htm)
00081     QString fname, snum, line;
00082     QFile f;
00083     double DegtoRad;
00084     double T, L, D, M, M1, F, E, A1, A2, A3;
00085     double sumL, sumR, sumB;
00086 
00087     DegtoRad = acos( -1.0 )/180.0;
00088 
00089     //Julian centuries since J2000
00090     T = num->julianCenturies();
00091 
00092     double Et = 1.0 - 0.002516*T - 0.0000074*T*T;
00093 
00094     //Moon's mean longitude
00095     L = 218.3164591 + 481267.88134236*T - 0.0013268*T*T + T*T*T/538841.0 - T*T*T*T/65194000.0;
00096     while ( L > 360.0 ) L -= 360.0;
00097     while ( L < 0.0 ) L += 360.0;
00098     L *= DegtoRad;
00099     //Moon's mean elongation
00100     D = 297.8502042 + 445267.1115168*T - 0.0016300*T*T + T*T*T/545868.0 - T*T*T*T/113065000.0;
00101     while ( D > 360.0 ) D -= 360.0;
00102     while ( D < 0.0 ) D += 360.0;
00103     D *= DegtoRad;
00104     //Sun's mean anomaly
00105   M = 357.5291092 + 35999.0502909*T - 0.0001536*T*T + T*T*T/24490000.0;
00106     while ( M > 360.0 ) M -= 360.0;
00107     while ( M < 0.0 ) M += 360.0;
00108     M *= DegtoRad;
00109     //Moon's mean anomaly
00110     M1= 134.9634114 + 477198.8676313*T + 0.0089970*T*T + T*T*T/69699.0 - T*T*T*T/14712000.0;
00111     while ( M1 > 360.0 ) M1 -= 360.0;
00112     while ( M1 < 0.0 ) M1 += 360.0;
00113     M1 *= DegtoRad;
00114   //Moon's argument of latitude (angle from ascending node)
00115     F = 93.2720993 + 483202.0175273*T - 0.0034029*T*T - T*T*T/3526000.0 + T*T*T*T/863310000.0;
00116     while ( F > 360.0 ) F -= 360.0;
00117     while ( F < 0.0 ) F += 360.0;
00118     F *= DegtoRad;
00119 
00120     A1 = 119.75 +    131.849*T;
00121     A2 =  53.09 + 479264.290*T;
00122     A3 = 313.45 + 481226.484*T;
00123     while ( A1 > 360.0 ) A1 -= 360.0;
00124     while ( A1 < 0.0 ) A1 += 360.0;
00125     while ( A2 > 360.0 ) A2 -= 360.0;
00126     while ( A2 < 0.0 ) A2 += 360.0;
00127     while ( A3 > 360.0 ) A3 -= 360.0;
00128     while ( A3 < 0.0 ) A3 += 360.0;
00129     A1 *= DegtoRad;
00130     A2 *= DegtoRad;
00131     A3 *= DegtoRad;
00132 
00133     //Calculate the series expansions stored in moonLR.txt and moonB.txt.
00134     //
00135     sumL = 0.0;
00136     sumR = 0.0;
00137 
00138     if (!loadData()) return false;
00139 
00140     for (MoonLRData *mlrd = LRData.first(); mlrd != 0; mlrd = LRData.next()) {
00141 
00142         E = 1.0;
00143         if ( mlrd->nm ) { //if M != 0, include changing eccentricity of Earth's orbit
00144             E = Et;
00145             if ( abs( mlrd->nm )==2 ) E = E*E; //use E^2
00146         }
00147         sumL += E*mlrd->Li*sin( mlrd->nd*D + mlrd->nm*M + mlrd->nm1*M1 + mlrd->nf*F );
00148         sumR += E*mlrd->Ri*cos( mlrd->nd*D + mlrd->nm*M + mlrd->nm1*M1 + mlrd->nf*F );
00149     }
00150 
00151     sumB = 0.0;
00152     for (MoonBData *mbd = BData.first(); mbd != 0; mbd = BData.next()) {
00153 
00154         E = 1.0;
00155         if ( mbd->nm ) { //if M != 0, include changing eccentricity of Earth's orbit
00156             E = Et;
00157             if ( abs( mbd->nm )==2 ) E = E*E; //use E^2
00158         }
00159         sumB += E*mbd->Bi*sin( mbd->nd*D + mbd->nm*M + mbd->nm1*M1 + mbd->nf*F );
00160     }
00161 
00162     //Additive terms for sumL and sumB
00163     sumL += ( 3958.0*sin( A1 ) + 1962.0*sin( L-F ) + 318.0*sin( A2 ) );
00164     sumB += ( -2235.0*sin( L ) + 382.0*sin( A3 ) + 175.0*sin( A1-F ) + 175.0*sin( A1+F ) + 127.0*sin( L-M1 ) - 115.0*sin( L+M1 ) );
00165 
00166     //Geocentric coordinates
00167     setEcLong( ( L + DegtoRad*sumL/1000000.0 ) * 180./dms::PI );  //convert radians to degrees
00168     setEcLat( ( DegtoRad*sumB/1000000.0 ) * 180./dms::PI );
00169     Rearth = ( 385000.56 + sumR/1000.0 )/AU_KM; //distance from Earth, in AU
00170     setAngularSize( asin(physicalSize()/Rearth/AU_KM)*60.*180./dms::PI ); //angular size in arcmin
00171 
00172     EclipticToEquatorial( num->obliquity() );
00173 
00174     //Determine position angle
00175     findPA( num );
00176 
00177     return true;
00178 }
00179 
00180 void KSMoon::findPhase( const KSSun *Sun ) {
00181     Phase.setD( ecLong()->Degrees() - Sun->ecLong()->Degrees() );
00182     Phase.setD( Phase.reduce().Degrees() );
00183     int iPhase = int( 0.1*Phase.Degrees()+0.5 );
00184     if (iPhase==36) iPhase = 0;
00185     QString sPhase;
00186     sPhase = sPhase.sprintf( "%02d", iPhase );
00187     QString imName = "moon" + sPhase + ".png";
00188 
00189     QFile imFile;
00190     if ( KSUtils::openDataFile( imFile, imName ) ) {
00191         imFile.close();
00192         image0()->load( imFile.name() );
00193         image()->load( imFile.name() );
00194 
00195     }
00196 }
00197 
00198 QString KSMoon::phaseName() const {
00199     double f = illum();
00200     double p = phase().Degrees();
00201     
00202     //First, handle the major phases
00203     if ( f > 0.99 ) return i18n( "moon phase, 100 percent illuminated", "Full moon" );
00204     if ( f < 0.01 ) return i18n( "moon phase, 0 percent illuminated", "New moon" );
00205     if ( fabs( f - 0.50 ) < 0.01 ) {
00206         if ( p < 180.0 ) return i18n( "moon phase, half-illuminated and growing", "First quarter" );
00207         else return i18n( "moon phase, half-illuminated and shrinking", "Third quarter" );
00208     }
00209 
00210     //Next, handle the more general cases
00211     if ( p < 90.0 ) return i18n( "moon phase between new moon and 1st quarter", "Waxing crescent" );
00212     else if ( p < 180.0 ) return i18n( "moon phase between 1st quarter and full moon", "Waxing gibbous" );
00213     else if ( p < 270.0 ) return i18n( "moon phase between full moon and 3rd quarter", "Waning gibbous" );
00214     else if ( p < 360.0 ) return i18n( "moon phase between 3rd quarter and new moon", "Waning crescent" );
00215 
00216     else return i18n( "unknown" );
00217 }

kstars

Skip menu "kstars"
  • Main Page
  • Modules
  • Class Hierarchy
  • Alphabetical List
  • Class List
  • File List
  • Class Members
  • Related Pages

API Reference

Skip menu "API Reference"
  • keduca
  • kstars
Generated for API Reference by doxygen 1.5.9
This website is maintained by Adriaan de Groot and Allen Winter.
KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal