diff --git a/Pocketing.cpp b/Pocketing.cpp index ac99835..7f3b518 100644 --- a/Pocketing.cpp +++ b/Pocketing.cpp @@ -1285,7 +1285,7 @@ Pocketing::GetCurves( SelData Id, ICURVEPLIST& lstPC) return false ; if ( nStat == 0 || nStat == 2) { // se non c'è overlap o geometria complessa pCrvBorder->SetCurveTempProp( c, 0, 0) ; // lato chiuso - pCrvBorder->SetCurveTempProp( c, -1, 1) ; // lato esterno non definito + pCrvBorder->SetCurveTempProp( c, -2, 1) ; // lato esterno non definito } } @@ -1421,7 +1421,9 @@ Pocketing::ResetCurveAllTempProp( ICurve* pCurve) if ( pCC != nullptr) { for ( int i = 0 ; i < pCC->GetCurveCount() ; ++ i) { pCC->SetCurveTempProp( i, 0, 0) ; - pCC->SetCurveTempProp( i, -1, 1) ; + int nTmpProp1 ; pCC->GetCurveTempProp( i, nTmpProp1, 1) ; + if ( nTmpProp1 != -2) + pCC->SetCurveTempProp( i, -1, 1) ; } } return true ; @@ -1902,6 +1904,7 @@ Pocketing::CalcRegionElevation( const ICurveComposite* pCompo, const Vector3d& v Point3d ptStart ; pCrvC->GetStartPoint( ptStart) ; Point3d ptMid ; pCrvC->GetMidPoint( ptMid) ; Point3d ptEnd ; pCrvC->GetEndPoint( ptEnd) ; + // elevazione della curva double dCurrElev ; if ( GetElevation( m_nPhase, ptStart - vtDepth, ptMid - vtDepth, ptEnd - vtDepth, vtTool, dCurrElev)) { @@ -1930,6 +1933,7 @@ Pocketing::CalcRegionElevation( const ICurveComposite* pCompo, const Vector3d& v pCompoL->GetLocalBBox( b3Pocket) ; Point3d ptMin ; double dDimX, dDimY, dDimZ ; b3Pocket.GetMinDim( ptMin, dDimX, dDimY, dDimZ) ; + // passi in Y const double STEP = 50 ; int nYStep = max( int( ceil( ( dDimY - 20 * EPS_SMALL) / STEP)), 2) ; @@ -1944,6 +1948,7 @@ Pocketing::CalcRegionElevation( const ICurveComposite* pCompo, const Vector3d& v m_pMchMgr->SetLastError( 2408, "Error in Pocketing : Entity GetElevation") ; return false ; } + // calcolo la classificazione della curva rispetto al contorno IntersCurveCurve intCC( *pLine, *pCompoL) ; CRVCVECTOR ccClass ; @@ -4414,6 +4419,7 @@ Pocketing::AddSpiralIn( const ISurfFlatRegion* pSrfPock, const Vector3d& vtTool, // modifico le superifici in base alla geometria del grezzo // RECUPERO DEL GREZZO -> INTERSEZIONE CON GREZZO -> PROIEZIONE CON GREZZO -> MODIFICA DEI LATI APERTI + ISURFFRPOVECTOR vSrfSliced( nStep) ; vector vCrvOEWithFlags( nStep) ; BOOLVECTOR vbChangedPrec( nStep, false) ; @@ -9506,9 +9512,10 @@ Pocketing::VerifyLeadInZigZag( ISurfFlatRegion* pSrfChunk, const Point3d& ptPa, //---------------------------------------------------------------------------- bool Pocketing::GetParamsAtEachStep( ISURFFRPOVECTOR& vSrfSliced, vector& vCrvOEWithFlags, - BOOLVECTOR& vbChangedPrec, const ISurfFlatRegion* pSrfChunk, const int& nStep, const Vector3d vtTool, const double& dElev, - const double& dDepth, const double& dStep) + BOOLVECTOR& vbChangedPrec, const ISurfFlatRegion* pSrfChunk, const int& nStep, + const Vector3d vtTool, const double& dElev, const double& dDepth, const double& dStep) { + for ( int j = 1 ; j <= nStep ; ++ j) { // vettore traslazione corrente allo step j-esimo @@ -9517,11 +9524,18 @@ Pocketing::GetParamsAtEachStep( ISURFFRPOVECTOR& vSrfSliced, vector pSrfH( CreateSurfFlatRegion()) ; + if ( ! GetAdaptedSfrByTrimesh( pSrfChunk, vtTrasl, pSrfH, GLOB_FRM)) + return false ; + // copia del chunk c-esimo della superificie attuale PtrOwner pSrfToAdapt( CloneSurfFlatRegion( pSrfChunk)) ; if ( IsNull( pSrfToAdapt)) return false ; + pSrfToAdapt.Set( pSrfH->Clone()) ; + // adatto la superficie dello step corrente con la geometria del grezzo if ( AdaptSfrWithRaw( pSrfToAdapt, vtTrasl, 5 * ( dDepth - dElev + dStep) - 50 * EPS_SMALL, vCrvOEF, bChanged, j, dStep)) { vSrfSliced[j-1].Set( pSrfToAdapt->Clone()) ; @@ -9549,6 +9563,223 @@ Pocketing::GetParamsAtEachStep( ISURFFRPOVECTOR& vSrfSliced, vectorIsValid() || pNewSrfPock == nullptr) + return false ; + pNewSrfPock->Clear() ; + + // ================================ RECUPERO DELLA TRIMESH ============================== + // recupero il bordo della superficie + PtrOwner pCrvBorder( GetCurveComposite( pSrfPock->GetLoop( 0, 0))) ; + if ( IsNull( pCrvBorder) || ! pCrvBorder->IsValid()) + return false ; + int nId = pCrvBorder->GetTempProp( 0) ; + // recupero l'oggetto dal database con tale Id + const IGeoObj* pGObj = m_pGeomDB->GetGeoObj( nId) ; + if ( pGObj == nullptr) + return false ; + // recupero il frame in cui si trova + Frame3d frGeObj ; + m_pGeomDB->GetGlobFrame( nId, frGeObj) ; + // controllo che sia una Trimesh, altrimenti non modifico nulla + if ( pGObj->GetType() != SRF_TRIMESH) { + pNewSrfPock->CopyFrom( pSrfPock) ; + return true ; + } + // recupero la Trimesh originale + PtrOwner pStmORIG( CloneSurfTriMesh( pGObj)) ; + if ( IsNull( pStmORIG) || ! pStmORIG->IsValid()) + return false ; + // porto la trimesh in globale + pStmORIG->LocToLoc( frGeObj, frPocket) ; + + // clono la superficie da svuotare e la porto allo step corrente + PtrOwner pSrfPock_cl( CloneSurfFlatRegion( pSrfPock)) ; + if ( IsNull( pSrfPock_cl) || ! pSrfPock_cl->IsValid()) + return false ; + pSrfPock_cl->Translate( vtTrasl) ; + + // creo una superficie fittizzia dal bordo esterno dell'originale + PtrOwner pSrf_Fit( CreateSurfFlatRegion()) ; + if ( IsNull( pSrf_Fit)) + return false ; + pSrf_Fit->AddExtLoop( pCrvBorder->Clone()) ; + + int r = m_pGeomDB->AddGeoObj( GDB_ID_NULL, GDB_ID_ROOT, pStmORIG->Clone()) ; + m_pGeomDB->SetMaterial( r, BLACK) ; + // ===================================================================================== + + // recupero estrusione, thickness e tmpProp + Vector3d vtExtr ; pCrvBorder->GetExtrusion( vtExtr) ; + double dThick ; pCrvBorder->GetThickness( dThick) ; + int nTmpProp0_ = pCrvBorder->GetTempProp( 0) ; + int nTmpProp1_ = pCrvBorder->GetTempProp( 1) ; + + // ================== CREAZIONE DELLA REGIONE DI INCIDENZA ============================= + ICRVCOMPOPOVECTOR vNull ; + // 1) ESTENDO I LATI APERTI --------------------------------------------------------- + PtrOwner pSrfInc_1( CreateSurfFlatRegion()) ; + PtrOwner pCrvInc_1( CloneCurveComposite( pCrvBorder)) ; + if ( IsNull( pSrfInc_1) || IsNull( pCrvInc_1) || ! pCrvInc_1->IsValid()) + return false ; + + if ( AdjustContourWithOpenEdges( pCrvInc_1, vNull, m_dMaxLenRawProj, 0, 0, vtTrasl, nullptr, true)) { + pSrfInc_1->AddExtLoop( pCrvInc_1->Clone()) ; + pSrfInc_1->Translate( vtTrasl) ; + pSrfInc_1->Subtract( *pSrf_Fit) ; + int p = m_pGeomDB->AddGeoObj( GDB_ID_NULL, GDB_ID_ROOT, pSrfInc_1->Clone()) ; + m_pGeomDB->SetMaterial( p, Color( 0.0, 1.0, 1.0, 0.5)) ; + } + else + pSrfInc_1.Set( pSrfPock->Clone()) ; + + // 2) ALLARGO PRESSO I CHIUSI CHE NON DERIVANO DA PROEIZIONI ------------------------ + PtrOwner pSrfInc_2( CreateSurfFlatRegion()) ; + if ( IsNull( pSrfInc_2)) + return false ; + + PtrOwner pCrvInc_2( CloneCurveComposite( pCrvBorder)) ; + if ( IsNull( pCrvInc_2) || ! pCrvInc_2->IsValid()) + return false ; + // 2.1) -> chiudo gli aperti e apro i chiusi che non derivano da proiezioni + for ( int u = 0 ; u < pCrvInc_2->GetCurveCount() ; ++ u) { + int nTmpProp0 ; pCrvInc_2->GetCurveTempProp( u, nTmpProp0, 0) ; + if ( nTmpProp0 == 1) // se aperto -> chiudo + pCrvInc_2->SetCurveTempProp( u, 0, 0) ; + else { + // se chiuso -> apro se non deriva da proiezione + int nTmpProp1 ; pCrvInc_2->GetCurveTempProp( u, nTmpProp1, 1) ; + if ( nTmpProp1 != -2) + pCrvInc_2->SetCurveTempProp( u, 1, 0) ; + } + } + if ( AdjustContourWithOpenEdges( pCrvInc_2, vNull, m_dMaxLenRawProj, 0, 0, vtTrasl, nullptr, true)) { + pSrfInc_2->AddExtLoop( pCrvInc_2->Clone()) ; + pSrfInc_2->Translate( vtTrasl) ; + pSrfInc_2->Subtract( *pSrf_Fit) ; + int k = m_pGeomDB->AddGeoObj( GDB_ID_NULL, GDB_ID_ROOT, pSrfInc_2->Clone()) ; + m_pGeomDB->SetMaterial( k, Color( 1.0, 0.0, 0.0, 0.5)) ; + } + else + pSrfInc_2.Set( pSrfPock->Clone()) ; + + // 3) SOMMA DELLE REGIONI DI INCIDENZA + PtrOwner pSrfINC( CreateSurfFlatRegion()) ; + if ( IsNull( pSrfINC)) + return false ; + pSrfINC.Set( pSrfInc_1->Clone()) ; + pSrfINC->Add( * pSrfInc_2) ; + pSrfINC->Add( * pSrf_Fit) ; + + // 4) VETTORE DI CURVE CON TMP PROP + ICRVCOMPOPOVECTOR vCrvCheck ; + pCrvBorder->Translate( vtTrasl) ; + vCrvCheck.emplace_back( pCrvBorder->Clone()) ; + for ( int c = 0 ; c < pSrfInc_2->GetChunkCount() ; ++ c) { + for ( int l = 0 ; l < pSrfInc_2->GetLoopCount( c) ; ++ l) { + PtrOwner pCrvCompo( ConvertCurveToComposite( pSrfInc_2->GetLoop( c, l))) ; + if ( IsNull( pCrvCompo) || ! pCrvCompo->IsValid()) + return false ; + for ( int u = 0 ; u < pCrvCompo->GetCurveCount() ; ++ u) + pCrvCompo->SetCurveTempProp( u, 1, 0) ; // tutte aperte + vCrvCheck.emplace_back( Release( pCrvCompo)) ; + } + } + for ( int c = 0 ; c < pSrfInc_1->GetChunkCount() ; ++ c) { + for ( int l = 0 ; l < pSrfInc_1->GetLoopCount( c) ; ++ l) { + PtrOwner pCrvCompo( ConvertCurveToComposite( pSrfInc_1->GetLoop( c, l))) ; + if ( IsNull( pCrvCompo) || ! pCrvCompo->IsValid()) + return false ; + for ( int u = 0 ; u < pCrvCompo->GetCurveCount() ; ++ u) + pCrvCompo->SetCurveTempProp( u, 1, 0) ; // tutte aperte + vCrvCheck.emplace_back( Release( pCrvCompo)) ; + } + } + + for ( int i = 0 ; i < vCrvCheck.size() ; ++ i) { + //m_pGeomDB->AddGeoObj( GDB_ID_NULL, GDB_ID_ROOT, vCrvCheck[i]->Clone()) ; + } + + // 5) TAGLIO DELLA REGIONE DI INCIDENZA CON LA TRIMESH + PtrOwner pStmINC( CloneSurfTriMesh( pSrfINC->GetAuxSurf())) ; + if ( ! IsNull( pStmINC) && pStmINC->IsValid()) { + if ( pStmINC->CutWithOtherSurf( *pStmORIG, false, true)) { + PtrOwner pSrfPock_Cut( CreateSurfFlatRegion()) ; + if ( IsNull( pSrfPock_Cut)) + return false ; + Plane3d plPock ; + Point3d ptC ; + if ( ! pSrfPock->GetCentroid( ptC)) + if ( ! pCrvBorder->GetStartPoint( ptC)) + return false ; + Vector3d vtN = pSrfPock->GetNormVersor() ; + plPock.Set( ptC, vtN) ; + if ( ! plPock.IsValid()) + return false ; + plPock.Translate( vtTrasl) ; + if ( GetSfrByStm( pStmINC, pSrfPock_Cut, plPock, vtExtr, dThick)) { + int k = m_pGeomDB->AddGeoObj( GDB_ID_NULL, GDB_ID_ROOT, pSrfPock_Cut->Clone()) ; + m_pGeomDB->SetMaterial( k, Color( 0.5, 0.5, 1.0, 0.8)) ; + // devo calcolare i lati aperti + SurfFlatRegionByContours pSrf_Final ; + for ( int c = 0 ; c < pSrfPock_Cut->GetChunkCount() ; ++ c) { + for ( int l = 0 ; l < pSrfPock_Cut->GetLoopCount( c) ; ++ l) { + PtrOwner pCrvCompo( GetCurveComposite( pSrfPock_Cut->GetLoop( c, l ))) ; + if ( IsNull( pCrvCompo) || ! pCrvCompo->IsValid()) + return false ; + // tutta aperta di base + for ( int u = 0 ; u < pCrvCompo->GetCurveCount() ; ++ u) + pCrvCompo->SetCurveTempProp( u, 1, 0) ; + + if ( l > 1) { + for ( int u = 0 ; u < pCrvCompo->GetCurveCount() ; ++ u) + pCrvCompo->SetCurveTempProp( u, 0, 0) ; + } + else { + if ( ! SetTmpPropWithRawProjectedFaces( pCrvCompo, vCrvCheck, vtN)) + return false ; + } + + /* + ----- + */ + for ( int u = 0 ; u < pCrvCompo->GetCurveCount() ; ++ u) { + int nProp0 ; pCrvCompo->GetCurveTempProp( u, nProp0, 0) ; + int nProp1 ; pCrvCompo->GetCurveTempProp( u, nProp1, 1) ; + int aaa = m_pGeomDB->AddGeoObj( GDB_ID_NULL, GDB_ID_ROOT, pCrvCompo->GetCurve( u)->Clone()) ; + m_pGeomDB->SetMaterial( aaa, nProp0 == 0 ? BLUE : RED) ; + } + /* + ------ + */ + + pSrf_Final.AddCurve( Release( pCrvCompo)) ; + } + } + // recupero la superficie finale + PtrOwner pSrf_ToWork( pSrf_Final.GetSurf()) ; + if ( ! IsNull( pSrf_ToWork) && pSrf_ToWork->IsValid()) { + pNewSrfPock->CopyFrom( pSrf_ToWork) ; + pNewSrfPock->Translate( - vtTrasl) ; + return true ; + } + } + } + } + + // ===================================================================================== + // unlucky... + pNewSrfPock->CopyFrom( pSrfPock) ; + return true ; +} + + + //---------------------------------------------------------------------------- bool Pocketing::AdaptSfrWithRaw( ISurfFlatRegion* pSrf, Vector3d vtTrasl, const double& dRawSecLen, @@ -9565,7 +9796,6 @@ Pocketing::AdaptSfrWithRaw( ISurfFlatRegion* pSrf, Vector3d vtTrasl, const doubl return false ; int nProp0 = pCrv->GetTempProp( 0) ; - // ricavo il grezzo attuale della lavorazione PtrOwner pStmRaw( CreateSurfTriMesh()) ; pStmRaw->AdjustTopology() ; @@ -10964,9 +11194,6 @@ Pocketing::GetProjStmOnSfr( const ISurfFlatRegion* pSfr, const ISurfTriMesh* pSt if ( IsNull( pSfrPock)) return false ; - // costante di estrusione per creazione delle regioni - const double STEP_HEIGHT = 500. ; - // ------------------------- CREAZIONE DEI PIANI DI TAGLIO NEAR, FAR E DI PROIEZIONE -------------------------------------- // recupero il piano di proiezione ( piano che contiene la flatRegion) PtrOwner pCrv( ConvertCurveToComposite( pSfrPock->GetLoop( 0, 0))) ; @@ -10981,7 +11208,7 @@ Pocketing::GetProjStmOnSfr( const ISurfFlatRegion* pSfr, const ISurfTriMesh* pSt if ( vtNorm.IsSmall()) return false ; plNear.Set( ptCen - 2 * EPS_SMALL * vtNorm, -vtNorm ) ; // taglio tutto ciò che sta nel semipiano negativo - Vector3d vtTraslPlane = ( nStep == 1 ? STEP_HEIGHT : dStep) * vtNorm ; + Vector3d vtTraslPlane = dStep * vtNorm ; plFar.Set( ptCen + vtTraslPlane, vtNorm) ; // taglio tutto ciò che sta nel semepiano positivo plProj.Set( ptCen, -vtNorm) ; if ( ! plNear.IsValid() || ! plFar.IsValid() || ! plProj.IsValid()) @@ -11001,6 +11228,7 @@ Pocketing::GetProjStmOnSfr( const ISurfFlatRegion* pSfr, const ISurfTriMesh* pSt vCrv.emplace_back( vCrvPO.back()) ; } } + const int STEP_HEIGHT = dStep * 1.5 ; PtrOwner pSrf_ForCuttingRaw( GetSurfTriMeshByRegionExtrusion( vCrv, vtNorm * STEP_HEIGHT)) ; if ( IsNull( pSrf_ForCuttingRaw) || ! pSrf_ForCuttingRaw->IsValid()) return false ; @@ -11016,7 +11244,7 @@ Pocketing::GetProjStmOnSfr( const ISurfFlatRegion* pSfr, const ISurfTriMesh* pSt if ( pSrfRaw_clone->IsValid()) pSrfRaw_clone->Cut( plFar, true) ; // se step > 1 -> chiudo la superificie dalla parte del piano di far - if ( nStep > 1 && ! IsNull( pSrfRaw_clone) && pSrfRaw_clone->IsValid()) { + if ( ! IsNull( pSrfRaw_clone) && pSrfRaw_clone->IsValid()) { POLYLINEVECTOR vPL ; pSrfRaw_clone->GetLoops( vPL) ; for ( int p = 0 ; p < ( int)vPL.size() ; ++ p) { diff --git a/Pocketing.h b/Pocketing.h index f43500d..4eed5c1 100644 --- a/Pocketing.h +++ b/Pocketing.h @@ -100,6 +100,8 @@ class Pocketing : public Machining bool GetParamsAtEachStep( ISURFFRPOVECTOR& vSrfSliced, std::vector& vCrvOEWithFlags, BOOLVECTOR& vbChangedPrec, const ISurfFlatRegion* pSrfChunk, const int& nStep, const Vector3d vtTool, const double& dElev, const double& dDepth, const double& dStep) ; + bool GetAdaptedSfrByTrimesh( const ISurfFlatRegion* pSrfPock, const Vector3d& vtTrasl, ISurfFlatRegion* pNewSrfPock, + Frame3d frPocket = GLOB_FRM) ; bool AdaptSfrWithRaw( ISurfFlatRegion* pSrf, Vector3d vtTrasl, const double& dRawSecLen, ICRVCOMPOPOVECTOR& vCrvOEFlags, bool& bChanged, int nStep, double dStep, double dAreaToll = 500 * EPS_SMALL) ;