From ecdb8d279ffdf2979ed0883265ed3f7356431eb8 Mon Sep 17 00:00:00 2001 From: mzn Date: Tue, 7 Jul 2015 17:29:48 +0300 Subject: [PATCH] refs #576: Artificial object that does not follow the polyline. --- src/HYDROData/HYDROData_Channel.cxx | 199 ++++++++++++++--- src/HYDROData/HYDROData_Polyline3D.cxx | 87 ++++++++ src/HYDROData/HYDROData_Polyline3D.h | 5 + src/HYDROData/HYDROData_Profile.cxx | 44 ++++ src/HYDROData/HYDROData_Profile.h | 6 + src/HYDROData/HYDROData_Stream.cxx | 293 ++++++++++++++----------- src/HYDROData/HYDROData_Stream.h | 11 + 7 files changed, 486 insertions(+), 159 deletions(-) diff --git a/src/HYDROData/HYDROData_Channel.cxx b/src/HYDROData/HYDROData_Channel.cxx index f6890813..819e3030 100644 --- a/src/HYDROData/HYDROData_Channel.cxx +++ b/src/HYDROData/HYDROData_Channel.cxx @@ -26,12 +26,34 @@ #include "HYDROData_ShapesGroup.h" #include "HYDROData_ShapesTool.h" #include "HYDROData_Pipes.h" +#include "HYDROData_Stream.h" + +#include #include #include #include +#include + +#include + +#include +#include + +#include + +#include + #include +#include + +#include +#include + +#include + +#include #include #include @@ -102,48 +124,175 @@ TopoDS_Shape HYDROData_Channel::GetShape3D() const } bool HYDROData_Channel::CreatePresentations( const Handle(HYDROData_Polyline3D)& theGuideLine, - const Handle(HYDROData_Profile)& theProfile, - PrsDefinition& thePrs ) + const Handle(HYDROData_Profile)& theProfile, + PrsDefinition& thePrs ) { - if ( theGuideLine.IsNull() || theProfile.IsNull() ) + // Check input parameters + if ( theGuideLine.IsNull() || theProfile.IsNull() ) { return false; + } - // build 3d shape TopoDS_Wire aPathWire = TopoDS::Wire( theGuideLine->GetShape3D() ); TopoDS_Wire aProfileWire = TopoDS::Wire( theProfile->GetShape3D() ); - if ( aPathWire.IsNull() || aProfileWire.IsNull() ) + if ( aPathWire.IsNull() || aProfileWire.IsNull() ) { return false; + } #ifdef DEB_CHANNEL BRepTools::Write( aPathWire, "guideline.brep" ); BRepTools::Write( aProfileWire, "profile.brep" ); #endif - HYDROData_Canal3dAnd2d aChannelConstructor( aProfileWire, aPathWire ); - if( aChannelConstructor.GetStatus() != 0 ) + // Pre-processing + Handle(HYDROData_PolylineXY) aPolylineXY = theGuideLine->GetPolylineXY(); + if ( aPolylineXY.IsNull() ) { return false; + } - aChannelConstructor.Create3dPresentation(); - aChannelConstructor.Create2dPresentation(); - thePrs.myPrs3D = aChannelConstructor.Get3dPresentation(); - thePrs.myPrs2D = aChannelConstructor.Get2dPresentation(); + /* + HYDROData_IPolyline::SectionType aSectionType = aPolylineXY->GetSectionType( 0 ); + HYDROData_IPolyline::PointsList aPolylinePoints = aPolylineXY->GetPoints( 0 ); + int aNbPoints = aPolylinePoints.Length(); + */ - thePrs.myLeftBank = aChannelConstructor.GetLeftBank(); - thePrs.myRightBank = aChannelConstructor.GetRightBank(); - thePrs.myInlet = aChannelConstructor.GetInlet(); - thePrs.myOutlet = aChannelConstructor.GetOutlet(); + HYDROData_Polyline3D::Polyline3DPoints aPolylinePoints3D = theGuideLine->GetPoints(); + int aNbPoints = aPolylinePoints3D.Length(); + if ( aNbPoints < 2 ) { + return false; + } + + // Get tangent in each point of the guide line ( 2D ) + TColgp_Array1OfDir aTangents( 1, aNbPoints ); + + HYDROData_IPolyline::SectionType aSectionType = aPolylineXY->GetSectionType( 0 ); + + if ( aSectionType == HYDROData_IPolyline::SECTION_POLYLINE ) { + for ( int i = 1; i <= aNbPoints; ++i ) { + gp_XYZ aPnt = aPolylinePoints3D.Value( i ); + aPnt.SetZ( 0. ); + gp_XYZ aPrevPnt; + if ( i > 1 ) { + aPrevPnt = aPolylinePoints3D.Value( i - 1 ); + aPrevPnt.SetZ( 0. ); + } + + gp_Vec aDir; + if ( i < aNbPoints ) { + gp_XYZ aNextPnt = aPolylinePoints3D.Value( i + 1 ); + aNextPnt.SetZ( 0. ); + + gp_Vec anEdgeVec( aPnt, aNextPnt ); + + if ( i == 1 ) { + aDir = anEdgeVec; + } else { + gp_Vec aPrevVec( aPrevPnt, aPnt ); + aDir = aPrevVec.Normalized() + anEdgeVec.Normalized(); + } + } else { + aDir = gp_Vec( aPrevPnt, aPnt ); + } + + aTangents.SetValue( i, aDir ); + } + } else { + // Get curve from the first edge ( 2D ) + TopTools_SequenceOfShape anEdges; + HYDROData_ShapesTool::ExploreShapeToShapes( aPolylineXY->GetShape(), TopAbs_EDGE, anEdges ); + Standard_Real aStart, anEnd; + + Handle(Geom_Curve) aCurve = BRep_Tool::Curve( TopoDS::Edge( anEdges.First() ), aStart, anEnd ); + GeomAPI_ProjectPointOnCurve aProject; + + // Get tangents + for ( int i = 1; i <= aNbPoints; ++i ) { + gp_XYZ aPointToTest = aPolylinePoints3D.Value( i ); + aPointToTest.SetZ( 0. ); + + aProject.Init( aPointToTest, aCurve ); + Quantity_Parameter aParam = aProject.LowerDistanceParameter(); + gp_Pnt aPnt; + gp_Vec aDir; + aCurve->D1( aParam, aPnt, aDir); + + aTangents.SetValue( i, aDir ); + } + } -#ifdef DEB_CHANNEL - BRepTools::Write( thePrs.myPrs2D, "channel2d.brep" ); - BRepTools::Write( thePrs.myPrs3D, "channel3d.brep" ); - HYDROData_ShapesTool::DumpShapeSubShapes( std::cout, "Top shape edges:", thePrs.myPrs2D, TopAbs_EDGE ); - HYDROData_ShapesTool::DumpShapeSubShapes( std::cout, "Left bank edges:", thePrs.myLeftBank, TopAbs_EDGE ); - HYDROData_ShapesTool::DumpShapeSubShapes( std::cout, "Right bank edges:", thePrs.myRightBank, TopAbs_EDGE ); - HYDROData_ShapesTool::DumpShapeSubShapes( std::cout, "Inlet edges:", thePrs.myInlet, TopAbs_EDGE ); - HYDROData_ShapesTool::DumpShapeSubShapes( std::cout, "Outlet edges:", thePrs.myOutlet, TopAbs_EDGE ); -#endif + // Get the profile middle point ( 3D ) + gp_Pnt aMiddlePoint( theProfile->GetMiddlePoint() ); + + // Translate the profile to each point on the guide line ( 3D ) + Handle(TColgp_HArray1OfPnt) anArrayOfFPnt = new TColgp_HArray1OfPnt(1, aNbPoints ); + Handle(TColgp_HArray1OfPnt) anArrayOfLPnt = new TColgp_HArray1OfPnt(1, aNbPoints ); + Handle(TopTools_HArray1OfShape) anArrOfProfiles = new TopTools_HArray1OfShape( 1, aNbPoints ); + + for ( int i = 1; i <= aNbPoints; ++i ) { + // Get point on the guide line + gp_Pnt aPointOnGuide( aPolylinePoints3D.Value( i ) ); + + // Define translation and rotation: + gp_Trsf Translation, Rotation; + + // Translation + Translation.SetTranslation( aMiddlePoint, aPointOnGuide ); + TopoDS_Wire aTransformedProfile = + TopoDS::Wire( BRepBuilderAPI_Transform( aProfileWire, Translation, Standard_True ) ); + + // Rotation + gp_Vec aVertical( 0., 0., 1. ); + TopoDS_Vertex aLeftVertex, aRightVertex; + TopExp::Vertices( aTransformedProfile, aLeftVertex, aRightVertex ); + gp_Pnt aLeftPoint = BRep_Tool::Pnt( aLeftVertex ); + gp_Pnt aRightPoint = BRep_Tool::Pnt( aRightVertex ); + gp_Vec aLeftToRight( aLeftPoint, aRightPoint); + gp_Vec NormalToProfile = aVertical ^ aLeftToRight; + + gp_Vec aDir = aTangents.Value( i ); + gp_Vec AxisOfRotation = NormalToProfile ^ aDir; + if (AxisOfRotation.Magnitude() <= gp::Resolution()) { + if ( aVertical * aLeftToRight < 0. ) { + gp_Ax1 theVertical(aPointOnGuide, gp::DZ() ); + Rotation.SetRotation(theVertical, M_PI); + } + } else { + gp_Ax1 theAxis(aPointOnGuide, AxisOfRotation); + Standard_Real theAngle = NormalToProfile.AngleWithRef(aDir, AxisOfRotation); + Rotation.SetRotation(theAxis, theAngle); + } + + aTransformedProfile = TopoDS::Wire(BRepBuilderAPI_Transform( aTransformedProfile, Rotation, Standard_True) ); + + // Get the first and the last points of the transformed profile + TopoDS_Vertex V1, V2; + TopExp::Vertices( aTransformedProfile, V1, V2 ); + + // Fill the data + anArrayOfFPnt->SetValue( i, BRep_Tool::Pnt( V1 ) ); + anArrayOfLPnt->SetValue( i, BRep_Tool::Pnt( V2 ) ); + + anArrOfProfiles->SetValue( i, aTransformedProfile ); + } - return true; + // Create presentation + HYDROData_Stream::PrsDefinition aPrs; + Handle(TopTools_HArray1OfShape) anArrOf2DProfiles; // we don't need 2D profiles for channel/digue presentation + bool aRes = HYDROData_Stream::CreatePresentations( anArrayOfFPnt, anArrayOfLPnt, + anArrOfProfiles, anArrOf2DProfiles, aPrs ); + if ( aRes ) { + thePrs.myPrs3D = aPrs.myPrs3D; + thePrs.myPrs2D = TopoDS::Face( aPrs.myPrs2D ); + BRepBuilderAPI_MakeWire aMakeWire( aPrs.myLeftBank ) ; + thePrs.myLeftBank = aMakeWire.Wire(); + aMakeWire = BRepBuilderAPI_MakeWire( aPrs.myRightBank ); + thePrs.myRightBank = aMakeWire.Wire(); + aMakeWire = BRepBuilderAPI_MakeWire( aPrs.myInlet ); + thePrs.myInlet = aMakeWire.Wire(); + aMakeWire = BRepBuilderAPI_MakeWire( aPrs.myOutlet ); + thePrs.myOutlet = aMakeWire.Wire(); + } + + return aRes; } void HYDROData_Channel::Update() diff --git a/src/HYDROData/HYDROData_Polyline3D.cxx b/src/HYDROData/HYDROData_Polyline3D.cxx index dfc002f1..67098e95 100644 --- a/src/HYDROData/HYDROData_Polyline3D.cxx +++ b/src/HYDROData/HYDROData_Polyline3D.cxx @@ -23,15 +23,30 @@ #include "HYDROData_PolylineXY.h" #include "HYDROData_Profile.h" #include "HYDROData_ProfileUZ.h" +#include "HYDROData_ShapesTool.h" #include "HYDROData_Tool.h" +#include + +#include + #include #include #include +#include + #include +#include +#include #include +#include + +#include + +#include + #include #include @@ -421,4 +436,76 @@ void HYDROData_Polyline3D::removeChildProfileUZ() */ } +HYDROData_Polyline3D::Polyline3DPoints HYDROData_Polyline3D::GetPoints() const +{ + Polyline3DPoints aPoints; + + Handle(HYDROData_PolylineXY) aPolylineXY = GetPolylineXY(); + TopoDS_Wire aWire = TopoDS::Wire( GetShape3D() ); + if ( aPolylineXY.IsNull() || aWire.IsNull() ) { + return aPoints; + } + + // Explode polyline on edges + TopTools_SequenceOfShape anEdges; + HYDROData_ShapesTool::ExploreShapeToShapes( aWire, TopAbs_EDGE, anEdges ); + + // Get points + if ( !anEdges.IsEmpty() ) { + HYDROData_IPolyline::SectionType aSectionType = aPolylineXY->GetSectionType( 0 ); + + if ( aSectionType == HYDROData_IPolyline::SECTION_POLYLINE ) { + // Get points from wire + /* Seems that intermediate vertices are duplicated + TopExp_Explorer anExp( aWire, TopAbs_VERTEX ); + for ( ; anExp.More(); anExp.Next() ) { + TopoDS_Vertex aVertex = TopoDS::Vertex( anExp.Current() ); + if ( !aVertex.IsNull() ) { + gp_Pnt aPnt = BRep_Tool::Pnt( aVertex ); + aPoints.Append( aPnt.XYZ() ); + } + } + */ + TopExp_Explorer anExp( aWire, TopAbs_EDGE ); + bool isFirst = true; + for ( ; anExp.More(); anExp.Next() ) { + TopoDS_Edge anEdge = TopoDS::Edge( anExp.Current() ); + if ( !anEdge.IsNull() ) { + TopoDS_Vertex aV1, aV2; + TopExp::Vertices( anEdge, aV1, aV2 ); + if ( isFirst ) { + gp_Pnt aPnt1 = BRep_Tool::Pnt( aV1 ); + aPoints.Append( aPnt1.XYZ() ); + } + + gp_Pnt aPnt2 = BRep_Tool::Pnt( aV2 ); + aPoints.Append( aPnt2.XYZ() ); + + isFirst = false; + } + } + } else { + // Get points from spline curve + Standard_Real aStart, anEnd; + Handle(Geom_Curve) aCurve = BRep_Tool::Curve( TopoDS::Edge( anEdges.First() ), aStart, anEnd ); + Handle(Geom_BSplineCurve) aGeomSpline = Handle(Geom_BSplineCurve)::DownCast( aCurve ); + + if ( !aGeomSpline.IsNull() ) { + int aNbKnots = aGeomSpline->NbKnots(); + + TColStd_Array1OfReal aSplineKnots( 1, aNbKnots ); + aGeomSpline->Knots( aSplineKnots ); + + for ( int i = 1; i <= aNbKnots; ++i ) { + const Standard_Real& aKnot = aSplineKnots.Value( i ); + gp_Pnt aPnt; + aGeomSpline->D0( aKnot, aPnt ); + aPoints.Append( aPnt.XYZ() ); + } + } + } + } + + return aPoints; +} diff --git a/src/HYDROData/HYDROData_Polyline3D.h b/src/HYDROData/HYDROData_Polyline3D.h index 259a5047..aa4520ff 100644 --- a/src/HYDROData/HYDROData_Polyline3D.h +++ b/src/HYDROData/HYDROData_Polyline3D.h @@ -154,6 +154,11 @@ public: */ HYDRODATA_EXPORT void SetChildProfileUZ( const Handle(HYDROData_ProfileUZ)& theProfile ); + /** + * Returns list of polyline points. + * \return list of 3D points + */ + HYDRODATA_EXPORT Polyline3DPoints GetPoints() const; protected: diff --git a/src/HYDROData/HYDROData_Profile.cxx b/src/HYDROData/HYDROData_Profile.cxx index 6fbfd97a..cef87e2f 100755 --- a/src/HYDROData/HYDROData_Profile.cxx +++ b/src/HYDROData/HYDROData_Profile.cxx @@ -29,6 +29,11 @@ #include #include +#include + +#include + +#include #include #include #include @@ -36,8 +41,10 @@ #include #include +#include #include #include +#include #include #include @@ -748,3 +755,40 @@ HYDROData_Profile::ProfilePoint HYDROData_Profile::GetBottomPoint() const return aBottom; } + HYDROData_Profile::ProfilePoint HYDROData_Profile::GetMiddlePoint() const + { + ProfilePoint aMiddlePoint; + + gp_XY aLeftPnt, aRightPnt; + if ( GetLeftPoint( aLeftPnt, false ) && GetRightPoint( aRightPnt, false ) ) { + gp_XYZ aPnt1( aLeftPnt.X(), aLeftPnt.Y(), 0. ); + gp_XYZ aPnt2( aRightPnt.X(), aRightPnt.Y(), 0. ); + gp_Pnt aMiddlePoint2d( 0.5 * ( aPnt1 + aPnt2 ) ); + + gp_Lin aMidLin( aMiddlePoint2d, gp::DZ() ); + TopoDS_Edge aMidEdge = BRepLib_MakeEdge( aMidLin ); + + TopoDS_Iterator anIt( TopoDS::Wire( GetShape3D() ) ); + for ( ; anIt.More(); anIt.Next()) { + const TopoDS_Edge& anEdge = TopoDS::Edge( anIt.Value() ); + + /* + Standard_Real aStart, anEnd; + Handle(Geom_Curve) aCurve = BRep_Tool::Curve( anEdge, aStart, anEnd ); + gp_Pnt aMiddlePointOnCurve = aCurve->Value( ( aStart + anEnd ) / 2 ); + */ + + BRepExtrema_ExtCC ExtremaEE( aMidEdge, anEdge); + if (ExtremaEE.IsDone() && ExtremaEE.NbExt() != 0) { + for ( Standard_Integer i = 1; i <= ExtremaEE.NbExt(); i++ ) { + if ( ExtremaEE.SquareDistance(i) <= Precision::Confusion() ) { + aMiddlePoint = ExtremaEE.PointOnE1(i).XYZ(); + break; + } + } + } + } + } + + return aMiddlePoint; + } \ No newline at end of file diff --git a/src/HYDROData/HYDROData_Profile.h b/src/HYDROData/HYDROData_Profile.h index 0c3ab048..fb7edcd7 100644 --- a/src/HYDROData/HYDROData_Profile.h +++ b/src/HYDROData/HYDROData_Profile.h @@ -196,6 +196,12 @@ public: */ HYDRODATA_EXPORT ProfilePoint GetBottomPoint() const; + /** + * Return profile middle point. + * \return non-parametric profile point + */ + HYDRODATA_EXPORT ProfilePoint GetMiddlePoint() const; + public: // Public methods to work with files. diff --git a/src/HYDROData/HYDROData_Stream.cxx b/src/HYDROData/HYDROData_Stream.cxx index e9da1296..42a62b57 100644 --- a/src/HYDROData/HYDROData_Stream.cxx +++ b/src/HYDROData/HYDROData_Stream.cxx @@ -73,7 +73,7 @@ #include #include -#include +#include #include @@ -197,11 +197,10 @@ bool HYDROData_Stream::CreatePresentations( const Handle(HYDROData_PolylineXY)& if ( theHydAxis.IsNull() || theProfiles.Length() < 2 ) return false; - gp_Pnt aPrevFirstPoint, aPrevLastPoint; Handle(TColgp_HArray1OfPnt) anArrayOfFPnt = new TColgp_HArray1OfPnt(1, theProfiles.Length()); Handle(TColgp_HArray1OfPnt) anArrayOfLPnt = new TColgp_HArray1OfPnt(1, theProfiles.Length()); - TopTools_Array1OfShape anArrOfProfiles(1, theProfiles.Length()); - TopTools_Array1OfShape anArrOf2DProfiles(1, theProfiles.Length()); + Handle(TopTools_HArray1OfShape) anArrOfProfiles = new TopTools_HArray1OfShape(1, theProfiles.Length()); + Handle(TopTools_HArray1OfShape) anArrOf2DProfiles = new TopTools_HArray1OfShape(1, theProfiles.Length()); // Pre-processing HYDROData_SequenceOfObjects::Iterator anIter( theProfiles ); @@ -217,11 +216,10 @@ bool HYDROData_Stream::CreatePresentations( const Handle(HYDROData_PolylineXY)& if ( !aProfile->GetLeftPoint( aPnt1, false ) || !aProfile->GetRightPoint( aPnt2, false ) ) continue; - anArrOfProfiles.SetValue(i,aProfile->GetShape3D());//aProfile->GetTopShape(); - anArrOf2DProfiles.SetValue(i,aProfile->GetTopShape()); + anArrOfProfiles->SetValue(i,aProfile->GetShape3D());//aProfile->GetTopShape(); + anArrOf2DProfiles->SetValue(i,aProfile->GetTopShape()); - gp_Pnt aCurFirstPoint( aPnt1.X(), aPnt1.Y(), 0 ), aCurFP; - gp_Pnt aCurLastPoint( aPnt2.X(), aPnt2.Y(), 0 ), aCurLP; + gp_Pnt aCurFP, aCurLP; TopoDS_Vertex aV1, aV2; TopExp::Vertices(TopoDS::Wire(aProf3d), aV1, aV2); gp_Pnt aP1 = BRep_Tool::Pnt(aV1); @@ -238,132 +236,7 @@ bool HYDROData_Stream::CreatePresentations( const Handle(HYDROData_PolylineXY)& anArrayOfLPnt->SetValue(i,aCurLP); } - // Construct of the 3D presentation - Handle(Geom_BSplineCurve) aBSpline = buildInterpolationCurve (anArrayOfFPnt); - if(aBSpline.IsNull()) - return false; - - TopoDS_Edge anEdgLeft, anEdgRight; - - BRepBuilderAPI_MakeEdge aMakeEdge(aBSpline); - if(aMakeEdge.IsDone()) - anEdgLeft = aMakeEdge.Edge(); - - if(anEdgLeft.IsNull()) - return false; - - aBSpline.Nullify(); - aBSpline = buildInterpolationCurve (anArrayOfLPnt); - if(aBSpline.IsNull()) - return false; - - aMakeEdge.Init(aBSpline); - if(aMakeEdge.IsDone()) - anEdgRight = aMakeEdge.Edge(); - - if(anEdgRight.IsNull()) - return false; - - BRep_Builder aBB; - TopoDS_Compound aCmp; - aBB.MakeCompound(aCmp); - anIter.Init( theProfiles ); - for (int i=1 ; i < anArrOfProfiles.Length() +1; i++ ) - aBB.Add(aCmp, anArrOfProfiles.Value(i)); - - aBB.Add(aCmp,anEdgLeft); - aBB.Add(aCmp,anEdgRight); - BRepCheck_Analyzer aCh(aCmp); - if(aCh.IsValid()) - thePrs.myPrs3D = aCmp; -#ifdef DEB_UPDATE - else { - BRepTools::Write(aCmp, "str3d.brep"); - thePrs.myPrs3D = aCmp; - } -#endif - - // Construct the top presentation - for(int i=1;i<= anArrayOfLPnt->Length();i++) { - gp_Pnt aPnt = anArrayOfFPnt->Value(i); - aPnt.SetZ(.0); // make 2d - anArrayOfFPnt->SetValue(i, aPnt); - aPnt = anArrayOfLPnt->Value(i); - aPnt.SetZ(.0); - anArrayOfLPnt->SetValue(i, aPnt); - } - - aBSpline.Nullify(); - aBSpline = buildInterpolationCurve (anArrayOfFPnt); - if(aBSpline.IsNull()) - return false; - - aMakeEdge.Init(aBSpline); - if(aMakeEdge.IsDone()) - anEdgLeft = aMakeEdge.Edge(); - - aBSpline.Nullify(); - aBSpline = buildInterpolationCurve (anArrayOfLPnt); - if(aBSpline.IsNull()) - return false; - - aMakeEdge.Init(aBSpline); - if(aMakeEdge.IsDone()) - anEdgRight = aMakeEdge.Edge(); - if(anEdgRight.IsNull()) - return false; - - BRepBuilderAPI_MakeEdge aMakeEdge2(anArrayOfFPnt->Value(1),anArrayOfLPnt->Value(1)); - TopoDS_Edge aBotEdge, aTopEdge; - if(aMakeEdge2.IsDone()) - aBotEdge = aMakeEdge2.Edge(); - - BRepBuilderAPI_MakeEdge aMakeEdge3(anArrayOfFPnt->Value(anArrayOfFPnt->Length()),anArrayOfLPnt->Value(anArrayOfLPnt->Length())); - if(aMakeEdge3.IsDone()) - aTopEdge = aMakeEdge3.Edge(); - - // Make wire for 2D presentation with updating of corresponding edges - BRepBuilderAPI_MakeWire aMakeWire; - - aMakeWire.Add( aBotEdge ); - thePrs.myInlet = aMakeWire.Edge(); - - aMakeWire.Add( anEdgLeft ); - thePrs.myLeftBank = aMakeWire.Edge(); - - aMakeWire.Add( aTopEdge ); - thePrs.myOutlet = aMakeWire.Edge(); - - aMakeWire.Add( anEdgRight ); - thePrs.myRightBank = aMakeWire.Edge(); - - TopoDS_Wire aSectProfileWire; - if(aMakeWire.IsDone()) - aSectProfileWire = aMakeWire.Wire(); - - BRepBuilderAPI_MakeFace aMakeFace( aSectProfileWire, Standard_True ); - TopoDS_Face aFace; - aMakeFace.Build(); - if( aMakeFace.IsDone() ) - aFace = aMakeFace.Face(); - - aCmp.Nullify(); - aBB.MakeCompound(aCmp); - aBB.Add(aCmp,aFace); - for(int i=1;i <= anArrOf2DProfiles.Length(); i++) - aBB.Add(aCmp,anArrOf2DProfiles.Value(i)); - - aCh.Init(aCmp); - if(aCh.IsValid()) - thePrs.myPrs2D = aCmp; -#ifdef DEB_UPDATE - else { - BRepTools::Write(aCmp, "str2d.brep"); - thePrs.myPrs2D = aCmp; - } -#endif - - return true; + return CreatePresentations( anArrayOfFPnt, anArrayOfLPnt, anArrOfProfiles, anArrOf2DProfiles, thePrs ); } void HYDROData_Stream::UpdatePrs() @@ -1182,4 +1055,156 @@ void HYDROData_Stream::CopyTo( const Handle(HYDROData_Entity)& theDestination ) } } } +} + +bool HYDROData_Stream::CreatePresentations( const Handle(TColgp_HArray1OfPnt) theArrayOfFPnt, + const Handle(TColgp_HArray1OfPnt) theArrayOfLPnt, + const Handle(TopTools_HArray1OfShape) theArrOfProfiles, + const Handle(TopTools_HArray1OfShape) theArrOf2DProfiles, + PrsDefinition& thePrs ) +{ + if ( theArrayOfFPnt.IsNull() || theArrayOfLPnt.IsNull() || theArrOfProfiles.IsNull() ) { + return false; + } + + if ( theArrayOfFPnt->Length() != theArrayOfLPnt->Length() ) { + return false; + } + + // Construct of the 3D presentation + Handle(Geom_BSplineCurve) aBSpline = buildInterpolationCurve (theArrayOfFPnt); + if(aBSpline.IsNull()) + return false; + + TopoDS_Edge anEdgLeft, anEdgRight; + + BRepBuilderAPI_MakeEdge aMakeEdge(aBSpline); + if(aMakeEdge.IsDone()) + anEdgLeft = aMakeEdge.Edge(); + + if(anEdgLeft.IsNull()) + return false; + + aBSpline.Nullify(); + aBSpline = buildInterpolationCurve (theArrayOfLPnt); + if(aBSpline.IsNull()) + return false; + + aMakeEdge.Init(aBSpline); + if(aMakeEdge.IsDone()) + anEdgRight = aMakeEdge.Edge(); + + if(anEdgRight.IsNull()) + return false; + + BRep_Builder aBB; + TopoDS_Compound aCmp; + aBB.MakeCompound(aCmp); + for (int i=1 ; i < theArrOfProfiles->Length() +1; i++ ) + aBB.Add(aCmp, theArrOfProfiles->Value(i)); + + aBB.Add(aCmp,anEdgLeft); + aBB.Add(aCmp,anEdgRight); + BRepCheck_Analyzer aCh(aCmp); + if(aCh.IsValid()) + thePrs.myPrs3D = aCmp; +#ifdef DEB_UPDATE + else { + BRepTools::Write(aCmp, "str3d.brep"); + thePrs.myPrs3D = aCmp; + } +#endif + + // Construct the top presentation + int aNbPoints = theArrayOfFPnt->Length(); + Handle(TColgp_HArray1OfPnt) anArrayOfFPnt = new TColgp_HArray1OfPnt(1, aNbPoints); + Handle(TColgp_HArray1OfPnt) anArrayOfLPnt = new TColgp_HArray1OfPnt(1, aNbPoints); + for( int i=1; i <= aNbPoints; i++ ) { + gp_Pnt aPnt = theArrayOfFPnt->Value(i); + aPnt.SetZ(.0); // make 2d + anArrayOfFPnt->SetValue(i, aPnt); + aPnt = theArrayOfLPnt->Value(i); + aPnt.SetZ(.0); + anArrayOfLPnt->SetValue(i, aPnt); + } + + aBSpline.Nullify(); + aBSpline = buildInterpolationCurve (anArrayOfFPnt); + if(aBSpline.IsNull()) + return false; + + aMakeEdge.Init(aBSpline); + if(aMakeEdge.IsDone()) + anEdgLeft = aMakeEdge.Edge(); + + aBSpline.Nullify(); + aBSpline = buildInterpolationCurve (anArrayOfLPnt); + if(aBSpline.IsNull()) + return false; + + aMakeEdge.Init(aBSpline); + if(aMakeEdge.IsDone()) + anEdgRight = aMakeEdge.Edge(); + if(anEdgRight.IsNull()) + return false; + + BRepBuilderAPI_MakeEdge aMakeEdge2(anArrayOfFPnt->Value(1),anArrayOfLPnt->Value(1)); + TopoDS_Edge aBotEdge, aTopEdge; + if(aMakeEdge2.IsDone()) + aBotEdge = aMakeEdge2.Edge(); + + BRepBuilderAPI_MakeEdge aMakeEdge3(anArrayOfFPnt->Value(anArrayOfFPnt->Length()),anArrayOfLPnt->Value(anArrayOfLPnt->Length())); + if(aMakeEdge3.IsDone()) + aTopEdge = aMakeEdge3.Edge(); + + // Make wire for 2D presentation with updating of corresponding edges + BRepBuilderAPI_MakeWire aMakeWire; + + aMakeWire.Add( aBotEdge ); + thePrs.myInlet = aMakeWire.Edge(); + + aMakeWire.Add( anEdgLeft ); + thePrs.myLeftBank = aMakeWire.Edge(); + + aMakeWire.Add( aTopEdge ); + thePrs.myOutlet = aMakeWire.Edge(); + + aMakeWire.Add( anEdgRight ); + thePrs.myRightBank = aMakeWire.Edge(); + + TopoDS_Wire aSectProfileWire; + if(aMakeWire.IsDone()) + aSectProfileWire = aMakeWire.Wire(); + + BRepBuilderAPI_MakeFace aMakeFace( aSectProfileWire, Standard_True ); + TopoDS_Face aFace; + aMakeFace.Build(); + if( aMakeFace.IsDone() ) + aFace = aMakeFace.Face(); + + TopoDS_Shape aPrs2D; + + if ( !theArrOf2DProfiles.IsNull() ) { + aCmp.Nullify(); + aBB.MakeCompound(aCmp); + aBB.Add(aCmp,aFace); + for(int i=1;i <= theArrOf2DProfiles->Length(); i++) + aBB.Add(aCmp, theArrOf2DProfiles->Value(i)); + + aPrs2D = aCmp; + } else { + aPrs2D = aFace; + } + + aCh.Init(aPrs2D); + if(aCh.IsValid()) + thePrs.myPrs2D = aPrs2D; +#ifdef DEB_UPDATE + else { + BRepTools::Write(aPrs2D, "str2d.brep"); + thePrs.myPrs2D = aPrs2D; + } +#endif + + return true; } \ No newline at end of file diff --git a/src/HYDROData/HYDROData_Stream.h b/src/HYDROData/HYDROData_Stream.h index 16d76503..6ebf6427 100644 --- a/src/HYDROData/HYDROData_Stream.h +++ b/src/HYDROData/HYDROData_Stream.h @@ -33,6 +33,7 @@ class Handle(HYDROData_Polyline3D); class Handle(HYDROData_Profile); class HYDROData_IProfilesInterpolator; class TColStd_Array1OfReal; +class Handle(TopTools_HArray1OfShape); /**\class HYDROData_Stream @@ -79,6 +80,16 @@ public: const HYDROData_SequenceOfObjects& theProfiles, PrsDefinition& thePrs ); + /** + * Creates the presentations(2D and 3D) by given first points, last points and profiles. + * If 2D profiles is null - they will not used in the presentation. + */ + HYDRODATA_EXPORT static bool CreatePresentations( const Handle(TColgp_HArray1OfPnt) theArrayOfFPnt, + const Handle(TColgp_HArray1OfPnt) theArrayOfLPnt, + const Handle(TopTools_HArray1OfShape) theArrOfProfiles, + const Handle(TopTools_HArray1OfShape) theArrOf2DProfiles, + PrsDefinition& thePrs ); + public: /** -- 2.39.2