Skip to content

Fix branch 3 direction#241

Merged
1-Bart-1 merged 2 commits into
mainfrom
fix-projection-radial
May 28, 2026
Merged

Fix branch 3 direction#241
1-Bart-1 merged 2 commits into
mainfrom
fix-projection-radial

Conversation

@1-Bart-1
Copy link
Copy Markdown
Member

@1-Bart-1 1-Bart-1 commented May 25, 2026

Summary

Fixes a bug in the Lamb-Oseen-style core regularization (Branch 3 of velocity_3D_bound_vortex\! and velocity_3D_trailing_vortex_semiinfinite\!). The projection onto the core boundary was being done in the azimuthal direction (r1×r0 / |r1×r0|) instead of the radial direction. This made the regularized induced velocity inside the core point in the wrong direction — typically perpendicular to where it should point.

The bug is pre-existing and shared with the Python implementation (Vortex-Step-Method/src/VSM/core/Filament.py); both inherit it from the original KiteAeroDyn-style implementation referenced as Damiani et al. The Julia tests didn't catch it because they were calibrated under the bug. The Python tests all set core_radius_fraction = 1e-20, which makes Branch 3 effectively never fire, so the verification suite never exercised the regularization code path.

The fix

A vortex's induced velocity is purely azimuthal (perpendicular to both the axis and the radial direction) — this is a direct consequence of Biot-Savart and axial symmetry. Inside the core, the standard regularization (Rankine / Scully / Lamb-Oseen profiles) projects the field point radially outward onto the core boundary, evaluates the inviscid Biot-Savart velocity there, and scales by d_perp / epsilon (linear ramp from zero on axis to peak at boundary).

The fix replaces the azimuthal projection direction with the actual radial direction — the perpendicular component of r1 to the filament axis r0:

r_rad = r1 - (r1·r0/|r0|²) · r0
r1_proj = (axial component) + epsilon · r_rad / |r_rad|

Same fix in both velocity_3D_bound_vortex\! and velocity_3D_trailing_vortex_semiinfinite\!.

References for the radial-projection convention:

  • Saffman, P.G. (1992). Vortex Dynamics, §1.5
  • Katz, J. & Plotkin, A. (2001). Low-Speed Aerodynamics, §10.4.5
  • van Garrel, A. (2003). ECN-C-03-079, §3.3
  • Cottet, G.-H. & Koumoutsakos, P.D. (2000). Vortex Methods: Theory and Practice, Ch. 4

Tests

New tests on test/filament/test_bound_filament.jl that exercise the regularization code path properly:

  • "Velocity is azimuthal" — at multiple radii (in-core and outside-core) and azimuthal positions, asserts induced velocity is perpendicular to both the filament axis and the radial direction. Old code returned velocities with a nonzero radial component.
  • "Solid-body rotation inside core" — magnitudes scale linearly with d_perp, directions stay parallel along a radial line.
  • "Branch 1 / Branch 3 agree at core boundary" — probes just inside and just outside the core boundary, asserts magnitude and direction match. Old code returned orthogonal directions.
  • "Matches Rankine vortex profile inside core" — direct comparison against the textbook closed form v_θ = Γr/(2π·r_c²) for a long filament. Independent of the rest of the panel method.

Equivalent direction-check test added on test_semi_infinite_filament.jl.

Updated existing tests where the old fixtures encoded the bug:

  • "Long Filament" — was asserting induced_velocity[3] ≈ 0, but the azimuthal direction is ±z for this geometry, so that component must be the only nonzero one. Updated to assert axial/radial components are zero and the azimuthal component is nonzero.

Notes / follow-ups

  • The semi-infinite Branch 3 does not apply the d_perp/epsilon linear ramp that the bound vortex Branch 3 does — it returns the peak velocity throughout the core. Looks unintentional (and inconsistent between the two filament functions) but is out of scope here. The new "Constant azimuthal direction inside core" test for the semi-infinite filament only asserts direction continuity inside the core, not magnitude.
  • The Python repo (Vortex-Step-Method/src/VSM/core/Filament.py) has the identical bug in both velocity_3D_bound_vortex and velocity_3D_trailing_vortex, plus a closely-related (but distinct) issue in velocity_3D_trailing_vortex_semiinfinite that uses an r1/|r1| - Vf approximation instead of the exact radial direction. Worth a parallel PR upstream.

Test plan

  • julia --project=. -e 'using Pkg; Pkg.test()' locally
  • CI green
  • Check whether downstream consumers (SymbolicAWEModels.jl etc.) see any change in production CFx / CD on representative cases

@codecov
Copy link
Copy Markdown

codecov Bot commented May 25, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.

📢 Thoughts on this report? Let us know!

@1-Bart-1 1-Bart-1 merged commit 0afee2d into main May 28, 2026
7 of 9 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant