1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
//! Bevy `Component` newtypes for derived states — orbital elements,
//! Euler angles, LVLH frame, geodetic state, solar beta angle, and
//! Earth lighting (eclipse / albedo) — plus the per-state config
//! components that gate computation.
use ;
use *;
// ── Derived State Configuration ──
/// Configuration for orbital elements computation.
///
/// The `gravity_source` identity resolves to a registered source entity
/// (issue #668), which is queried for `GravitySourceC` to obtain `mu`.
/// Presence of this component + `OrbitalElementsC` on an entity enables
/// per-step orbital elements computation in `AstrodynSet::DerivedState`.
/// Configuration for Euler angle decomposition.
///
/// Presence of this component + `EulerAnglesC` on an entity enables
/// per-step Euler angle computation in `AstrodynSet::DerivedState`.
/// Configuration for geodetic state computation.
///
/// The `planet` entity is queried for `PlanetFixedRotationC<P>` to obtain
/// the inertial→planet-fixed rotation each step; the ellipsoid radii
/// `r_eq` / `r_pol` are carried directly on this config (mirroring the
/// runner's `body.geodetic_planet: (idx, r_eq, r_pol)` shape) so a
/// scenario whose source entity does not carry the planet shape — e.g.
/// the `SimulationBuilder::populate_app` path, which inserts only the
/// gravity/rotation components on the source — can still drive
/// geodetic computation. Presence of this component + `GeodeticStateC`
/// on an entity enables per-step geodetic computation in
/// `AstrodynSet::DerivedState`.
// ── Derived State Outputs ──
/// Orbital elements computed each step.
///
/// Written by `orbital_elements_system` for entities that also have
/// `OrbitalElementsConfigC`. Generic over the planet `P` whose
/// gravitational parameter `mu` was used in the conversion. Every call
/// site must pin `P` explicitly — there is no fallback.
;
/// Euler angles `[phi, theta, psi]` computed each step.
///
/// Written by `euler_angles_system` for entities that also have
/// `EulerAnglesConfigC`. Each component is a [`Angle`] (uom radian-backed
/// scalar) so consumers don't have to remember the radian convention.
;
/// LVLH (Local Vertical Local Horizontal) frame computed each step.
///
/// Presence of this component alone enables computation — no separate
/// config component needed (only requires translational state).
;
/// Geodetic state (latitude, longitude, altitude) computed each step.
///
/// Written by `geodetic_system` for entities that also have `GeodeticConfigC`.
///
/// # Numerical stability at the poles
///
/// The inner [`astrodyn::GeodeticState`] inherits the longitude
/// instability of the underlying chart: at 89.8° latitude, longitude has
/// roughly `3.7e-6 rad/m` sensitivity to planet-fixed position drift, and
/// at the pole itself the kernel assigns `longitude = 0.0` by convention
/// because all meridians converge. Mission code reading this component
/// near the poles should treat longitude as low-confidence (the Tier 3 NED
/// suite uses `~3.3e-5 rad` polar tolerance vs `~6.5e-8 rad` inclined-orbit
/// tolerance). This is fundamental geometry, not a bug — see
/// [`astrodyn::GeodeticState`] for the full rationale.
;
/// Solar beta angle (radians) computed each step.
///
/// Presence of this component alone enables computation — requires a
/// `SunMarker` entity to exist in the world.
;
/// Configuration for Earth lighting (eclipse/albedo) computation.
///
/// Requires `SunMarker` and `MoonMarker` entities to exist in the world.
/// Presence of this component + `EarthLightingStateC` on an entity enables
/// per-step earth lighting computation in `AstrodynSet::DerivedState`.
/// Earth lighting state computed each step.
///
/// Written by `earth_lighting_system` for entities that also have
/// `EarthLightingConfigC`.
;