1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.orekit.propagation;
18
19 import org.hipparchus.analysis.differentiation.Gradient;
20 import org.hipparchus.analysis.differentiation.GradientField;
21 import org.hipparchus.linear.MatrixUtils;
22 import org.hipparchus.linear.RealMatrix;
23 import org.hipparchus.util.MathArrays;
24 import org.orekit.frames.LOF;
25 import org.orekit.frames.LOFType;
26 import org.orekit.orbits.FieldOrbit;
27 import org.orekit.orbits.Orbit;
28 import org.orekit.orbits.OrbitType;
29 import org.orekit.orbits.PositionAngleBased;
30 import org.orekit.orbits.PositionAngleType;
31 import org.orekit.utils.DerivativeStateUtils;
32
33
34
35
36
37
38
39
40
41 class LinearKeplerianCovarianceMapper {
42
43
44 private static final LOF DEFAULT_LOF = LOFType.QSW;
45
46
47 private final Orbit orbit;
48
49
50 private final StateCovariance stateCovariance;
51
52
53 private final StateCovariance convertedCovariance;
54
55
56
57
58
59
60 LinearKeplerianCovarianceMapper(final Orbit orbit, final StateCovariance stateCovariance) {
61 this.orbit = orbit;
62 this.stateCovariance = stateCovariance;
63 this.convertedCovariance = changeCovarianceBefore();
64 }
65
66
67
68
69
70
71
72 StateCovariance map(final Orbit targetOrbit) {
73 final PositionAngleType positionAngleType = findPositionAngleType();
74 final StateCovariance shiftedCovariance = shiftCovariance(orbit, convertedCovariance, targetOrbit,
75 positionAngleType);
76 return changeCovarianceAfter(shiftedCovariance, targetOrbit, positionAngleType);
77 }
78
79
80
81
82
83 private StateCovariance changeCovarianceBefore() {
84 final PositionAngleType positionAngleType = findPositionAngleType();
85 final StateCovariance intermediateCovariance = stateCovariance.changeCovarianceFrame(orbit, orbit.getFrame());
86 return intermediateCovariance.changeCovarianceType(orbit, orbit.getType(), positionAngleType);
87 }
88
89
90
91
92
93 private PositionAngleType findPositionAngleType() {
94 if (orbit instanceof PositionAngleBased<?>) {
95 final PositionAngleBased<?> positionAngleBased = (PositionAngleBased<?>) orbit;
96 return positionAngleBased.getCachedPositionAngleType();
97 } else {
98
99 return null;
100 }
101 }
102
103
104
105
106
107
108
109
110
111 private static StateCovariance shiftCovariance(final Orbit orbit, final StateCovariance convertedCovariance,
112 final Orbit nextOrbit, final PositionAngleType positionAngleType) {
113 final RealMatrix initialCovarianceMatrix = convertedCovariance.getMatrix();
114 final GradientField gradientField = GradientField.getField(6);
115 final FieldOrbit<Gradient> fieldOrbit = DerivativeStateUtils.buildOrbitGradient(gradientField, orbit);
116 final FieldOrbit<Gradient> shiftedFieldOrbit = fieldOrbit.shiftedBy(nextOrbit.durationFrom(orbit));
117 final Gradient[] orbitalArray = MathArrays.buildArray(gradientField, 6);
118 shiftedFieldOrbit.getType().mapOrbitToArray(shiftedFieldOrbit, positionAngleType, orbitalArray, null);
119 final RealMatrix stateTransitionMatrix = MatrixUtils.createRealMatrix(6, 6);
120 for (int i = 0; i < orbitalArray.length; i++) {
121 stateTransitionMatrix.setRow(i, orbitalArray[i].getGradient());
122 }
123 final RealMatrix covarianceMatrix = stateTransitionMatrix.multiply(initialCovarianceMatrix
124 .multiplyTransposed(stateTransitionMatrix));
125 return new StateCovariance(covarianceMatrix, nextOrbit.getDate(), nextOrbit.getFrame(),
126 nextOrbit.getType(), positionAngleType);
127 }
128
129
130
131
132
133
134
135
136 private StateCovariance changeCovarianceAfter(final StateCovariance covarianceToConvert, final Orbit nextOrbit,
137 final PositionAngleType positionAngleType) {
138 final Orbit propagatedOrbit = orbit.shiftedBy(nextOrbit.durationFrom(orbit));
139 final LOF lof = stateCovariance.getLOF() == null ? DEFAULT_LOF : stateCovariance.getLOF();
140 final StateCovariance cartesianCovarianceInFrame = covarianceToConvert.changeCovarianceType(propagatedOrbit,
141 OrbitType.CARTESIAN, positionAngleType);
142 final StateCovariance covarianceInLof = cartesianCovarianceInFrame.changeCovarianceFrame(propagatedOrbit, lof);
143 if (stateCovariance.getLOF() != null) {
144 return covarianceInLof;
145 } else {
146
147 final StateCovariance covariance = covarianceInLof.changeCovarianceFrame(nextOrbit, nextOrbit.getFrame());
148 if (stateCovariance.getOrbitType() != OrbitType.CARTESIAN) {
149 return covariance.changeCovarianceType(propagatedOrbit, stateCovariance.getOrbitType(), positionAngleType);
150 } else {
151 return covariance;
152 }
153 }
154 }
155 }