EgtGeomKernel :
- sistemati vari bug nella creazione della superficie trimesh trimmata si una superficie di bezier Problemi noti : - sui casi con un tree reale entro in un loop infinito o seleziono oppure seleziono un elemento inesistente di un vettore
This commit is contained in:
@@ -1393,6 +1393,12 @@ Tree::FindCell( const Point3d& ptToAssign, CurveLine& clTrim) const
|
||||
//nCells.push_back( - 2) ;
|
||||
return nCells ;
|
||||
}
|
||||
|
||||
// se lo spazio parametrico non è stato suddiviso ( ho un piano), restituisco la cella root
|
||||
if ( m_mTree.at(nId).IsLeaf() ) {
|
||||
nCells.push_back( nId) ;
|
||||
return nCells ;
|
||||
}
|
||||
|
||||
while ( ! m_mTree.at(nId).IsLeaf()) {
|
||||
if ( m_mTree.at(nId).IsSplitVert()) {
|
||||
@@ -2164,23 +2170,24 @@ Tree::CreateCellPolygons( int nLeafId, std::vector<POLYLINEVECTOR>& vPolygons, I
|
||||
// in questo for analizzo solo i loop che tagliano la cella
|
||||
int nEdgeIn = -1 ;
|
||||
int nFirstLoopInPoly = -1 ;
|
||||
INTVECTOR vAddedLoops ;
|
||||
for ( int w = 0 ; w < (int)vToCheckNow.size() ; ++ w) {
|
||||
// primo loop di questo poligono
|
||||
// indice del loop in m_vInters
|
||||
int j = vToCheckNow[w] ;
|
||||
Inters inA = m_mTree[nId].m_vInters[j] ;
|
||||
if ( inA.nIn != -1 ) {
|
||||
int nEdge ;
|
||||
if ( nEdgeIn == -1 )
|
||||
if ( nEdgeIn == -1 ) {
|
||||
// salvo il lato di ingresso del primo lato del poligono che sto costruendo
|
||||
nEdgeIn = inA.nIn ;
|
||||
nFirstLoopInPoly = j ;
|
||||
}
|
||||
for ( Point3d ptInt : inA.vpt ) {
|
||||
AddVertex( nId, vEdgeVertex, plTrimmedPoly, c, ptInt) ;
|
||||
//plTrimmedPoly.AddUPoint(c, ptInt) ;
|
||||
//++c ;
|
||||
}
|
||||
vAddedLoops.push_back( j) ;
|
||||
nEdge = inA.nOut ;
|
||||
// se la curva è CW devo verifica di non essere uscito in un vertice, con un tratto sovrapposto al lato che ripercorrerò tra poco
|
||||
// qui ho tolto l'if e esteso anche ai casi CCW perché anche lì devo controllare!!!!!////////////////////////////////////////////////////////////
|
||||
// devo verificare di non essere uscito in un vertice, con un tratto sovrapposto al lato che ripercorrerò tra poco
|
||||
Point3d ptLast, ptSecondToLast;
|
||||
plTrimmedPoly.GetLastPoint(ptLast) ;
|
||||
plTrimmedPoly.GetPrevPoint(ptSecondToLast) ;
|
||||
@@ -2240,7 +2247,7 @@ Tree::CreateCellPolygons( int nLeafId, std::vector<POLYLINEVECTOR>& vPolygons, I
|
||||
bool bNotCameBack = true ;
|
||||
bool bValidNextStart = false ;
|
||||
bool bAtNextStart = false ;
|
||||
if ( j < nPassToCheck - 1) {
|
||||
if ( w < nPassToCheck - 1) { // ho messo w al posto di j ////////////////////////////////////////////////////////////////////////////////////////
|
||||
int nSecondCheck = 0 ;
|
||||
int nNext ;
|
||||
// ciclo sui loop successivi per vedere se ne ho uno con un valid start
|
||||
@@ -2253,39 +2260,12 @@ Tree::CreateCellPolygons( int nLeafId, std::vector<POLYLINEVECTOR>& vPolygons, I
|
||||
}
|
||||
else {
|
||||
++ nSecondCheck ;
|
||||
vToCheck.push_back( t) ;
|
||||
vToCheck.push_back( vToCheckNow[t]) ;
|
||||
}
|
||||
}
|
||||
|
||||
//// ciclo sui loop successivi per vedere se ne ho uno su questo lato con un valid start
|
||||
//for ( int t = w ; t < nPassToCheck -1 ; ++ t) {
|
||||
// if ( AreSameEdge( nEdge, m_mTree[nId].m_vInters[j].nIn) ) {
|
||||
// if ( m_mTree[nId].m_vInters[j].bCCW) {
|
||||
// bValidNextStart = ( AreSameEdge( m_mTree[nId].m_vInters[vToCheckNow[t + 1]].nIn, nEdge)) && // loop successivo inizia su questo lato
|
||||
// ! CheckIfAfter( plTrimmedPoly, m_mTree[nId].m_vInters[vToCheckNow[t + 1]].vpt[0], nEdge) ; // in posizione giusta da essere concatenato
|
||||
// }
|
||||
// else {
|
||||
// // se il loop è CW e sono tornato sul lato di partenza allora controllo se sono prima del primo punto della polyline
|
||||
// bValidNextStart = ( AreSameEdge( m_mTree[nId].m_vInters[vToCheckNow[t + 1]].nIn, nEdge)) &&
|
||||
// CheckIfAfter( plTrimmedPoly, m_mTree[nId].m_vInters[vToCheckNow[t + 1]].vpt[0], nEdge) ;
|
||||
// }
|
||||
// }
|
||||
// else
|
||||
// bValidNextStart = CheckIfAfter( plTrimmedPoly, m_mTree[nId].m_vInters[vToCheckNow[t + 1]].vpt[0], nEdge) ;
|
||||
// if ( ! AreSameEdge( m_mTree[nId].m_vInters[vToCheckNow[t + 1]].nIn, nEdge) || bValidNextStart)
|
||||
// //if ( bValidNextStart)
|
||||
// break ;
|
||||
// // se ho trovato un loop successivo che devo saltare, lo salvo e considero i loop più avanti.
|
||||
// if ( AreSameEdge( m_mTree[nId].m_vInters[vToCheckNow[t + 1]].nIn, nEdge) && ! bValidNextStart){
|
||||
// //else {
|
||||
// ++ nSecondCheck ;
|
||||
// vToCheck.push_back( t + 1) ;
|
||||
// }
|
||||
//}
|
||||
|
||||
bNotCameBack = ! ( AreSameEdge( nEdge, nEdgeIn) && CheckIfBefore( plTrimmedPoly, nEdge)) ;
|
||||
|
||||
//while ( ! bValidNextStart && bNotCameBack) {
|
||||
while ( ! ( bValidNextStart && bAtNextStart) && bNotCameBack) {
|
||||
Point3d ptVert ;
|
||||
if ( nEdge == 0)
|
||||
@@ -2297,8 +2277,6 @@ Tree::CreateCellPolygons( int nLeafId, std::vector<POLYLINEVECTOR>& vPolygons, I
|
||||
else if ( nEdge == 3)
|
||||
ptVert = m_mTree[nId].GetTopRight() ;
|
||||
AddVertex( nId, vEdgeVertex, plTrimmedPoly, c, ptVert) ;
|
||||
//plTrimmedPoly.AddUPoint( c, ptVert) ;
|
||||
//++c ;
|
||||
if ( nEdge > 3 && nEdge != 7)
|
||||
nEdge = nEdge - 4 ;
|
||||
else if ( nEdge < 3 )
|
||||
@@ -2311,50 +2289,10 @@ Tree::CreateCellPolygons( int nLeafId, std::vector<POLYLINEVECTOR>& vPolygons, I
|
||||
bAtNextStart = AreSameEdge( nEdge, m_mTree[nId].m_vInters[vToCheckNow[nNext]].nIn) ;
|
||||
|
||||
bNotCameBack = ! ( AreSameEdge( nEdge, nEdgeIn) && CheckIfBefore( plTrimmedPoly, nEdge)) ;
|
||||
|
||||
/*for ( int t = w + 1 ; t < nPassToCheck -1 ; ++ t) {
|
||||
bValidNextStart = CheckIfBetween( m_mTree[nId].m_vInters[j], m_mTree[nId].m_vInters[vToCheckNow[t]]) ;
|
||||
if ( bValidNextStart) {
|
||||
bAtNextStart = AreSameEdge( m_mTree[nId].m_vInters[j].nOut, m_mTree[nId].m_vInters[vToCheckNow[t]].nIn) ;
|
||||
break ;
|
||||
}
|
||||
else {
|
||||
++ nSecondCheck ;
|
||||
vToCheck.push_back( t) ;
|
||||
}
|
||||
}*/
|
||||
|
||||
// ciclo sui loop successivi per vedere se ne ho uno su questo lato con un valid start
|
||||
//for ( int t = w ; t < nPassToCheck -1 ; ++ t) {
|
||||
// if ( AreSameEdge( nEdge, m_mTree[nId].m_vInters[j].nIn) ) {
|
||||
// if ( m_mTree[nId].m_vInters[j].bCCW) {
|
||||
// bValidNextStart = ( AreSameEdge( m_mTree[nId].m_vInters[vToCheckNow[t + 1]].nIn, nEdge)) && // loop successivo inizia su questo lato
|
||||
// ! CheckIfAfter( plTrimmedPoly, m_mTree[nId].m_vInters[vToCheckNow[t + 1]].vpt[0], nEdge) ; // in posizione giusta da essere concatenato
|
||||
// }
|
||||
// else {
|
||||
// // se il loop è CW e sono tornato sul lato di partenza allora controllo se sono prima del primo punto della polyline
|
||||
// bValidNextStart = ( AreSameEdge( m_mTree[nId].m_vInters[vToCheckNow[t + 1]].nIn, nEdge)) &&
|
||||
// CheckIfAfter( plTrimmedPoly, m_mTree[nId].m_vInters[vToCheckNow[t + 1]].vpt[0], nEdge) ;
|
||||
// }
|
||||
// }
|
||||
// else
|
||||
// bValidNextStart = CheckIfAfter( plTrimmedPoly, m_mTree[nId].m_vInters[vToCheckNow[t + 1]].vpt[0], nEdge) ;
|
||||
// if ( ! AreSameEdge( m_mTree[nId].m_vInters[vToCheckNow[t + 1]].nIn, nEdge) || bValidNextStart)
|
||||
// //if ( bValidNextStart)
|
||||
// break ;
|
||||
// // se ho trovato un loop successivo che devo saltare, lo salvo e considero i loop più avanti.
|
||||
// if ( AreSameEdge( m_mTree[nId].m_vInters[vToCheckNow[t + 1]].nIn, nEdge) && ! bValidNextStart){
|
||||
// //else {
|
||||
// ++ nSecondCheck ;
|
||||
// vToCheck.push_back( t + 1) ;
|
||||
// }
|
||||
//}
|
||||
}
|
||||
// se ho trovato un altro loop salto all'inizio del for
|
||||
//
|
||||
//if ( AreSameEdge( m_mTree[nId].m_vInters[vToCheckNow[w + 1 + nSecondCheck]].nIn, nEdge) && bValidNextStart) { // qui ho aggiunto bValidNextStart/////////////////////////
|
||||
if ( bValidNextStart) { ///////////////////////////////
|
||||
w = w + nSecondCheck ;
|
||||
if ( bValidNextStart) {
|
||||
w = w + nSecondCheck ;
|
||||
continue ;
|
||||
}
|
||||
}
|
||||
@@ -2398,6 +2336,14 @@ Tree::CreateCellPolygons( int nLeafId, std::vector<POLYLINEVECTOR>& vPolygons, I
|
||||
c = 0 ;
|
||||
plTrimmedPoly.Clear() ;
|
||||
nEdgeIn = -1 ;
|
||||
// devo verificare se tra i loop che sono finiti in vToCheck in realtà qualcuno l'ho usato per fare un poligono/////////////////////////////////////
|
||||
for ( int k = 0 ; k < (int)vToCheck.size() ; ++ k) {
|
||||
for ( int i = 0 ; i < (int)vAddedLoops.size() ; ++ i) {
|
||||
if ( vToCheck[k] == vAddedLoops[i] ) {
|
||||
vToCheck.erase(vToCheck.begin() + k) ;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
continue ;
|
||||
@@ -2551,7 +2497,7 @@ bool
|
||||
Tree::CheckIfBefore( int& nEdge1, Point3d& ptP1, int& nEdge2, Point3d& ptP2) const
|
||||
{
|
||||
INTVECTOR vEdges = { 7, 0, 4, 1, 5, 2, 6} ;
|
||||
// controllo se nEdge1 viene prima di nEdge2. la partenza è da ptTR e l'arrivo è ptBr
|
||||
// controllo se ptP1, che è su nEdge1, viene prima di ptP2, che è su nEdge2. la partenza è da ptTR e l'arrivo è ptBr
|
||||
INTVECTOR :: iterator iter1 = find( vEdges.begin(), vEdges.end(), nEdge1) ;
|
||||
int nPos1 = std::distance( vEdges.begin(), iter1) ;
|
||||
INTVECTOR :: iterator iter2 = find( vEdges.begin(), vEdges.end(), nEdge2) ;
|
||||
@@ -2574,53 +2520,58 @@ Tree::CheckIfBefore( int& nEdge1, Point3d& ptP1, int& nEdge2, Point3d& ptP2) con
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
bool
|
||||
Tree::CheckIfAfter( PolyLine& pl, Point3d& ptNextStart, int nEdge, bool bSameEdge) const
|
||||
Tree::CheckIfBefore( int& nEdge, Point3d& ptP1, Point3d& ptP2) const
|
||||
{
|
||||
// sul lato nEdge controllo se ptP1 viene prima di ptP2.
|
||||
// i lati vengono percorsi in senso antiorario
|
||||
if ( nEdge == 0 ) {
|
||||
return ptP1.x > ptP2.x ;
|
||||
}
|
||||
else if ( nEdge == 1 ) {
|
||||
return ptP1.y > ptP2.y ;
|
||||
}
|
||||
else if ( nEdge == 2 ) {
|
||||
return ptP1.x < ptP2.x ;
|
||||
}
|
||||
else if ( nEdge == 3 ) {
|
||||
return ptP1.y < ptP2.y ;
|
||||
}
|
||||
return false ;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
bool
|
||||
Tree::CheckIfAfter( PolyLine& pl, Point3d& ptNextStart, int nEdge) const
|
||||
{
|
||||
// controllo se ptNextStart è più avanti rispetto a ptEnd in senso antiorario
|
||||
// ATTENZIONE i due punti devono essere sullo stesso lato!
|
||||
|
||||
// se i punti non sono sullo stesso lato ritorno false ( con bSameEdge == true)
|
||||
// se i punti non sono sullo stesso lato ritorno false
|
||||
Point3d ptEnd ;
|
||||
pl.GetLastPoint( ptEnd) ;
|
||||
if ( nEdge == 0 ) {
|
||||
if ( bSameEdge) {
|
||||
if ( ptNextStart.y > ptEnd.y - EPS_SMALL && ptNextStart.y < ptEnd.y + EPS_SMALL)
|
||||
return ptEnd.x > ptNextStart.x ;
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
else
|
||||
if ( ptNextStart.y > ptEnd.y - EPS_SMALL && ptNextStart.y < ptEnd.y + EPS_SMALL)
|
||||
return ptEnd.x > ptNextStart.x ;
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
else if ( nEdge == 1 ) {
|
||||
if ( bSameEdge) {
|
||||
if ( ptNextStart.x > ptEnd.x - EPS_SMALL && ptNextStart.x < ptEnd.x + EPS_SMALL)
|
||||
return ptEnd.y > ptNextStart.y ;
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
else
|
||||
if ( ptNextStart.x > ptEnd.x - EPS_SMALL && ptNextStart.x < ptEnd.x + EPS_SMALL)
|
||||
return ptEnd.y > ptNextStart.y ;
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
else if ( nEdge == 2 ) {
|
||||
if ( bSameEdge) {
|
||||
if ( ptNextStart.y > ptEnd.y - EPS_SMALL && ptNextStart.y < ptEnd.y + EPS_SMALL)
|
||||
return ptEnd.x < ptNextStart.x ;
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
else
|
||||
if ( ptNextStart.y > ptEnd.y - EPS_SMALL && ptNextStart.y < ptEnd.y + EPS_SMALL)
|
||||
return ptEnd.x < ptNextStart.x ;
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
else if ( nEdge == 3 ) {
|
||||
if ( bSameEdge) {
|
||||
if ( ptNextStart.x > ptEnd.x - EPS_SMALL && ptNextStart.x < ptEnd.x + EPS_SMALL)
|
||||
return ptEnd.y < ptNextStart.y ;
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
else
|
||||
if ( ptNextStart.x > ptEnd.x - EPS_SMALL && ptNextStart.x < ptEnd.x + EPS_SMALL)
|
||||
return ptEnd.y < ptNextStart.y ;
|
||||
else
|
||||
return false ;
|
||||
}
|
||||
return false ;
|
||||
}
|
||||
@@ -2992,33 +2943,72 @@ Tree::CategorizeCell( int& nId)
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
bool
|
||||
Tree::CheckIfBetween( Inters& intA, Inters& intB) const
|
||||
Tree::CheckIfBetween( Inters& inA, Inters& inB) const
|
||||
{
|
||||
// controllo se intB è compreso tra l'end e lo start di intA
|
||||
// controllo se inB è compreso tra l'end e lo start di inA
|
||||
// ( dall'end di A percorro i bordi della cella fino a tornare allo start e devo incontrare In e Out di B)
|
||||
INTVECTOR vEdges ;
|
||||
int nEdge = intA.nOut ;
|
||||
vEdges.push_back( nEdge) ;
|
||||
if ( nEdge == 3)
|
||||
nEdge = 0 ;
|
||||
else
|
||||
++ nEdge ;
|
||||
while ( nEdge != intA.nIn ) {
|
||||
int nEdge = inA.nOut ;
|
||||
//vEdges.push_back( nEdge) ;
|
||||
//if ( nEdge == 3)
|
||||
// nEdge = 0 ;
|
||||
//else
|
||||
// ++ nEdge ;
|
||||
while ( nEdge != inA.nIn || (int) vEdges.size() == 0) {
|
||||
vEdges.push_back( nEdge) ;
|
||||
if ( nEdge == 3)
|
||||
nEdge = 0 ;
|
||||
else
|
||||
++ nEdge ;
|
||||
}
|
||||
if ( inA.nIn != inA.nOut)
|
||||
vEdges.push_back( nEdge) ;
|
||||
bool bFound = false ;
|
||||
for ( int i : vEdges) {
|
||||
if ( intB.nIn == i) {
|
||||
PolyLine pl ;
|
||||
pl.AddUPoint( 0, intA.vpt[0]) ;
|
||||
pl.AddUPoint( 1, intA.vpt.back()) ;
|
||||
if ( CheckIfAfter( pl, intB.vpt[0], i, false))
|
||||
bFound = true ;
|
||||
if ( inB.nIn == i) {
|
||||
if ( inB.nIn == inA.nIn && inA.nIn == inA.nOut ) {
|
||||
nEdge = inA.nIn ;
|
||||
//se l'inizio di A è prima della fine, allora devo controllare che B sia compreso tra Out e In (esterno)
|
||||
if ( CheckIfBefore( nEdge, inA.vpt[0], inA.vpt.back()) ) {
|
||||
if ( CheckIfBefore( nEdge, inA.vpt.back(), inB.vpt[0]) || CheckIfBefore( nEdge, inB.vpt[0], inA.vpt[0]))
|
||||
bFound = true ;
|
||||
}
|
||||
// se l'inizio di A è dopo la fine, allora devo controllare che B sia compreso tra In e Out ( interno)
|
||||
else {
|
||||
if ( CheckIfBefore( nEdge, inA.vpt.back(), inB.vpt[0]) && CheckIfBefore( nEdge, inB.vpt[0], inA.vpt[0]))
|
||||
bFound = true ;
|
||||
}
|
||||
|
||||
// alternativa
|
||||
// percorrendo il lato in modo ciclico ( con condizioni al contorno che dalla fine mi riportano all'inizio)
|
||||
// partendo da OutA devo incontrare InB e poi InA
|
||||
//if ( CheckIfBefore( nEdge, inA.vpt.back(), nEdge, inB.vpt[0]) && CheckIfBefore( nEdge, inA.vpt.back(), nEdge, inB.vpt[0])) {
|
||||
// bFound = true ;
|
||||
//}
|
||||
// mancano gli altri due casi da aggiungere alla ( condizione) || ( ) || ( )
|
||||
}
|
||||
else if ( inB.nIn == inA.nOut) {
|
||||
PolyLine pl ;
|
||||
pl.AddUPoint( 0, inA.vpt[0]) ;
|
||||
pl.AddUPoint( 1, inA.vpt.back()) ;
|
||||
if ( CheckIfAfter( pl, inB.vpt[0], i))
|
||||
bFound = true ;
|
||||
}
|
||||
else if ( inB.nIn == inA.nIn ) {
|
||||
//devo controllare il loop b sia prima dell'inizio di A
|
||||
if ( CheckIfBefore(inA.nIn, inB.vpt[0], inA.nIn, inA.vpt[0]))
|
||||
bFound = true ;
|
||||
}
|
||||
else
|
||||
// devo controllare che inB sia prima di OutB
|
||||
if ( inB.nOut == inB.nIn && CheckIfBefore( inB.nOut, inB.vpt[0], inB.vpt.back())) {
|
||||
bFound = true ;
|
||||
}
|
||||
else if ( inB.nOut != inB.nIn)
|
||||
bFound = true ;
|
||||
}
|
||||
if ( inB.nOut == i && ! bFound)
|
||||
break ;
|
||||
}
|
||||
return bFound ;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user