SWMMVis  6.0.0-alpha.4
Qt6/C++ GIS-based graphical user interface for the SWMMVis engine (6.0.0-alpha.4)
Loading...
Searching...
No Matches
cellsurfaceinterp.h File Reference

Per-cell free-surface sampling with physically consistent extrapolation into no-data corners (2D profile WSE fix, see workplans/2D_PROFILE_WSE_EXTRAPOLATION_PLAN_2026-08-02.md). More...

#include <QPointF>
#include <algorithm>
Include dependency graph for cellsurfaceinterp.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Namespaces

namespace  CellSurfaceInterp
 

Functions

double CellSurfaceInterp::depthAt (const QPointF &p, const QPointF &a, const QPointF &b, const QPointF &c, double z0, double z1, double z2, double sd0, double sd1, double sd2, bool *degenerate=nullptr)
 Water depth at p inside the triangle (a,b,c).
 

Detailed Description

Per-cell free-surface sampling with physically consistent extrapolation into no-data corners (2D profile WSE fix, see workplans/2D_PROFILE_WSE_EXTRAPOLATION_PLAN_2026-08-02.md).

Author
Caleb Buahin caleb.nosp@m..bua.nosp@m.hin@g.nosp@m.mail.nosp@m..com
Date
2026
License\n GPL-3.0-or-later

The per-vertex field carries a SIGNED depth sd_v = η_v − z_v with three states (SimulationSnapshot.hpp contract): sd_v > 0 wet — η valid, water stands above the bed; sd_v < 0 dry side of a partially-wet cell — η valid, below bed (legacy files only: engines with the wetted-contact gate emit positive-or-sentinel); sd_v == 0 NO DATA — no qualifying incident cell, η undefined.

A bare barycentric blend of sd reads the no-data sentinel as η = z, dragging the interpolated surface up to the bed of a dry corner — the "water climbs walls" artifact. Instead, bed elevation never stands in for η: no-data corners are filled by extending the surface from the valid corners with zero gradient in the dry direction (constant-η extrapolation), then depth = max(0, η − z) puts the waterline exactly at the sub-cell bed intercept.

Mixed tri/quad meshes (TRI_QUAD_MESHING_PLAN_2026-09-06.md): the routine stays per triangle. Callers pass the display SUB-triangle of the containing cell (a quad's VFR half, mesh::cellGeom), with the cell's value on each half — never a bilinear quad blend, which would disagree with the engine's storage model.

Header-only so SWMM2DResultsLayer (depthAtCellInterp / maxDepthAtSceneInterp) and the unit tests share one implementation — the layer's link closure is too large to drive from a leaf test (see the test_2dresults_vizfixes note in tests/gui/CMakeLists.txt).