limit_accel_xy() splits the acceleration command into along-track and
cross-track components using the normalised velocity, and prioritises the
cross-track component when the command saturates the maximum lean angle.
As the velocity vector rotates through zero (e.g. a hard stick reversal in
Loiter, where forward speed passes through zero before reversing) the unit
velocity spins rapidly. With any small residual lateral velocity (wind crab,
residual velocity from prior manoeuvring) this re-projects the saturated
longitudinal braking command onto a rapidly rotating axis and emits a large
lateral acceleration spike, seen as a roll wobble at the moment of the stop
and as a PSCE.TAE spike at each PSCN.VN zero crossing.
Fade the cross-track prioritisation out to a direction-preserving magnitude
limit below LIMIT_ACCEL_XY_MIN_SPEED_MS (1 m/s). Above that speed behaviour is
unchanged, so path/corner tracking is unaffected. The limiter only acts when
the command saturates the lean-angle limit, and stationary hold already used
the isotropic branch, so precision position hold is unaffected.
Adds a regression test sweeping velocity through zero and asserting no lateral
acceleration is injected.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Polygon_closest_distance_line()'s fallback loop (used whenever the
query line does not cross the polygon) iterated i=0..N-2 and never
tested the closing edge V[N-1]->V[0]. Every other polygon helper in
this file (Polygon_outside, Polygon_intersects) and the sibling
Polygon_closest_distance_point() already wrap around to include this
edge; this function was the one left behind.
The only caller, AP_OABendyRuler::calc_margin_from_inclusion_and_exclusion_polygons(),
passes in AC_Fence polygons in their raw unclosed form (no duplicated
closing vertex), so in real fences this is a genuine edge that was
silently skipped, causing the reported clearance/margin to the fence
boundary to be overestimated near that edge.
Fix mirrors the existing wrap-around pattern from Polygon_intersects()
a few lines above in the same file. Added a regression test using a
simple square fence to confirm the closing edge is now considered and
that behaviour near unaffected edges is unchanged.
Assisted-by: Claude:claude-sonnet-5