Skip to content

plot_section_polars draws cl, cd and cm against alpha per panel, for every aero model - #354

Open
1-Bort-1 wants to merge 5 commits into
mainfrom
agent/331-plot-section-polars-covers-only-polar-ve
Open

1-Bort-1 wants to merge 5 commits into
mainfrom
agent/331-plot-section-polars-covers-only-polar-ve

Conversation

@1-Bort-1

@1-Bort-1 1-Bort-1 commented Sep 16, 2026

Copy link
Copy Markdown
Contributor

TL;DR

plot_section_polars(body_aero; panels, alphas, delta) now draws cl, cd and cm in one figure, one curve per chosen panel, through the panel's own calculate_cl/calculate_cd/calculate_cm. Before, it drew one coefficient per call from raw POLAR_VECTORS section data only. A POLY, INVISCID or POLAR_MATRICES wing gave No POLAR_VECTORS sections found in body, and nothing showed what a panel uses at a given flap deflection (#113).

What changed

  • One path for every model. A new helper, panel_polar_curves(panels, alphas, deltas), runs the same calculate_* functions the solver calls over an α grid. The plot therefore shows what the solver sees: the averaged, interpolated panel polar, with its extrapolation and alpha_window. It no longer shows the unrefined section's CSV points.
  • Flap deflection. delta [rad] sets the deflection a POLAR_MATRICES panel is evaluated at. It defaults to each panel's stored delta, and other models ignore it.
  • Keywords and figure.
    • panels takes one index or a list and defaults to all panels.
    • alphas is in radians, like plot_polar_data's. The default −20°…30° is the range of the Python plot_panel_coefficients.
    • The figure is one MakieControlPlots.plotx with three rows on a shared α axis.
  • Changelog. Listed under Added. The positional coefficient argument is gone, so plot_section_polars(body_aero, :cd) now raises a MethodError; its one caller, examples/obj_to_yaml_kite.jl, now makes a single call.
  • Cleanup in the same file, near-identical behaviour. The POLAR_VECTORS panel of plot_combined_analysis used to call the raw cl_interp/cd_interp/cm_interp for the same three curves; it now uses the same helper. The two paths differ only where alpha_window > 0, which the raw interpolants skipped. On create_body_aero_with_skin over −5…20° the old and new values are identical (alpha_window = 0).

after: plot_section_polars on a POLY (Breukels) panel, lei_poly_coeffs(0.1, 0.08); cl and cd jump at alpha = 20 deg

after: plot_section_polars on the TU Delft V3 kite, POLAR_VECTORS panels 1 and 25

There is no before figure. Old code raised an error on the POLY wing, and on the V3 kite it plotted different data: raw section points, not panel polars.

Found on the way (not changed here)

  • POLY is discontinuous at |α| = 20°, which the plot shows at once: at lei_poly_coeffs(0.1, 0.08) cl drops from 1.0706 to 0.2200 across 20°, and cm's quadratic reaches −5.53 at 30°. Fixing it changes existing POLY results, so it is POLY cl and cd jump at |alpha| = 20 deg, and cm runs its quadratic unbounded past it #359.
  • plot_combined_analysis draws its POLAR_MATRICES wireframes transposed.
    • The matrix is built for alpha in alphas, delta_te in delta_tes, which puts α on the rows. It is then drawn with wireframe!(ax, delta_tes, alphas, M), which expects δ on the rows.
    • plot_polar_data builds the matrix the other way round and is correct.
    • Both grids are -5:0.3:20, so nothing errors. I'd fix it by having both functions share one wireframe helper; that changes a figure, so it is not in this diff.
  • CI matrix. .github/workflows/CI.yml:22 carries fail-fast: false, so one failing cell does not cancel the others and a red run costs the whole matrix; turning it off is a cleanup: PR of its own.

