Skip to content

Add MoorDyn mooring coupling with real-time tension visualization#88

Merged
dav-og merged 14 commits intoProject-SEA-Stack:mainfrom
dav-og:feature/moordyn-coupling
Feb 26, 2026
Merged

Add MoorDyn mooring coupling with real-time tension visualization#88
dav-og merged 14 commits intoProject-SEA-Stack:mainfrom
dav-og:feature/moordyn-coupling

Conversation

@dav-og
Copy link
Copy Markdown
Collaborator

@dav-og dav-og commented Feb 26, 2026

Overview

This PR integrates MoorDyn v2.6.1 as a mooring dynamics solver within HydroChrono using the existing force-component architecture.

Mooring lines are visualized in real time in the VSG viewer as tube meshes with per-vertex tension colouring and an interactive colour bar.

The design follows the established pattern (hydrostatics, radiation, excitation): a thin RAII wrapper around the external library, a ForceComponent adapter, and configuration via both C++ and YAML.

Also included: IRF truncation refactoring, RegularWave API cleanup, and cross-machine build fixes required for the mooring work.


Summary

  • MoorDyn v2.6.1 coupled as a mooring force component
  • Clean RAII wrapper (create → init → step → close), no raw C API leakage
  • Real-time tube visualization with Turbo colourmap (tension magnitude)
  • ImGui controls: colour toggle and adaptive/locked range
  • Cross-code verification against WEC-Sim/MoorDyn (RM3, 3-line catenary)
  • IRF truncation decoupled from smoothing/tapering
  • RegularWave refactored with validated setters (SetPeriod / SetOmega)

Core Components

MoorDynWrapper (src/hydro/mooring/)

  • Manages full MoorDyn lifetime via RAII
  • Maps SystemState ↔ flat DOF arrays
  • Extracts per-node tensions and attachment types for visualization
  • Throws on init/step errors (no silent failures)

MooringComponent (src/hydro/force_components/)

  • Implements IHydroForceComponent
  • Delegates to MoorDynWrapper and applies mooring forces to bodies

MooringLinesViz (src/gui/)

  • Tube mesh per line (8-sided cross-section + caps)
  • Per-frame GPU buffer updates
  • Endpoint markers (anchor, fairlead, clump/free)
  • Adaptive colour scaling with high-water-mark logic

API & YAML

C++:

MoorDynConfig cfg;
cfg.enabled = true;
cfg.input_file = "mooring/lines.txt";
cfg.coupled_body_indices = {1};
hydro_forces.SetMoorDynConfig(cfg);

YAML:

mooring:
  enabled: true
  input_file: mooring/lines.txt
  coupled_body_indices: [1]

IRF Refactoring

Three independent, composable controls:

  • Excitation IRF truncation
  • Radiation RIRF truncation
  • Radiation kernel processing (smoothing/tapering)

Each can be used independently or combined. Existing regression tests pass.
rm3_mooring_screenshot

rm3_mooring_verification_fairten4_comparison
rm3_mooring_10mb.mp4

dav-og and others added 14 commits February 23, 2026 16:41
Replace public data members on RegularWave with validated setter/getter methods (SetAmplitude, SetOmega, SetPeriod, SetPhase) so users can specify wave frequency as either angular frequency (rad/s) or period (s). Omega remains the single stored quantity; period is computed on demand. RegularWaveParams also accepts either field, throwing if both are set. All demos, tests, and internal call sites updated.
Mooring lines now colour each tube segment by MoorDyn tension magnitude using a Turbo colormap, with an ImGui colour bar and real-time controls.
M_PI was defined independently in multiple files. Consolidate into a single header that's shared.
Previously, truncating the radiation impulse response function (RIRF) was bundled into the TaperedDirect mode -- you couldn't shorten the kernel without also enabling smoothing and tapering. Excitation IRF truncation was buried inside the irregular wave settings.

Introduce three independent, composable controls:

1. Excitation truncation time -- shorten the excitation IRF to ±T s
2. Radiation truncation time -- shorten the RIRF to [0, T] s
3. Kernel processing -- optionally smooth and/or taper the RIRF

Each can be used on its own or combined. All three are exposed via both the C++ API (SetExcitationTruncationTime, SetRadiationTruncationTime, SetRadiationKernelProcessing) and YAML configuration. Truncation works regardless of wave type.

YAML schema changes:
Old: convolution.mode, convolution.taper.end_time
New: excitation.truncation_time, radiation.truncation_time, radiation.smoothing, radiation.taper

Additional quality improvements:
- ExcitationRampType moved to hydrochrono::waves namespace (kLinear, kCosine)
- Frequency defaults extracted to named constants in IrregularWaveParams
- SG filter coefficients documented with citation, constexpr std::array
- Embed RadiationKernelProcessing directly in YAMLHydroData (was 7 flat fields)
Cross-code verification of the RM3 two-body point absorber with MoorDyn mooring against WEC-Sim/MoorDyn co-simulation reference data. Compares body heave motions and fairlead tensions after the 40s ramp transient.

The test uses the new excitation truncation and cosine ramp features to match WEC-Sim's elevationImport mode (CITime=20s, rampTime=40s). Requires HYDROCHRONO_ENABLE_MOORDYN; skipped otherwise.

Includes test infrastructure (tests/verification/CMakeLists.txt) that mirrors the existing regression pattern with CTest fixtures.
The early find_package(HDF5 CONFIG QUIET) before find_package(Chrono) was writing HDF5_DIR-NOTFOUND into the CMake cache. Chrono's config then failed to overwrite it, so the later REQUIRED find also failed.

Fix: extract HDF5_DIR from chrono-config.cmake in build.ps1 and pass it on the cmake command line (same pattern as Eigen3). Also fix the detection regex to match CHRONO_HDF5_AVAILABLE set to 1 (not just ON/TRUE).
@dav-og dav-og merged commit 9c9141a into Project-SEA-Stack:main Feb 26, 2026
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