1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.orekit.forces.gravity;
18
19 import java.util.List;
20 import java.util.stream.Collectors;
21
22 import org.hipparchus.Field;
23 import org.hipparchus.analysis.differentiation.DerivativeStructure;
24 import org.hipparchus.analysis.differentiation.Gradient;
25 import org.hipparchus.analysis.differentiation.GradientField;
26 import org.hipparchus.geometry.euclidean.threed.FieldVector3D;
27 import org.hipparchus.geometry.euclidean.threed.Vector3D;
28 import org.hipparchus.ode.AbstractIntegrator;
29 import org.hipparchus.ode.nonstiff.DormandPrince853Integrator;
30 import org.hipparchus.util.Binary64;
31 import org.hipparchus.util.Binary64Field;
32 import org.hipparchus.util.FastMath;
33 import org.junit.jupiter.api.Assertions;
34 import org.junit.jupiter.api.BeforeEach;
35 import org.junit.jupiter.api.Test;
36 import org.orekit.Utils;
37 import org.orekit.attitudes.AttitudeProvider;
38 import org.orekit.attitudes.LofOffset;
39 import org.orekit.bodies.CelestialBodyFactory;
40 import org.orekit.forces.AbstractLegacyForceModelTest;
41 import org.orekit.forces.ForceModel;
42 import org.orekit.forces.gravity.potential.GravityFieldFactory;
43 import org.orekit.forces.gravity.potential.NormalizedSphericalHarmonicsProvider;
44 import org.orekit.frames.Frame;
45 import org.orekit.frames.FramesFactory;
46 import org.orekit.frames.LOFType;
47 import org.orekit.orbits.KeplerianOrbit;
48 import org.orekit.orbits.Orbit;
49 import org.orekit.orbits.OrbitType;
50 import org.orekit.orbits.PositionAngleType;
51 import org.orekit.propagation.FieldSpacecraftState;
52 import org.orekit.propagation.SpacecraftState;
53 import org.orekit.propagation.ToleranceProvider;
54 import org.orekit.propagation.events.DateDetector;
55 import org.orekit.propagation.events.EventDetector;
56 import org.orekit.propagation.events.EventDetectorsProvider;
57 import org.orekit.propagation.events.FieldDateDetector;
58 import org.orekit.propagation.events.FieldEventDetector;
59 import org.orekit.propagation.numerical.NumericalPropagator;
60 import org.orekit.time.AbsoluteDate;
61 import org.orekit.time.FieldAbsoluteDate;
62 import org.orekit.time.TimeScale;
63 import org.orekit.time.TimeScalesFactory;
64 import org.orekit.time.TimeStamped;
65 import org.orekit.time.UT1Scale;
66 import org.orekit.utils.Constants;
67 import org.orekit.utils.IERSConventions;
68 import org.orekit.utils.ParameterDriver;
69
70
71 public class SolidTidesTest extends AbstractLegacyForceModelTest {
72
73 private static final AttitudeProvider DEFAULT_LAW = Utils.defaultLaw();
74
75 @Override
76 protected FieldVector3D<DerivativeStructure> accelerationDerivatives(final ForceModel forceModel,
77 final FieldSpacecraftState<DerivativeStructure> state) {
78 try {
79 java.lang.reflect.Field attractionModelField = SolidTides.class.getDeclaredField("attractionModel");
80 attractionModelField.setAccessible(true);
81 ForceModel attractionModel = (ForceModel) attractionModelField.get(forceModel);
82 Field<DerivativeStructure> field = state.getDate().getField();
83 return attractionModel.acceleration(state, attractionModel.getParameters(field, state.getDate()));
84
85 } catch (IllegalArgumentException | IllegalAccessException | NoSuchFieldException | SecurityException e) {
86 return null;
87 }
88 }
89
90 @Override
91 protected FieldVector3D<Gradient> accelerationDerivativesGradient(final ForceModel forceModel,
92 final FieldSpacecraftState<Gradient> state) {
93 try {
94 final FieldVector3D<Gradient> position = state.getPVCoordinates().getPosition();
95 java.lang.reflect.Field attractionModelField = SolidTides.class.getDeclaredField("attractionModel");
96 attractionModelField.setAccessible(true);
97 ForceModel attractionModel = (ForceModel) attractionModelField.get(forceModel);
98 final int freeParameters = position.getX().getFreeParameters();
99 Field<Gradient> field = GradientField.getField(freeParameters);
100 return attractionModel.acceleration(state, attractionModel.getParameters(field, state.getDate()));
101
102 } catch (IllegalArgumentException | IllegalAccessException | NoSuchFieldException | SecurityException e) {
103 return null;
104 }
105 }
106
107 @Test
108 void testDefaultInterpolation() {
109
110 IERSConventions conventions = IERSConventions.IERS_2010;
111 Frame eme2000 = FramesFactory.getEME2000();
112 Frame itrf = FramesFactory.getITRF(conventions, true);
113 TimeScale utc = TimeScalesFactory.getUTC();
114 UT1Scale ut1 = TimeScalesFactory.getUT1(conventions, true);
115 NormalizedSphericalHarmonicsProvider gravityField =
116 GravityFieldFactory.getNormalizedProvider(5, 5);
117
118
119 AbsoluteDate date = new AbsoluteDate(1970, 07, 01, 13, 59, 27.816, utc);
120 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
121 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
122 0, PositionAngleType.MEAN, eme2000, date,
123 gravityField.getMu());
124
125 AbsoluteDate target = date.shiftedBy(7 * Constants.JULIAN_DAY);
126 ForceModel hf = new HolmesFeatherstoneAttractionModel(itrf, gravityField);
127 SpacecraftState raw = propagate(orbit, target, hf,
128 new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
129 gravityField.getTideSystem(), true, Double.NaN, -1,
130 conventions, ut1,
131 CelestialBodyFactory.getSun(),
132 CelestialBodyFactory.getMoon()));
133 SpacecraftState interpolated = propagate(orbit, target, hf,
134 new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
135 gravityField.getTideSystem(),
136 conventions, ut1,
137 CelestialBodyFactory.getSun(),
138 CelestialBodyFactory.getMoon()));
139 Assertions.assertEquals(0.0,
140 Vector3D.distance(raw.getPosition(),
141 interpolated.getPosition()),
142 2.1e-5);
143
144 }
145
146 @Test
147 void testTideEffect1996() {
148 Frame eme2000 = FramesFactory.getEME2000();
149 TimeScale utc = TimeScalesFactory.getUTC();
150 AbsoluteDate date = new AbsoluteDate(2003, 07, 01, 13, 59, 27.816, utc);
151 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
152 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
153 0, PositionAngleType.MEAN, eme2000, date,
154 Constants.EIGEN5C_EARTH_MU);
155 doTestTideEffect(orbit, IERSConventions.IERS_1996, 44.09481, 0.00000);
156 }
157
158 @Test
159 void testTideEffect2003WithinAnnualPoleRange() {
160 Frame eme2000 = FramesFactory.getEME2000();
161 TimeScale utc = TimeScalesFactory.getUTC();
162 AbsoluteDate date = new AbsoluteDate(1969, 07, 01, 13, 59, 27.816, utc);
163 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
164 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
165 0, PositionAngleType.MEAN, eme2000, date,
166 Constants.EIGEN5C_EARTH_MU);
167 doTestTideEffect(orbit, IERSConventions.IERS_2003, 73.14011, 0.87360);
168 }
169
170 @Test
171 void testTideEffect2003AfterAnnualPoleRange() {
172 Frame eme2000 = FramesFactory.getEME2000();
173 TimeScale utc = TimeScalesFactory.getUTC();
174 AbsoluteDate date = new AbsoluteDate(2003, 07, 01, 13, 59, 27.816, utc);
175 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
176 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
177 0, PositionAngleType.MEAN, eme2000, date,
178 Constants.EIGEN5C_EARTH_MU);
179 doTestTideEffect(orbit, IERSConventions.IERS_2003, 44.24999, 0.61752);
180 }
181
182 @Test
183 void testTideEffect2010BeforePoleModelChange() {
184 Frame eme2000 = FramesFactory.getEME2000();
185 TimeScale utc = TimeScalesFactory.getUTC();
186 AbsoluteDate date = new AbsoluteDate(2003, 07, 01, 13, 59, 27.816, utc);
187 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
188 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
189 0, PositionAngleType.MEAN, eme2000, date,
190 Constants.EIGEN5C_EARTH_MU);
191 doTestTideEffect(orbit, IERSConventions.IERS_2010, 44.25001, 0.70710);
192 }
193
194 @Test
195 void testTideEffect2010AfterModelChange() {
196 Frame eme2000 = FramesFactory.getEME2000();
197 TimeScale utc = TimeScalesFactory.getUTC();
198 AbsoluteDate date = new AbsoluteDate(2964, 8, 12, 11, 30, 00.000, utc);
199 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
200 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
201 0, PositionAngleType.MEAN, eme2000, date,
202 Constants.EIGEN5C_EARTH_MU);
203 doTestTideEffect(orbit, IERSConventions.IERS_2010, 24.02815, 30.37047);
204 }
205
206 @Test
207 void testStateJacobianVs80ImplementationNoPoleTide()
208 {
209 Frame eme2000 = FramesFactory.getEME2000();
210 TimeScale utc = TimeScalesFactory.getUTC();
211 AbsoluteDate date = new AbsoluteDate(2964, 8, 12, 11, 30, 00.000, utc);
212 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
213 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
214 0, PositionAngleType.MEAN, eme2000, date,
215 Constants.EIGEN5C_EARTH_MU);
216 Frame itrf = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
217 UT1Scale ut1 = TimeScalesFactory.getUT1(IERSConventions.IERS_2010, true);
218 NormalizedSphericalHarmonicsProvider gravityField =
219 GravityFieldFactory.getNormalizedProvider(5, 5);
220
221 ForceModel forceModel = new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
222 gravityField.getTideSystem(), false,
223 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
224 IERSConventions.IERS_2010, ut1,
225 CelestialBodyFactory.getSun(),
226 CelestialBodyFactory.getMoon());
227 Assertions.assertTrue(forceModel.dependsOnPositionOnly());
228
229 checkStateJacobianVs80Implementation(new SpacecraftState(orbit), forceModel,
230 new LofOffset(orbit.getFrame(), LOFType.LVLH_CCSDS),
231 2.0e-15, false);
232
233 }
234
235 @Test
236 void testStateJacobianVs80ImplementationGradientNoPoleTide()
237 {
238 Frame eme2000 = FramesFactory.getEME2000();
239 TimeScale utc = TimeScalesFactory.getUTC();
240 AbsoluteDate date = new AbsoluteDate(2964, 8, 12, 11, 30, 00.000, utc);
241 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
242 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
243 0, PositionAngleType.MEAN, eme2000, date,
244 Constants.EIGEN5C_EARTH_MU);
245 Frame itrf = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
246 UT1Scale ut1 = TimeScalesFactory.getUT1(IERSConventions.IERS_2010, true);
247 NormalizedSphericalHarmonicsProvider gravityField =
248 GravityFieldFactory.getNormalizedProvider(5, 5);
249
250 ForceModel forceModel = new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
251 gravityField.getTideSystem(), false,
252 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
253 IERSConventions.IERS_2010, ut1,
254 CelestialBodyFactory.getSun(),
255 CelestialBodyFactory.getMoon());
256 Assertions.assertTrue(forceModel.dependsOnPositionOnly());
257
258 checkStateJacobianVs80ImplementationGradient(new SpacecraftState(orbit), forceModel,
259 new LofOffset(orbit.getFrame(), LOFType.LVLH_CCSDS),
260 2.0e-15, false);
261
262 }
263
264 @Test
265 void testStateJacobianVs80ImplementationPoleTide()
266 {
267 Frame eme2000 = FramesFactory.getEME2000();
268 TimeScale utc = TimeScalesFactory.getUTC();
269 AbsoluteDate date = new AbsoluteDate(2964, 8, 12, 11, 30, 00.000, utc);
270 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
271 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
272 0, PositionAngleType.MEAN, eme2000, date,
273 Constants.EIGEN5C_EARTH_MU);
274 Frame itrf = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
275 UT1Scale ut1 = TimeScalesFactory.getUT1(IERSConventions.IERS_2010, true);
276 NormalizedSphericalHarmonicsProvider gravityField =
277 GravityFieldFactory.getNormalizedProvider(5, 5);
278
279 ForceModel forceModel = new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
280 gravityField.getTideSystem(), true,
281 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
282 IERSConventions.IERS_2010, ut1,
283 CelestialBodyFactory.getSun(),
284 CelestialBodyFactory.getMoon());
285
286 checkStateJacobianVs80Implementation(new SpacecraftState(orbit), forceModel,
287 new LofOffset(orbit.getFrame(), LOFType.LVLH_CCSDS),
288 2.0e-15, false);
289
290 }
291
292 @Test
293 void testStateJacobianVs80ImplementationGradientPoleTide()
294 {
295 Frame eme2000 = FramesFactory.getEME2000();
296 TimeScale utc = TimeScalesFactory.getUTC();
297 AbsoluteDate date = new AbsoluteDate(2964, 8, 12, 11, 30, 00.000, utc);
298 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
299 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
300 0, PositionAngleType.MEAN, eme2000, date,
301 Constants.EIGEN5C_EARTH_MU);
302 Frame itrf = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
303 UT1Scale ut1 = TimeScalesFactory.getUT1(IERSConventions.IERS_2010, true);
304 NormalizedSphericalHarmonicsProvider gravityField =
305 GravityFieldFactory.getNormalizedProvider(5, 5);
306
307 ForceModel forceModel = new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
308 gravityField.getTideSystem(), true,
309 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
310 IERSConventions.IERS_2010, ut1,
311 CelestialBodyFactory.getSun(),
312 CelestialBodyFactory.getMoon());
313
314 checkStateJacobianVs80ImplementationGradient(new SpacecraftState(orbit), forceModel,
315 new LofOffset(orbit.getFrame(), LOFType.LVLH_CCSDS),
316 2.0e-15, false);
317
318 }
319
320 @Test
321 void testStateJacobianVsFiniteDifferencesNoPoleTide()
322 {
323 Frame eme2000 = FramesFactory.getEME2000();
324 TimeScale utc = TimeScalesFactory.getUTC();
325 AbsoluteDate date = new AbsoluteDate(2964, 8, 12, 11, 30, 00.000, utc);
326 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
327 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
328 0, PositionAngleType.MEAN, eme2000, date,
329 Constants.EIGEN5C_EARTH_MU);
330 Frame itrf = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
331 UT1Scale ut1 = TimeScalesFactory.getUT1(IERSConventions.IERS_2010, true);
332 NormalizedSphericalHarmonicsProvider gravityField =
333 GravityFieldFactory.getNormalizedProvider(5, 5);
334
335 ForceModel forceModel = new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
336 gravityField.getTideSystem(), false,
337 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
338 IERSConventions.IERS_2010, ut1,
339 CelestialBodyFactory.getSun(),
340 CelestialBodyFactory.getMoon());
341
342 checkStateJacobianVsFiniteDifferences(new SpacecraftState(orbit), forceModel, DEFAULT_LAW,
343 10.0, 2.0e-10, false);
344
345 }
346
347 @Test
348 void testStateJacobianVsFiniteDifferencesGradientNoPoleTide()
349 {
350 Frame eme2000 = FramesFactory.getEME2000();
351 TimeScale utc = TimeScalesFactory.getUTC();
352 AbsoluteDate date = new AbsoluteDate(2964, 8, 12, 11, 30, 00.000, utc);
353 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
354 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
355 0, PositionAngleType.MEAN, eme2000, date,
356 Constants.EIGEN5C_EARTH_MU);
357 Frame itrf = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
358 UT1Scale ut1 = TimeScalesFactory.getUT1(IERSConventions.IERS_2010, true);
359 NormalizedSphericalHarmonicsProvider gravityField =
360 GravityFieldFactory.getNormalizedProvider(5, 5);
361
362 ForceModel forceModel = new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
363 gravityField.getTideSystem(), false,
364 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
365 IERSConventions.IERS_2010, ut1,
366 CelestialBodyFactory.getSun(),
367 CelestialBodyFactory.getMoon());
368
369 checkStateJacobianVsFiniteDifferencesGradient(new SpacecraftState(orbit), forceModel, DEFAULT_LAW,
370 10.0, 2.0e-10, false);
371
372 }
373
374 @Test
375 void testStateJacobianVsFiniteDifferencesPoleTide()
376 {
377 Frame eme2000 = FramesFactory.getEME2000();
378 TimeScale utc = TimeScalesFactory.getUTC();
379 AbsoluteDate date = new AbsoluteDate(2964, 8, 12, 11, 30, 00.000, utc);
380 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
381 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
382 0, PositionAngleType.MEAN, eme2000, date,
383 Constants.EIGEN5C_EARTH_MU);
384 Frame itrf = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
385 UT1Scale ut1 = TimeScalesFactory.getUT1(IERSConventions.IERS_2010, true);
386 NormalizedSphericalHarmonicsProvider gravityField =
387 GravityFieldFactory.getNormalizedProvider(5, 5);
388
389 ForceModel forceModel = new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
390 gravityField.getTideSystem(), true,
391 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
392 IERSConventions.IERS_2010, ut1,
393 CelestialBodyFactory.getSun(),
394 CelestialBodyFactory.getMoon());
395
396 checkStateJacobianVsFiniteDifferences(new SpacecraftState(orbit), forceModel, DEFAULT_LAW,
397 10.0, 2.0e-10, false);
398
399 }
400
401 @Test
402 void testStateJacobianVsFiniteDifferencesGradientPoleTide()
403 {
404 Frame eme2000 = FramesFactory.getEME2000();
405 TimeScale utc = TimeScalesFactory.getUTC();
406 AbsoluteDate date = new AbsoluteDate(2964, 8, 12, 11, 30, 00.000, utc);
407 Orbit orbit = new KeplerianOrbit(7201009.7124401, 1e-3, FastMath.toRadians(98.7),
408 FastMath.toRadians(93.0), FastMath.toRadians(15.0 * 22.5),
409 0, PositionAngleType.MEAN, eme2000, date,
410 Constants.EIGEN5C_EARTH_MU);
411 Frame itrf = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
412 UT1Scale ut1 = TimeScalesFactory.getUT1(IERSConventions.IERS_2010, true);
413 NormalizedSphericalHarmonicsProvider gravityField =
414 GravityFieldFactory.getNormalizedProvider(5, 5);
415
416 ForceModel forceModel = new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
417 gravityField.getTideSystem(), true,
418 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
419 IERSConventions.IERS_2010, ut1,
420 CelestialBodyFactory.getSun(),
421 CelestialBodyFactory.getMoon());
422
423 checkStateJacobianVsFiniteDifferencesGradient(new SpacecraftState(orbit), forceModel, DEFAULT_LAW,
424 10.0, 2.0e-10, false);
425
426 }
427
428
429
430
431 @Test
432 void testGetEventDetectors() {
433
434
435
436
437 final IERSConventions conventions = IERSConventions.IERS_2010;
438 final Frame itrf = FramesFactory.getITRF(conventions, true);
439 final AbsoluteDate t0 = AbsoluteDate.ARBITRARY_EPOCH;
440
441 final NormalizedSphericalHarmonicsProvider gravityField =
442 GravityFieldFactory.getNormalizedProvider(5, 5);
443 final UT1Scale ut1 = TimeScalesFactory.getUT1(conventions, true);
444
445
446 final ForceModel solidTidesModel = new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
447 gravityField.getTideSystem(), false,
448 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
449 conventions, ut1,
450 CelestialBodyFactory.getSun(),
451 CelestialBodyFactory.getMoon());
452
453
454 List<EventDetector> detectors = solidTidesModel.getEventDetectors().collect(Collectors.toList());
455 List<FieldEventDetector<Binary64>> fieldDetectors = solidTidesModel.getFieldEventDetectors(Binary64Field.getInstance()).collect(Collectors.toList());
456
457
458 Assertions.assertTrue(detectors.isEmpty());
459 Assertions.assertTrue(fieldDetectors.isEmpty());
460
461
462 final List<ParameterDriver> drivers = solidTidesModel.getParametersDrivers();
463
464 for (final ParameterDriver driver : drivers) {
465 driver.addSpanAtDate(t0);
466 }
467
468 detectors = solidTidesModel.getEventDetectors().collect(Collectors.toList());
469 DateDetector dateDetector = (DateDetector) detectors.get(0);
470 List<TimeStamped> dates = dateDetector.getDates();
471
472 fieldDetectors = solidTidesModel.getFieldEventDetectors(Binary64Field.getInstance()).collect(Collectors.toList());
473 FieldDateDetector<Binary64> fieldDateDetector = (FieldDateDetector<Binary64>) fieldDetectors.get(0);
474 FieldAbsoluteDate<Binary64> fieldDate = fieldDateDetector.getDate();
475
476
477 Assertions.assertFalse(detectors.isEmpty());
478 Assertions.assertEquals(1, detectors.size());
479 Assertions.assertTrue(detectors.get(0) instanceof DateDetector);
480
481 Assertions.assertEquals(1, dates.size());
482 Assertions.assertEquals(0., dates.get(0).durationFrom(t0), 0.);
483
484 Assertions.assertFalse(fieldDetectors.isEmpty());
485 Assertions.assertEquals(1, fieldDetectors.size());
486 Assertions.assertTrue(fieldDetectors.get(0) instanceof FieldDateDetector);
487 Assertions.assertEquals(0., fieldDate.durationFrom(t0).getReal(), 0.);
488 }
489
490 private void doTestTideEffect(Orbit orbit, IERSConventions conventions, double delta1, double delta2) {
491
492 Frame itrf = FramesFactory.getITRF(conventions, true);
493 UT1Scale ut1 = TimeScalesFactory.getUT1(conventions, true);
494 NormalizedSphericalHarmonicsProvider gravityField =
495 GravityFieldFactory.getNormalizedProvider(5, 5);
496
497
498
499 AbsoluteDate target = orbit.getDate().shiftedBy(7 * Constants.JULIAN_DAY);
500 ForceModel hf = new HolmesFeatherstoneAttractionModel(itrf, gravityField);
501 SpacecraftState noTides = propagate(orbit, target, hf);
502 SpacecraftState solidTidesNoPoleTide = propagate(orbit, target, hf,
503 new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
504 gravityField.getTideSystem(), false,
505 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
506 conventions, ut1,
507 CelestialBodyFactory.getSun(),
508 CelestialBodyFactory.getMoon()));
509 SpacecraftState solidTidesPoleTide = propagate(orbit, target, hf,
510 new SolidTides(itrf, gravityField.getAe(), gravityField.getMu(),
511 gravityField.getTideSystem(), true,
512 SolidTides.DEFAULT_STEP, SolidTides.DEFAULT_POINTS,
513 conventions, ut1,
514 CelestialBodyFactory.getSun(),
515 CelestialBodyFactory.getMoon()));
516 Assertions.assertEquals(delta1,
517 Vector3D.distance(noTides.getPosition(),
518 solidTidesNoPoleTide.getPosition()),
519 0.01);
520 Assertions.assertEquals(delta2,
521 Vector3D.distance(solidTidesNoPoleTide.getPosition(),
522 solidTidesPoleTide.getPosition()),
523 0.01);
524
525 }
526
527 private SpacecraftState propagate(Orbit orbit, AbsoluteDate target, ForceModel... forceModels)
528 {
529 double[][] tolerances = ToleranceProvider.getDefaultToleranceProvider(10.).getTolerances(orbit, OrbitType.KEPLERIAN);
530 AbstractIntegrator integrator = new DormandPrince853Integrator(1.0e-3, 300, tolerances[0], tolerances[1]);
531 NumericalPropagator propagator = new NumericalPropagator(integrator);
532 for (ForceModel forceModel : forceModels) {
533 propagator.addForceModel(forceModel);
534 }
535 propagator.setInitialState(new SpacecraftState(orbit));
536 return propagator.propagate(target);
537 }
538
539 @BeforeEach
540 public void setUp() {
541 Utils.setDataRoot("regular-data:potential/icgem-format");
542 }
543
544 }