Verification

  • Reproduced first, on unchanged code: plot_section_polars(create_body_aero(), :cl) (INVISCID) and plot_section_polars(BodyAerodynamics([ram_wing]), :cl) (POLAR_MATRICES) both raise No POLAR_VECTORS sections found in body.
  • The new testset in test/plotting/test_plotting.jl was red before the change (MethodError: no method matching plot_section_polars(...; panels, alphas)) and is green after, 19/19. It has one nested testset per behaviour:
    • INVISCID gives cl = 2πα and cd = cm = 0;
    • POLAR_VECTORS gives cl = 0.5 + 0.25·α°, cd = 0.02 and cm = −0.05;
    • POLY matches evalpoly of the Breukels coefficients;
    • POLAR_MATRICES at delta = 1° matches the interpolants there and differs from the stored delta;
    • panel selection, and the saved file.
  • All testsets in test/plotting/test_plotting.jl pass in the juliaserver session: Plotting 58/58, the new testset 19/19, Airfoil skin 22/22, generated_slices 6/6, Audit slices 7/7.
  • plot_combined_analysis on a POLAR_VECTORS body still builds a Figure (checked by hand; no test covers that branch).
  • Docs build (docs/make.jl) is clean apart from the existing size-threshold warnings. The repo has no REUSE.
  • Up to date with main: merged origin/main twice, most recently at 7103702 (after Name the apparent wind va, va_vec and va_dist everywhere except the public API #349's va rename, Bound and trailing vortices share one segment kernel, so the trailing core induces azimuthal velocity #351 and linearize and make_dual_shadow take a BodyAerodynamics with several wings #355). The only conflict was the changelog's Added list, where both entries are kept. test/plotting/test_plotting.jl was re-run after each merge, and all testsets pass as above, now on Julia 1.13.0.
  • GitHub CI on 7103702: PASS on every job (Julia 1.12 ubuntu/windows/macOS, 1.13 ubuntu, Documentation, setup test). Local full suite on 7103702: PASS (13 min, Julia 1.13, one cell).
  • Benchmark: n/a
  • Risk: scripts calling plot_section_polars(body_aero, :cd) break. The old form had no test and one example caller.

Scope

+126 / −53 across 6 files against main:

  • ext/VortexStepMethodMakieExt.jl: the function body, now shorter, plus the helper and the three lines in plot_combined_analysis.
  • The stub docstring and its private-docs entry.
  • The testset.
  • The example call and the changelog entry under Added.

Searched for calculate_cl, cl_interp(, plot_polar, panel_coefficients and alpha_range in src/ and ext/. The only other code that evaluates a panel over an α grid is plot_combined_analysis, which is folded in above.

Closes #331 · task VortexStepMethod.jl-331

1-Bort-1 and others added 2 commits September 17, 2026 01:06
plot_section_polars(body_aero; panels, alphas, delta) evaluates each chosen
panel through calculate_cl/cd/cm and draws the three coefficients in one
MakieControlPlots figure, so POLY, INVISCID, POLAR_VECTORS and POLAR_MATRICES
share one path. Replaces the POLAR_VECTORS-only, one-coefficient-per-call form.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
panel_polar_curves evaluates calculate_cl/cd/cm over an alpha grid; both
plot_section_polars and the POLAR_VECTORS panel of plot_combined_analysis use it
instead of calling the raw interpolants. Split the plot_section_polars test into
one testset per aero model and reuse create_body_aero for the POLY wing.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@1-Bort-1 1-Bort-1 added agent:running Agent task state agent:ci Agent task state and removed agent:running Agent task state labels Sep 16, 2026

@1-Bort-1 1-Bort-1 left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Independent review (advisory)

Verdict: APPROVE WITH COMMENTS · 1 inline, 0 off the diff

Good

  • The plot now reaches every aero model: calculate_cl/cd/cm in src/panel.jl:504-580 handle POLY, INVISCID, POLAR_VECTORS and POLAR_MATRICES, and use delta only for POLAR_MATRICES, as the docstring says.
  • One code path, as the card promises: panel_polar_curves replaces the three raw *_interp calls in the POLAR_VECTORS branch of plot_combined_analysis, so no third copy exists.
  • Panels and deflections pair up correctly: calculate_cl.(panels, alphas', deltas) with a per-panel deltas vector gives an n×m grid, something.(nothing, …) works because broadcasting treats nothing as a scalar, and vcat(panels) accepts both an Int and a range.
  • labels=[labels] fits MakieControlPlots.plotx (plotx.jl:27-37): the panel legend goes only on the first (cl) row, which is right for three rows sharing an α axis.
  • The tests pin each model to a closed form (2πα, the linear table, evalpoly of the Breukels coefficients, the POLAR_MATRICES interpolant at the passed delta) and do not just check that a figure exists; they reuse create_body_aero through new keywords, not a new fixture family.
  • The BREAKING change is small: a search finds only the one example caller, updated in this diff, plus the changelog and docs stubs; the new helper is listed in private_functions.md.
  • The scope matches the card: six files, the combined-analysis tidy-up is named, and the found problems (POLY jump at 20°, transposed wireframe) are noted, not fixed silently.

Not good

  • ext/VortexStepMethodMakieExt.jl:1521 — By default panels is every panel, so a normal 20–40-panel wing draws 20–40 overlapping curves and a legend with that many entries on the cl row; the one example caller already overrides it with [1, 10], which suggests the default is not a useful figure.
  • The title is still "Section polars" and the file section_polars.png, but the figure now shows panel polars (averaged over the refined panels); the function name is API, but the title string could say what is drawn.
  • The two found problems (POLY discontinuity at |α| = 20°, transposed POLAR_MATRICES wireframe in plot_combined_analysis) have no issue yet; they are left to the human, where §5 says to open issues and link them from the PR.
  • The wireframe transposition is in the same if block this PR edits, and fixing it changes only which axis is labelled what; it could arguably have gone into this diff, not just been noted.
  • The CI matrix fail-fast: false bullet does not say what is wrong with it, so a reader cannot tell why it is listed under found problems.
  • Local CI and GitHub CI are both still pending in the card, so the only green result so far is from the juliaserver session.
  • The panel_polar_curves docstring allows "one shared deflection" only for the plot_combined_analysis caller; plot_section_polars always passes a vector, so the helper supports two argument shapes for two callers.

claude, rubric CLEAN_CODE.md. A different lab from the implementer
on purpose: a reviewer sharing its blind spots would not flag its mistakes.

end
isempty(series) && error("No POLAR_VECTORS sections found in body")
function VortexStepMethod.plot_section_polars(body_aero::BodyAerodynamics;
panels=eachindex(body_aero.panels), alphas=deg2rad.(-20:0.5:30), delta=nothing,

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

MINOR: By default panels is every panel, so a normal 20–40-panel wing draws 20–40 overlapping curves and a legend with that many entries on the cl row; the one example caller already overrides it with [1, 10], which suggests the default is not a useful figure.

@codecov

codecov Bot commented Sep 16, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 72.22222% with 5 lines in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
ext/VortexStepMethodMakieExt.jl 72.22% 5 Missing ⚠️

📢 Thoughts on this report? Let us know!

@1-Bort-1 1-Bort-1 added agent:review Agent task state and removed agent:ci Agent task state labels Sep 16, 2026
Comment thread CHANGELOG.md Outdated
- The Makie `plot!` methods for a `Panel` or a `BodyAerodynamics` return a
`Vector{Makie.AbstractPlot}` instead of a `Vector{Any}`; for a `BodyAerodynamics`
drawn as flat panels it is one flat list rather than a list per panel.
- BREAKING - `plot_section_polars(body_aero; panels, alphas, delta)` draws cl, cd and cm

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is not a breaking change but an added feature

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Moved to Added in 9ae2ab2. The old positional form, plot_section_polars(body_aero, :cd), now raises a MethodError; that is the one thing a script could trip on.

@1-Bort-1 1-Bort-1 added agent:queued Agent task state agent:running Agent task state and removed agent:review Agent task state agent:queued Agent task state labels Sep 17, 2026
1-Bort-1 and others added 2 commits September 17, 2026 09:44
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@1-Bort-1 1-Bort-1 added agent:queued Agent task state agent:running Agent task state and removed agent:running Agent task state agent:queued Agent task state labels Sep 17, 2026
@1-Bort-1 1-Bort-1 added agent:ci Agent task state agent:review Agent task state and removed agent:running Agent task state agent:ci Agent task state labels Sep 17, 2026
@1-Bort-1

1-Bort-1 commented Sep 17, 2026

Copy link
Copy Markdown
Contributor Author

Local full suite: PASS (6 min, Julia 1.13.0, one cell of the matrix)

@1-Bort-1 1-Bort-1 added agent:queued Agent task state agent:running Agent task state and removed agent:review Agent task state agent:queued Agent task state labels Sep 18, 2026
…n-polars-covers-only-polar-ve

# Conflicts:
#	CHANGELOG.md
@1-Bort-1 1-Bort-1 added agent:queued Agent task state agent:running Agent task state agent:ci Agent task state agent:review Agent task state and removed agent:running Agent task state agent:queued Agent task state agent:ci Agent task state labels Sep 18, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

agent:review Agent task state

Projects

None yet

Development

Successfully merging this pull request may close these issues.

plot_section_polars covers only POLAR_VECTORS: plot cl, cd, cm against alpha per panel for every aero model

2 participants