]> git.localhorst.tv Git - blobs.git/blob - tst/world/OrbitTest.cpp
ea13860ea3d0d6c4d904a009124d95d3b19a1e7a
[blobs.git] / tst / world / OrbitTest.cpp
1 #include "OrbitTest.hpp"
2
3 #include "../assert.hpp"
4
5 #include "const.hpp"
6 #include "world/Orbit.hpp"
7
8 CPPUNIT_TEST_SUITE_REGISTRATION(blobs::test::world::OrbitTest);
9
10 using blobs::world::Orbit;
11
12
13 namespace blobs {
14 namespace test {
15 namespace world {
16
17 void OrbitTest::setUp() {
18 }
19
20 void OrbitTest::tearDown() {
21 }
22
23
24 void OrbitTest::testDefaultOrbit() {
25         Orbit orbit;
26         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
27                 "wrong semi-major axis on default orbit",
28                 1.0, orbit.SemiMajorAxis(), std::numeric_limits<double>::epsilon()
29         );
30         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
31                 "wrong eccentricity on default orbit",
32                 0.0, orbit.Eccentricity(), std::numeric_limits<double>::epsilon()
33         );
34         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
35                 "wrong inclination on default orbit",
36                 0.0, orbit.Inclination(), std::numeric_limits<double>::epsilon()
37         );
38         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
39                 "wrong longitude of ascending node on default orbit",
40                 0.0, orbit.LongitudeAscending(), std::numeric_limits<double>::epsilon()
41         );
42         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
43                 "wrong argument of periapsis on default orbit",
44                 0.0, orbit.ArgumentPeriapsis(), std::numeric_limits<double>::epsilon()
45         );
46         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
47                 "wrong mean anomaly on default orbit",
48                 0.0, orbit.MeanAnomaly(), std::numeric_limits<double>::epsilon()
49         );
50
51         // reference direction is +X, so at t=0, the body should be
52         // at (sma,0,0) relative to its parent
53         glm::vec4 pos(orbit.Matrix(0.0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f));
54         AssertEqual(
55                 "wrong position at t=0",
56                 glm::vec3(1.0f, 0.0f, 0.0f),
57                 glm::vec3(pos) / pos.w
58         );
59
60         // at 90° position should be (0,0,sma) since the zero inclination
61         // reference plane is XZ and rotates counter-clockwise
62         pos = orbit.Matrix(PI_0p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
63         AssertEqual(
64                 "wrong position at t=90°",
65                 glm::vec3(0.0f, 0.0f, -1.0f),
66                 glm::vec3(pos) / pos.w
67         );
68
69         // at 180° position should be (-sma,0,0)
70         pos = orbit.Matrix(PI) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
71         AssertEqual(
72                 "wrong position at t=180°",
73                 glm::vec3(-1.0f, 0.0f, 0.0f),
74                 glm::vec3(pos) / pos.w
75         );
76
77         // at 270° position should be (0,0,-sma)
78         pos = orbit.Matrix(PI_1p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
79         AssertEqual(
80                 "wrong position at t=270°",
81                 glm::vec3(0.0f, 0.0f, 1.0f),
82                 glm::vec3(pos) / pos.w
83         );
84
85         // at 360° position should be (sma,0,0), the initial position
86         pos = orbit.Matrix(PI_2p0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
87         AssertEqual(
88                 "wrong position at t=360°",
89                 glm::vec3(1.0f, 0.0f, 0.0f),
90                 glm::vec3(pos) / pos.w
91         );
92 }
93
94 void OrbitTest::testSMA() {
95         Orbit orbit;
96         orbit.SemiMajorAxis(2.0);
97         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
98                 "wrong semi-major axis on orbit",
99                 2.0, orbit.SemiMajorAxis(), std::numeric_limits<double>::epsilon()
100         );
101
102         // reference direction is +X, so at t=0, the body should be
103         // at (sma,0,0) relative to its parent
104         glm::vec4 pos(orbit.Matrix(0.0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f));
105         AssertEqual(
106                 "wrong position at t=0",
107                 glm::vec3(2.0f, 0.0f, 0.0f),
108                 glm::vec3(pos) / pos.w
109         );
110
111         // at 90° position should be (0,0,sma) since the zero inclination
112         // reference plane is XZ and rotates counter-clockwise
113         pos = orbit.Matrix(PI_0p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
114         AssertEqual(
115                 "wrong position at t=90°",
116                 glm::vec3(0.0f, 0.0f, -2.0f),
117                 glm::vec3(pos) / pos.w
118         );
119
120         // at 180° position should be (-sma,0,0)
121         pos = orbit.Matrix(PI) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
122         AssertEqual(
123                 "wrong position at t=180°",
124                 glm::vec3(-2.0f, 0.0f, 0.0f),
125                 glm::vec3(pos) / pos.w
126         );
127
128         // at 270° position should be (0,0,-sma)
129         pos = orbit.Matrix(PI_1p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
130         AssertEqual(
131                 "wrong position at t=270°",
132                 glm::vec3(0.0f, 0.0f, 2.0f),
133                 glm::vec3(pos) / pos.w
134         );
135
136         // at 360° position should be (sma,0,0), the initial position
137         pos = orbit.Matrix(PI_2p0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
138         AssertEqual(
139                 "wrong position at t=360°",
140                 glm::vec3(2.0f, 0.0f, 0.0f),
141                 glm::vec3(pos) / pos.w
142         );
143 }
144
145 void OrbitTest::testEcc() {
146         Orbit orbit;
147         orbit.Eccentricity(0.5);
148         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
149                 "wrong eccentricity on orbit",
150                 0.5, orbit.Eccentricity(), std::numeric_limits<double>::epsilon()
151         );
152
153         glm::vec4 pos(orbit.Matrix(0.0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f));
154         AssertEqual(
155                 "wrong position at t=0",
156                 glm::vec3(0.5f, 0.0f, 0.0f),
157                 glm::vec3(pos) / pos.w
158         );
159
160         pos = orbit.Matrix(PI_0p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
161         AssertEqual(
162                 "wrong position at t=90°",
163                 glm::vec3(-0.935130834579468f, 0.0f, -0.779740869998932f),
164                 glm::vec3(pos) / pos.w
165         );
166
167         pos = orbit.Matrix(PI) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
168         AssertEqual(
169                 "wrong position at t=180°",
170                 glm::vec3(-1.5f, 0.0f, 0.0f),
171                 glm::vec3(pos) / pos.w
172         );
173
174         pos = orbit.Matrix(PI_1p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
175         AssertEqual(
176                 "wrong position at t=270°",
177                 glm::vec3(-0.935130834579468f, 0.0f, 0.779740869998932f),
178                 glm::vec3(pos) / pos.w
179         );
180
181         pos = orbit.Matrix(PI_2p0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
182         AssertEqual(
183                 "wrong position at t=360°",
184                 glm::vec3(0.5f, 0.0f, 0.0f),
185                 glm::vec3(pos) / pos.w
186         );
187 }
188
189 void OrbitTest::testInc() {
190         Orbit orbit;
191         orbit.Inclination(PI * 0.25); // 45°
192         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
193                 "wrong inclination on orbit",
194                 PI * 0.25, orbit.Inclination(), std::numeric_limits<double>::epsilon()
195         );
196
197         // inclination rotates counter clockwise around +X, so at t=0 should be
198         // at (sma,0,0) relative to its parent
199         glm::vec4 pos(orbit.Matrix(0.0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f));
200         AssertEqual(
201                 "wrong position at t=0",
202                 glm::vec3(1.0f, 0.0f, 0.0f),
203                 glm::vec3(pos) / pos.w
204         );
205
206         pos = orbit.Matrix(PI_0p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
207         AssertEqual(
208                 "wrong position at t=90°",
209                 glm::vec3(0.0f, 0.70710676908493f, -0.70710676908493f),
210                 glm::vec3(pos) / pos.w
211         );
212
213         pos = orbit.Matrix(PI) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
214         AssertEqual(
215                 "wrong position at t=180°",
216                 glm::vec3(-1.0f, 0.0f, 0.0f),
217                 glm::vec3(pos) / pos.w
218         );
219
220         pos = orbit.Matrix(PI_1p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
221         AssertEqual(
222                 "wrong position at t=270°",
223                 glm::vec3(0.0f, -0.70710676908493f, 0.70710676908493f),
224                 glm::vec3(pos) / pos.w
225         );
226
227         pos = orbit.Matrix(PI_2p0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
228         AssertEqual(
229                 "wrong position at t=360°",
230                 glm::vec3(1.0f, 0.0f, 0.0f),
231                 glm::vec3(pos) / pos.w
232         );
233 }
234
235 void OrbitTest::testLngAsc() {
236         Orbit orbit;
237         orbit.LongitudeAscending(PI * 0.25); // 45°
238         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
239                 "wrong longitude of ascending node on orbit",
240                 PI * 0.25, orbit.LongitudeAscending(), std::numeric_limits<double>::epsilon()
241         );
242         // using an inclination of 90° as well to make the rotation more apparent
243         orbit.Inclination(PI * 0.5);
244
245         // inclination rotates counter clockwise around +X, while LAN rotates it
246         // around +Y, so at t=0 should be at (sma*sin(45°),0,-sma*cos(45°))
247         glm::vec4 pos(orbit.Matrix(0.0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f));
248         AssertEqual(
249                 "wrong position at t=0",
250                 glm::vec3(0.70710676908493f, 0.0f, -0.70710676908493f),
251                 glm::vec3(pos) / pos.w
252         );
253
254         pos = orbit.Matrix(PI_0p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
255         AssertEqual(
256                 "wrong position at t=90°",
257                 glm::vec3(0.0f, 1.0f, 0.0f),
258                 glm::vec3(pos) / pos.w
259         );
260
261         pos = orbit.Matrix(PI) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
262         AssertEqual(
263                 "wrong position at t=180°",
264                 glm::vec3(-0.70710676908493f, 0.0f, 0.70710676908493f),
265                 glm::vec3(pos) / pos.w
266         );
267
268         pos = orbit.Matrix(PI_1p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
269         AssertEqual(
270                 "wrong position at t=270°",
271                 glm::vec3(0.0f, -1.0f, 0.0f),
272                 glm::vec3(pos) / pos.w
273         );
274
275         pos = orbit.Matrix(PI_2p0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
276         AssertEqual(
277                 "wrong position at t=360°",
278                 glm::vec3(0.70710676908493f, 0.0f, -0.70710676908493f),
279                 glm::vec3(pos) / pos.w
280         );
281 }
282
283 void OrbitTest::testArgPe() {
284         Orbit orbit;
285         orbit.ArgumentPeriapsis(PI * 0.25); // 45°
286         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
287                 "wrong argument of periapsis node on orbit",
288                 PI * 0.25, orbit.ArgumentPeriapsis(), std::numeric_limits<double>::epsilon()
289         );
290         // using an inclination of 90° as well to make the rotation more apparent
291         orbit.Inclination(PI * 0.5);
292
293         // inclination rotates counter clockwise around +X, while APe rotates it
294         // around +Y in the rotated coordinate system, so at t=0 should be at
295         // (sma*sin(45°),0,sma*cos(45°))
296         glm::vec4 pos(orbit.Matrix(0.0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f));
297         AssertEqual(
298                 "wrong position at t=0",
299                 glm::vec3(0.70710676908493f, 0.0f, 0.70710676908493f),
300                 glm::vec3(pos) / pos.w
301         );
302
303         pos = orbit.Matrix(PI_0p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
304         AssertEqual(
305                 "wrong position at t=90°",
306                 glm::vec3(0.0f, 1.0f, 0.0f),
307                 glm::vec3(pos) / pos.w
308         );
309
310         pos = orbit.Matrix(PI) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
311         AssertEqual(
312                 "wrong position at t=180°",
313                 glm::vec3(-0.70710676908493f, 0.0f, -0.70710676908493f),
314                 glm::vec3(pos) / pos.w
315         );
316
317         pos = orbit.Matrix(PI_1p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
318         AssertEqual(
319                 "wrong position at t=270°",
320                 glm::vec3(0.0f, -1.0f, 0.0f),
321                 glm::vec3(pos) / pos.w
322         );
323
324         pos = orbit.Matrix(PI_2p0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
325         AssertEqual(
326                 "wrong position at t=360°",
327                 glm::vec3(0.70710676908493f, 0.0f, 0.70710676908493f),
328                 glm::vec3(pos) / pos.w
329         );
330 }
331
332 void OrbitTest::testMnAn() {
333         Orbit orbit;
334         orbit.MeanAnomaly(PI * 0.25); // 45°
335         CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
336                 "wrong mean anomaly on default orbit",
337                 PI * 0.25, orbit.MeanAnomaly(), std::numeric_limits<double>::epsilon()
338         );
339
340         // mean anomaly just phase shifts the orbit
341         glm::vec4 pos(orbit.Matrix(0.0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f));
342         AssertEqual(
343                 "wrong position at t=0",
344                 glm::vec3(0.70710676908493f, 0.0f, -0.70710676908493f),
345                 glm::vec3(pos) / pos.w
346         );
347
348         // at 90° position should be (0,0,sma) since the zero inclination
349         // reference plane is XZ and rotates counter-clockwise
350         pos = orbit.Matrix(PI_0p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
351         AssertEqual(
352                 "wrong position at t=90°",
353                 glm::vec3(-0.70710676908493f, 0.0f, -0.70710676908493f),
354                 glm::vec3(pos) / pos.w
355         );
356
357         // at 180° position should be (-sma,0,0)
358         pos = orbit.Matrix(PI) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
359         AssertEqual(
360                 "wrong position at t=180°",
361                 glm::vec3(-0.70710676908493f, 0.0f, 0.70710676908493f),
362                 glm::vec3(pos) / pos.w
363         );
364
365         // at 270° position should be (0,0,-sma)
366         pos = orbit.Matrix(PI_1p5) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
367         AssertEqual(
368                 "wrong position at t=270°",
369                 glm::vec3(0.70710676908493f, 0.0f, 0.70710676908493f),
370                 glm::vec3(pos) / pos.w
371         );
372
373         // at 360° position should be (sma,0,0), the initial position
374         pos = orbit.Matrix(PI_2p0) * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f);
375         AssertEqual(
376                 "wrong position at t=360°",
377                 glm::vec3(0.70710676908493f, 0.0f, -0.70710676908493f),
378                 glm::vec3(pos) / pos.w
379         );
380 }
381
382 }
383 }
384 }