From 8d1d3f766a6ce506855d883631dac35b7b6f012c Mon Sep 17 00:00:00 2001 From: Dario Sassi Date: Tue, 16 Jul 2024 08:38:40 +0200 Subject: [PATCH] =?UTF-8?q?EgtGeomKernel=20:=20-=20irrobustita=20funzione?= =?UTF-8?q?=20IsClosedAndFlat=20di=20PolyLine=20(facendo=20i=20conti=20ris?= =?UTF-8?q?petto=20al=20baricentro)=20-=20per=20Regioni=20quando=20si=20ag?= =?UTF-8?q?giune=20il=20loop=20esterno,=20se=20risulta=20formato=20da=20pi?= =?UTF-8?q?=C3=B9=20parti=20disgiunte=20(per=20autonitersezioni)=20si=20ig?= =?UTF-8?q?norano=20quelle=20molto=20piccole.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- PolyLine.cpp | 17 ++++++++++++++--- SurfFlatRegion.cpp | 16 +++++++++++++--- SurfFlatRegion.h | 2 +- 3 files changed, 28 insertions(+), 7 deletions(-) diff --git a/PolyLine.cpp b/PolyLine.cpp index 755b064..4678ce9 100644 --- a/PolyLine.cpp +++ b/PolyLine.cpp @@ -587,18 +587,29 @@ PolyLine::IsClosedAndFlat( Plane3d& plPlane, double& dArea, double dToler) const // Test if closed if ( ! IsClosed()) return false ; - // Compute a representative plane for the polygon Point3d ptP ; + // Calcolo il centro (per minimizzare gli errori nelle successive operazioni) + Point3d ptCen = ORIG ; + int nCount = 0 ; + for ( bool bFound = GetFirstPoint( ptP) ; bFound ; bFound = GetNextPoint( ptP)) { + ptCen += ptP ; + ++ nCount ; + } + ptCen /= nCount ; + Vector3d vtMove = ptCen - ORIG ; + // Compute a representative plane for the polygon (faccio il calcolo nel centro e poi traslo al contrario il piano) PolygonPlane PolyPlane ; for ( bool bFound = GetFirstPoint( ptP) ; bFound ; bFound = GetNextPoint( ptP)) - PolyPlane.AddPoint( ptP) ; + PolyPlane.AddPoint( ptP - vtMove) ; if ( ! PolyPlane.GetPlane( plPlane) || ! PolyPlane.GetArea( dArea)) { dArea = 0 ; return IsFlat( plPlane, dToler) ; } + plPlane.Translate( vtMove) ; + // Sistemo il piano per l'offset utilizzato // Test each vertex to see if it is farther from plane than allowed max distance for ( bool bFound = GetFirstPoint( ptP) ; bFound ; bFound = GetNextPoint( ptP)) { - double dDist = ( ( ptP - ORIG) * plPlane.GetVersN()) - plPlane.GetDist() ; + double dDist = DistPointPlane( ptP, plPlane) ; if ( abs( dDist) > dToler) return false ; } diff --git a/SurfFlatRegion.cpp b/SurfFlatRegion.cpp index 0027f7c..41b74cb 100644 --- a/SurfFlatRegion.cpp +++ b/SurfFlatRegion.cpp @@ -109,18 +109,25 @@ SurfFlatRegion::AddExtLoop( ICurve* pCrv) if ( ! AdjustLoops( Release( pMyCrv), CrvLst, true)) return false ; // aggiungo le singole curve + int nExtAdded = 0 ; bool bOk = true ; for ( auto& pSingCrv : CrvLst) { - if ( ! AddSimpleExtLoop( pSingCrv)) + bool bAdded = false ; + if ( AddSimpleExtLoop( pSingCrv, bAdded)) + ++ nExtAdded ; + else bOk = false ; + } - return bOk ; + return ( bOk && nExtAdded > 0) ; } //---------------------------------------------------------------------------- bool -SurfFlatRegion::AddSimpleExtLoop( ICurve* pCrv) +SurfFlatRegion::AddSimpleExtLoop( ICurve* pCrv, bool& bAdded) { + // default + bAdded = false ; // acquisisco la curva PtrOwner pMyCrv( pCrv) ; if ( IsNull( pMyCrv)) @@ -133,6 +140,8 @@ SurfFlatRegion::AddSimpleExtLoop( ICurve* pCrv) Plane3d plPlane ; if ( ! pMyCrv->GetArea( plPlane, dArea)) return false ; + if ( dArea < SQ_EPS_SMALL) + return true ; // se sto costruendo il primo chunk if ( m_vExtInd.size() == 0) { // assegno il riferimento intrinseco @@ -198,6 +207,7 @@ SurfFlatRegion::AddSimpleExtLoop( ICurve* pCrv) m_OGrMgr.Reset() ; // imposto ricalcolo Voronoi ResetVoronoiObject() ; + bAdded = true ; return true ; } diff --git a/SurfFlatRegion.h b/SurfFlatRegion.h index c1198e8..d257fce 100644 --- a/SurfFlatRegion.h +++ b/SurfFlatRegion.h @@ -142,7 +142,7 @@ class SurfFlatRegion : public ISurfFlatRegion, public IGeoObjRW private : bool CopyFrom( const SurfFlatRegion& clSrc) ; - bool AddSimpleExtLoop( ICurve* pCrv) ; + bool AddSimpleExtLoop( ICurve* pCrv, bool& bAdded) ; bool MyAddExtLoop( ICurve* pCrv) ; bool AddSimpleIntLoop( ICurve* pCrv) ; bool MyAddIntLoop( ICurve* pCrv, int nChunk) ;