From 4b77ad6ff7582dabf507bca33eb71b0b3f8b3117 Mon Sep 17 00:00:00 2001 From: cinnaboot Date: Mon, 9 Feb 2026 09:06:02 -0500 Subject: [PATCH] Fix true anomaly trigger at periapsis Swap order in update_simulation() to check maneuvers before physics update. This ensures triggers fire at the correct position instead of after the spacecraft has moved past the trigger point. Also fix test config to avoid interference between time-based and true anomaly triggers. --- src/simulation.cpp | 2 +- tests/test_maneuver_planning.toml | 3 ++- tests/test_periapsis_burn.cpp | 18 +++--------------- 3 files changed, 6 insertions(+), 17 deletions(-) diff --git a/src/simulation.cpp b/src/simulation.cpp index a734ea4..3ff4df0 100644 --- a/src/simulation.cpp +++ b/src/simulation.cpp @@ -165,8 +165,8 @@ void update_soi(CelestialBody* body, CelestialBody* parent, double semi_major_ax void update_simulation(SimulationState* sim) { update_bodies_physics(sim); compute_global_coordinates(sim); - update_spacecraft_physics(sim); execute_pending_maneuvers(sim); + update_spacecraft_physics(sim); compute_spacecraft_globals(sim); sim->time += sim->dt; } diff --git a/tests/test_maneuver_planning.toml b/tests/test_maneuver_planning.toml index cdc98eb..b931d6e 100644 --- a/tests/test_maneuver_planning.toml +++ b/tests/test_maneuver_planning.toml @@ -33,9 +33,10 @@ parent_index = 1 orbit = { semi_major_axis = 6.771e6, eccentricity = 0.0, - true_anomaly = 0.0 + true_anomaly = 1.57 } # LEO orbit: 400 km altitude (Earth radius 6.371e6 m + 400e3 m) +# Start at true_anomaly = 1.57 (90 degrees) to avoid triggering immediately [[maneuvers]] name = "orbit_raise_1" diff --git a/tests/test_periapsis_burn.cpp b/tests/test_periapsis_burn.cpp index 80d6606..5131c2b 100644 --- a/tests/test_periapsis_burn.cpp +++ b/tests/test_periapsis_burn.cpp @@ -8,11 +8,9 @@ #include "../src/orbital_mechanics.h" #include -// This test documents a bug: when a true anomaly trigger is set to 0 (periapsis), -// the maneuver doesn't execute because the spacecraft moves past periapsis before -// the trigger check happens (trigger check occurs after physics update). -// The expected behavior is that the maneuver should execute when at periapsis. -TEST_CASE("Prograde burn at periapsis preserves periapsis distance", "[maneuver][periapsis][bug]") { +// Test prograde burn at periapsis (true anomaly = 0) +// Verifies that the maneuver executes correctly when starting at periapsis +TEST_CASE("Prograde burn at periapsis preserves periapsis distance", "[maneuver][periapsis]") { const double TIME_STEP = 60.0; SimulationState* sim = create_simulation(10, 10, 100, TIME_STEP); @@ -76,11 +74,6 @@ TEST_CASE("Prograde burn at periapsis raises apoapsis not periapsis", "[maneuver update_simulation(sim); - // Skip verification if bug not fixed - if (!sim->maneuvers[0].executed) { - SKIP("Maneuver didn't execute - known bug"); - } - double final_sma = craft->orbit.semi_major_axis; double final_ecc = craft->orbit.eccentricity; double final_periapsis = final_sma * (1.0 - final_ecc); @@ -107,11 +100,6 @@ TEST_CASE("Burn location equals new periapsis after prograde burn", "[maneuver][ update_simulation(sim); - // Skip verification if bug not fixed - if (!sim->maneuvers[0].executed) { - SKIP("Maneuver didn't execute - known bug"); - } - double final_periapsis = craft->orbit.semi_major_axis * (1.0 - craft->orbit.eccentricity); INFO("Burn radius: " << burn_radius);