X-Git-Url: http://git.salome-platform.org/gitweb/?a=blobdiff_plain;ds=sidebyside;f=src%2FHYDROData%2FHYDROData_ChannelAltitude.cxx;h=5467a236a944ab05535c689f998bb341d1876385;hb=f09552db523068b952c3e6e64c5f8acb165d243d;hp=1a7b515f8aad49d45d430ceae576761e43a9a4dd;hpb=fb4a3fcbc15b382e6af6a82329b74418775b6c5e;p=modules%2Fhydro.git diff --git a/src/HYDROData/HYDROData_ChannelAltitude.cxx b/src/HYDROData/HYDROData_ChannelAltitude.cxx index 1a7b515f..5467a236 100644 --- a/src/HYDROData/HYDROData_ChannelAltitude.cxx +++ b/src/HYDROData/HYDROData_ChannelAltitude.cxx @@ -23,9 +23,12 @@ #include "HYDROData_Channel.h" #include "HYDROData_Projection.h" #include "HYDROData_Polyline3D.h" +#include "HYDROData_PolylineXY.h" +#include "HYDROData_ProfileUZ.h" #include "HYDROData_Profile.h" +#include -#define _DEVDEBUG_ +//#define _DEVDEBUG_ #include "HYDRO_trace.hxx" #include @@ -51,7 +54,6 @@ #include #include -IMPLEMENT_STANDARD_HANDLE(HYDROData_ChannelAltitude, HYDROData_IAltitudeObject) IMPLEMENT_STANDARD_RTTIEXT(HYDROData_ChannelAltitude, HYDROData_IAltitudeObject) HYDROData_ChannelAltitude::HYDROData_ChannelAltitude() @@ -63,9 +65,10 @@ HYDROData_ChannelAltitude::~HYDROData_ChannelAltitude() { } -double HYDROData_ChannelAltitude::GetAltitudeForPoint( const gp_XY& thePoint ) const +double HYDROData_ChannelAltitude::GetAltitudeForPoint( const gp_XY& thePoint, + int theMethod) const { - DEBTRACE("HYDROData_ChannelAltitude::GetAltitudeForPoint"); + DEBTRACE("GetAltitudeForPoint p(" << thePoint.X() << ", " << thePoint.Y() << ")"); double aResAltitude = GetInvalidAltitude(); Handle(HYDROData_Channel) aChannel = @@ -76,30 +79,50 @@ double HYDROData_ChannelAltitude::GetAltitudeForPoint( const gp_XY& thePoint ) c return aResAltitude; } DEBTRACE("aChannel: " << aChannel->GetName().toStdString()); + Handle(HYDROData_Polyline3D) aGuideLine = aChannel->GetGuideLine(); if (aGuideLine.IsNull()) { DEBTRACE("aGuideLine.IsNull()"); return aResAltitude; } - DEBTRACE("aGuideLine: " << aGuideLine->GetName().toStdString()); + //DEBTRACE("aGuideLine: " << aGuideLine->GetName().toStdString()); + + Handle(HYDROData_PolylineXY) aGuideXY = aGuideLine->GetPolylineXY(); + if (aGuideXY.IsNull()) + { + DEBTRACE("aGuideXY.IsNull()"); + return aResAltitude; + } + //DEBTRACE("aGuideXY: " << aGuideXY->GetName().toStdString()); + + Handle(HYDROData_ProfileUZ) aGuideUZ = aGuideLine->GetProfileUZ(); + if (aGuideUZ.IsNull()) + { + aGuideUZ = aGuideLine->GetChildProfileUZ(); // profile obtained from bathymetry + } + if (aGuideUZ.IsNull()) + { + DEBTRACE("aGuideUZ.IsNull()"); + return aResAltitude; + } + //DEBTRACE("aGuideUZ: " << aGuideUZ->GetName().toStdString()); + Handle (HYDROData_Profile) aProfile = aChannel->GetProfile(); if (aProfile.IsNull()) { return aResAltitude; } - DEBTRACE("aProfile: " << aProfile->GetName().toStdString()); + //DEBTRACE("aProfile: " << aProfile->GetName().toStdString()); // --- See GEOMImpl_ProjectionDriver.cxx - TopoDS_Shape aShape = aGuideLine->GetShape3D(); - double middleZ = -9999; - aGuideLine->GetMiddleZ(middleZ); // use the middle Z value of the 3d line to help the projection. - gp_Pnt P1(thePoint.X(), thePoint.Y(), middleZ); - if (middleZ < -9000) - { - DEBTRACE("the middle Z value of the 3d line is incorrect"); - } + gp_XY LP, RP; + aProfile->GetLeftPoint(LP); + aProfile->GetRightPoint(RP); + + TopoDS_Shape aShape = aGuideXY->GetShape(); + gp_Pnt P1(thePoint.X(), thePoint.Y(), 0); TopoDS_Shape aPoint = BRepBuilderAPI_MakeVertex(P1).Shape(); if (aPoint.IsNull() || aShape.IsNull()) @@ -229,23 +252,91 @@ double HYDROData_ChannelAltitude::GetAltitudeForPoint( const gp_XY& thePoint ) c // Store the valid solution. hasValidSolution = Standard_True; - // Normalize parameter. - TopoDS_Edge aSupportEdge = TopoDS::Edge(aSupportShape); - Standard_Real aF, aL; - - BRep_Tool::Range(aSupportEdge, aF, aL); - - if (Abs(aL - aF) <= aTolConf) + // profile altitude at projection point + HYDROData_IPolyline::PointsList aProfilePoints = aGuideUZ->GetPoints(); + if ( aProfilePoints.IsEmpty() ) { - DEBTRACE("Projection aborted : degenerated projection edge"); + DEBTRACE("empty profile UZ"); return aResAltitude; } + double aDepth = HYDROData_ProfileUZ::GetDepthFromDistance( aProfilePoints, aParam ); + DEBTRACE("profile altitude: " << aDepth); + + // Compute edge index. + TopExp_Explorer anExp(aShape, TopAbs_EDGE); + int anIndex = 0; + for (; anExp.More(); anExp.Next(), anIndex++) + { + if (aSupportShape.IsSame(anExp.Current())) + { + break; + } + } - // Construct a projection vertex. + // get the XY distance from point to guideline const gp_Pnt &aPntProj = aDistShSh.PointOnShape2(i); - TopoDS_Shape aProj = BRepBuilderAPI_MakeVertex(aPntProj).Shape(); DEBTRACE("projection: (" << aPntProj.X() << ", " << aPntProj.Y() << ", " << aPntProj.Z() << ")"); - return aPntProj.Z() + 2.; + gp_XY aProjXY = gp_XY(aPntProj.X(), aPntProj.Y()); + aProjXY.Subtract(thePoint); + double distance = aProjXY.Modulus(); + + gp_Vec2d aProjDir = aProjXY; + gp_Vec2d aProfileDir(LP, RP); + double aSign = 1.0; + if( aProfileDir.Dot(aProjDir) < 0 ) + aSign = -1.0; + + distance *= aSign; + DEBTRACE("distance to guideline " << distance); + + if (GetInvertDirection()) + distance*=-1; + + // get delta altitude on section (supposed symmetric) from guideline distance (aParam) + double delta = 0; + int i1 = 0; + int i2 = 0; + gp_XY pt1 = gp_XY(); + gp_XY pt2 = gp_XY(); + HYDROData_ProfileUZ::PointsList aSectionPoints = aProfile->GetParametricPoints(); + for ( int i = 1, aNbPoints = aSectionPoints.Size(); i <= aNbPoints; ++i ) + { + const HYDROData_IPolyline::Point& aPolylinePoint = aSectionPoints.Value( i ); + DEBTRACE(" i, size, profile point: " << i << " " << aSectionPoints.Size() << " " << aPolylinePoint.X() << " " << aPolylinePoint.Y()); + if (aPolylinePoint.X() < distance) + { + i1 = i; + pt1 = aPolylinePoint; + } + if (aPolylinePoint.X() >= distance) + { + i2 = i; + pt2 = aPolylinePoint; + break; + } + } + if ((i1 == 0) && (i2 == 0)) + { + DEBTRACE("Projection aborted : non centered profile"); + return aResAltitude; + } + else if (i1 == 0) // distance < - profile width + { + DEBTRACE("distance < - profile width"); + delta = pt2.Y(); + } + else if (i1 == aSectionPoints.Size()) // distance >= profile width + { + DEBTRACE("distance >= profile width"); + delta = pt1.Y(); + } + else + { + delta = pt1.Y() + (pt2.Y() - pt1.Y())*(distance -pt1.X())/(pt2.X()-pt1.X()); + } + aResAltitude = delta + aDepth; + DEBTRACE("distance XY: "<< aParam << " distance to guideline: " << distance << " final altitude: " << aResAltitude << " delta: " << delta); + return aResAltitude; } } @@ -259,5 +350,27 @@ double HYDROData_ChannelAltitude::GetAltitudeForPoint( const gp_XY& thePoint ) c } +void HYDROData_ChannelAltitude::SetInvertDirection(bool IsInverted) +{ + if ( GetInvertDirection() == IsInverted ) + return; + + TDataStd_Integer::Set( myLab.FindChild( DataTag_InvertDirection ), (Standard_Integer)IsInverted ); +} + +bool HYDROData_ChannelAltitude::GetInvertDirection() const +{ + bool aRes = false; + + TDF_Label aLabel = myLab.FindChild( DataTag_InvertDirection, false ); + if ( !aLabel.IsNull() ) + { + Handle(TDataStd_Integer) anIntVal; + if ( aLabel.FindAttribute( TDataStd_Integer::GetID(), anIntVal ) ) + aRes = (bool)anIntVal->Get(); + } + + return aRes; +}