## File: orbit.h

package info (click to toggle)
xplanet 0.43-5
 `123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161` ``````/****************************************************************************** orbit - orbit class header Copyright (C) 1999 Detlev Zundel This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA ******************************************************************************/ // First we have to build up some mathematical toolkit so the orbit // calculations can be expressed concisely. // We'll have to have some stripped down matrix and vector handling // facilities. // Sorry folks, most of this code is inline. Don't think I like it. #include #include #define DEG2RAD(Phi) (M_PI/180.0*Phi) #define RAD2DEG(Phi) (180.0/M_PI*Phi) class Vector; // The classes matrix and vector do exactly what one would expect from // them. class Matrix { private: double el[4][4]; public: Matrix() { for (int i=0; i<4; i++) for (int j=0; j<4; j++) el[i][j]=0.0; } void Matrix::operator=(const Matrix& a) { for (int i=0; i<4; i++) for (int j=0; j<4; j++) el[i][j]=a.el[i][j]; } Matrix(const Matrix& a) { for (int i=0; i<4; i++) for (int j=0; j<4; j++) el[i][j]=a.el[i][j]; } double& element(int idx1, int idx2) { return(el[idx1][idx2]); } void Print() { cout << "[ "; for (int i=0; i<4; i++) { cout << "[ "; for (int j=0; j<4; j++) cout << el[i][j] << (j<4-1?", ":""); cout << "]" << (i<4-1?"\n":""); } cout << "]\n"; } friend Matrix operator*(const Matrix& a, const Matrix& b); friend Matrix operator+(const Matrix& a, const Matrix& b); friend Vector operator*(const Matrix& a, const Vector& x); static Matrix TranslateMatrix(double x, double y, double z); static Matrix RotateXMatrix(double Phi); static Matrix RotateZMatrix(double Phi); static Matrix RotateYMatrix(double Phi); static Matrix ScaleMatrix(double x, double y, double z); }; Matrix operator*(const Matrix& a, const Matrix& b); Matrix operator+(const Matrix& a, const Matrix& b); Vector operator*(const Matrix& a, const Vector& x); class Vector { private: double el[4]; public: Vector(double x, double y, double z) { el[0]=x; el[1]=y; el[2]=z; el[3]=1; } Vector() { for (int i=0; i<3; i++) el[i]=0.0; el[3]=1.0; } Vector Vector::operator=(const Vector& a) { for (int i=0; i<4; i++) el[i]=a.el[i]; return a; } Vector(const Vector& a) { for (int i=0; i<4; i++) el[i]=a.el[i]; } double& operator[](const int index) { return(el[index]); } void Print() { cout << "[ "; for (int i=0; i<4; i++) cout << el[i] << (i<4-1?", ":""); cout << "]"; } void PrintPol() { cout << "[ " << RAD2DEG(this->Phi()) << ", " << RAD2DEG(this->Psi()) << ", " << this->Length() << " ]"; } double Length() { return sqrt(el[0]*el[0]+el[1]*el[1]+el[2]*el[2]); } double Phi() { return(atan2(el[1],el[0])); } double Psi() { return(atan2(el[2],sqrt(el[0]*el[0]+el[1]*el[1]))); } friend Vector operator*(const Matrix& a, const Vector& x); }; // Orbit translates a major circle lying in the aequatorial plane // so that it passes over the specified starting position at time 0 // and has an inclination at that point of dir degrees (90 = north). class Orbit { private: double duration; Vector startpos, posnow; double startdir; double elapsedtime; Matrix translate; public: Orbit(double dur, double pos_lat, double pos_long, double dir) { duration=dur; startpos=Vector(cos(DEG2RAD(pos_lat))*cos(DEG2RAD(pos_long)), cos(DEG2RAD(pos_lat))*sin(DEG2RAD(pos_long)), sin(DEG2RAD(pos_lat))); startdir=dir; elapsedtime=0; translate= Matrix::RotateZMatrix(startpos.Phi())* Matrix::RotateYMatrix(startpos.Psi())* Matrix::RotateXMatrix(-DEG2RAD(startdir)); this->Update(); } void SetElapsedTime(double t) { elapsedtime=t; this->Update(); } void WaitTime(double t) { elapsedtime+=t; this->Update(); } double Long() { double ret=RAD2DEG(posnow.Phi()); return(ret>0?ret:ret+360.0); } double Lat() { return(RAD2DEG(posnow.Psi())); } private: void Update() { if (duration == 0) return; posnow=translate* Matrix::RotateZMatrix(2.0*M_PI*elapsedtime/duration)* Vector(1,0,0); } }; ``````