EgtGeomKernel :

- VM 5 assi con volumi chiusi, con bilineari.
This commit is contained in:
Daniele Bariletti
2025-07-14 17:30:03 +02:00
parent c6e80a0b6a
commit ba75033f0a
2 changed files with 436 additions and 183 deletions
+430 -181
View File
@@ -1131,10 +1131,10 @@ GetAlongAcrossRotation( const Vector3d& vtDir1, const Vector3d& vtDir2, const Ve
//----------------------------------------------------------------------------
bool
VolZmap::UpdateMaxMin( Point3d ptBez, Vector3d vtN, PNTVECTVECTOR& vInters) const
VolZmap::UpdateMaxMin( Point3d& ptBez, Vector3d& vtN, PNTVEC3DVECTOR& vInters) const
{
if ( ! AreSameVectorExact( vtN, V_NULL))
vInters.emplace_back( PNTVECT( ptBez, vtN)) ;
vInters.emplace_back( PNTVEC3D( ptBez, vtN)) ;
return true ;
}
@@ -1308,10 +1308,13 @@ VolZmap::GenTool_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR&
return true ;
}
//debug
static vector<IGeoObj*> vGeo ;
//static int nCount = 0 ;
//debug
#if true
//debug
#define TEST
static vector<IGeoObj*> vGeo ;
//static int nCount = 0 ;
//debug
#endif
//----------------------------------------------------------------------------
bool
@@ -1337,11 +1340,11 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
DBLVECTOR A1, B1, C1, A2, B2, C2 ;
int nTotSurf = 4;
if ( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS)
nTotSurf = 2 + nSub * 2 ;
nTotSurf = 2 * nStepCnt + nSub * 2 * nStepCnt + nSub * 2 ; // sup laterali, sup superiori e inferiori, superfici verticali di inizio e fine
else if( n5AxisType == VolZmap::Move5Axis::ALONG_CONVEX || n5AxisType == VolZmap::Move5Axis::ALONG_CONCAVE)
nTotSurf = 2 + nSub * 2 + nStepCnt ;
nTotSurf = 2 * nStepCnt + nSub * 2 * nStepCnt + nStepCnt + nSub * 2 + nSub * 2 ; // verticali esterne e verticali interne
else if( n5AxisType == VolZmap::Move5Axis::ACROSS)
nTotSurf = 2 + nSub * 4 ;
nTotSurf = 2 * nStepCnt + nSub * 4 * nStepCnt + nSub * 4 ;
ISURFBEZPOVECTOR vSurfBez( nTotSurf * nStepCnt) ;
BOXVECTOR vSurfBox( nTotSurf * nStepCnt) ;
@@ -1356,10 +1359,12 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
Vector3d vtDirTipStartEx ;
Vector3d vtDirTipEndEx ;
#ifdef TEST
//debug
if( nGrid == 0)
vGeo.clear() ;
//debug
#endif
for ( int s = 0 ; s < nStepCnt ; ++s) {
// punti di riferimento sul tool
@@ -1432,6 +1437,12 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
vtDirTopStartEx = vtTopBaseStart ;
Point3d ptRefStart = ptS[s] + vtTopBaseStart ;
dSide = (ptRefEnd - ptRefStart) * vtLs[s] ;
//debug
string sOut = ToString( dSide) ;
LOG_INFO( GetEGkLogger(), sOut.c_str())
//debug
// calcolo anche i vettori per le basi inferiori
Vector3d vtTipBaseStart = - (vtLs[s] ^ vtDirTip) ;
vtTipBaseStart.Normalize() ;
@@ -1539,6 +1550,13 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
for ( int i = 0 ; i < nSub ; ++i) {
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTopStart[i], vPntTopStart[i+1], vPntTopEnd[i], vPntTopEnd[i+1]})) ;
}
// chiudo il volume con le superici verticali
if( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS) {
for ( int i = 0 ; i < nSub ; ++i ) {
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTipStart[i+1], vPntTipStart[i], vPntTopStart[nSub - i - 1], vPntTopStart[nSub - i]})) ;
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTipEnd[i], vPntTipEnd[i+1], vPntTopEnd[nSub - i], vPntTopEnd[nSub - i- 1]})) ;
}
}
// aggiungo le superfici bilineari anche nell'altro verso sia per il top che per il tip
if( n5AxisType == VolZmap::Move5Axis::ACROSS) {
// inferiori
@@ -1549,6 +1567,16 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
for ( int i = 0 ; i < nSub ; ++i) {
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTopStart2[i], vPntTopStart2[i+1], vPntTopEnd2[i], vPntTopEnd2[i+1]})) ;
}
// chiudo il volume con le superici verticali in avanti
for ( int i = 0 ; i < nSub ; ++i) {
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTipStart[i+1], vPntTipStart[i], vPntTopStart2[nSub - i - 1], vPntTopStart2[nSub - i]})) ;
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTipEnd2[i], vPntTipEnd2[i+1], vPntTopEnd[nSub - i], vPntTopEnd[nSub - i -1]})) ;
}
// chiudo il volume con le superici verticali indietro
for ( int i = 0 ; i < nSub ; ++i) {
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTipStart2[i+1], vPntTipStart2[i], vPntTopStart[nSub - i - 1], vPntTopStart[nSub - i]})) ;
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTipEnd[i], vPntTipEnd[i+1], vPntTopEnd2[nSub - i], vPntTopEnd2[nSub - i - 1]})) ;
}
}
}
else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONVEX) {
@@ -1562,6 +1590,26 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
}
// superfici inferiori semplici
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTipStart.front(), vPntTipStart.back(), vPntTipEnd.front(), vPntTipEnd.back()})) ;
// calcolo i punti di split dei diametri
PNTVECTOR vSplitDiamStart ;
PNTVECTOR vSplitDiamEnd ;
Vector3d vDirDiamStart = (vPntTipStart.back() - vPntTipStart.front()) / nSub ;
Vector3d vDirDiamEnd = (vPntTipEnd.back() - vPntTipEnd.front()) / nSub ;
for ( int i = 0 ; i <= nSub ; ++i) {
vSplitDiamStart.push_back( vPntTipStart.front() + i * vDirDiamStart) ;
vSplitDiamEnd.push_back( vPntTipEnd.front() + i * vDirDiamEnd) ;
}
// aggiungo le superfici verticali esterne
for ( int i = 0 ; i < nSub ; ++i) {
vvPtCtrl.emplace_back( PNTVECTOR({ vSplitDiamStart[i+1], vSplitDiamStart[i], vPntTopStart[nSub - i - 1], vPntTopStart[nSub - i]})) ;
vvPtCtrl.emplace_back( PNTVECTOR({ vSplitDiamEnd[i], vSplitDiamEnd[i+1], vPntTopEnd2[nSub - i], vPntTopEnd2[nSub - i- 1]})) ;
}
// aggiungo le superfici verticali interne
for ( int i = 0 ; i < nSub ; ++i) {
vvPtCtrl.emplace_back( PNTVECTOR({ vSplitDiamStart[i+1], vSplitDiamStart[i], vPntTopStart2[nSub - i - 1], vPntTopStart2[nSub - i]})) ;
vvPtCtrl.emplace_back( PNTVECTOR({ vSplitDiamEnd[i], vSplitDiamEnd[i+1], vPntTopEnd[nSub - i], vPntTopEnd[nSub - i- 1]})) ;
}
}
else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONCAVE) {
// superfici inferiori
@@ -1574,6 +1622,26 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
}
// superfici superiori semplici
vvPtCtrl.emplace_back( PNTVECTOR({ vPntTopStart.front(), vPntTopStart.back(), vPntTopEnd.front(), vPntTopEnd.back()})) ;
// calcolo i punti di split dei diametri
PNTVECTOR vSplitDiamStart ;
PNTVECTOR vSplitDiamEnd ;
Vector3d vDirDiamStart = (vPntTopStart.back() - vPntTopStart.front()) / nSub ;
Vector3d vDirDiamEnd = (vPntTopEnd.back() - vPntTopEnd.front()) / nSub ;
for ( int i = 0 ; i <= nSub ; ++i) {
vSplitDiamStart.push_back( vPntTopStart.front() + i * vDirDiamStart) ;
vSplitDiamEnd.push_back( vPntTopEnd.front() + i * vDirDiamEnd) ;
}
// aggiungo le superfici verticali esterne
for ( int i = 0 ; i < nSub ; ++i) {
vvPtCtrl.emplace_back( PNTVECTOR({ vSplitDiamStart[i+1], vSplitDiamStart[i], vPntTipStart[nSub - i - 1], vPntTipStart[nSub - i]})) ;
vvPtCtrl.emplace_back( PNTVECTOR({ vSplitDiamEnd[i], vSplitDiamEnd[i+1], vPntTipEnd2[nSub - i], vPntTipEnd2[nSub - i- 1]})) ;
}
// aggiungo le superfici verticali interne
for ( int i = 0 ; i < nSub ; ++i) {
vvPtCtrl.emplace_back( PNTVECTOR({ vSplitDiamStart[i+1], vSplitDiamStart[i], vPntTipStart2[nSub - i - 1], vPntTipStart2[nSub - i]})) ;
vvPtCtrl.emplace_back( PNTVECTOR({ vSplitDiamEnd[i], vSplitDiamEnd[i+1], vPntTipEnd[nSub - i], vPntTipEnd[nSub - i- 1]})) ;
}
}
}
@@ -1599,16 +1667,23 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
A2.push_back( a.y * q.z - a.z * q.y) ;
B2.push_back( b.y * q.z - b.z * q.y) ;
C2.push_back( c.y * q.z - c.z * q.y) ;
if ( nGrid == 0)
vGeo.push_back( vSurfBez[nSurfInd]->Clone()) ;
#ifdef TEST
if ( nGrid == 0)
vGeo.push_back( vSurfBez[nSurfInd]->Clone()) ;
#endif
}
}
#ifdef TEST
//debug
if ( nGrid == 0) {
SaveGeoObj( vGeo, "D:/Temp/VirtualMilling/5axisAdvanced/finalApprox.nge", 2) ;
vector<Color> vCol( vGeo.size()) ;
fill(vCol.begin(), vCol.end(), Color( 255,128,0)) ;
SaveGeoObj( vGeo, vCol, "D:/Temp/VirtualMilling/5axisAdvanced/finalApprox.nge", 2) ;
}
//debug
#endif
BBox3d bbStartCyl = GetCylMoveBBox( ptS[0], ptS[0], vtLs[0], dMaxRad, dHeight) ;
BBox3d bbEndCyl = GetCylMoveBBox( ptE.back(), ptE.back(), vtLe.back(), dMaxRad, dHeight) ;
@@ -1668,7 +1743,11 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
double dX = ( i + 0.5) * m_dStep ;
double dY = ( j + 0.5) * m_dStep ;
Point3d r( dX, dY, 0) ;
PNTVECTVECTOR vInters ;
PNTVEC3DVECTOR vInters ;
//debug
INTVECTOR vSurfInters ;
// interseco con le bilineari
for( int s = 0 ; s < nAllStepsSurfs ; ++s) {
// verifico che lo spillone faccia interferenza con il box della superficie
@@ -1689,7 +1768,11 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
Point3d ptBez1 ;
Vector3d vtN1 ;
vSurfBez[s]->GetPointNrmD1D2(dU1, dV1, ISurfBezier::Side::FROM_MINUS, ISurfBezier::Side::FROM_MINUS, ptBez1, vtN1) ;
UpdateMaxMin( ptBez1, -vtN1, vInters) ;
vtN1 *= -1 ;
UpdateMaxMin( ptBez1, vtN1, vInters) ;
//debug
vSurfInters.push_back( s) ;
}
}
if ( nRoots > 1 && vdRoots[1] > 0 - EPS_ZERO && vdRoots[1] < 1 + EPS_ZERO) {
@@ -1699,13 +1782,53 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
Point3d ptBez2 ;
Vector3d vtN2 ;
vSurfBez[s]->GetPointNrmD1D2(dU2, dV2, ISurfBezier::Side::FROM_MINUS, ISurfBezier::Side::FROM_MINUS, ptBez2, vtN2) ;
UpdateMaxMin( ptBez2, -vtN2, vInters) ;
vtN2 *= -1 ;
UpdateMaxMin( ptBez2, vtN2, vInters) ;
//debug
vSurfInters.push_back( s) ;
}
}
}
}
}
INTINTVECTOR vStartEnds ;
if ( vInters.size() > 2) {
sort( vInters.begin(), vInters.end(), []( PNTVEC3D& a, PNTVEC3D& b){ return a.first.z < b.first.z ;}) ;
INTINT pStartEnd ;
bool bDirStart = vInters.front().second * Z_AX > 0 ;
bool bFirstEndFound = false ;
pStartEnd.first = 0 ;
for ( int w = 1 ; w < int( vInters.size()) ; ++w) {
bool bDir = vInters[w].second * Z_AX > 0 ;
// se è l'ultimo punto esco
if ( w == int( vInters.size() - 1) && bDirStart != bDir) {
pStartEnd.second = w ;
vStartEnds.push_back( pStartEnd) ;
break ;
}
// sennò scorro finché non trovo l'uscita più lontana ( prima di un altro ingresso o eventualmente l'ultima inters)
else if( bDirStart != bDir)
bFirstEndFound = true ;
// se trovo di nuovo un'intersezione orientata come la prima dello spillone allora ho un nuovo start e posso chiudere l'intervallo precedente
else if( bFirstEndFound && bDirStart == bDir) {
pStartEnd.second = w - 1 ;
bFirstEndFound = false ;
vStartEnds.push_back( pStartEnd) ;
pStartEnd.first = w ;
pStartEnd.second = -1 ;
}
}
for( auto p : vStartEnds)
SubtractIntervals(nGrid, i, j, vInters[p.first].first.z, vInters[p.second].first.z, vInters[p.first].second, vInters[p.second].second, nToolNum) ;
}
else if ( vInters.size() == 2)
SubtractIntervals( nGrid, i, j, vInters.front().first.z, vInters.back().first.z, vInters.front().second, vInters.back().second, nToolNum) ;
else if ( vInters.size() == 1)
return false ;
vInters.clear() ;
// interseco con la prima metà del tool in posizione iniziale e con la seconda metà del tool in posizione finale
// se sto trattando un cilindro
BOOLVECTOR vbUpdate( 2) ;
@@ -1735,180 +1858,306 @@ VolZmap::Comp_5AxisMilling( int nGrid, const PNTVECTOR& ptS, const PNTVECTOR& pt
bIntersFound = IntersLineConus( r, Z_AX, frTool, dTan, dMinH, dMaxH, false, false, vPntInters[0], vVtIntersNorm[0], vPntInters[1], vVtIntersNorm[1]) ;
if ( bIntersFound) {
// ciclo sulle due intersezioni
fill(vbUpdate.begin(), vbUpdate.end(), false) ;
for( int p = 0 ; p < 2 ; ++p) {
bool bOnTopBase = ( vPntInters[p] - frTool.Orig() ) * frTool.VersZ() > dHeight - EPS_SMALL ;
bool bOnBottomBase = ( vPntInters[p] - frTool.Orig() ) * frTool.VersZ() < EPS_SMALL ;
// se ho un'intersezione su una base devo verificare se la devo considerare o no
if ( bOnBottomBase || bOnTopBase) {
// verifico se sono nella metà della base il cui contorno è in contatto con le bilineari
//base inferiore
double dSectorAng = 0 ;
bool bApproxedSideBottom = false ;
bool bApproxedSideTop = false ;
double dBottomBaseSide = 0 ;
if ( t == 0)
dBottomBaseSide = ( vPntInters[p] - frTool.Orig()) * vtDirTipStartEx ;
else if ( t == 1)
dBottomBaseSide = ( vPntInters[p] - frTool.Orig()) * vtDirTipEndEx ;
double dTopBaseSide = 0 ;
if ( t == 0)
dTopBaseSide = ( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight)) * vtDirTopStartEx ;
else if ( t == 1)
dTopBaseSide = ( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight)) * vtDirTopEndEx ;
fill(vbUpdate.begin(), vbUpdate.end(), true) ; // tengo tutte le intersezioni col cilindro
if ( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS) {
if ( dSide < 0) {
bApproxedSideBottom = dBottomBaseSide < 0 ;
bApproxedSideTop = dTopBaseSide > 0 ;
}
else {
bApproxedSideBottom = dBottomBaseSide > 0 ;
bApproxedSideTop = dTopBaseSide < 0 ;
}
}
else if ( n5AxisType == VolZmap::Move5Axis::ACROSS) {
if ( t == 0) {
bApproxedSideBottom = dBottomBaseSide < 0 ;
bApproxedSideTop = dTopBaseSide < 0 ;
}
else if ( t == 1) {
bApproxedSideBottom = dBottomBaseSide > 0 ;
bApproxedSideTop = dTopBaseSide > 0 ;
}
}
else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONVEX){
if ( bOnBottomBase) {
if ( t == 0)
vbUpdate[p] = dBottomBaseSide < 0 ;
else if ( t == 1)
vbUpdate[p] = dBottomBaseSide > 0 ;
}
else if ( bOnTopBase)
bApproxedSideTop = true ;
}
else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONCAVE) {
if ( bOnBottomBase)
bApproxedSideBottom = true ;
else if ( bOnTopBase) {
if ( t == 0)
vbUpdate[p] = dTopBaseSide < 0 ;
else if( t == 1)
vbUpdate[p] = dTopBaseSide > 0 ;
}
}
if ( bOnBottomBase && bApproxedSideBottom) {
if ( t == 0)
vvtTipStartAux.front().GetAngle( vPntInters[p] - frTool.Orig(), dSectorAng) ;
else if( t == 1)
vvtTipEndAux.front().GetAngle( vPntInters[p] - frTool.Orig(), dSectorAng) ;
// determino in quale settore del semicerchio approssimato mi trovo
int nSector = int( dSectorAng / ( 180. / nSub) + 1) ;
// verifico se l'intersezione linea-base è interna o esterna
if ( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS) {
double dDist = 0 ;
if ( t == 0)
dDist = ( vPntInters[p] - frTool.Orig() ) * vvtTipStartAux[nSector] ;
else if( t == 1)
dDist = ( vPntInters[p] - frTool.Orig() ) * vvtTipEndAux[nSector] ;
//// ciclo sulle due intersezioni
//fill(vbUpdate.begin(), vbUpdate.end(), false) ;
//for( int p = 0 ; p < 2 ; ++p) {
// bool bOnTopBase = ( vPntInters[p] - frTool.Orig() ) * frTool.VersZ() > dHeight - EPS_SMALL ;
// bool bOnBottomBase = ( vPntInters[p] - frTool.Orig() ) * frTool.VersZ() < EPS_SMALL ;
// // se ho un'intersezione su una base devo verificare se la devo considerare o no
// if ( bOnBottomBase || bOnTopBase) {
// // verifico se sono nella metà della base il cui contorno è in contatto con le bilineari
// //base inferiore
// double dSectorAng = 0 ;
// bool bApproxedSideBottom = false ;
// bool bApproxedSideTop = false ;
// double dBottomBaseSide = 0 ;
// if ( t == 0)
// dBottomBaseSide = ( vPntInters[p] - frTool.Orig()) * vtDirTipStartEx ;
// else if ( t == 1)
// dBottomBaseSide = ( vPntInters[p] - frTool.Orig()) * vtDirTipEndEx ;
// double dTopBaseSide = 0 ;
// if ( t == 0)
// dTopBaseSide = ( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight)) * vtDirTopStartEx ;
// else if ( t == 1)
// dTopBaseSide = ( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight)) * vtDirTopEndEx ;
if ( dSide > 0)
vbUpdate[p] = dDist < dMinRadApprox - EPS_SMALL ;
else
vbUpdate[p] = dDist > dMinRadApprox - EPS_SMALL && dDist < dMinRad ;
}
else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONCAVE) {
double dDist = 0 ;
// per il caso ALONG_CONCAVE dovrei avere dSide < 0, quindi sulla base bottom avere i punti ausiliari nella parte posteriore del cerchio di base
if ( dBottomBaseSide > 0) {
if ( t == 0) {
// in questo caso devo prendere il vettore Aux dell'angolo supplementare e con segno opposto
dDist = ( vPntInters[p] - frTool.Orig() ) * ( -vvtTipStartAux[( nSub + 1 ) - nSector] ) ;
vbUpdate[p] = dDist < dMinRadApprox - EPS_SMALL ;
}
else if ( t == 1)
vbUpdate[p] = true ;
}
else {
if ( t == 0)
vbUpdate[p] = true ;
else if ( t == 1 ) {
dDist = (vPntInters[p] - frTool.Orig()) * vvtTipEndAux[nSector] ;
vbUpdate[p] = dDist < dMinRadApprox - EPS_SMALL ;
}
}
}
else if ( n5AxisType == VolZmap::Move5Axis::ACROSS)
vbUpdate[p] = true ;
}
// base superiore
else if( bOnTopBase && bApproxedSideTop) {
if ( t == 0)
vvtTopStartAux.front().GetAngle( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight ), dSectorAng) ;
else if( t == 1)
vvtTopEndAux.front().GetAngle( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight ), dSectorAng) ;
// determino in quale settore del semicerchio approssimato mi trovo
int nSector = int( dSectorAng / ( 180. / nSub)) + 1 ;
// verifico se l'intersezione linea-base è interna o esterna
if ( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS) {
double dDist = 0 ;
if ( t == 0)
dDist = ( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight)) * vvtTopStartAux[nSector] ;
else if( t == 1)
dDist = ( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight)) * vvtTopEndAux[nSector] ;
// if ( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS) {
// if ( dSide < 0) {
// bApproxedSideBottom = dBottomBaseSide < 0 ;
// bApproxedSideTop = dTopBaseSide > 0 ;
// }
// else {
// bApproxedSideBottom = dBottomBaseSide > 0 ;
// bApproxedSideTop = dTopBaseSide < 0 ;
// }
// }
// else if ( n5AxisType == VolZmap::Move5Axis::ACROSS) {
// //if ( t == 0) {
// // bApproxedSideBottom = dBottomBaseSide < 0 ;
// // bApproxedSideTop = dTopBaseSide < 0 ;
// //}
// //else if ( t == 1) {
// // bApproxedSideBottom = dBottomBaseSide > 0 ;
// // bApproxedSideTop = dTopBaseSide > 0 ;
// //}
if( dSide < 0)
vbUpdate[p] = dDist < dMaxRadApprox - EPS_SMALL ;
else
vbUpdate[p] = dDist > dMaxRadApprox - EPS_SMALL && dDist < dMaxRad ;
}
else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONVEX) {
double dDist = 0 ;
// per il caso ALONG_CONVEX dovrei avere dSide > 0, quindi sulla base top avere i punti ausiliari nella parte posteriore del cerchio di base
if ( dTopBaseSide > 0) {
// in questo caso devo prendere il vettore Aux dell'angolo supplementare e con segno opposto
if ( t == 0)
dDist = ( vPntInters[p] - frTool.Orig()) * ( -vvtTipStartAux[( nSub + 1 ) - nSector]) ;
else if( t == 1)
dDist = ( vPntInters[p] - frTool.Orig()) * ( -vvtTipEndAux[( nSub + 1 ) - nSector]) ;
vbUpdate[p] = dDist < dMinRadApprox - EPS_SMALL ;
}
else
vbUpdate[p] = true ;
}
else if ( n5AxisType == VolZmap::Move5Axis::ACROSS)
vbUpdate[p] = true ;
}
else if ( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS &&
(( t == 0 && ((bOnTopBase && dSide < 0) || ( bOnBottomBase && dSide > 0))) ||
( t == 1 && ((bOnTopBase && dSide > 0) || ( bOnBottomBase && dSide < 0)))))
vbUpdate[p] = true ;
}
else {
double dHInters = 0 ;
if ( t == 0)
dHInters = (vPntInters[p] - ptP1T) * vtLs.front() ;
else if( t == 1)
dHInters = (vPntInters[p] - ptP2T) * vtLe.back() ;
Vector3d vtDir = Media( vtDirTip, vtDirTop, dHInters / dHeight) ;
if ( t == 0)
vbUpdate[p] = vVtIntersNorm[p] * vtDir > 0 ;
else if ( t == 1)
vbUpdate[p] = vVtIntersNorm[p] * vtDir < 0 ;
}
}
if ( vbUpdate[0])
// bApproxedSideBottom = true ;
// bApproxedSideTop = true ;
// }
// else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONVEX){
// if ( bOnBottomBase) {
// if ( t == 0)
// vbUpdate[p] = dBottomBaseSide < 0 ;
// else if ( t == 1)
// vbUpdate[p] = dBottomBaseSide > 0 ;
// }
// else if ( bOnTopBase)
// bApproxedSideTop = true ;
// }
// else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONCAVE) {
// if ( bOnBottomBase)
// bApproxedSideBottom = true ;
// else if ( bOnTopBase) {
// if ( t == 0)
// vbUpdate[p] = dTopBaseSide < 0 ;
// else if( t == 1)
// vbUpdate[p] = dTopBaseSide > 0 ;
// }
// }
// if ( bOnBottomBase && bApproxedSideBottom) {
// if ( t == 0)
// vvtTipStartAux.front().GetAngle( vPntInters[p] - frTool.Orig(), dSectorAng) ;
// else if( t == 1)
// vvtTipEndAux.front().GetAngle( vPntInters[p] - frTool.Orig(), dSectorAng) ;
// // determino in quale settore del semicerchio approssimato mi trovo
// int nSector = int( dSectorAng / ( 180. / nSub) + 1) ;
// // verifico se l'intersezione linea-base è interna o esterna
// if ( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS) {
// double dDist = 0 ;
// if ( t == 0)
// dDist = ( vPntInters[p] - frTool.Orig() ) * vvtTipStartAux[nSector] ;
// else if( t == 1)
// dDist = ( vPntInters[p] - frTool.Orig() ) * vvtTipEndAux[nSector] ;
// if ( dSide > 0)
// vbUpdate[p] = dDist < dMinRadApprox - EPS_SMALL ;
// else
// vbUpdate[p] = dDist > dMinRadApprox - EPS_SMALL && dDist < dMinRad ;
// }
// else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONCAVE) {
// double dDist = 0 ;
// // per il caso ALONG_CONCAVE dovrei avere dSide < 0, quindi sulla base bottom avere i punti ausiliari nella parte posteriore del cerchio di base
// if ( dBottomBaseSide > 0) {
// if ( t == 0) {
// // in questo caso devo prendere il vettore Aux dell'angolo supplementare e con segno opposto
// dDist = ( vPntInters[p] - frTool.Orig() ) * ( -vvtTipStartAux[( nSub + 1 ) - nSector] ) ;
// vbUpdate[p] = dDist < dMinRadApprox - EPS_SMALL ;
// }
// else if ( t == 1)
// vbUpdate[p] = true ;
// }
// else {
// if ( t == 0)
// vbUpdate[p] = true ;
// else if ( t == 1 ) {
// dDist = (vPntInters[p] - frTool.Orig()) * vvtTipEndAux[nSector] ;
// vbUpdate[p] = dDist < dMinRadApprox - EPS_SMALL ;
// }
// }
// }
// else if ( n5AxisType == VolZmap::Move5Axis::ACROSS) {
// double dDist = 0 ;
// // con dSide < 0 sulla base bottom/top ho i punti ausiliari nella parte posteriore/anteriore del cerchio di base
// // con dSide > 0 sulla base bottom/top ho i punti ausiliari nella parte anteriore/posteriore del cerchio di base
//
// if ( dBottomBaseSide > 0) {
// if ( t == 0) {
// if ( dSide < 0) {
// // in questo caso devo prendere il vettore Aux dell'angolo supplementare e con segno opposto
// dDist = ( vPntInters[p] - frTool.Orig() ) * ( -vvtTipStartAux[( nSub + 1 ) - nSector] ) ;
// }
// else {
// dDist = ( vPntInters[p] - frTool.Orig() ) * vvtTipStartAux[nSector] ;
// }
// vbUpdate[p] = dDist < dMinRadApprox - EPS_SMALL ;
// }
// else if ( t == 1)
// vbUpdate[p] = true ;
// }
// else {
// if ( t == 0)
// vbUpdate[p] = true ;
// else if ( t == 1) {
// if ( dSide < 0) {
// dDist = ( vPntInters[p] - frTool.Orig() ) * vvtTipStartAux[nSector] ;
// }
// else {
// // in questo caso devo prendere il vettore Aux dell'angolo supplementare e con segno opposto
// dDist = ( vPntInters[p] - frTool.Orig() ) * ( -vvtTipStartAux[( nSub + 1 ) - nSector] ) ;
// }
// vbUpdate[p] = dDist < dMinRadApprox - EPS_SMALL ;
// }
// }
// //vbUpdate[p] = true ;
// }
// }
// // base superiore
// else if( bOnTopBase && bApproxedSideTop) {
// if ( t == 0)
// vvtTopStartAux.front().GetAngle( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight ), dSectorAng) ;
// else if( t == 1)
// vvtTopEndAux.front().GetAngle( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight ), dSectorAng) ;
// // determino in quale settore del semicerchio approssimato mi trovo
// int nSector = int( dSectorAng / ( 180. / nSub)) + 1 ;
// // verifico se l'intersezione linea-base è interna o esterna
// if ( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS) {
// double dDist = 0 ;
// if ( t == 0)
// dDist = ( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight)) * vvtTopStartAux[nSector] ;
// else if( t == 1)
// dDist = ( vPntInters[p] - ( frTool.Orig() + frTool.VersZ() * dHeight)) * vvtTopEndAux[nSector] ;
// if( dSide < 0)
// vbUpdate[p] = dDist < dMaxRadApprox - EPS_SMALL ;
// else
// vbUpdate[p] = dDist > dMaxRadApprox - EPS_SMALL && dDist < dMaxRad ;
// }
// else if ( n5AxisType == VolZmap::Move5Axis::ALONG_CONVEX) {
// double dDist = 0 ;
// // per il caso ALONG_CONVEX dovrei avere dSide > 0, quindi sulla base top avere i punti ausiliari nella parte posteriore del cerchio di base
// if ( dTopBaseSide > 0) {
// // in questo caso devo prendere il vettore Aux dell'angolo supplementare e con segno opposto
// if ( t == 0)
// dDist = ( vPntInters[p] - frTool.Orig()) * ( -vvtTopStartAux[( nSub + 1 ) - nSector]) ;
// else if( t == 1)
// dDist = ( vPntInters[p] - frTool.Orig()) * ( -vvtTopEndAux[( nSub + 1 ) - nSector]) ;
// vbUpdate[p] = dDist < dMaxRadApprox - EPS_SMALL ;
// }
// else
// vbUpdate[p] = true ;
// }
// else if ( n5AxisType == VolZmap::Move5Axis::ACROSS) {
// double dDist = 0 ;
// // con dSide < 0 sulla base bottom/top ho i punti ausiliari nella parte posteriore/anteriore del cerchio di base
// // con dSide > 0 sulla base bottom/top ho i punti ausiliari nella parte anteriore/posteriore del cerchio di base
// if ( dTopBaseSide > 0) {
// if ( t == 0) {
// if ( dSide < 0) {
// dDist = ( vPntInters[p] - frTool.Orig()) * vvtTopStartAux[nSector] ;
// }
// else {
// // in questo caso devo prendere il vettore Aux dell'angolo supplementare e con segno opposto
// dDist = ( vPntInters[p] - frTool.Orig()) * ( -vvtTopStartAux[( nSub + 1 ) - nSector] ) ;
// }
// vbUpdate[p] = dDist < dMaxRadApprox - EPS_SMALL ;
// }
// else if ( t == 1)
// vbUpdate[p] = true ;
// }
// else {
// if ( t == 0)
// vbUpdate[p] = true ;
// else if ( t == 1) {
// if ( dSide < 0) {
// // in questo caso devo prendere il vettore Aux dell'angolo supplementare e con segno opposto
// dDist = ( vPntInters[p] - frTool.Orig()) * ( -vvtTopStartAux[( nSub + 1 ) - nSector] ) ;
// }
// else {
// dDist = ( vPntInters[p] - frTool.Orig()) * vvtTopStartAux[nSector] ;
// }
// vbUpdate[p] = dDist < dMaxRadApprox - EPS_SMALL ;
// }
// }
// //vbUpdate[p] = true ;
// }
// }
// else if ( n5AxisType == VolZmap::Move5Axis::NO_BASE_INTERS &&
// (( t == 0 && ((bOnTopBase && dSide < 0) || ( bOnBottomBase && dSide > 0))) ||
// ( t == 1 && ((bOnTopBase && dSide > 0) || ( bOnBottomBase && dSide < 0)))))
// vbUpdate[p] = true ;
// }
// else {
// double dHInters = 0 ;
// if ( t == 0)
// dHInters = (vPntInters[p] - ptP1T) * vtLs.front() ;
// else if( t == 1)
// dHInters = (vPntInters[p] - ptP2T) * vtLe.back() ;
// Vector3d vtDir = Media( vtDirTip, vtDirTop, dHInters / dHeight) ;
// if ( t == 0)
// vbUpdate[p] = vVtIntersNorm[p] * vtDir > 0 ; // le normali dei punti di intersezione sul cilindro sono rivolte verso l'interno del cilindro
// else if ( t == 1)
// vbUpdate[p] = vVtIntersNorm[p] * vtDir < 0 ;
// }
//}
if ( vbUpdate[0]) {
UpdateMaxMin( vPntInters[0], vVtIntersNorm[0], vInters) ;
if ( vbUpdate[1])
//debug
vSurfInters.push_back( t == 0 ? -1 : -2) ;
}
if ( vbUpdate[1]) {
UpdateMaxMin( vPntInters[1], vVtIntersNorm[1], vInters) ;
//debug
vSurfInters.push_back( t == 0 ? -1 : -2) ;
}
}
if ( vInters.size() == 2) {
sort( vInters.begin(), vInters.end(), []( PNTVEC3D& a, PNTVEC3D& b){ return a.first.z < b.first.z ;}) ;
SubtractIntervals( nGrid, i, j, vInters.front().first.z, vInters.back().first.z, vInters.front().second, vInters.back().second, nToolNum) ;
vInters.clear() ;
}
}
}
if ( vInters.size() != 0 ) {
sort( vInters.begin(), vInters.end(), []( PNTVECT& a, PNTVECT& b){ return a.first.z < b.first.z ;}) ;
SubtractIntervals( nGrid, i, j, vInters.front().first.z, vInters.back().first.z, vInters.front().second, vInters.back().second, nToolNum) ;
}
//if ( vInters.size() != 0 ) {
// // se ho un numero dispari di intersezioni devo migliorare la gestione
// // riordino le intersezioni rispetto alla loro z
// sort( vInters.begin(), vInters.end(), []( PNTVEC3D& a, PNTVEC3D& b){ return a.first.z < b.first.z ;}) ;
// INTINTVECTOR vStartEnds ;
// if ( vInters.size() > 2) {
// INTINT pStartEnd ;
// bool bDirStart = vInters.front().second * Z_AX > 0 ;
// bool bFirstEndFound = false ;
// pStartEnd.first = 0 ;
// for ( int w = 1 ; w < int( vInters.size()) ; ++w) {
// bool bDir = vInters[w].second * Z_AX > 0 ;
// // se è l'ultimo punto esco
// if ( w == int( vInters.size() - 1) && bDirStart != bDir) {
// pStartEnd.second = w ;
// vStartEnds.push_back( pStartEnd) ;
// break ;
// }
// // sennò scorro finché non trovo l'uscita più lontana ( prima di un altro ingresso o eventualmente l'ultima inters)
// else if( bDirStart != bDir)
// bFirstEndFound = true ;
// // se trovo di nuovo un'intersezione orientata come la prima dello spillone allora ho un nuovo start e posso chiudere l'intervallo precedente
// else if( bFirstEndFound && bDirStart == bDir) {
// pStartEnd.second = w - 1 ;
// bFirstEndFound = false ;
// vStartEnds.push_back( pStartEnd) ;
// pStartEnd.first = w ;
// pStartEnd.second = -1 ;
// }
// }
// for( auto p : vStartEnds)
// SubtractIntervals(nGrid, i, j, vInters[p.first].first.z, vInters[p.second].first.z, vInters[p.first].second, vInters[p.second].second, nToolNum) ;
// }
// else
// SubtractIntervals( nGrid, i, j, vInters.front().first.z, vInters.back().first.z, vInters.front().second, vInters.back().second, nToolNum) ;
//}
//if ( vInters.size() != 0 ) {
// sort( vInters.begin(), vInters.end(), []( PNTVEC3D& a, PNTVEC3D& b){ return get<0>(a).z < get<0>(b).z ;}) ;
// SubtractIntervals( nGrid, i, j, vInters.front().first.z, vInters.back().first.z, vInters.front().second, vInters.back().second, nToolNum) ;
//}
}
}