1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.orekit.frames;
18
19
20 import org.hipparchus.geometry.euclidean.threed.Rotation;
21 import org.hipparchus.geometry.euclidean.threed.Vector3D;
22 import org.hipparchus.util.FastMath;
23 import org.hipparchus.util.MathUtils;
24 import org.junit.Assert;
25 import org.junit.Before;
26 import org.junit.Test;
27 import org.orekit.Utils;
28 import org.orekit.time.AbsoluteDate;
29 import org.orekit.time.DateComponents;
30 import org.orekit.time.TTScale;
31 import org.orekit.time.TimeComponents;
32 import org.orekit.time.TimeScale;
33 import org.orekit.time.TimeScalesFactory;
34 import org.orekit.time.UT1Scale;
35 import org.orekit.utils.Constants;
36 import org.orekit.utils.IERSConventions;
37 import org.orekit.utils.PVCoordinates;
38
39 public class ITRFProviderTest {
40
41 @Test
42 public void testTidalEffects() {
43
44 final Frame itrfWith = FramesFactory.getITRF(IERSConventions.IERS_2010, false);
45 final Frame itrfWithout = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
46 final AbsoluteDate date0 = new AbsoluteDate(2007, 10, 20, TimeScalesFactory.getUTC());
47
48 double minCorrection = Double.POSITIVE_INFINITY;
49 double maxCorrection = Double.NEGATIVE_INFINITY;
50 for (double dt = 0; dt < 3 * Constants.JULIAN_DAY; dt += 60) {
51 final AbsoluteDate date = date0.shiftedBy(dt);
52 final Transform t = itrfWith.getTransformTo(itrfWithout, date);
53 Assert.assertEquals(0, t.getTranslation().getNorm(), 1.0e-15);
54 final double milliarcSeconds = FastMath.toDegrees(t.getRotation().getAngle()) * 3600000.0;
55 minCorrection = FastMath.min(minCorrection, milliarcSeconds);
56 maxCorrection = FastMath.max(maxCorrection, milliarcSeconds);
57 }
58
59 Assert.assertEquals(0.064, minCorrection, 0.001);
60 Assert.assertEquals(0.613, maxCorrection, 0.001);
61
62 }
63
64 @Test
65 public void testAASReferenceLEO() {
66
67
68
69
70
71
72 Utils.setLoaders(IERSConventions.IERS_2010,
73 Utils.buildEOPList(IERSConventions.IERS_2010, ITRFVersion.ITRF_2008, new double[][] {
74 { 53098, -0.4399619, 0.0015563, -0.140682, 0.333309, Double.NaN, Double.NaN, -0.000199, -0.000252 },
75 { 53099, -0.4399619, 0.0015563, -0.140682, 0.333309, Double.NaN, Double.NaN, -0.000199, -0.000252 },
76 { 53100, -0.4399619, 0.0015563, -0.140682, 0.333309, Double.NaN, Double.NaN, -0.000199, -0.000252 },
77 { 53101, -0.4399619, 0.0015563, -0.140682, 0.333309, Double.NaN, Double.NaN, -0.000199, -0.000252 },
78 { 53102, -0.4399619, 0.0015563, -0.140682, 0.333309, Double.NaN, Double.NaN, -0.000199, -0.000252 },
79 { 53103, -0.4399619, 0.0015563, -0.140682, 0.333309, Double.NaN, Double.NaN, -0.000199, -0.000252 },
80 { 53104, -0.4399619, 0.0015563, -0.140682, 0.333309, Double.NaN, Double.NaN, -0.000199, -0.000252 },
81 { 53105, -0.4399619, 0.0015563, -0.140682, 0.333309, Double.NaN, Double.NaN, -0.000199, -0.000252 }
82 }));
83 AbsoluteDate t0 = new AbsoluteDate(new DateComponents(2004, 04, 06),
84 new TimeComponents(07, 51, 28.386009),
85 TimeScalesFactory.getUTC());
86
87
88 Frame itrfA = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
89 PVCoordinates pvITRF =
90 new PVCoordinates(new Vector3D(-1033479.3830, 7901295.2754, 6380356.5958),
91 new Vector3D(-3225.636520, -2872.451450, 5531.924446));
92
93
94 PVCoordinates pvGcrfIau2000A =
95 new PVCoordinates(new Vector3D(5102508.9579, 6123011.4038, 6378136.9252),
96 new Vector3D(-4743.220156, 790.536497, 5533.755728));
97 checkPV(pvGcrfIau2000A,
98 itrfA.getTransformTo(FramesFactory.getGCRF(), t0).transformPVCoordinates(pvITRF),
99 0.0192, 2.15e-5);
100
101 PVCoordinates pvEME2000EqA =
102 new PVCoordinates(new Vector3D(5102509.0383, 6123011.9758, 6378136.3118),
103 new Vector3D(-4743.219766, 790.536344, 5533.756084));
104 checkPV(pvEME2000EqA,
105 itrfA.getTransformTo(FramesFactory.getEME2000(), t0).transformPVCoordinates(pvITRF),
106 0.0191, 2.13e-5);
107
108 }
109
110 @Test
111 public void testAASReferenceGEO() {
112
113
114
115
116
117 Utils.setLoaders(IERSConventions.IERS_2010,
118 Utils.buildEOPList(IERSConventions.IERS_2010, ITRFVersion.ITRF_2008, new double[][] {
119 { 53153, -0.4709050, 0.0000000, -0.083853, 0.467217, Double.NaN, Double.NaN, -0.000199, -0.000252 },
120 { 53154, -0.4709050, 0.0000000, -0.083853, 0.467217, Double.NaN, Double.NaN, -0.000199, -0.000252 },
121 { 53155, -0.4709050, 0.0000000, -0.083853, 0.467217, Double.NaN, Double.NaN, -0.000199, -0.000252 },
122 { 53156, -0.4709050, 0.0000000, -0.083853, 0.467217, Double.NaN, Double.NaN, -0.000199, -0.000252 },
123 { 53157, -0.4709050, 0.0000000, -0.083853, 0.467217, Double.NaN, Double.NaN, -0.000199, -0.000252 },
124 { 53158, -0.4709050, 0.0000000, -0.083853, 0.467217, Double.NaN, Double.NaN, -0.000199, -0.000252 },
125 { 53159, -0.4709050, 0.0000000, -0.083853, 0.467217, Double.NaN, Double.NaN, -0.000199, -0.000252 },
126 { 53160, -0.4709050, 0.0000000, -0.083853, 0.467217, Double.NaN, Double.NaN, -0.000199, -0.000252 }
127 }));
128
129 AbsoluteDate t0 = new AbsoluteDate(new DateComponents(2004, 06, 01),
130 TimeComponents.H00,
131 TimeScalesFactory.getUTC());
132
133
134 Frame itrfA = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
135 PVCoordinates pvITRF =
136 new PVCoordinates(new Vector3D(24796919.2915, -34115870.9234, 10226.0621),
137 new Vector3D(-0.979178, -1.476538, -0.928776));
138
139 PVCoordinates pvGCRFiau2000A =
140 new PVCoordinates(new Vector3D(-40588150.3617, -11462167.0397, 27143.1974),
141 new Vector3D(834.787458, -2958.305691, -1.172993));
142 checkPV(pvGCRFiau2000A,
143 itrfA.getTransformTo(FramesFactory.getGCRF(), t0).transformPVCoordinates(pvITRF),
144 0.0806, 1.03e-4);
145
146 PVCoordinates pvEME2000EqA =
147 new PVCoordinates(new Vector3D(-40588149.5482, -11462169.9118, 27146.8462),
148 new Vector3D(834.787667, -2958.305632, -1.172963));
149 checkPV(pvEME2000EqA,
150 itrfA.getTransformTo(FramesFactory.getEME2000(), t0).transformPVCoordinates(pvITRF),
151 0.0806, 1.04e-4);
152
153 }
154
155 @Test
156 public void testAASReferenceGEODX0DY0() {
157
158
159
160
161
162 Utils.setLoaders(IERSConventions.IERS_2010,
163 Utils.buildEOPList(IERSConventions.IERS_2010, ITRFVersion.ITRF_2008, new double[][] {
164 { 53153, -0.4709050, 0.0000000, -0.083853, 0.467217, 0.0, 0.0, 0.0, 0.0 },
165 { 53154, -0.4709050, 0.0000000, -0.083853, 0.467217, 0.0, 0.0, 0.0, 0.0 },
166 { 53155, -0.4709050, 0.0000000, -0.083853, 0.467217, 0.0, 0.0, 0.0, 0.0 },
167 { 53156, -0.4709050, 0.0000000, -0.083853, 0.467217, 0.0, 0.0, 0.0, 0.0 },
168 { 53157, -0.4709050, 0.0000000, -0.083853, 0.467217, 0.0, 0.0, 0.0, 0.0 },
169 { 53158, -0.4709050, 0.0000000, -0.083853, 0.467217, 0.0, 0.0, 0.0, 0.0 },
170 { 53159, -0.4709050, 0.0000000, -0.083853, 0.467217, 0.0, 0.0, 0.0, 0.0 },
171 { 53160, -0.4709050, 0.0000000, -0.083853, 0.467217, 0.0, 0.0, 0.0, 0.0 }
172 }));
173
174 AbsoluteDate t0 = new AbsoluteDate(new DateComponents(2004, 06, 01),
175 TimeComponents.H00,
176 TimeScalesFactory.getUTC());
177
178
179 Frame itrfA = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
180 PVCoordinates pvITRF =
181 new PVCoordinates(new Vector3D(24796919.2915, -34115870.9234, 10226.0621),
182 new Vector3D(-0.979178, -1.476538, -0.928776));
183
184 PVCoordinates pvGCRFdx0dy0 =
185 new PVCoordinates(new Vector3D(-40588150.3643, -11462167.0302, 27143.1979),
186 new Vector3D(834.787457, -2958.305691, -1.172993));
187 checkPV(pvGCRFdx0dy0,
188 itrfA.getTransformTo(FramesFactory.getGCRF(), t0).transformPVCoordinates(pvITRF),
189 0.0505, 1.06e-4);
190
191 PVCoordinates pvEME2000EqA =
192 new PVCoordinates(new Vector3D(-40588149.5482, -11462169.9118, 27146.8462),
193 new Vector3D(834.787667, -2958.305632, -1.172963));
194 checkPV(pvEME2000EqA,
195 itrfA.getTransformTo(FramesFactory.getEME2000(), t0).transformPVCoordinates(pvITRF),
196 0.0603, 1.07e-4);
197
198 }
199
200 @Test
201 public void testSofaCookbook() {
202
203
204
205
206
207
208
209
210
211
212
213
214
215 Utils.setLoaders(IERSConventions.IERS_2010,
216 Utils.buildEOPList(IERSConventions.IERS_2010, ITRFVersion.ITRF_2008, new double[][] {
217 { 54192, -0.072073685, 1.4020, 0.0349282, 0.4833163, -Double.NaN, Double.NaN, 0.0001750, -0.0002259 },
218 { 54193, -0.072073685, 1.4020, 0.0349282, 0.4833163, -Double.NaN, Double.NaN, 0.0001750, -0.0002259 },
219 { 54194, -0.072073685, 1.4020, 0.0349282, 0.4833163, -Double.NaN, Double.NaN, 0.0001750, -0.0002259 },
220 { 54195, -0.072073685, 1.4020, 0.0349282, 0.4833163, -Double.NaN, Double.NaN, 0.0001750, -0.0002259 },
221 { 54196, -0.072073685, 1.4020, 0.0349282, 0.4833163, -Double.NaN, Double.NaN, 0.0001750, -0.0002259 },
222 { 54197, -0.072073685, 1.4020, 0.0349282, 0.4833163, -Double.NaN, Double.NaN, 0.0001750, -0.0002259 },
223 { 54198, -0.072073685, 1.4020, 0.0349282, 0.4833163, -Double.NaN, Double.NaN, 0.0001750, -0.0002259 },
224 { 54199, -0.072073685, 1.4020, 0.0349282, 0.4833163, -Double.NaN, Double.NaN, 0.0001750, -0.0002259 }
225 }));
226
227 EOPHistory eopHistory = FramesFactory.getEOPHistory(IERSConventions.IERS_2010, true);
228
229 TimeScale utc = TimeScalesFactory.getUTC();
230 TTScale tt = TimeScalesFactory.getTT();
231 UT1Scale ut1 = TimeScalesFactory.getUT1(eopHistory);
232 Frame gcrf = FramesFactory.getGCRF();
233 Frame itrf = FramesFactory.getITRF(IERSConventions.IERS_2010, true);
234 Frame gtod = itrf.getParent();
235 Frame tod = gtod.getParent();
236
237
238 AbsoluteDate date = new AbsoluteDate(new DateComponents(2007, 4, 5), TimeComponents.H12, utc);
239 Assert.assertEquals(0.50075444444444,
240 date.getComponents(tt).getTime().getSecondsInUTCDay() / Constants.JULIAN_DAY,
241 5.0e-15);
242 Assert.assertEquals(0.499999165813831,
243 date.getComponents(ut1).getTime().getSecondsInUTCDay() / Constants.JULIAN_DAY,
244 1.0e-15);
245
246
247 double era = IERSConventions.IERS_2010.getEarthOrientationAngleFunction(ut1).value(date);
248 Assert.assertEquals(13.318492966097 * 3600 * 1.0e6,
249 radToMicroAS(MathUtils.normalizeAngle(era, 0)),
250 0.0022);
251
252
253 Rotation refNPB = new Rotation(new double[][] {
254 { +0.999999746339445, -0.000000005138721, -0.000712264730182 },
255 { -0.000000026475329, +0.999999999014975, -0.000044385242666 },
256 { +0.000712264729708, +0.000044385250265, +0.999999745354420 }
257 }, 1.0e-13);
258 Rotation npb = gcrf.getTransformTo(tod, date).getRotation();
259 Assert.assertEquals(0.0, radToMicroAS(Rotation.distance(refNPB, npb)), 0.31);
260
261
262 Rotation refWithoutPolarMotion = new Rotation(new double[][] {
263 { +0.973104317573104, +0.230363826247808, -0.000703332818915 },
264 { -0.230363798804281, +0.973104570735550, +0.000120888549767 },
265 { +0.000712264729708, +0.000044385250265, +0.999999745354420 }
266 }, 1.0e-13);
267 Rotation withoutPM = gcrf.getTransformTo(gtod, date).getRotation();
268 Assert.assertEquals(0.0, radToMicroAS(Rotation.distance(refWithoutPolarMotion, withoutPM)), 0.31);
269
270
271 Rotation refWithPolarMotion = new Rotation(new double[][] {
272 { +0.973104317697512, +0.230363826239227, -0.000703163482268 },
273 { -0.230363800456136, +0.973104570632777, +0.000118545366806 },
274 { +0.000711560162777, +0.000046626403835, +0.999999745754024 }
275 }, 1.0e-13);
276 Rotation withPM = gcrf.getTransformTo(itrf, date).getRotation();
277 Assert.assertEquals(0.0, radToMicroAS(Rotation.distance(refWithPolarMotion, withPM)), 0.31);
278
279 }
280
281 @Before
282 public void setUp() {
283 Utils.setDataRoot("compressed-data");
284 }
285
286 private void checkPV(PVCoordinates reference, PVCoordinates result,
287 double expectedPositionError, double expectedVelocityError) {
288
289 Vector3D dP = result.getPosition().subtract(reference.getPosition());
290 Vector3D dV = result.getVelocity().subtract(reference.getVelocity());
291 Assert.assertEquals(expectedPositionError, dP.getNorm(), 0.01 * expectedPositionError);
292 Assert.assertEquals(expectedVelocityError, dV.getNorm(), 0.01 * expectedVelocityError);
293 }
294
295 double radToMicroAS(double deltaRad) {
296 return deltaRad * 1.0e6 / Constants.ARC_SECONDS_TO_RADIANS;
297 }
298
299 }