1 /* Copyright 2002-2026 CS GROUP
2 * Licensed to CS GROUP (CS) under one or more
3 * contributor license agreements. See the NOTICE file distributed with
4 * this work for additional information regarding copyright ownership.
5 * CS licenses this file to You under the Apache License, Version 2.0
6 * (the "License"); you may not use this file except in compliance with
7 * the License. You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17
18 package org.orekit.files.ccsds.ndm.odm.ocm;
19
20 import java.util.ArrayList;
21 import java.util.List;
22
23 import org.hipparchus.linear.DefaultRealMatrixChangingVisitor;
24 import org.hipparchus.linear.MatrixUtils;
25 import org.hipparchus.linear.RealMatrix;
26 import org.orekit.files.ccsds.definitions.CcsdsFrameMapper;
27 import org.orekit.files.ccsds.ndm.CommonPhysicalProperties;
28 import org.orekit.frames.Frame;
29 import org.orekit.time.AbsoluteDate;
30 import org.orekit.utils.Constants;
31
32 /** Spacecraft physical properties.
33 * @author Luc Maisonobe
34 * @since 11.0
35 */
36 public class OrbitPhysicalProperties extends CommonPhysicalProperties {
37
38 /** Satellite manufacturer name. */
39 private String manufacturer;
40
41 /** Bus model name. */
42 private String busModel;
43
44 /** Other space objects this object is docked to. */
45 private List<String> dockedWith;
46
47 /** Attitude-independent drag cross-sectional area, not already into attitude-dependent area along OEB. */
48 private double dragConstantArea;
49
50 /** Nominal drag coefficient. */
51 private double dragCoefficient;
52
53 /** Drag coefficient 1σ uncertainty. */
54 private double dragUncertainty;
55
56 /** Total mass at beginning of life. */
57 private double initialWetMass;
58
59 /** Total mass at T₀. */
60 private double wetMass;
61
62 /** Mass without propellant. */
63 private double dryMass;
64
65 /** Minimum cross-sectional area for collision probability estimation purposes. */
66 private double minAreaForCollisionProbability;
67
68 /** Maximum cross-sectional area for collision probability estimation purposes. */
69 private double maxAreaForCollisionProbability;
70
71 /** Typical (50th percentile) cross-sectional area for collision probability estimation purposes. */
72 private double typAreaForCollisionProbability;
73
74 /** Attitude-independent SRP area, not already into attitude-dependent area along OEB. */
75 private double srpConstantArea;
76
77 /** Nominal SRP coefficient. */
78 private double srpCoefficient;
79
80 /** SRP coefficient 1σ uncertainty. */
81 private double srpUncertainty;
82
83 /** Attitude control mode. */
84 private String attitudeControlMode;
85
86 /** Type of actuator for attitude control. */
87 private String attitudeActuatorType;
88
89 /** Accuracy of attitude knowledge. */
90 private double attitudeKnowledgeAccuracy;
91
92 /** Accuracy of attitude control. */
93 private double attitudeControlAccuracy;
94
95 /** Overall accuracy of spacecraft to maintain attitude. */
96 private double attitudePointingAccuracy;
97
98 /** Average average frequency of orbit or attitude maneuvers (in SI units, hence per second). */
99 private double maneuversFrequency;
100
101 /** Maximum composite thrust the spacecraft can accomplish. */
102 private double maxThrust;
103
104 /** Total ΔV capability at beginning of life. */
105 private double bolDv;
106
107 /** Total ΔV remaining for spacecraft. */
108 private double remainingDv;
109
110 /** Inertia matrix. */
111 private final RealMatrix inertiaMatrix;
112
113 /**
114 * Simple constructor.
115 *
116 * @param epochT0 T0 epoch from file metadata
117 * @param frameMapper for creating a {@link Frame}.
118 * @since 13.1.5
119 */
120 public OrbitPhysicalProperties(final AbsoluteDate epochT0,
121 final CcsdsFrameMapper frameMapper) {
122
123 // Call to CommonPhysicalProperties constructor
124 super(frameMapper);
125
126 // we don't call the setXxx() methods in order to avoid
127 // calling refuseFurtherComments as a side effect
128 dockedWith = new ArrayList<>();
129 // 502.0-B-3 (page 6-22) says these drag values are optional.
130 dragConstantArea = Double.NaN;
131 dragCoefficient = Double.NaN;
132 dragUncertainty = Double.NaN;
133 // 502.0-B-3 (page 6-25) says these SRP values are optional.
134 srpCoefficient = Double.NaN;
135 srpConstantArea = Double.NaN;
136 srpUncertainty = Double.NaN;
137 initialWetMass = Double.NaN;
138 wetMass = Double.NaN;
139 dryMass = Double.NaN;
140 minAreaForCollisionProbability = Double.NaN;
141 maxAreaForCollisionProbability = Double.NaN;
142 typAreaForCollisionProbability = Double.NaN;
143 attitudeKnowledgeAccuracy = Double.NaN;
144 attitudeControlAccuracy = Double.NaN;
145 attitudePointingAccuracy = Double.NaN;
146 maneuversFrequency = Double.NaN;
147 maxThrust = Double.NaN;
148 bolDv = Double.NaN;
149 remainingDv = Double.NaN;
150 // 502.0-B-3 (page 6-27) says these inertia values are optional.
151 inertiaMatrix = MatrixUtils.createRealMatrix(3, 3);
152 // set all values to NaN
153 inertiaMatrix.walkInOptimizedOrder(new DefaultRealMatrixChangingVisitor() {
154 @Override
155 public double visit(final int i, final int j, final double v) {
156 return Double.NaN;
157 }
158 });
159 }
160
161 /** Get manufacturer name.
162 * @return manufacturer name
163 */
164 public String getManufacturer() {
165 return manufacturer;
166 }
167
168 /** Set manufacturer name.
169 * @param manufacturer manufacturer name
170 */
171 public void setManufacturer(final String manufacturer) {
172 refuseFurtherComments();
173 this.manufacturer = manufacturer;
174 }
175
176 /** Get the bus model name.
177 * @return bus model name
178 */
179 public String getBusModel() {
180 return busModel;
181 }
182
183 /** Set the bus model name.
184 * @param busModel bus model name
185 */
186 public void setBusModel(final String busModel) {
187 refuseFurtherComments();
188 this.busModel = busModel;
189 }
190
191 /** Get the other space objects this object is docked to.
192 * @return the oother space objects this object is docked to
193 */
194 public List<String> getDockedWith() {
195 return dockedWith;
196 }
197
198 /** Set the other space objects this object is docked to.
199 * @param dockedWith the other space objects this object is docked to
200 */
201 public void setDockedWith(final List<String> dockedWith) {
202 refuseFurtherComments();
203 this.dockedWith = dockedWith;
204 }
205
206 /** Get the attitude-independent drag cross-sectional area, not already into attitude-dependent area along OEB.
207 * @return attitude-independent drag cross-sectional area, not already into attitude-dependent area along OEB
208 */
209 public double getDragConstantArea() {
210 return dragConstantArea;
211 }
212
213 /** Set the attitude-independent drag cross-sectional area, not already into attitude-dependent area along OEB.
214 * @param dragConstantArea attitude-independent drag cross-sectional area, not already into attitude-dependent area along OEB
215 */
216 public void setDragConstantArea(final double dragConstantArea) {
217 refuseFurtherComments();
218 this.dragConstantArea = dragConstantArea;
219 }
220
221 /** Get the nominal drag coefficient.
222 * @return the nominal drag coefficient
223 */
224 public double getDragCoefficient() {
225 return dragCoefficient;
226 }
227
228 /** Set the the nominal drag coefficient.
229 * @param dragCoefficient the nominal drag coefficient
230 */
231 public void setDragCoefficient(final double dragCoefficient) {
232 refuseFurtherComments();
233 this.dragCoefficient = dragCoefficient;
234 }
235
236 /** Get the drag coefficient 1σ uncertainty.
237 * @return drag coefficient 1σ uncertainty (in %)
238 */
239 public double getDragUncertainty() {
240 return dragUncertainty;
241 }
242
243 /** Set the drag coefficient 1σ uncertainty.
244 * @param dragUncertainty drag coefficient 1σ uncertainty (in %)
245 */
246 public void setDragUncertainty(final double dragUncertainty) {
247 refuseFurtherComments();
248 this.dragUncertainty = dragUncertainty;
249 }
250
251 /** Get the total mass at beginning of life.
252 * @return total mass at beginning of life
253 */
254 public double getInitialWetMass() {
255 return initialWetMass;
256 }
257
258 /** Set the total mass at beginning of life.
259 * @param initialWetMass total mass at beginning of life
260 */
261 public void setInitialWetMass(final double initialWetMass) {
262 refuseFurtherComments();
263 this.initialWetMass = initialWetMass;
264 }
265
266 /** Get the total mass at T₀.
267 * @return total mass at T₀
268 */
269 public double getWetMass() {
270 return wetMass;
271 }
272
273 /** Set the total mass at T₀.
274 * @param wetMass total mass at T₀
275 */
276 public void setWetMass(final double wetMass) {
277 refuseFurtherComments();
278 this.wetMass = wetMass;
279 }
280
281 /** Get the mass without propellant.
282 * @return mass without propellant
283 */
284 public double getDryMass() {
285 return dryMass;
286 }
287
288 /** Set the mass without propellant.
289 * @param dryMass mass without propellant
290 */
291 public void setDryMass(final double dryMass) {
292 refuseFurtherComments();
293 this.dryMass = dryMass;
294 }
295
296 /** Get the minimum cross-sectional area for collision probability estimation purposes.
297 * @return minimum cross-sectional area for collision probability estimation purposes
298 */
299 public double getMinAreaForCollisionProbability() {
300 return minAreaForCollisionProbability;
301 }
302
303 /** Set the minimum cross-sectional area for collision probability estimation purposes.
304 * @param minAreaForCollisionProbability minimum cross-sectional area for collision probability estimation purposes
305 */
306 public void setMinAreaForCollisionProbability(final double minAreaForCollisionProbability) {
307 refuseFurtherComments();
308 this.minAreaForCollisionProbability = minAreaForCollisionProbability;
309 }
310
311 /** Get the maximum cross-sectional area for collision probability estimation purposes.
312 * @return maximum cross-sectional area for collision probability estimation purposes
313 */
314 public double getMaxAreaForCollisionProbability() {
315 return maxAreaForCollisionProbability;
316 }
317
318 /** Set the maximum cross-sectional area for collision probability estimation purposes.
319 * @param maxAreaForCollisionProbability maximum cross-sectional area for collision probability estimation purposes
320 */
321 public void setMaxAreaForCollisionProbability(final double maxAreaForCollisionProbability) {
322 refuseFurtherComments();
323 this.maxAreaForCollisionProbability = maxAreaForCollisionProbability;
324 }
325
326 /** Get the typical (50th percentile) cross-sectional area for collision probability estimation purposes.
327 * @return typical (50th percentile) cross-sectional area for collision probability estimation purposes
328 */
329 public double getTypAreaForCollisionProbability() {
330 return typAreaForCollisionProbability;
331 }
332
333 /** Get the typical (50th percentile) cross-sectional area for collision probability estimation purposes.
334 * @param typAreaForCollisionProbability typical (50th percentile) cross-sectional area for collision probability estimation purposes
335 */
336 public void setTypAreaForCollisionProbability(final double typAreaForCollisionProbability) {
337 refuseFurtherComments();
338 this.typAreaForCollisionProbability = typAreaForCollisionProbability;
339 }
340
341 /** Get the attitude-independent SRP area, not already into attitude-dependent area along OEB.
342 * @return attitude-independent SRP area, not already into attitude-dependent area along OEB
343 */
344 public double getSrpConstantArea() {
345 return srpConstantArea;
346 }
347
348 /** Set the attitude-independent SRP area, not already into attitude-dependent area along OEB.
349 * @param srpConstantArea attitude-independent SRP area, not already into attitude-dependent area along OEB
350 */
351 public void setSrpConstantArea(final double srpConstantArea) {
352 refuseFurtherComments();
353 this.srpConstantArea = srpConstantArea;
354 }
355
356 /** Get the nominal SRP coefficient.
357 * @return nominal SRP coefficient
358 */
359 public double getSrpCoefficient() {
360 return srpCoefficient;
361 }
362
363 /** Set the nominal SRP coefficient.
364 * @param srpCoefficient nominal SRP coefficient
365 */
366 public void setSrpCoefficient(final double srpCoefficient) {
367 refuseFurtherComments();
368 this.srpCoefficient = srpCoefficient;
369 }
370
371 /** Get the SRP coefficient 1σ uncertainty.
372 * @return SRP coefficient 1σ uncertainty
373 */
374 public double getSrpUncertainty() {
375 return srpUncertainty;
376 }
377
378 /** Set the SRP coefficient 1σ uncertainty.
379 * @param srpUncertainty SRP coefficient 1σ uncertainty.
380 */
381 public void setSrpUncertainty(final double srpUncertainty) {
382 refuseFurtherComments();
383 this.srpUncertainty = srpUncertainty;
384 }
385
386 /** Get the attitude control mode.
387 * @return attitude control mode
388 */
389 public String getAttitudeControlMode() {
390 return attitudeControlMode;
391 }
392
393 /** Set the attitude control mode.
394 * @param attitudeControlMode attitude control mode
395 */
396 public void setAttitudeControlMode(final String attitudeControlMode) {
397 refuseFurtherComments();
398 this.attitudeControlMode = attitudeControlMode;
399 }
400
401 /** Get the type of actuator for attitude control.
402 * @return type of actuator for attitude control
403 */
404 public String getAttitudeActuatorType() {
405 return attitudeActuatorType;
406 }
407
408 /** Set the type of actuator for attitude control.
409 * @param attitudeActuatorType type of actuator for attitude control
410 */
411 public void setAttitudeActuatorType(final String attitudeActuatorType) {
412 refuseFurtherComments();
413 this.attitudeActuatorType = attitudeActuatorType;
414 }
415
416 /** Get the accuracy of attitude knowledge.
417 * @return accuracy of attitude knowledge
418 */
419 public double getAttitudeKnowledgeAccuracy() {
420 return attitudeKnowledgeAccuracy;
421 }
422
423 /** Set the accuracy of attitude knowledge.
424 * @param attitudeKnowledgeAccuracy accuracy of attitude knowledge
425 */
426 public void setAttitudeKnowledgeAccuracy(final double attitudeKnowledgeAccuracy) {
427 refuseFurtherComments();
428 this.attitudeKnowledgeAccuracy = attitudeKnowledgeAccuracy;
429 }
430
431 /** Get the accuracy of attitude control.
432 * @return accuracy of attitude control
433 */
434 public double getAttitudeControlAccuracy() {
435 return attitudeControlAccuracy;
436 }
437
438 /** Set the accuracy of attitude control.
439 * @param attitudeControlAccuracy accuracy of attitude control
440 */
441 public void setAttitudeControlAccuracy(final double attitudeControlAccuracy) {
442 refuseFurtherComments();
443 this.attitudeControlAccuracy = attitudeControlAccuracy;
444 }
445
446 /** Get the overall accuracy of spacecraft to maintain attitude.
447 * @return overall accuracy of spacecraft to maintain attitude
448 */
449 public double getAttitudePointingAccuracy() {
450 return attitudePointingAccuracy;
451 }
452
453 /** Set the overall accuracy of spacecraft to maintain attitude.
454 * @param attitudePointingAccuracy overall accuracy of spacecraft to maintain attitude
455 */
456 public void setAttitudePointingAccuracy(final double attitudePointingAccuracy) {
457 refuseFurtherComments();
458 this.attitudePointingAccuracy = attitudePointingAccuracy;
459 }
460
461 /** Get the average number of orbit or attitude maneuvers per year.
462 * @return average number of orbit or attitude maneuvers per year.
463 */
464 public double getManeuversPerYear() {
465 return maneuversFrequency * Constants.JULIAN_YEAR;
466 }
467
468 /** Get the average frequency of orbit or attitude maneuvers (in SI units, hence per second).
469 * @return average frequency of orbit or attitude maneuvers (in SI units, hence per second).
470 */
471 public double getManeuversFrequency() {
472 return maneuversFrequency;
473 }
474
475 /** Set the average frequency of orbit or attitude maneuvers (in SI units, hence per second).
476 * @param maneuversFrequency average frequency of orbit or attitude (in SI units, hence per second).
477 */
478 public void setManeuversFrequency(final double maneuversFrequency) {
479 refuseFurtherComments();
480 this.maneuversFrequency = maneuversFrequency;
481 }
482
483 /** Get the maximum composite thrust the spacecraft can accomplish.
484 * @return maximum composite thrust the spacecraft can accomplish
485 */
486 public double getMaxThrust() {
487 return maxThrust;
488 }
489
490 /** Set the maximum composite thrust the spacecraft can accomplish.
491 * @param maxThrust maximum composite thrust the spacecraft can accomplish
492 */
493 public void setMaxThrust(final double maxThrust) {
494 refuseFurtherComments();
495 this.maxThrust = maxThrust;
496 }
497
498 /** Get the total ΔV capability at beginning of life.
499 * @return total ΔV capability at beginning of life
500 */
501 public double getBolDv() {
502 return bolDv;
503 }
504
505 /** Set the total ΔV capability at beginning of life.
506 * @param bolDv total ΔV capability at beginning of life
507 */
508 public void setBolDv(final double bolDv) {
509 refuseFurtherComments();
510 this.bolDv = bolDv;
511 }
512
513 /** Get the total ΔV remaining for spacecraft.
514 * @return total ΔV remaining for spacecraft
515 */
516 public double getRemainingDv() {
517 return remainingDv;
518 }
519
520 /** Set the total ΔV remaining for spacecraft.
521 * @param remainingDv total ΔV remaining for spacecraft
522 */
523 public void setRemainingDv(final double remainingDv) {
524 refuseFurtherComments();
525 this.remainingDv = remainingDv;
526 }
527
528 /** Get the inertia matrix.
529 * @return the inertia matrix
530 */
531 public RealMatrix getInertiaMatrix() {
532 return inertiaMatrix;
533 }
534
535 /** Set an entry in the inertia matrix.
536 * <p>
537 * Both I(j, k) and I(k, j) are set.
538 * </p>
539 * @param j row index (must be between 0 and 3 (inclusive)
540 * @param k column index (must be between 0 and 3 (inclusive)
541 * @param entry value of the matrix entry
542 */
543 public void setInertiaMatrixEntry(final int j, final int k, final double entry) {
544 refuseFurtherComments();
545 inertiaMatrix.setEntry(j, k, entry);
546 inertiaMatrix.setEntry(k, j, entry);
547 }
548
549 }