001 package fr.isae.orbit;
002
003 import fr.isae.geometry.Point;
004 import java.util.ArrayList;
005
006 /**
007 * <code>OrbitePoints</code> modelise une orbite elliptique autour de
008 * la Terre avec lancement a l'equateur (argument du perigee nul) sous
009 * forme d'une sequence de points. On peut translater l'orbite, lui
010 * appliquer une homothetie, calculer sa circonference et trouver une
011 * approximation d'un vecteur tangent en un point.
012 *
013 * @author <a href="mailto:garion@isae.fr">Christophe Garion</a>
014 * @version 1.0
015 */
016 public class OrbitePoints {
017
018 private ArrayList<Point> points;
019 private Point centre;
020
021 /**
022 * Creer une instance de <code>OrbitePoints</code> en utilisant
023 * une orbite definie geometriquement.
024 *
025 * @param orbite l'orbite geometrique servant a calculer la
026 * sequence de points
027 * @param pasAngle le pas servant a incrementer l'angle pour
028 * le calcul des points
029 */
030 public OrbitePoints(Orbite orbite, double pasAngle) {
031 this.points = new ArrayList<Point>();
032
033 for (double angle = 0.0;
034 angle < 2.0 * Math.PI;
035 angle += pasAngle) {
036 this.points.add(orbite.calculerPointSurOrbite(angle));
037 }
038
039 this.centre = orbite.getFoyer();
040 this.centre.translater(-orbite.getC(), 0.0);
041 }
042
043 private OrbitePoints(ArrayList<Point> points, Point centre) {
044 this.points = new ArrayList<Point>();
045
046 for (Point p: points) {
047 this.points.add(p.clone());
048 }
049
050 this.centre = centre.clone();
051 }
052
053 /**
054 * Le nombre de points contenu dans l'orbite.
055 *
056 * @return le nombre de points stockes
057 */
058 public int getNbPoints() {
059 return this.points.size();
060 }
061
062 /**
063 * Retourner un point de l'orbite.
064 *
065 * @param i un index, compris entre <code>1</code> et
066 * <code>this.getNbPoints()</code>
067 * @return le ieme point dans la sequence
068 */
069 public Point getPoint(int i) {
070 return this.points.get(i - 1).clone();
071 }
072
073 /**
074 * Retourner le centre de l'orbite.
075 *
076 * @return une instance de <code>Point</code> qui est egale
077 * au centre de l'orbite. Il s'agit d'une copie et
078 * non pas d'une reference vers le point stocke
079 */
080 public Point getCentre() {
081 return this.centre.clone();
082 }
083
084 /**
085 * Retourner une approximation de la circonference de l'ellipse.
086 *
087 * @return une approximation de la circonference de l'ellipse
088 * calculee en utilisant le perimetre du polygone forme
089 * par les points
090 */
091 public double getCirconference() {
092 double c = 0;
093
094 for (int i = 1; i <= this.getNbPoints() - 1; i++) {
095 c += this.getPoint(i).distance(this.getPoint(i + 1));
096 }
097
098 c += this.getPoint(this.getNbPoints()).distance(this.getPoint(1));
099
100 return c;
101 }
102
103 /**
104 * Retourner une approximation du vecteur tangent en un point.
105 * On utilise le vecteur forme par le point precedent et le point
106 * suivant dans la liste de points. Le vecteur tangent renvoye est
107 * normalise.
108 *
109 * @param i un index, compris entre <code>1</code> et
110 * <code>this.getNbPoints()</code>
111 * @return une approximation du vecteur tangent
112 */
113 public Point getVecteurTangent(int i) {
114 Point precedent;
115 Point suivant;
116
117 if (i == 1) {
118 precedent = this.points.get(this.points.size() - 1);
119 } else {
120 precedent = this.points.get(i - 2);
121 }
122
123 if (i == this.points.size()) {
124 suivant = this.points.get(0);
125 } else {
126 suivant = this.points.get(i);
127 }
128
129 Point vecteur = new Point(suivant.getX() - precedent.getX(),
130 suivant.getY() - precedent.getY());
131 double longueur = vecteur.getModule();
132
133 vecteur.setX(vecteur.getX() / longueur);
134 vecteur.setY(vecteur.getY() / longueur);
135
136 return vecteur;
137 }
138
139 /**
140 * Translater l'orbite. Les points de l'orbite et le centre sont
141 * translates.
142 *
143 * @param dx l'abscisse du vecteur de translation
144 * @param dy l'ordonnee du vecteur de translation
145 */
146 public void translater(double dx, double dy) {
147 for (Point p: this.points) {
148 p.translater(dx, dy);
149 }
150
151 this.centre.translater(dx, dy);
152 }
153
154 /**
155 * Appliquer une homothetie a l'orbite. L'homothetie est effectuee
156 * par rapport au centre de l'ellipse.
157 *
158 * @param rapport le rapport d'homothetie
159 */
160 public void homothetie(double rapport) {
161 this.translater(-centre.getX(), -centre.getY());
162
163 // on effectue l'homothetie
164 for (Point p: this.points) {
165 p.setModule(p.getModule() * rapport);
166 }
167
168 this.translater(centre.getX(), centre.getY());
169 }
170
171 /**
172 * Verifier si deux orbites sont egales. Pour cela on verifie qu'elles
173 * ont le meme nombre de points, que tous leurs points sont egaux (au
174 * sens de <code>equals</code>) et que leurs centres sont egaux.
175 *
176 * @param o l'orbite dont on veut verifier si elle est egale a
177 * <code>this</code>
178 * @return un booleen qui est <code>true</code> si les deux orbites
179 * sont egales
180 */
181 public boolean equals(OrbitePoints o) {
182 if (this.points.size() != o.points.size()) {
183 return false;
184 }
185
186 if (!this.centre.equals(o.centre)) {
187 return false;
188 }
189
190 for (int i = 0; i < this.points.size(); i++) {
191 if (!this.points.get(i).equals(o.points.get(i))) {
192 return false;
193 }
194 }
195
196 return true;
197 }
198
199 /**
200 * Cloner une orbite. L'orbite obtenue est un objet different, mais est
201 * egale a <code>this</code>.
202 *
203 * @return un clone de <code>this</code>
204 */
205 public OrbitePoints clone() {
206 return new OrbitePoints(this.points, this.centre);
207 }
208
209 /**
210 * Representer l'orbite sous forme d'une chaine de caracteres. On affiche
211 * le centre de l'orbite puis 10 points parmi l'ensemble de points de
212 * l'orbite.
213 *
214 * @return une instance de <code>String</code> representant l'orbite
215 */
216 public String toString() {
217 String s = "centre : " + this.centre + "\n[";
218
219 int step = this.points.size() / 10;
220
221 for (int i = 0; i < 10; i++) {
222 s += this.points.get(i * step) + (i == 9 ? "\n]" : " ...\n");
223 }
224
225 return s + "]";
226 }
227 }
|