From fc29cbd471294ce463453da64204b918b445b7c8 Mon Sep 17 00:00:00 2001 From: Riccardo Elitropi Date: Wed, 25 Feb 2026 18:07:19 +0100 Subject: [PATCH] EgtMachKernel (Preview) : - primo Test Preview Utensile. --- Machine.h | 2 +- Machining.cpp | 590 +++++++++++++++++++++++++++++++++++++++++++------- Machining.h | 17 +- 3 files changed, 529 insertions(+), 80 deletions(-) diff --git a/Machine.h b/Machine.h index 5fbc446..deb68c9 100644 --- a/Machine.h +++ b/Machine.h @@ -100,6 +100,7 @@ class Machine bool LoadAllTools( void) ; bool UnloadAllTools( void) ; bool ResetHeadSet( const std::string& sHead) ; + const STRVECTOR& GetHSet( const std::string& sHead) const ; bool GetAxisToken( const std::string& sAxis, std::string& sToken) const ; bool GetAxisInvert( const std::string& sAxis, bool& bInvert) const ; bool GetAxisOffset( const std::string& sAxis, double& dOffset) const ; @@ -267,7 +268,6 @@ class Machine TcPos* GetTcPos( int nGroup) const ; Exit* GetExit( int nGroup) const ; bool AddHeadToSet( const std::string& sHSet, const std::string& sName) ; - const STRVECTOR& GetHSet( const std::string& sHead) const ; bool EnableHeadInSet( const std::string& sHead) ; bool LoadTool( Exit* pExit, const std::string& sTool) ; bool ModifyMachineHeadAuxDirection( const std::string& sHead, const Vector3d& vtADir) ; diff --git a/Machining.cpp b/Machining.cpp index af745c8..0025672 100644 --- a/Machining.cpp +++ b/Machining.cpp @@ -19,13 +19,42 @@ #include "OperUserNotesConst.h" #include "/EgtDev/Include/EGkGeoPoint3d.h" #include "/EgtDev/Include/EGkCurve.h" +#include "/EgtDev/Include/EGkGeoVector3d.h" +#include +#include using namespace std ; +const string KEY_AXIS_GROUP = "PreviewAxisGroup" ; +const string KEY_ROT_AXIS_VAL = "PreviewRotAxisVal" ; // salvata per ogni gruppo di Preview + +// struttura per informazioni sugli assi +struct PreviewAxisInfo { + string sName ; + double dVal ; + bool bLinear ; + PreviewAxisInfo( string sN, double dV, bool bL) + : sName( sN), dVal( dV), bLinear( bL) {} +} ; +typedef vector VPREVIEWAXISINFO ; + //---------------------------------------------------------------------------- //---------------------------------------------------------------------------- Machining::Machining( void) { + m_nLookFlag = MCH_LOOK_TAB_HEAD ; + m_nPreviewHeadId = GDB_ID_NULL ; + m_nPreviewToolTip = GDB_ID_NULL ; + m_vPreviewAxisIds = {} ; +} + +//---------------------------------------------------------------------------- +Machining::~Machining( void) +{ + m_nLookFlag = MCH_LOOK_NONE ; + m_nPreviewHeadId = GDB_ID_NULL ; + m_nPreviewToolTip = GDB_ID_NULL ; + m_vPreviewAxisIds.clear() ; } //---------------------------------------------------------------------------- @@ -67,18 +96,18 @@ Machining:: NeedPrevHome( void) const bool Machining::GetStartPoint( Point3d& ptStart) const { - // verifico validità gestore DB geometrico + // verifico validità gestore DB geometrico if ( m_pGeomDB == nullptr) return false ; // recupero gruppo per geometria di lavorazione (Cutter Location) int nClId = m_pGeomDB->GetFirstNameInGroup( GetOwner(), MCH_CL) ; if ( nClId == GDB_ID_NULL) return false ; - // recupero la prima entità del primo sottogruppo + // recupero la prima entità del primo sottogruppo int nEntId = m_pGeomDB->GetFirstInGroup( m_pGeomDB->GetFirstGroupInGroup( nClId)) ; if ( nEntId == GDB_ID_NULL) return false ; - // recupero il punto iniziale di questa entità + // recupero il punto iniziale di questa entità const IGeoObj* pGeoObj = m_pGeomDB->GetGeoObj( nEntId) ; if ( pGeoObj->GetType() == GEO_PNT3D) { ptStart = GetGeoPoint3d( pGeoObj)->GetPoint() ; @@ -94,18 +123,18 @@ Machining::GetStartPoint( Point3d& ptStart) const bool Machining::GetEndPoint( Point3d& ptEnd) const { - // verifico validità gestore DB geometrico + // verifico validità gestore DB geometrico if ( m_pGeomDB == nullptr) return false ; // recupero gruppo per geometria di lavorazione (Cutter Location) int nClId = m_pGeomDB->GetFirstNameInGroup( GetOwner(), MCH_CL) ; if ( nClId == GDB_ID_NULL) return false ; - // recupero l'ultima entità dell'ultimo sottogruppo + // recupero l'ultima entità dell'ultimo sottogruppo int nEntId = m_pGeomDB->GetLastInGroup( m_pGeomDB->GetLastGroupInGroup( nClId)) ; if ( nEntId == GDB_ID_NULL) return false ; - // recupero il punto finale di questa entità + // recupero il punto finale di questa entità const IGeoObj* pGeoObj = m_pGeomDB->GetGeoObj( nEntId) ; if ( pGeoObj->GetType() == GEO_PNT3D) { ptEnd = GetGeoPoint3d( pGeoObj)->GetPoint() ; @@ -119,14 +148,129 @@ Machining::GetEndPoint( Point3d& ptEnd) const //---------------------------------------------------------------------------- bool -Machining::PrepareToolPreview( void) const +Machining::UpdateToolView( int nLookFlag) { - // verifico validità gestori DB geometrico e CAM + // verifico validità del Flag + if ( nLookFlag != MCH_LOOK_NONE && nLookFlag != MCH_LOOK_TAB_TOOL && nLookFlag != MCH_LOOK_TAB_HEAD) + return false ; + + // se stesso Flag, non faccio nulla + if ( m_nLookFlag == nLookFlag) + return true ; + + // aggiorno il flag + m_nLookFlag = nLookFlag ; + + // se non esiste un gruppo di Preview, non faccio nulla + int nStId = m_pGeomDB->GetFirstNameInGroup( GetOwner(), MCH_ST) ; + if ( nStId == GDB_ID_NULL) + return true ; + + // recupero la macchina corrente + Machine* pMch = m_pMchMgr->GetCurrMachine() ; + if ( pMch == nullptr) + return false ; + + // se non ho una testa corrente in Preview, non faccio nulla + if ( m_nPreviewHeadId == GDB_ID_NULL) { + RemoveToolPreview() ; + return false ; + } + + // recupero l'identificativo del gruppo di base della macchina + int nMBaseId = m_pGeomDB->GetFirstInGroup( pMch->GetMachineId()) ; + + // se non devo visualizzare nulla, allora spengo il gruppo "ST" + if ( m_nLookFlag == MCH_LOOK_NONE) + m_pGeomDB->SetStatus( nStId, GDB_ST_OFF) ; + // altrimenti + else { + m_pGeomDB->SetStatus( nStId, GDB_ST_ON) ; + // contatori locali + const int MAX_ITER = 50 ; + bool bStop = false ; + int nIter = 0 ; + // se devo visualizzare solamente il gruppo della testa corrente + if ( m_nLookFlag == MCH_LOOK_TAB_TOOL) { + // la testa diventa visibile + m_pGeomDB->SetStatus( m_nPreviewHeadId, GDB_ST_ON) ; + // tutti i gruppi che contengono la testa diventano visibili fino a "ST", l'unico loro + // figlio visibile deve essere quello che contiene la testa corrente + int nCurrId = m_nPreviewHeadId ; + while ( ! bStop && nIter < MAX_ITER) { + int nParentId = m_pGeomDB->GetParentId( nCurrId) ; + if ( nParentId == GDB_ID_NULL) { + RemoveToolPreview() ; + return false ; + } + m_pGeomDB->SetStatus( nParentId, GDB_ST_ON) ; + int nChildId = m_pGeomDB->GetFirstGroupInGroup( nParentId) ; + while ( nChildId != GDB_ID_NULL) { + if ( m_pGeomDB->GetGdbType( nChildId) == GDB_TY_GROUP && nChildId == nCurrId) + m_pGeomDB->SetStatus( nChildId, GDB_ST_ON) ; + else + m_pGeomDB->SetStatus( nChildId, GDB_ST_OFF) ; + nChildId = m_pGeomDB->GetNextGroup( nChildId) ; + } + bStop = ( nParentId == nStId || nParentId == nMBaseId) ; + nCurrId = nParentId ; + ++ nIter ; + } + } + // se devo visualizzare tutta la gerarchia + else { + deque dqHierarchy ; + dqHierarchy.push_front( nStId) ; + while ( ! bStop && nIter < MAX_ITER) { + // recupero ed elimino dalla deque il primo Id memorizzato + int nCurrId = dqHierarchy.front() ; + dqHierarchy.pop_front() ; + if ( nCurrId == GDB_ID_NULL) { + RemoveToolPreview() ; + return false ; + } + // rendo visibile tale Layer + m_pGeomDB->SetStatus( nCurrId, GDB_ST_ON) ; + // se il gruppo corrente è la testa, ho finito + bStop = ( nCurrId == m_nPreviewHeadId) ; + if ( ! bStop) { + // tutti i gruppi figli diventano visibili + int nChildId = m_pGeomDB->GetFirstInGroup( nCurrId) ; + while ( nChildId != GDB_ID_NULL) { + if ( m_pGeomDB->GetGdbType( nChildId) == GDB_TY_GROUP) + dqHierarchy.push_back( nChildId) ; + nChildId = m_pGeomDB->GetNext( nChildId) ; + } + } + else { + for ( auto Iter = dqHierarchy.begin() ; Iter != dqHierarchy.end() ; ++ Iter) { + if ( m_pGeomDB->GetGdbType( *Iter) == GDB_TY_GROUP) + m_pGeomDB->SetStatus( *Iter, GDB_ST_ON) ; + } + } + ++ nIter ; + } + } + } + + return true ; +} + +//---------------------------------------------------------------------------- +bool +Machining::PrepareToolPreview() +{ + // verifico validità gestori DB geometrico e CAM if ( m_pGeomDB == nullptr || m_pMchMgr == nullptr) return false ; - // creo o svuoto gruppo per anteprima utensile + + // recupero la macchina corrente + Machine* pMch = m_pMchMgr->GetCurrMachine() ; + if ( pMch == nullptr) + return false ; + + // se non esite il Gruppo di Preview, lo aggiungo int nStId = m_pGeomDB->GetFirstNameInGroup( GetOwner(), MCH_ST) ; - // se non c'è, lo aggiungo if ( nStId == GDB_ID_NULL) { nStId = m_pGeomDB->AddGroup( GDB_ID_NULL, GetOwner(), Frame3d()) ; if ( nStId == GDB_ID_NULL) @@ -134,9 +278,10 @@ Machining::PrepareToolPreview( void) const m_pGeomDB->SetName( nStId, MCH_ST) ; m_pGeomDB->SetLevel( nStId, GDB_LV_TEMP) ; } - // altrimenti lo svuoto + // altrimenti lo svuoto else m_pGeomDB->EmptyGroup( nStId) ; + // se necessario, imposto l'utensile corrente string sCurrTool ; m_pMchMgr->GetCalcTool( sCurrTool) ; const_cast( this)->UpdateToolData() ; @@ -144,34 +289,269 @@ Machining::PrepareToolPreview( void) const if ( ! m_pMchMgr->SetCalcTool( GetToolName(), GetHeadName(), GetExitNbr())) return false ; } - // copio la testa della lavorazione nel gruppo - int nHeadId = m_pMchMgr->GetHeadId( GetHeadName()) ; - int nId = m_pGeomDB->CopyGlob( nHeadId, GDB_ID_NULL, nStId) ; - m_pGeomDB->SetMode( nId, GDB_MD_STD) ; - m_pGeomDB->SetStatus( nId, GDB_ST_OFF) ; - // elimino eventuali gruppi opportunamente indicati - int nSubId = m_pGeomDB->GetFirstGroupInGroup( nId) ; - while ( nSubId != GDB_ID_NULL) { - int nNextSubId = m_pGeomDB->GetNextGroup( nSubId) ; - bool bShow = true ; - if ( m_pGeomDB->GetInfo( nSubId, KEY_PREVIEWSHOW, bShow) && ! bShow) - m_pGeomDB->Erase( nSubId) ; - nSubId = nNextSubId ; + + // recupero l'identificativo del gruppo di base della macchina + int nMBaseId = m_pGeomDB->GetFirstInGroup( pMch->GetMachineId()) ; + + // recupero l'identificativo della testa della lavorazione corrente e il set di teste associato + string sHead = GetHeadName() ; + int nHeadId = m_pMchMgr->GetHeadId( sHead) ; + const STRVECTOR& vSetHead = pMch->GetHSet( sHead) ; + INTVECTOR vSetHeadIds ; vSetHeadIds.reserve( ssize( vSetHead)) ; + for ( const string& sSetHead : vSetHead) + vSetHeadIds.push_back( pMch->GetHeadId( sSetHead)) ; + + // recupero la tavola corrente + int nCurrTab = pMch->GetCurrTable() ; + + // il gruppo iniziale di costruzione della gerarchia è "ST" + int nCurrHierarchyId = nStId ; + + // Per prima cosa verifico se ci sono degli assi rotativi associati alla tavola, questi devono + // essere inseriti in ordine inverso all'interno del gruppo "ST" e il loro versore associato + // deve essere invertito + // NB. Per il momento viene memorizzato solo l'inverso del vettore; le geometrie vengono scartate + if ( nCurrTab != GDB_ID_NULL) { + // scorro i gruppi rotativi che influenzano tale tavola + bool bStop = false ; + int nCurrGrp = nCurrTab ; + const int MAX_ITER = 50 ; + int nIter = 0 ; + while ( ! bStop && nIter < MAX_ITER) { + // recupero il Parent Id del gruppo corrente + int nParentId = m_pGeomDB->GetParentId( nCurrGrp) ; + bStop = ( nParentId == GDB_ID_NULL || nParentId == nMBaseId || + ! pMch->IsRotaryAxisGroup( nParentId)) ; + if ( ! bStop) { + // recupero il suo Name, il suo Frame e creo il nuovo gruppo rotativo di Tavola + string sName ; + bool bOk = ( m_pGeomDB->GetName( nParentId, sName) && ! sName.empty()) ; + Frame3d* pFrame = ( bOk ? m_pGeomDB->GetGroupFrame( nParentId) : nullptr) ; + bOk = bOk && ( pFrame != nullptr) ; + int nNewTabRotAxisId = ( bOk ? m_pGeomDB->AddGroup( GDB_ID_NULL, nCurrHierarchyId, pFrame) : GDB_ID_NULL) ; + bOk = bOk && ( nNewTabRotAxisId != GDB_ID_NULL) && + m_pGeomDB->SetName( nNewTabRotAxisId, sName) ; + double dAxisPos = 0. ; + bOk = bOk && pMch->GetAxisPos( sName, dAxisPos) && + m_pGeomDB->SetInfo( nNewTabRotAxisId, KEY_ROT_AXIS_VAL, dAxisPos) ; + if ( ! bOk) { + RemoveToolPreview() ; + return false ; + } + nCurrHierarchyId = nNewTabRotAxisId ; + m_vPreviewAxisIds.push_back( nNewTabRotAxisId) ; + // aggiungo il versore invertito + int nChildId = m_pGeomDB->GetFirstInGroup( nParentId) ; + while ( nChildId != GDB_ID_NULL) { + const IGeoVector3d* pGV = GetGeoVector3d( m_pGeomDB->GetGeoObj( nChildId)) ; + if ( pGV != nullptr) { + PtrOwner pGVInv( CloneGeoVector3d( pGV)) ; + if ( ! IsNull( pGVInv)) { + pGVInv->Mirror( pGV->GetBase(), pGV->GetVector()) ; + string sName ; m_pGeomDB->GetName( nChildId, sName) ; + int nNewGVId = m_pGeomDB->AddGeoObj( GDB_ID_NULL, nNewTabRotAxisId, Release( pGVInv)) ; + if ( nNewGVId == GDB_ID_NULL || ! m_pGeomDB->SetName( nNewGVId, sName) || + ! m_pGeomDB->SetStatus( nNewGVId, GDB_ST_OFF)) { + RemoveToolPreview() ; + return false ; + } + break ; + } + } + nChildId = m_pGeomDB->GetNext( nChildId) ; + } + nCurrGrp = nParentId ; + } + ++ nIter ; + } } - return ( nId != GDB_ID_NULL) ; + + // A partire dal gruppo corrente della gerarchia devo inserire tutti gli assi angolari + // che contengono la testa attuale. + // - Gli assi Lineari vengono scartati. + // - Gli assi Angolari sono rappresentati solo ed esclusivamente dal loro vettore. + // - I Gruppi Figli degli assi Angolari che non sono altri assi Angolari vengono memorizzati + // solamente se presentano il flag "PreviewShow" a 1. + // - I Gruppi figli degli assi Angolari che non sono presenti nell'HeadSet corrente vengono visualizzati + // - Se percorrendo la Catena cinamentica dalla Head al Gruppo Base incontro un asse Lineare, allora + // tutti gli assi Angolari successivi non presenteranno Geometrie Attive, solamente il vettore. + struct HierarchyAxis { + int nId ; + string sName ; + bool bRotary ; + HierarchyAxis( int nI, const string& sN, bool bR) + : nId( nI), sName( sN), bRotary( bR) {} ; + } ; + vector vHierarchyAxis ; + set setAxisIdNoPreview ; + // parto dal gruppo HeadId e a ritroso recupero la gerarchia + int nCurrGrp = nHeadId ; + const int MAX_ITER = 50 ; + int nIter = 0 ; + bool bFoundLinear = false ; + while ( nIter < MAX_ITER) { + // recupero il Parent Id del gruppo corrente + int nParentId = m_pGeomDB->GetParentId( nCurrGrp) ; + if ( nParentId == GDB_ID_NULL || nParentId == nMBaseId) + break ; + // verifico se asse Lineare o Rotativo + bool bRotary = pMch->IsRotaryAxisGroup( nParentId) ; + if ( ! bFoundLinear && ! bRotary) + bFoundLinear = true ; + // recupero il nome dell'Asse + string sAxName ; m_pGeomDB->GetName( nParentId, sAxName) ; + // memorizzo l'asse + vHierarchyAxis.emplace_back( nParentId, sAxName, bRotary) ; + // aggiorno i controlli + if ( bFoundLinear) + setAxisIdNoPreview.insert( nParentId) ; + nCurrGrp = nParentId ; + ++ nIter ; + } + + // se non c'è alcuna gerarchia, allora inserisco solo la testa corrente + if ( vHierarchyAxis.empty()) { + m_nPreviewHeadId = m_pGeomDB->CopyGlob( nHeadId, GDB_ID_NULL, nCurrHierarchyId) ; + if ( m_nPreviewHeadId == GDB_ID_NULL) { + RemoveToolPreview() ; + return false ; + } + } + // se esiste una gerarchia, allora la ricreo l'albero + else { + for ( auto Iter = vHierarchyAxis.rbegin() ; Iter != vHierarchyAxis.rend() ; ++ Iter) { + int nParentId = Iter->nId ; + // recupero il suo Name, il Frame e creo il nuovo gruppo + string sParentName ; + bool bOk = ( m_pGeomDB->GetName( nParentId, sParentName) && ! sParentName.empty()) ; + Frame3d* pParentFrame = ( bOk ? m_pGeomDB->GetGroupFrame( nParentId) : nullptr) ; + bOk = bOk && ( pParentFrame != nullptr) ; + int nNewParentId = ( bOk ? m_pGeomDB->AddGroup( GDB_ID_NULL, nCurrHierarchyId, *pParentFrame) : GDB_ID_NULL) ; + bOk = bOk && ( nNewParentId != GDB_ID_NULL) && + m_pGeomDB->SetName( nNewParentId, sParentName) ; + if ( bOk) { + // recupero il tipo di asse + bool bRotary = ( pMch->IsRotaryAxisGroup( nParentId)) ; + if ( bRotary) { + m_vPreviewAxisIds.push_back( nNewParentId) ; + // memorizzo la sua posizione iniziale + double dAxisPos = 0. ; + bOk = bOk && pMch->GetAxisPos( sParentName, dAxisPos) && + m_pGeomDB->SetInfo( nNewParentId, KEY_ROT_AXIS_VAL, dAxisPos) ; + } + // scorro i suoi figli + int nChildId = m_pGeomDB->GetFirstInGroup( nParentId) ; + while ( bOk && nChildId != GDB_ID_NULL) { + // se vettore ausiliario lo inserisco solo se asse padre rotativo + if ( m_pGeomDB->GetGdbType( nChildId) == GDB_TY_GEO) { + if ( bRotary) { + const IGeoVector3d* pGV = GetGeoVector3d( m_pGeomDB->GetGeoObj( nChildId)) ; + if ( pGV != nullptr) { + int nNewChildId = m_pGeomDB->CopyGlob( nChildId, GDB_ID_NULL, nNewParentId) ; + bOk = ( nNewChildId != GDB_ID_NULL && m_pGeomDB->SetStatus( nNewChildId, GDB_ST_OFF)) ; + } + } + } + // se gruppo + else if ( m_pGeomDB->GetGdbType( nChildId) == GDB_TY_GROUP) { + // se gruppo testa lo inserisco a prescindere + if ( nChildId == nHeadId) { + m_nPreviewHeadId = m_pGeomDB->CopyGlob( nHeadId, GDB_ID_NULL, nNewParentId) ; + bOk = ( m_nPreviewHeadId == GDB_ID_NULL) ; + } + else { + // se asse successivo nella catena cinematica, sarà il nuovo gruppo padre + auto NextIter = Iter ; ++ NextIter ; + if ( NextIter != vHierarchyAxis.rend() && NextIter->nId == nChildId) + ; + // altrimenti + else { + // se asse precedente ad un asse lineare, non lo inserisco + auto Iter = setAxisIdNoPreview.find( nParentId) ; + if ( Iter != setAxisIdNoPreview.end()) + ; + // altrimenti controllo il valore del Flag di visualizzazione + else { + bool bPreviewShow = false ; + if ( m_pGeomDB->GetInfo( nChildId, KEY_PREVIEWSHOW, bPreviewShow) && bPreviewShow) { + int nNewChildId = m_pGeomDB->CopyGlob( nChildId, GDB_ID_NULL, nNewParentId) ; + bOk = ( nNewChildId != GDB_ID_NULL) ; + } + } + } + } + } + nChildId = m_pGeomDB->GetNext( nChildId) ; + } + nCurrHierarchyId = nNewParentId ; + } + } + } + + // recupero il gruppo dove inserire il punto di tip dell'utensile + int nExitGrpId = pMch->GetCurrExit() ; + if ( nExitGrpId == GDB_ID_NULL) + return false ; + // recupero il name di tale gruppo, devo confrontarlo con la copia di tale gruppo sotto "ST" + string sExitGrpName ; m_pGeomDB->GetName( nExitGrpId, sExitGrpName) ; + // dentro la gerarchia della testa sotto al gruppo "ST" ricerco il gruppo dell'uscita + deque dqIds ; dqIds.push_front( m_nPreviewHeadId) ; + const int MAX_TRY = 50 ; + int nCount = 0 ; + int nNewExitGrpId = GDB_ID_NULL ; + while ( ! dqIds.empty() && nCount < MAX_TRY) { + int nId = dqIds.front() ; + dqIds.pop_front() ; + string sName ; m_pGeomDB->GetName( nId, sName) ; + if ( EqualNoCase( sName, sExitGrpName)) { + nNewExitGrpId = nId ; + break ; + } + int nChildId = m_pGeomDB->GetFirstGroupInGroup( nId) ; + while ( nChildId != GDB_ID_NULL) { + dqIds.push_back( nChildId) ; + nChildId = m_pGeomDB->GetNextGroup( nChildId) ; + } + ++ nCount ; + } + if ( nNewExitGrpId == GDB_ID_NULL) { + RemoveToolPreview() ; + return false ; + } + // Inserisco il punto di Tip ( non visibile) + PtrOwner ptGToolTip( CreateGeoPoint3d()) ; + if ( IsNull( ptGToolTip) || ! ptGToolTip->Set( ORIG - Z_AX * GetToolData().m_dLen)) + return false ; + m_nPreviewToolTip = m_pGeomDB->AddGeoObj( GDB_ID_NULL, nNewExitGrpId, Release( ptGToolTip)) ; + if ( m_nPreviewToolTip == GDB_ID_NULL || + ! m_pGeomDB->SetStatus( m_nPreviewToolTip, GDB_ST_ON)) + return false ; + + // aggiorno la Preview a seconda della modalità + if ( ! UpdateToolView( MCH_LOOK_TAB_TOOL)) { + RemoveToolPreview() ; + return false ; + } + + return true ; } //---------------------------------------------------------------------------- bool -Machining::RemoveToolPreview( void) const +Machining::RemoveToolPreview( void) { - // verifico validità gestore DB geometrico + // verifico validità gestore DB geometrico if ( m_pGeomDB == nullptr) return false ; // recupero gruppo per anteprima utensile int nStId = m_pGeomDB->GetFirstNameInGroup( GetOwner(), MCH_ST) ; // lo svuoto m_pGeomDB->EmptyGroup( nStId) ; + // reset delle variabili membro + m_nPreviewHeadId = GDB_ID_NULL ; + m_nPreviewToolTip = GDB_ID_NULL ; + m_nLookFlag = MCH_LOOK_NONE ; + m_vPreviewAxisIds.clear() ; return true ; } @@ -179,31 +559,37 @@ Machining::RemoveToolPreview( void) const int Machining::GetToolPreviewStepCount( void) const { - // verifico validità gestori DB geometrico e CAM + // verifico validità gestori DB geometrico e CAM if ( m_pGeomDB == nullptr || m_pMchMgr == nullptr) return 0 ; // recupero gruppo per geometria di lavorazione (Cutter Location) int nClId = m_pGeomDB->GetFirstNameInGroup( GetOwner(), MCH_CL) ; if ( nClId == GDB_ID_NULL) return 0 ; - // determino il numero di entità di tutti i sottogruppi, escludendo CLIMB e RISE + // determino il numero di entità di tutti i sottogruppi, escludendo CLIMB e RISE int nCount = 0 ; int nPxId = m_pGeomDB->GetFirstGroupInGroup( nClId) ; while ( nPxId != GDB_ID_NULL) { - // aggiungo tutte le entità del truppo + // aggiungo tutte le entità del truppo nCount += m_pGeomDB->GetGroupObjs( nPxId) ; - // tolgo le entità CLIMB + // tolgo le entità CLIMB int nClimbId = m_pGeomDB->GetFirstNameInGroup( nPxId, MCH_CL_CLIMB) ; while ( nClimbId != GDB_ID_NULL) { -- nCount ; nClimbId = m_pGeomDB->GetNextName( nClimbId, MCH_CL_CLIMB) ; } - // tolgo le entità RISE + // tolgo le entità RISE int nRiseId = m_pGeomDB->GetFirstNameInGroup( nPxId, MCH_CL_RISE) ; while ( nRiseId != GDB_ID_NULL) { -- nCount ; nRiseId = m_pGeomDB->GetNextName( nRiseId, MCH_CL_RISE) ; } + // tolgo le entità di tipo HOME + int nHomeId = m_pGeomDB->GetFirstNameInGroup( nPxId, MCH_CL_HOME) ; + while ( nHomeId != GDB_ID_NULL) { + -- nCount ; + nHomeId = m_pGeomDB->GetNextName( nHomeId, MCH_CL_HOME) ; + } // passo al successivo sottogruppo nPxId = m_pGeomDB->GetNextGroup( nPxId) ; } @@ -223,13 +609,13 @@ Machining::GetToolPreviewNext( int nEntId, int nParentId, int nStId) const // ciclo nel gruppo while ( nNewId != GDB_ID_NULL) { string sName ; m_pGeomDB->GetName( nNewId, sName) ; - if ( sName != MCH_CL_CLIMB && sName != MCH_CL_RISE) + if ( sName != MCH_CL_CLIMB && sName != MCH_CL_RISE && sName != MCH_CL_HOME) break ; nNewId = m_pGeomDB->GetNext( nNewId) ; } // se trovata, esco if ( nNewId != GDB_ID_NULL) { - // se prima entità, eventuale attivazione uscite di gruppo a forare + // se prima entità, eventuale attivazione uscite di gruppo a forare if ( nEntId == GDB_ID_NULL && m_pGeomDB->ExistsInfo( nNewParentId, KEY_DRACEX)) { INTVECTOR vActExit ; if ( m_pGeomDB->GetInfo( nNewParentId, KEY_DRACEX, vActExit)) @@ -245,7 +631,7 @@ Machining::GetToolPreviewNext( int nEntId, int nParentId, int nStId) const if ( m_pGeomDB->GetInfo( nNewParentId, KEY_DRACEX, vActExit)) ActivateDrillingUnit( nStId, vActExit) ; } - // recupero la prima entità del successivo gruppo + // recupero la prima entità del successivo gruppo nNewId = m_pGeomDB->GetFirstInGroup( nNewParentId) ; } while ( nNewId != GDB_ID_NULL) ; return GDB_ID_NULL ; @@ -253,8 +639,16 @@ Machining::GetToolPreviewNext( int nEntId, int nParentId, int nStId) const //---------------------------------------------------------------------------- int -Machining::GetToolPreviewPrev( int nEntId, int nParentId, int nStId) const +Machining::GetToolPreviewPrev( int nEntId, int nParentId, int nStId) /*const*/ { + + if ( m_nLookFlag == MCH_LOOK_TAB_HEAD) + UpdateToolView( MCH_LOOK_TAB_TOOL) ; + else if ( m_nLookFlag == MCH_LOOK_TAB_TOOL) + UpdateToolView( MCH_LOOK_NONE) ; + else + UpdateToolView( MCH_LOOK_TAB_HEAD) ; + // recupero la precedente int nNewId = (( nEntId != GDB_ID_NULL) ? m_pGeomDB->GetPrev( nEntId) : m_pGeomDB->GetLastInGroup( nParentId)) ; int nNewParentId = nParentId ; @@ -263,7 +657,7 @@ Machining::GetToolPreviewPrev( int nEntId, int nParentId, int nStId) const // ciclo nel gruppo while ( nNewId != GDB_ID_NULL) { string sName ; m_pGeomDB->GetName( nNewId, sName) ; - if ( sName != MCH_CL_CLIMB && sName != MCH_CL_RISE) + if ( sName != MCH_CL_CLIMB && sName != MCH_CL_RISE && sName != MCH_CL_HOME) break ; nNewId = m_pGeomDB->GetPrev( nNewId) ; } @@ -278,7 +672,7 @@ Machining::GetToolPreviewPrev( int nEntId, int nParentId, int nStId) const if ( m_pGeomDB->GetInfo( nNewParentId, KEY_DRACEX, vActExit)) ActivateDrillingUnit( nStId, vActExit) ; } - // recupero l'ultima entità del precedente gruppo + // recupero l'ultima entità del precedente gruppo nNewId = m_pGeomDB->GetLastInGroup( nNewParentId) ; } while ( nNewId != GDB_ID_NULL) ; return GDB_ID_NULL ; @@ -286,9 +680,9 @@ Machining::GetToolPreviewPrev( int nEntId, int nParentId, int nStId) const //---------------------------------------------------------------------------- int -Machining::ToolPreview( int nEntId, int nStep) const +Machining::ToolPreview( int nEntId, int nStep) /*const*/ { - // verifico validità gestori DB geometrico e CAM + // verifico validità gestori DB geometrico e CAM if ( m_pGeomDB == nullptr || m_pMchMgr == nullptr) return GDB_ID_NULL ; // recupero la testa nel gruppo per anteprima utensile @@ -296,12 +690,16 @@ Machining::ToolPreview( int nEntId, int nStep) const if ( nStId == GDB_ID_NULL) return GDB_ID_NULL ; m_pGeomDB->SetStatus( nStId, GDB_ST_OFF) ; - // recupero gruppo per geometria di lavorazione (Cutter Location) + // recupero la macchina corrente + Machine* pMch = m_pMchMgr->GetCurrMachine() ; + if ( pMch == nullptr) + return false ; + // recupero il gruppo per geometria di lavorazione (Cutter Location) int nClId = m_pGeomDB->GetFirstNameInGroup( GetOwner(), MCH_CL) ; if ( nClId == GDB_ID_NULL) return GDB_ID_NULL ; int nParentId ; - // se entità nulla + // se entità nulla if ( nEntId == GDB_ID_NULL || ! m_pGeomDB->ExistsObj( nEntId)) { // recupero il gruppo di appartenenza nParentId = m_pGeomDB->GetFirstGroupInGroup( nClId) ; @@ -317,7 +715,7 @@ Machining::ToolPreview( int nEntId, int nStep) const } // altrimenti else { - // verifico che l'entità stia in un sottogruppo di CL + // verifico che l'entità stia in un sottogruppo di CL nParentId = m_pGeomDB->GetParentId( nEntId) ; if ( m_pGeomDB->GetParentId( nParentId) == nClId) { // se richiesta successiva @@ -351,7 +749,8 @@ Machining::ToolPreview( int nEntId, int nStep) const // se esiste il gruppo genitore, visualizzo testa preview if ( nParentId != GDB_ID_NULL) m_pGeomDB->SetStatus( nStId, GDB_ST_ON) ; - // recupero i dati di questa entità + + // recupero i dati dell'entità CamData corrrente const CamData* pCamData = GetCamData( m_pGeomDB->GetUserObj( nEntId)) ; if ( pCamData == nullptr) return GDB_ID_NULL ; @@ -359,36 +758,77 @@ Machining::ToolPreview( int nEntId, int nStep) const AdjustEndPointForAxesCalc( pCamData, ptEnd) ; Vector3d vtTool = pCamData->GetToolDir() ; Vector3d vtBAux = pCamData->GetBackAuxDir() ; - // dati correnti testa/uscita - int nExitId = m_pGeomDB->GetFirstNameInGroup( nStId, MCH_EXIT + ToString( GetExitNbr())) ; - Frame3d frExit ; - m_pGeomDB->GetGroupGlobFrame( nExitId, frExit) ; - // correggo eventuale movimento di disattivazione sempre in Z globale - double dVal ; - if ( m_pGeomDB->GetInfo( nExitId, MCH_EXIT_VAL, dVal)) - frExit.Translate( -dVal * Z_AX) ; - Point3d ptOrig = frExit.Orig() ; - Vector3d vtDir = frExit.VersZ() ; - Vector3d vtAux ; - int nAvId = m_pGeomDB->GetFirstNameInGroup( nStId, MCH_AUX_VECT) ; - ExeStartVector( nAvId, GDB_ID_ROOT, vtAux) ; - // rototraslo opportunamente - Frame3d frHead ; - m_pGeomDB->GetGroupGlobFrame( nStId, frHead) ; - Frame3d frRef ; - if ( vtAux.IsSmall() || AreSameOrOppositeVectorApprox( vtAux, vtDir)) - frRef.Set( ptOrig, vtDir) ; - else - frRef.Set( ptOrig, vtDir, vtAux) ; - Frame3d frShow ; - if ( vtBAux.IsSmall() || AreSameOrOppositeVectorApprox( vtBAux, vtTool)) - frShow.Set( ptEnd + vtTool * GetToolData().m_dLen, vtTool) ; - else - frShow.Set( ptEnd + vtTool * GetToolData().m_dLen, vtTool, vtBAux) ; - frHead.ToLoc( frRef) ; - frHead.ToGlob( frShow) ; - *(m_pGeomDB->GetGroupFrame( nStId)) = frHead ; + // recupero gli assi e i loro valori per la posizione corrente + const DBLVECTOR& vAxVal = pCamData->GetAxesVal() ; + STRVECTOR vAxNames ; m_pMchMgr->GetAllCurrAxesNames( vAxNames) ; + if ( ssize( vAxVal) != ssize( vAxNames)) + return GDB_ID_NULL ; + int nAxSize = ssize( vAxVal) ; + VPREVIEWAXISINFO vAxisInfo ; vAxisInfo.reserve( nAxSize) ; + for ( int i = 0 ; i < nAxSize ; ++ i) { + bool bLinear = false ; + pMch->GetAxisType( vAxNames[i], bLinear) ; + vAxisInfo.emplace_back( vAxNames[i], vAxVal[i], bLinear) ; + } + + // scorro gli assi dentro al gruppo "ST" ( vi sono solo quelli rotativi) + for ( auto Iter = m_vPreviewAxisIds.begin() ; Iter != m_vPreviewAxisIds.end() ; ++ Iter) { + // recupero l'Id dell'asse corrente + int nAxisId = *Iter ; + if ( nAxisId == GDB_ID_NULL) + return GDB_ID_NULL ; + // recupero il nome di tale asse + string sAxisName ; + if ( ! m_pGeomDB->GetName( nAxisId, sAxisName)) + return GDB_ID_NULL ; + // recupero il valore corrente dell'asse + double dCurrAxisVal = 0. ; + m_pGeomDB->GetInfo( nAxisId, KEY_ROT_AXIS_VAL, dCurrAxisVal) ; + // recupero il valore dell'asse + bool bFound = false ; + double dAxisVal = 0 ; + for ( int i = 0 ; ! bFound && i < nAxSize ; ++ i) { + if ( ! vAxisInfo[i].bLinear && EqualNoCase( sAxisName, vAxisInfo[i].sName)) { + bFound = true ; + dAxisVal = vAxisInfo[i].dVal ; + } + } + if ( ! bFound) + return GDB_ID_NULL ; + // recupero il vettore dell'asse + int nV = m_pGeomDB->GetFirstNameInGroup( nAxisId, sAxisName) ; + const IGeoVector3d* pGV = GetGeoVector3d( m_pGeomDB->GetGeoObj( nV)) ; + if ( pGV == nullptr) + return GDB_ID_NULL ; + Point3d ptPos = pGV->GetBase() ; + Vector3d vtDir = pGV->GetVector() ; + vtDir.Normalize() ; + m_pGeomDB->RotateGroup( nAxisId, ptPos, vtDir, ( dAxisVal - dCurrAxisVal)) ; + m_pGeomDB->SetInfo( nAxisId, KEY_ROT_AXIS_VAL, dAxisVal) ; + } + + // recupero la posizione del tip dell'utensile per movimento assi lineari + if ( m_nPreviewToolTip == GDB_ID_NULL) + return GDB_ID_NULL ; + const IGeoPoint3d* pToolTip = GetGeoPoint3d( m_pGeomDB->GetGeoObj( m_nPreviewToolTip)) ; + if ( pToolTip == nullptr) + return GDB_ID_NULL ; + Point3d ptToolTipLoc = pToolTip->GetPoint() ; + Frame3d frGlob ; m_pGeomDB->GetGlobFrame( m_nPreviewToolTip, frGlob) ; + Point3d ptToolTipGlob = GetToGlob( ptToolTipLoc, frGlob) ; + Vector3d vtMoveGlob = ptEnd - ptToolTipGlob ; + m_pGeomDB->GetGroupGlobFrame( nStId, frGlob) ; + Vector3d vtMoveLoc = GetToLoc( vtMoveGlob, frGlob) ; + /*IGeoPoint3d* A = CreateGeoPoint3d() ; A->Set( ptToolTipGlob) ; + int B = m_pGeomDB->AddGeoObj( GDB_ID_NULL, GDB_ID_ROOT, A->Clone()) ; + m_pGeomDB->SetMaterial( B, FUCHSIA) ; + IGeoPoint3d* C = CreateGeoPoint3d() ; C->Set( ptEnd) ; + int D = m_pGeomDB->AddGeoObj( GDB_ID_NULL, GDB_ID_ROOT, C->Clone()) ; + m_pGeomDB->SetMaterial( D, YELLOW) ;*/ + m_pGeomDB->TranslateGroup( nStId, vtMoveLoc) ; + + // ritorno l'Id dell'entità CamData corrente return nEntId ; } @@ -440,7 +880,7 @@ Machining::CalcMirrorByDouble( int nClId, const string& sUserNotes) if ( nDouble == 0) return true ; - // assegno Id entità originali + // assegno Id entità originali int nPathId = m_pGeomDB->GetFirstNameInGroup( nClId, MCH_PATH + "*") ; while ( nPathId != GDB_ID_NULL) { int nEntId = m_pGeomDB->GetFirstInGroup( nPathId) ; @@ -465,7 +905,7 @@ Machining::CalcMirrorByDouble( int nClId, const string& sUserNotes) m_pGeomDB->SetMaterial( nClPathId, GRAY) ; nClPathId = m_pGeomDB->GetNextGroup( nClPathId) ; } - // assegno Id entità double + // assegno Id entità double nPathId = m_pGeomDB->GetFirstNameInGroup( nDblId, MCH_PATH + "*") ; while ( nPathId != GDB_ID_NULL) { int nEntId = m_pGeomDB->GetFirstInGroup( nPathId) ; diff --git a/Machining.h b/Machining.h index 0be8395..18f6acc 100644 --- a/Machining.h +++ b/Machining.h @@ -8,6 +8,7 @@ // // // Modifiche : 07.06.15 DS Creazione modulo. +// 24.02.26 RE Aggiunta Gestione Preview per Utensile e Testa // // //---------------------------------------------------------------------------- @@ -49,13 +50,15 @@ class Machining : public Operation public : bool GetStartPoint( Point3d& ptStart) const ; bool GetEndPoint( Point3d& ptEnd) const ; - bool PrepareToolPreview( void) const ; - bool RemoveToolPreview( void) const ; + bool UpdateToolView( int nFlag) ; + bool PrepareToolPreview( void) ; + bool RemoveToolPreview( void) ; int GetToolPreviewStepCount( void) const ; - int ToolPreview( int nEntId, int nStep) const ; + int ToolPreview( int nEntId, int nStep) /*const*/ ; protected : Machining( void) ; + ~Machining( void) ; bool SpecialApply( std::string& sErr) ; bool PostApply( std::string& sErr) ; int GetDoubleType( const std::string& sUserNotes) ; @@ -65,7 +68,13 @@ class Machining : public Operation private : int GetToolPreviewNext( int nEntId, int nParentId, int nStId) const ; - int GetToolPreviewPrev( int nEntId, int nParentId, int nStId) const ; + int GetToolPreviewPrev( int nEntId, int nParentId, int nStId) /*const*/ ; + + private : + int m_nLookFlag ; // flag di Visualizzazione per Preview + int m_nPreviewHeadId ; // Id del gruppo testa di Preview + int m_nPreviewToolTip ; // Id del gruppo contenente il punto ToolTip + INTVECTOR m_vPreviewAxisIds ; // indici degli assi di Preview } ; //----------------------------------------------------------------------------