FazBrowse GitHub Viewer | Trending |
URL:
| Home
Tools: [Download Repo ZIP]   [Original HTTPS Page]

alignment: support spiral transition curves and cant in the PI-method CSV import (#6890) by BIMvoice · Pull Request #8833 · IfcOpenShell/IfcOpenShell · GitHub

alignment: support spiral transition curves and cant in the PI-method CSV import (#6890) - #8833

Open
BIMvoice wants to merge 2 commits into
v0.8.0from
alignment-6890-csv-spirals-cant
Open

alignment: support spiral transition curves and cant in the PI-method CSV import (#6890)#8833
BIMvoice wants to merge 2 commits into
v0.8.0from
alignment-6890-csv-spirals-cant

Conversation

BIMvoice commented Jul 21, 2026
edited
Loading

Copy link
Copy Markdown
Contributor

Fixes #6890

Restructured after @RickBrice's roadmap comment below: the clothoid and cant machinery is now a standalone, CSV-independent core in the alignment API, and the CSV import is a thin, disposable consumer. Two commits, in that order.

Commit 1: reusable transition-curve core (the durable part)

New solve_horizontal_alignment_by_pi_method.py in ifcopenshell.api.alignment:

  • solve_horizontal_alignment_by_pi_method(hpoints, radii, cants=None) runs the full PI solve as a pure computation (radii entries R or (R, Lin, Lout) for entry/exit clothoids; per-PI cant), returning HorizontalSegmentDefinition values whose fields mirror IfcAlignmentHorizontalSegment, so they write to file without further math.
  • compute_clothoid_end() (Gauss-Legendre clothoid integrals, signed curvatures) and compute_horizontal_segment_end() (endpoint evaluation of any LINE/CIRCULARARC/CLOTHOID definition) exposed for reuse and continuity checking by any caller.
  • Cant is embedded per horizontal segment, so the 1:1 cant/horizontal parity the cant mapping requires is structural.

layout_horizontal_alignment_by_pi_method() is now a thin writer over that solver, same public signature as before. This matters for the successor effort: the #7589 interactive editor (@DesertSpringsCivil) already calls exactly this function from tool.Alignment.layout_by_pi_method, so it gets schema-valid transition curves through its existing call site the moment its PI table passes (R, Lin, Lout) instead of R (verified live: that exact call produces LINE, CLOTHOID, CIRCULARARC, CLOTHOID, LINE). We also verified this branch adds no new merge conflicts with the saikei branch.

Commit 2: the CSV consumer (the disposable part)

create_from_csv.py is parser-only: it groups columns (header-selected formats: X,Y,R legacy unchanged, X,Y,R,Lin,Lout, X,Y,R,Lin,Lout,E) and forwards to the core. Kept because #6890 asks for it; structured so removing the CSV path later touches nothing but this one file. If the preference is not to grow the CSV surface at all, this commit can be dropped and the core stands alone.

Verification (re-run on the rewritten branch)

  • Test suite: 43 passed (37 baseline + 6 new core tests), no failures.
  • Continuity: pure solver max position gap 1.017e-12 m, direction 2.2e-16 rad; on the C++ evaluator 8.521e-07 m (the engine's clothoid series truncation), direction 2.2e-16.
  • ifcopenshell.validate with express rules: 0 errors on the tangent-clothoid-arc-clothoid-tangent cant alignment.
  • Legacy CSV output byte-identical to unmodified base (GUID/timestamp normalized).
  • Black + ruff clean.

This change was written with AI assistance.

Copy link
Copy Markdown
Contributor

@BIMvoice - I recommend some caution before moving forward with this is implemented. The original CSV import was a stop-gap measure to allow for the most minimal input of roadway alignment into Bonsai. One user has interest in adding clothoid transitions, but the real need for this requirement is suspect. In a completely different effort, @myoder89 is developing interactive infrastructure editing for Bonsai as part of a GSoC project. This effort will make the CSV input unnecessary, obsolete, and a candidate for removal from Bonsai.

Copy link
Copy Markdown
Contributor Author

@RickBrice thanks for the context, that is exactly the kind of steer we hoped for by flagging the open questions upfront.

We built this because #6890 asked for it, but if the CSV path is a stop-gap heading for removal once @myoder89's interactive editing lands, there is no point growing it. Happy to go whichever way you prefer: leave this PR open as an interim option until the GSoC work is usable, or close it (and #6890 along with it, if you consider the requirement superseded). Your call, no attachment on our side.

One small note in case it is useful independently of the CSV question: the clothoid endpoint math and the continuity test in this PR are self-contained and could be reused by the interactive editor's geometry layer whenever it needs transition curves; happy to extract that if it helps the GSoC effort.

BIMvoice added 2 commits July 21, 2026 17:49
Extends the PI method to horizontal alignments with clothoid spiral
transition curves and cant profiles for railway engineering, with the
geometry available as a pure, file-independent solver that any caller
(interactive editors, scripts, importers) can reuse.

solve_horizontal_alignment_by_pi_method() solves PI coordinates and radii
into a continuous sequence of HorizontalSegmentDefinition values whose
fields mirror IfcAlignmentHorizontalSegment. Each radii element is either
a circular curve radius R or a (R, Lin, Lout) sequence giving the entry
and exit spiral lengths. The circular curve is shifted inward so tangent
runs, spirals, and the circular curve remain continuous in position and
direction. Spiral end points are computed by Gauss-Legendre integration
of the clothoid position functions (compute_clothoid_end, exposed for
reuse), matching the exact clothoid to machine precision, and
compute_horizontal_segment_end() lets callers verify continuity of any
definition sequence without touching a file.

layout_horizontal_alignment_by_pi_method() is now a thin writer over the
solver: it accepts the same (R, Lin, Lout) elements and writes the
solved definitions to an IfcAlignmentHorizontal layout. When a cant
layout and cant values are given, cant segments are written one-for-one
with the horizontal segments, as expected by the cant segment lookup
used for Viennese bends: zero cant on tangent runs (CONSTANTCANT),
linearly varying cant over spirals (LINEARTRANSITION), and constant cant
over circular curves (CONSTANTCANT), applied to the rail on the outside
of the curve. Curves with a non-zero cant require both spirals so the
cant profile is continuous, which keeps the segmented reference curve
schema-valid. The parity is structural: every solved definition carries
its own cant values, so the two layouts cannot drift apart.

create_by_pi_method() passes radii elements through and accepts optional
cants and rail_head_distance; create() accepts rail_head_distance for
IfcAlignmentCant.RailHeadDistance. Plain-R input routes through the
verbatim legacy code path and produces unchanged output.

The tests check the quadrature against an independent dense Simpson
reference, pure-solver continuity (max position gap 1e-12), continuity
of the written geometry on the C++ evaluator (max position gap 8.5e-7,
the engine's clothoid series truncation), the cant profile and its
segment parity, error conditions, and an end-to-end
tangent-clothoid-arc-clothoid-tangent authoring example that validates
cleanly against the schema and express rules.

Part of #6890.

Generated with the assistance of an AI coding tool.
Thin CSV front end for the spiral and cant support in the PI method
core. The import can now start with an optional header row naming the
values that define each horizontal PI. The number of header columns
selects the format: X,Y,R (the existing format, also used when there is
no header), X,Y,R,Lin,Lout for spiral transition curves, and
X,Y,R,Lin,Lout,E for spiral transition curves with cant. The parser only
groups columns and forwards them to create() and
layout_horizontal_alignment_by_pi_method(); all geometry lives in the
core, so this surface stays small and remains removable without
affecting API users, per the maintainer guidance that the CSV import is
a stop-gap.

Files in the existing format import unchanged; the output is
byte-identical apart from GUIDs. Pure column-count auto-detection would
be ambiguous (15 values parse as 5 legacy PIs or 3 spiral PIs), so an
explicit header is required for the new groups, and no existing file can
collide with one because row 1 of a headerless file must parse as
numbers. Since cant requires horizontal, vertical, and cant layouts, at
least one vertical row is required when the cant format is used.
create_from_csv() accepts an optional rail_head_distance that is
assigned to IfcAlignmentCant.RailHeadDistance.

Fixes #6890

Generated with the assistance of an AI coding tool.

Copy link
Copy Markdown
Contributor Author

@RickBrice we restructured the PR around your comment. The clothoid and cant machinery no longer lives in the CSV path. It is now a standalone core in the alignment API: solve_horizontal_alignment_by_pi_method() does the whole PI solve (including (R, Lin, Lout) spiral entries and per-segment cant, one cant segment per horizontal segment) as a pure computation returning HorizontalSegmentDefinition values, with compute_clothoid_end() and compute_horizontal_segment_end() exposed for reuse and continuity checking. layout_horizontal_alignment_by_pi_method() is now a thin writer over that solver, same signature as before.

That matters for the successor effort: @DesertSpringsCivil's editor in #7589 already calls layout_horizontal_alignment_by_pi_method() from tool.Alignment.layout_by_pi_method, so with this PR the interactive editor gets schema-valid transition curves through its existing call site the moment its PI table passes (R, Lin, Lout) instead of R (we verified that exact call produces LINE, CLOTHOID, CIRCULARARC, CLOTHOID, LINE, and the pure solver is available for previews before writing to the file). We also checked this branch introduces no new merge conflicts with the saikei branch.

The CSV import is now a parser-only consumer of that core (commit 2 of 2), kept because #6890 asks for it, and structured so removing the CSV path later touches nothing but that one file. If you would rather it not grow at all, we can drop commit 2 and ship the core alone.

BIMvoice force-pushed the alignment-6890-csv-spirals-cant branch from b713c16 to c36fe0a Compare July 21, 2026 18:08
DesertSpringsCivil added a commit to DesertSpringsCivil/IfcOpenShell that referenced this pull request Aug 15, 2026
… (port of IfcOpenShell#8833)

Port of IfcOpenShell#8833 by Petru Conduraru (BIMvoice) onto
the v0.9.0 API surface: pure solve_horizontal_alignment_by_pi_method solver
(clothoid ends via Gauss-Legendre quadrature), (R, Lin, Lout) radii
elements, layout writer with cant segment parity, rail_head_distance on
create(). Adapted __init__ exports to the 0.9 module set; added a golden
spiral-curve-spiral worked-example test with independently derived
expected values.

Co-Authored-By: Petru Conduraru <petru@bimvoice.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
DesertSpringsCivil added a commit to DesertSpringsCivil/IfcOpenShell that referenced this pull request Aug 15, 2026
…curves, cant layout, vertical enumeration, station inverse

- solve_horizontal_alignment_by_pi_method: iterative clothoid spiral
  solver for PI-method horizontal layouts (spiral-curve-spiral)
- Compound (PCC) and reverse (PRC) curve support in the PI solver
- add_cant_layout: author IfcAlignmentCant layouts with configurable
  rail head distance
- get_vertical_layouts: enumerate all vertical layouts on an
  alignment, supporting multiple vertical alternatives
- station_from_distance_along: station inverse, aware of station
  equations carried on IfcReferent
- create_from_csv: extended import — spiral transition lengths, cant
  values, and vertical profile rows

Spiral solver ported from IfcOpenShell#8833 by Petru Conduraru (BIMvoice).

Co-Authored-By: Petru Conduraru <petru@bimvoice.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode characters
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.

Update alignment api CSV import to include transition curves

2 participants


Back | FazBrowse Home | New Git URL