EgtGeomKernel :
- miglioramento delle superfici di bezier. - aggiunta di una funzione per l'eliminazione delle span collassate e di una per l'inversione dei paramettri di una superficie.
This commit is contained in:
@@ -474,7 +474,8 @@ Tree::Split( int nId, double dSplitValue)
|
||||
GetPoint( dSplitValue, cToSplit.GetTopLeft().y, ptP01) ;
|
||||
GetPoint( cToSplit.GetTopRight().x, cToSplit.GetTopRight().y, ptP11) ;
|
||||
}
|
||||
if( AreSamePointApprox( ptP00, ptP10) && AreSamePointApprox( ptP01, ptP11))
|
||||
if( AreSamePointApprox( ptP00, ptP10) && AreSamePointApprox( ptP01, ptP11) &&
|
||||
( cToSplit.GetBottomRight().x - dSplitValue < SBZ_TREG_COEFF - EPS_SMALL || dSplitValue - cToSplit.GetBottomLeft().x < SBZ_TREG_COEFF - EPS_SMALL))
|
||||
bGoodSplitVert = false ;
|
||||
}
|
||||
if( bGoodSplitHoriz) {
|
||||
@@ -490,7 +491,8 @@ Tree::Split( int nId, double dSplitValue)
|
||||
GetPoint( cToSplit.GetTopLeft().x, cToSplit.GetTopLeft().y, ptP01) ;
|
||||
GetPoint( cToSplit.GetTopRight().x, cToSplit.GetTopRight().y, ptP11) ;
|
||||
}
|
||||
if( AreSamePointApprox( ptP00, ptP01) && AreSamePointApprox( ptP10, ptP11))
|
||||
if( AreSamePointApprox( ptP00, ptP01) && AreSamePointApprox( ptP10, ptP11) &&
|
||||
( cToSplit.GetTopLeft().y - dSplitValue < SBZ_TREG_COEFF - EPS_SMALL || dSplitValue - cToSplit.GetBottomLeft().y < SBZ_TREG_COEFF - EPS_SMALL))
|
||||
bGoodSplitHoriz = false ;
|
||||
}
|
||||
|
||||
@@ -786,6 +788,8 @@ Tree::BuildTree( double dLinTol, double dSideMin, double dSideMax)
|
||||
nCToSplit = pcToSplit->m_nChild1 ;
|
||||
pcToSplit = &m_mTree[nCToSplit] ;
|
||||
}
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
else {
|
||||
// sono arrivato ad una cella Leaf, quindi salvo la cella
|
||||
@@ -899,6 +903,8 @@ Tree::BuildTree( double dLinTol, double dSideMin, double dSideMax)
|
||||
nCToSplit = pcToSplit->m_nChild1 ;
|
||||
pcToSplit = &m_mTree[nCToSplit] ;
|
||||
}
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
else {
|
||||
// sono arrivato ad una cella Leaf, quindi salvo la cella
|
||||
@@ -1435,19 +1441,20 @@ Tree::GetPolygons( POLYLINEMATRIX& vvPolygons, POLYLINEMATRIX& vvPolygons3d, vec
|
||||
if ( ! TraceLoopLabelCell( vPolygonsBasic))
|
||||
return false ;
|
||||
// scorro sulle celle e costruisco i poligoni
|
||||
int nCells = int( vPolygonsBasic.size()) ;
|
||||
for ( int i = 0 ; i < nCells ; ++ i) {
|
||||
int nPoly = 0 ;
|
||||
for ( int nId: m_vnLeaves) {
|
||||
// costruisco i poligoni partendo dal vettore delle intersezioni, come spiegato a pag15 di Cripps
|
||||
int nId = m_vnLeaves[i] ;
|
||||
if ( m_mTree[nId].m_nFlag == 4) {
|
||||
// vettore dei poligoni ( loop) della cella nId
|
||||
vvPolygons.emplace_back() ;
|
||||
vvPolygons.back().push_back(std::move(vPolygonsCorrected[i])) ;
|
||||
vvPolygons.back().push_back(std::move(vPolygonsCorrected[nPoly])) ;
|
||||
vvPolygons3d.emplace_back() ;
|
||||
vvPolygons3d.back().push_back(std::move(vPolygonsBasic3d[i])) ;
|
||||
vvPolygons3d.back().push_back(std::move(vPolygonsBasic3d[nPoly])) ;
|
||||
}
|
||||
else if ( m_mTree[nId].m_nFlag == 0)
|
||||
continue ;
|
||||
else if( m_mTree[nId].m_nCollapsed != Cell::Collapsed::NO_COLLAPSE)
|
||||
continue ;
|
||||
else {
|
||||
// vettore in cui salvo il chunk di appartenenza di ogni loop che attraversa la cella
|
||||
INTVECTOR vnParentChunk ;
|
||||
@@ -1461,13 +1468,14 @@ Tree::GetPolygons( POLYLINEMATRIX& vvPolygons, POLYLINEMATRIX& vvPolygons3d, vec
|
||||
while ( ! vToCheck.empty()) {
|
||||
int nPolyBefore = nPoly ;
|
||||
PolyLine pl3d ;
|
||||
CreateCellPolygons( i, vvPolygons, vvPolygons3d, vToCheck, nPoly, vnParentChunk, vPolygonsCorrected[i], vPolygonsBasic3d[i]) ;
|
||||
CreateCellPolygons( nId, vvPolygons, vvPolygons3d, vToCheck, nPoly, vnParentChunk, vPolygonsCorrected[nPoly], vPolygonsBasic3d[nPoly]) ;
|
||||
if ( nPolyBefore == nPoly)
|
||||
break ;
|
||||
}
|
||||
// ora analizzo anche i loop che sono contenuti nella cella
|
||||
CreateIslandAndHoles( i, vvPolygons, vvPolygons3d, nPoly, vnParentChunk, vPolygonsCorrected[i], vPolygonsBasic3d[i]) ;
|
||||
CreateIslandAndHoles( nId, vvPolygons, vvPolygons3d, nPoly, vnParentChunk, vPolygonsCorrected[nPoly], vPolygonsBasic3d[nPoly]) ;
|
||||
}
|
||||
++ nPoly ;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1910,10 +1918,9 @@ Tree::FindCell( const Point3d& ptToAssign, const CurveLine& clTrim, bool bRecurs
|
||||
nCells.push_back( nId) ;
|
||||
if ( ! bRecurs) {
|
||||
// se sono in un vertice o su un lato devo controllare di aver trovato la cella giusta
|
||||
Point3d ptBr( m_mTree.at( nId).GetTopRight().x , m_mTree.at( nId).GetBottomLeft().y) ;
|
||||
Point3d ptTl( m_mTree.at( nId).GetBottomLeft().x , m_mTree.at( nId).GetTopRight().y) ;
|
||||
if ( abs( ptToAssign.x - ptTl.x) < EPS_SMALL || abs( ptToAssign.x - ptBr.x) < EPS_SMALL ||
|
||||
abs( ptToAssign.y - ptTl.y) < EPS_SMALL || abs( ptToAssign.y - ptBr.y) < EPS_SMALL) {
|
||||
int nEdge = - 2 ;
|
||||
OnWhichEdge( nId, ptToAssign, nEdge) ;
|
||||
if ( nEdge != - 2) {
|
||||
Vector3d vtDir ;
|
||||
clTrim.GetStartDir( vtDir) ;
|
||||
// proseguo lungo la curva di trim di EPS_SMALL
|
||||
@@ -1964,12 +1971,16 @@ Tree::FindCell( const Point3d& ptToAssign, const CurveLine& cl, INTVECTOR vCells
|
||||
}
|
||||
// se non ho trovato nulla vuol dire che sono su un vertice o su un lato
|
||||
if ( nCells.empty() && ! bRecurs) {
|
||||
int nEdge = -1 ;
|
||||
int nEdge = -2 ;
|
||||
for ( int nCell : vCells) {
|
||||
OnWhichEdge( nCell,ptToAssign, nEdge) ;
|
||||
if ( nEdge != -1)
|
||||
break ;
|
||||
OnWhichEdge( nCell, ptToAssign, nEdge) ;
|
||||
if ( nEdge != -2 && (m_mTree.at(nCell).m_nCollapsed == Cell::Collapsed::NO_COLLAPSE || m_mTree.at(nCell).m_nCollapsed == Cell::Collapsed::TO_VERIFY))
|
||||
nCells.push_back( nCell) ;
|
||||
nEdge = -2 ;
|
||||
}
|
||||
if( ssize( nCells) == 1)
|
||||
return nCells ;
|
||||
|
||||
Vector3d vtDir ;
|
||||
cl.GetStartDir( vtDir) ;
|
||||
Point3d ptIntersPlus = ptToAssign ;
|
||||
@@ -1977,7 +1988,7 @@ Tree::FindCell( const Point3d& ptToAssign, const CurveLine& cl, INTVECTOR vCells
|
||||
// potrei essere su un lato
|
||||
if ( nEdge == 0 || nEdge == 1 || nEdge == 2 || nEdge == 3) {
|
||||
// se è orientato con il lato mi sposto a destra
|
||||
if ( ( nEdge == 0 || nEdge == 2 ) && abs(vtDir.x) > 1 - EPS_SMALL/100 ) {
|
||||
if ( ( nEdge == 0 || nEdge == 2 ) && abs(vtDir.x) > 1 - EPS_SMALL/100) {
|
||||
Vector3d vtDirDX = vtDir ; vtDirDX.Rotate( Z_AX, -90) ;
|
||||
ptIntersPlus = ptIntersPlus + vtDirDX * EPS_SMALL ;
|
||||
}
|
||||
@@ -1996,10 +2007,17 @@ Tree::FindCell( const Point3d& ptToAssign, const CurveLine& cl, INTVECTOR vCells
|
||||
if ( abs(vtDir.x) < 1 - EPS_SMALL/100 && abs(vtDir.y) < 1 - EPS_SMALL/100 )
|
||||
ptIntersPlus = ptIntersPlus + vtDir * EPS_SMALL ;
|
||||
// altrimenti ruoto a destra
|
||||
else {
|
||||
else if( ( nEdge == 4 && vtDir.x > 1 - EPS_SMALL / 100) || ( nEdge == 6 && vtDir.x < - 1 + EPS_SMALL / 100) ||
|
||||
( nEdge == 5 && vtDir.y > 1 - EPS_SMALL / 100) || ( nEdge == 7 && vtDir.y < - 1 + EPS_SMALL / 100)) {
|
||||
Vector3d vtDirDX = vtDir ; vtDirDX.Rotate( Z_AX, -45) ;
|
||||
ptIntersPlus = ptIntersPlus + vtDirDX * EPS_SMALL ;
|
||||
}
|
||||
// altrimenti ruoto a sinistra
|
||||
else /*if( ( nEdge == 4 && vtDir.y < - 1 + EPS_SMALL / 100) || ( nEdge == 6 && vtDir.y < 1 - EPS_SMALL / 100) ||
|
||||
( nEdge == 5 && vtDir.x > 1 - EPS_SMALL / 100) || ( nEdge == 7 && vtDir.x < - 1 + EPS_SMALL / 100)) // + tutti gli altri casi */ {
|
||||
Vector3d vtDirDX = vtDir ; vtDirDX.Rotate( Z_AX, 45) ;
|
||||
ptIntersPlus = ptIntersPlus + vtDirDX * EPS_SMALL ;
|
||||
}
|
||||
}
|
||||
//
|
||||
else
|
||||
@@ -2011,7 +2029,7 @@ Tree::FindCell( const Point3d& ptToAssign, const CurveLine& cl, INTVECTOR vCells
|
||||
ptIntersPlus = ptToAssign + vtDirSX * EPS_SMALL ;
|
||||
}
|
||||
// rilancio la rigida ricerca
|
||||
nCells = FindCell( ptIntersPlus, cl, vCells, true) ;
|
||||
nCells = FindCell( ptIntersPlus, cl, nCells, true) ;
|
||||
}
|
||||
|
||||
return nCells ;
|
||||
@@ -2117,9 +2135,10 @@ Tree::TraceLoopLabelCell( const POLYLINEVECTOR& vplPolygons)
|
||||
pCell->m_vInters.back().nChunk = m_mChunk[i] ;
|
||||
bool bLoopInside = true ;
|
||||
Point3d ptCurr ;
|
||||
auto iter = find( m_vnLeaves.begin(), m_vnLeaves.end(), nId) ;
|
||||
int nIdPolygon = distance( m_vnLeaves.begin(), iter) ;
|
||||
if ( nIdPolygon > int( vplPolygons.size()) - 1)
|
||||
int nIdPolygon = - 1;
|
||||
if( ! pCell->m_vnPolyId.empty())
|
||||
nIdPolygon = pCell->m_vnPolyId[0] ;
|
||||
else
|
||||
return false ;
|
||||
bool bEraseNextPoint = false ;
|
||||
while ( plLoop.GetNextPoint( ptCurr)) {
|
||||
@@ -2128,6 +2147,8 @@ Tree::TraceLoopLabelCell( const POLYLINEVECTOR& vplPolygons)
|
||||
plLoop.GetNextPoint( ptTEnd) ;
|
||||
CurveLine clTrim ;
|
||||
clTrim.Set( ptTStart, ptTEnd) ;
|
||||
Point3d ptLastInters = P_INVALID ;
|
||||
int nInfiniteLoopCount = 0 ;
|
||||
// qui devo mettere una tolleranza negativa per poter tener conto anche dei punti che sono SULLA curva
|
||||
while ( ! IsPointInsidePolyLine( ptCurr, vplPolygons[nIdPolygon], dLinTol)) {
|
||||
// sto uscendo dalla cella, quindi cerco l'intersezione
|
||||
@@ -2153,13 +2174,23 @@ Tree::TraceLoopLabelCell( const POLYLINEVECTOR& vplPolygons)
|
||||
return false ;
|
||||
bEraseNextPoint = true ;
|
||||
}
|
||||
// ricalcolo la posizione di nId nel vettore delle foglie
|
||||
iter = find( m_vnLeaves.begin(), m_vnLeaves.end(), nId) ;
|
||||
nIdPolygon = distance( m_vnLeaves.begin(), iter) ;
|
||||
if ( nIdPolygon > int( vplPolygons.size()) - 1)
|
||||
return false ;
|
||||
// se l'intersezione e la stessa della precedente allora potrei essere entrato in un loop infinito
|
||||
// se per più volte il punto di intersezione resta più o meno lo stesso allora blocco tutto
|
||||
if( AreSamePointEpsilon( vptInters.back(), ptLastInters, 10 * EPS_SMALL)) {
|
||||
++ nInfiniteLoopCount ;
|
||||
if( nInfiniteLoopCount == 4) {
|
||||
LOG_ERROR( GetEGkLogger(), "Error Triangulating SurfBezier: infinte while loop occured in Tree::TraceLoopLabelCell")
|
||||
return false ;
|
||||
}
|
||||
}
|
||||
ptLastInters = vptInters.back() ;
|
||||
// aggiorno il puntatore alla cella
|
||||
pCell = &m_mTree[nId] ;
|
||||
// recupero l'indice del poligono base associato alla cella
|
||||
if( ! pCell->m_vnPolyId.empty())
|
||||
nIdPolygon = pCell->m_vnPolyId[0] ;
|
||||
else
|
||||
return false ;
|
||||
// salvo il verso del loop
|
||||
pCell->m_vInters.back().bCCW = bCCW ;
|
||||
// salvo il chunk del loop
|
||||
@@ -2783,11 +2814,10 @@ Tree::FindInters( int& nId, const CurveLine& clTrim, const PolyLine& plPolygon,
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
bool
|
||||
Tree::CreateCellPolygons( int nLeafId, POLYLINEMATRIX& vPolygons, POLYLINEMATRIX& vPolygons3d, INTVECTOR& vToCheck, int& nPoly,
|
||||
Tree::CreateCellPolygons( int nId, POLYLINEMATRIX& vPolygons, POLYLINEMATRIX& vPolygons3d, INTVECTOR& vToCheck, int& nPoly,
|
||||
INTVECTOR& vnParentChunk, const PolyLine& plCell, const PolyLine& plCell3d)
|
||||
{
|
||||
// conto quanti vertici in più ho per lato e creo un vettore dei vertici per lato
|
||||
int nId = m_vnLeaves[nLeafId] ;
|
||||
Cell& cCell = m_mTree[nId] ;
|
||||
PNTMATRIX vEdgeVertex(4) ;
|
||||
PNTMATRIX vEdgeVertex3d(4) ;
|
||||
@@ -2795,7 +2825,7 @@ Tree::CreateCellPolygons( int nLeafId, POLYLINEMATRIX& vPolygons, POLYLINEMATRIX
|
||||
Point3d ptTR = cCell.GetTopRight() ;
|
||||
Point3d ptTl = cCell.GetTopLeft() ;
|
||||
Point3d ptBr = cCell.GetBottomRight() ;
|
||||
int nVertToErase = m_mTree.at(nId).m_nVertToErase ;
|
||||
int nVertToErase = cCell.m_nVertToErase ;
|
||||
if ( nVertToErase != 2)
|
||||
vEdgeVertex[0].push_back( ptTR) ;
|
||||
if ( nVertToErase != 3)
|
||||
@@ -3116,11 +3146,10 @@ Tree::CreateCellPolygons( int nLeafId, POLYLINEMATRIX& vPolygons, POLYLINEMATRIX
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
bool
|
||||
Tree::CreateIslandAndHoles( int nLeafId, POLYLINEMATRIX& vPolygons, POLYLINEMATRIX& vPolygons3d, int& nPoly, INTVECTOR& vnParentChunk,
|
||||
Tree::CreateIslandAndHoles( int nId, POLYLINEMATRIX& vPolygons, POLYLINEMATRIX& vPolygons3d, int& nPoly, INTVECTOR& vnParentChunk,
|
||||
const PolyLine& plPolygonsBasic, const PolyLine& plPolygonsBasic3d)
|
||||
{
|
||||
// costruisco i poligoni partendo dal vettore delle intersezioni
|
||||
int nId = m_vnLeaves[nLeafId] ;
|
||||
Cell& cCell = m_mTree[nId] ;
|
||||
//capisco se sono in modalità ForTriangulation
|
||||
|
||||
@@ -3994,7 +4023,9 @@ Tree::OnWhichEdge( int nId, const Point3d& ptToAssign, int& nEdge) const
|
||||
Point3d ptTl ( ptBL.x, ptTR.y) ;
|
||||
Point3d ptBr ( ptTR.x, ptBL.y) ;
|
||||
|
||||
if ( AreSamePointXYApprox( ptToAssign, ptTR))
|
||||
if( ptToAssign.y < ptBL.y - EPS_SMALL || ptToAssign.y > ptTR.y + EPS_SMALL || ptToAssign.x < ptBL.x - EPS_SMALL || ptToAssign.x > ptTR.x + EPS_SMALL)
|
||||
return false ;
|
||||
else if ( AreSamePointXYApprox( ptToAssign, ptTR))
|
||||
nEdge = 7 ;
|
||||
else if ( AreSamePointXYApprox( ptToAssign, ptTl))
|
||||
nEdge = 4 ;
|
||||
|
||||
Reference in New Issue
Block a user