EgtExch3dm :
- corretto un errore di esportazione delle superfici di bezier. - aggiunta la possibilità di eliminare il layer rimasti vuoti durante l'esportazione. - aggiunte le facce composte nelle Mesh di un 3dm - corretta gestione dell'orientazione delle superfici importate - corretta l'importazione delle curve di trim delle superfici di rivoluzione ( spazio param diverso da quello della nurbs corrispondente) - resa più robusta la conversione dei BrepLoop in caso di curve compo composte da tratti molto corti.
This commit is contained in:
+46
-10
@@ -115,10 +115,11 @@ Export3dm::Export( IGeomDB* pGDB, int nId, const string& sFile)
|
||||
return false ;
|
||||
pIter->GoTo( nId) ;
|
||||
// esporto l'oggetto e i suoi eventuali figli
|
||||
bool bOk = ExportObject( *pIter, 0) ;
|
||||
bool bAdded = false ;
|
||||
bool bOk = ExportObject( *pIter, 0, bAdded) ;
|
||||
|
||||
// stampo il file
|
||||
int version = 7 ;
|
||||
int version = 8 ;
|
||||
// errors printed to stdout
|
||||
ON_TextLog error_log ;
|
||||
// writes model to archive
|
||||
@@ -131,7 +132,7 @@ Export3dm::Export( IGeomDB* pGDB, int nId, const string& sFile)
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
bool
|
||||
Export3dm::ExportObject( const IGdbIterator& iIter, const int& nLayer)
|
||||
Export3dm::ExportObject( const IGdbIterator& iIter, const int& nLayer, bool& bAdded)
|
||||
{
|
||||
// recupero il livello dell'oggetto
|
||||
int nLev = GDB_LV_USER ;
|
||||
@@ -164,36 +165,50 @@ Export3dm::ExportObject( const IGdbIterator& iIter, const int& nLayer)
|
||||
case GEO_PNT3D: {
|
||||
if ( ! ExportPnt( sName, iIter, frFrame, cCol, nLayer))
|
||||
return false ;
|
||||
else
|
||||
bAdded = true ;
|
||||
break ;
|
||||
}
|
||||
case SRF_BEZIER: {
|
||||
if ( ! ExportSrfBz( sName, iIter, frFrame, cCol, nLayer))
|
||||
return false ;
|
||||
else
|
||||
bAdded = true ;
|
||||
break ;
|
||||
}
|
||||
case SRF_FLATRGN :
|
||||
case SRF_TRIMESH :
|
||||
if ( ! ExportSTM( sName, iIter, frFrame, cCol, nLayer))
|
||||
return false ;
|
||||
else
|
||||
bAdded = true ;
|
||||
break ;
|
||||
case CRV_ARC : {
|
||||
if ( ! ExportCrvArc( sName, iIter, frFrame, cCol, nLayer))
|
||||
return false ;
|
||||
else
|
||||
bAdded = true ;
|
||||
break ;
|
||||
}
|
||||
case CRV_BEZIER : {
|
||||
if ( ! ExportCrvBezier( sName, iIter, frFrame, cCol, nLayer))
|
||||
return false ;
|
||||
else
|
||||
bAdded = true ;
|
||||
break ;
|
||||
}
|
||||
case CRV_COMPO : {
|
||||
if ( ! ExportCrvCompo( sName, iIter, frFrame, cCol, nLayer))
|
||||
return false ;
|
||||
else
|
||||
bAdded = true ;
|
||||
break ;
|
||||
}
|
||||
case CRV_LINE : {
|
||||
if ( ! ExportCrvLine( sName, iIter, frFrame, cCol, nLayer))
|
||||
return false ;
|
||||
else
|
||||
bAdded = true ;
|
||||
break ;
|
||||
}
|
||||
default :
|
||||
@@ -205,7 +220,8 @@ Export3dm::ExportObject( const IGdbIterator& iIter, const int& nLayer)
|
||||
int nLayer = iIter.GetId() ;
|
||||
if ( nLayer == 0) {
|
||||
m_model.RemoveModelComponent( ON_ModelComponent::Type::Layer, m_model.LayerFromIndex( 0).ModelComponentId()) ;
|
||||
return ScanGroup( iIter, nLayer) ;
|
||||
bool bEmpty = false ;
|
||||
return ScanGroup( iIter, nLayer, bEmpty) ;
|
||||
}
|
||||
// creo il layer e setto le proprietà
|
||||
ON_Layer* layer = new ON_Layer() ;
|
||||
@@ -236,11 +252,19 @@ Export3dm::ExportObject( const IGdbIterator& iIter, const int& nLayer)
|
||||
|
||||
// aggiungo il layer
|
||||
ON_ModelComponentReference mcr = m_model.AddManagedModelComponent( layer) ;
|
||||
ON_UUID uuid = mcr.ModelComponentId() ;
|
||||
int nIndex = mcr.ModelComponentIndex() ;
|
||||
m_mLayer.insert( pair< int, int>( nLayer, nIndex)) ;
|
||||
|
||||
|
||||
// esploro il gruppo
|
||||
return ScanGroup( iIter, nIndex) ;
|
||||
bool bEmpty = false ;
|
||||
bool bOk = ScanGroup( iIter, nIndex, bEmpty) ;
|
||||
if ( bEmpty)
|
||||
;
|
||||
//m_model.RemoveModelComponent( ON_ModelComponent::Type::Layer, uuid) ; // se si volessero cancellare i layer vuoti
|
||||
else
|
||||
bAdded = true ;
|
||||
return bOk ;
|
||||
}
|
||||
default :
|
||||
return false ;
|
||||
@@ -434,10 +458,10 @@ Export3dm::ExportSrfBz( const string& sName, const IGdbIterator& iIter, const Fr
|
||||
// imposto il vettore dei nodi in V
|
||||
int nKnotCountV = nDegV + nCPV - 1 ;
|
||||
dKnot = 0 ;
|
||||
// per costruzione nKnotCount é un multiplo di nDegU
|
||||
// per costruzione nKnotCount é un multiplo di nDegV
|
||||
for ( int v = 0 ; v < int ( nKnotCountV / nDegV) ; ++v) {
|
||||
for ( int p = 0 ; p < nDegV ; ++p)
|
||||
onNurbsSurf->SetKnot( 0, v * nDegV + p, dKnot) ;
|
||||
onNurbsSurf->SetKnot( 1, v * nDegV + p, dKnot) ;
|
||||
++dKnot ;
|
||||
}
|
||||
// aggiungo l'oggetto al modello
|
||||
@@ -482,6 +506,11 @@ Export3dm::ExportSTM( const string& sName, const IGdbIterator& iIter, const Fram
|
||||
int nIdVert[3] ; pSrfTm->GetTriangle( t, nIdVert) ;
|
||||
onMesh->SetTriangle( t, nIdVert[0], nIdVert[1], nIdVert[2]) ;
|
||||
}
|
||||
ON_MeshVertexFaceMap onMeshVertMap ;
|
||||
onMeshVertMap.SetFromMesh( onMesh, false) ;
|
||||
onMesh->AddPlanarNgons( onMeshVertMap.VertexFaceMap(), 0.1, 3, 1, true) ;
|
||||
onMesh->ComputeFaceNormals() ;
|
||||
onMesh->Compact() ;
|
||||
// aggiungo l'oggetto al modello
|
||||
return AddObjectToModel( iIter, onMesh, nLayer, sName, cCol) ;
|
||||
}
|
||||
@@ -689,7 +718,7 @@ Export3dm::ExportCrvLine( const string& sName, const IGdbIterator& iIter, const
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
bool
|
||||
Export3dm::ScanGroup( const IGdbIterator& iIter, const int& nLayer)
|
||||
Export3dm::ScanGroup( const IGdbIterator& iIter, const int& nLayer, bool& bEmpty)
|
||||
{
|
||||
// creo un iteratore
|
||||
PtrOwner<IGdbIterator> pIter( CreateGdbIterator( iIter.GetGDB())) ;
|
||||
@@ -697,12 +726,19 @@ Export3dm::ScanGroup( const IGdbIterator& iIter, const int& nLayer)
|
||||
return false ;
|
||||
// scandisco il gruppo
|
||||
bool bOk = true ;
|
||||
int nCount = 0 ;
|
||||
for ( bool bNext = pIter->GoToFirstInGroup( iIter) ;
|
||||
bNext ;
|
||||
bNext = pIter->GoToNext()) {
|
||||
if ( ! ExportObject( *pIter, nLayer))
|
||||
bool bAdded = false ;
|
||||
if ( ! ExportObject( *pIter, nLayer, bAdded))
|
||||
bOk = false ;
|
||||
else if ( bAdded)
|
||||
++ nCount ;
|
||||
}
|
||||
|
||||
if ( nCount == 0)
|
||||
bEmpty = true ;
|
||||
|
||||
return bOk ;
|
||||
}
|
||||
|
||||
+2
-2
@@ -41,11 +41,11 @@ class Export3dm : public IExport3dm
|
||||
}
|
||||
|
||||
private :
|
||||
bool ExportObject( const IGdbIterator& iIter, const int& nLayer) ;
|
||||
bool ExportObject( const IGdbIterator& iIter, const int& nLayer, bool& bAdded) ;
|
||||
bool AddObjectToModel( const IGdbIterator& iIter, ON_Object* onObject, const int& nLayer, const std::string& sName, const Color& cCol,
|
||||
ON_3dmObjectAttributes* pOnAttr = nullptr) ;
|
||||
bool AddInfoToObject( const IGdbIterator& iIter, ON_Object* onObject) ;
|
||||
bool ScanGroup( const IGdbIterator& iIter, const int& nLayer) ;
|
||||
bool ScanGroup( const IGdbIterator& iIter, const int& nLayer, bool& bEmpty) ; // nCount restituisce il numero di oggetti inseriti nel gruppo
|
||||
bool TestFilter( int nLev, int nMode, int nStat, bool bGroup = false) ;
|
||||
std::wstring ConvertString( const std::string& sName) { return std::wstring( sName.begin(), sName.end()) ;} ;
|
||||
ON_3dPoint ConvertPoint( const Point3d& pt) { return ON_3dPoint( pt.x, pt.y, pt.z) ;} ;
|
||||
|
||||
+173
-45
@@ -102,7 +102,7 @@ Import3dm::Import( const string& sFile, IGeomDB* pGDB, int nIdGroup,
|
||||
int nFirstId = 0 ;
|
||||
|
||||
ON_UUID ON_nil_uuid = { 0,0,0,{ 0,0,0,0,0,0,0,0}} ;
|
||||
int nLayDelCount = 0 ;
|
||||
//int nLayDelCount = 0 ; //serve solo se si vogliono cancellare i layer parent. Se però questi layer contengono oggetti, che non sono in sottolayer del parent, non verranno visualizzati
|
||||
for ( const ON_ModelComponent* mc = component_iterator_l.FirstComponent() ; mc != nullptr ; mc = component_iterator_l.NextComponent()) {
|
||||
ON_UUID uuid = mc->Id() ;
|
||||
const ON_Layer* onLayer = ON_Layer::Cast( mc) ;
|
||||
@@ -125,18 +125,21 @@ Import3dm::Import( const string& sFile, IGeomDB* pGDB, int nIdGroup,
|
||||
[uuidParent](pair< int, tuple<const ON_Layer*, ON_UUID, int, bool>> x){ return !ON_UuidCompare( get<1>(get<1>(x)), uuidParent) ;});
|
||||
}
|
||||
|
||||
// se era già stato aggiunto il parent e non era già indicata la presenza di sottolayer
|
||||
// devo eliminare il parent e mettere a true il flag dei sottolayer nella mappa dei layer
|
||||
if ( it_parent != m_mLayer.end() ) {
|
||||
if ( !get<3>(it_parent->second) ) {
|
||||
get<3>(it_parent->second) = true ;
|
||||
m_pGDB->Erase( it_parent->first) ;
|
||||
auto LayerDeleted = m_mLayer.extract(it_parent->first);
|
||||
LayerDeleted.key() = nLayDelCount ;
|
||||
-- nLayDelCount ;
|
||||
m_mLayer.insert(std::move(LayerDeleted));
|
||||
}
|
||||
}
|
||||
|
||||
// COMMENTO QUESTO TRATTO PERCHé, LASCIO I LAYER PARENT E LI CANCELLO ALLA FINE DELL'IMPORT SOLO SE RESTANO VUOTI
|
||||
//
|
||||
//// se era già stato aggiunto il parent e non era già indicata la presenza di sottolayer
|
||||
//// devo eliminare il parent e mettere a true il flag dei sottolayer nella mappa dei layer
|
||||
// if ( it_parent != m_mLayer.end() ) {
|
||||
// if ( !get<3>(it_parent->second) ) {
|
||||
// get<3>(it_parent->second) = true ;
|
||||
// m_pGDB->Erase( it_parent->first) ;
|
||||
// auto LayerDeleted = m_mLayer.extract(it_parent->first);
|
||||
// LayerDeleted.key() = nLayDelCount ;
|
||||
// -- nLayDelCount ;
|
||||
// m_mLayer.insert(std::move(LayerDeleted));
|
||||
// }
|
||||
// }
|
||||
|
||||
int nIdLayer = m_pGDB->AddGroup( GDB_ID_NULL, nIdGroup, GLOB_FRM) ;
|
||||
if ( nFirstId == 0)
|
||||
@@ -151,9 +154,7 @@ Import3dm::Import( const string& sFile, IGeomDB* pGDB, int nIdGroup,
|
||||
|
||||
// se non riesco a convertire un oggetto, lo scarto e incremento il contatore del suo tipo nel dizionario error_count
|
||||
int nId ;
|
||||
int nCount = 0 ;
|
||||
for( const ON_ModelComponent* mc = component_iterator.FirstComponent() ; mc != nullptr ; mc = component_iterator.NextComponent()) {
|
||||
++ nCount ;
|
||||
const ON_ModelGeometryComponent* mgc = ON_ModelGeometryComponent::Cast( mc) ;
|
||||
const ON_Object* oGeometry = mgc->Geometry( nullptr) ;
|
||||
// individuo a che layer appartiene l'oggetto
|
||||
@@ -327,6 +328,7 @@ Import3dm::Import( const string& sFile, IGeomDB* pGDB, int nIdGroup,
|
||||
}
|
||||
}
|
||||
|
||||
// CANCELLO I LAYER RIMASTI VUOTI ??
|
||||
|
||||
// messaggio di errore da mettere nel log per dire quanti oggetti sono stati ignorati perché la conversione non è riuscita
|
||||
map<string, int>::iterator it = m_mError_count.begin() ;
|
||||
@@ -456,7 +458,7 @@ Import3dm::ConvertCurve( const ON_Curve* onCurve)
|
||||
}
|
||||
case ON::eCurveType::ctProxy :{
|
||||
const ON_CurveProxy* onProxyCurve = ON_CurveProxy::Cast( onCurve) ;
|
||||
ON_Curve* onCurve = onProxyCurve->DuplicateCurve() ;
|
||||
const ON_Curve* onCurve = onProxyCurve->ProxyCurve() ;
|
||||
return ConvertCurve( onCurve) ;
|
||||
break ;
|
||||
}
|
||||
@@ -631,9 +633,13 @@ Import3dm::ConvertSurface( const ON_Surface* onSurf)
|
||||
// uso la nurbs form
|
||||
ON_NurbsSurface onNurbsSurface ;
|
||||
int nOk = onBrepFace->GetNurbForm( onNurbsSurface) ;
|
||||
if ( nOk != 0)
|
||||
|
||||
if ( nOk != 0){
|
||||
pSurf.Set( ConvertSurface( & onNurbsSurface)) ;
|
||||
}
|
||||
else {
|
||||
// QUI PERò NON TENGO CONTO DEL TRIM!!!!!!
|
||||
//
|
||||
// se non è riuscita la conversione in nurbs tengo la superficie originale
|
||||
const ON_Surface* onSurfFace = onBrepFace->ProxySurface() ;
|
||||
// qui devo applicare a mano le trasformazioni dalla superfice originale alla proxy
|
||||
@@ -649,7 +655,7 @@ Import3dm::ConvertSurface( const ON_Surface* onSurf)
|
||||
pSurf.Set( ConvertSurface( &onNurbsSurface)) ;
|
||||
}
|
||||
else
|
||||
pSurf.Set( ConvertSurface( onSurfaceProxy->DuplicateSurface())) ;
|
||||
pSurf.Set( ConvertSurface( onSurfaceProxy->ProxySurface())) ;
|
||||
return Release( pSurf) ;
|
||||
}
|
||||
|
||||
@@ -670,10 +676,11 @@ Import3dm::ConvertBrep( const ON_Brep* onBrep, const bool bForceTriMesh)
|
||||
if ( ! stmSoup.Start())
|
||||
return vSurf ;
|
||||
bool bSurfTm = false ;
|
||||
int nFailedBFace = 0, nFailedTm = 0, nFailedFr = 0, nFailedBz = 0 ;
|
||||
int nFailedBFace = 0, nFailedTm = 0, nFailedFr = 0, nFailedBz = 0, nFailedBTrim = 0 ;
|
||||
|
||||
for ( int i = 0 ; i < onBrep->m_F.Count() ; ++i) {
|
||||
ON_BrepFace* onFace = onBrep->Face( i) ;
|
||||
bool bRev = onFace->m_bRev ;
|
||||
const ON_Surface* onSurface = onFace->SurfaceOf() ;
|
||||
PtrOwner<ISurf> pSurf ;
|
||||
if ( const ON_PlaneSurface* onPlaneSurface = ON_PlaneSurface::Cast( onSurface)) {
|
||||
@@ -706,61 +713,93 @@ Import3dm::ConvertBrep( const ON_Brep* onBrep, const bool bForceTriMesh)
|
||||
if ( nType == SRF_TRIMESH) {
|
||||
bSurfTm = true ;
|
||||
PtrOwner<ISurfTriMesh> pSurfTm( GetSurfTriMesh( Release( pSurf))) ;
|
||||
if ( ! IsNull( pSurfTm) && pSurfTm->IsValid())
|
||||
if ( !IsNull(pSurfTm) && pSurfTm->IsValid() ) {
|
||||
if ( bRev)
|
||||
pSurfTm->Invert() ;
|
||||
stmSoup.AddSurfTriMesh( *pSurfTm) ;
|
||||
}
|
||||
else
|
||||
++ nFailedTm ;
|
||||
}
|
||||
else if ( nType == SRF_FLATRGN) {
|
||||
bSurfTm = true ;
|
||||
PtrOwner<ISurfFlatRegion> pSurfFr( GetSurfFlatRegion( Release( pSurf))) ;
|
||||
if ( ! IsNull( pSurfFr) && pSurfFr->IsValid())
|
||||
stmSoup.AddSurfTriMesh( *pSurfFr->GetAuxSurf()) ;
|
||||
if ( ! IsNull( pSurfFr) && pSurfFr->IsValid()) {
|
||||
if ( bRev)
|
||||
pSurfFr->Invert() ;
|
||||
stmSoup.AddSurfTriMesh(*pSurfFr->GetAuxSurf()) ;
|
||||
}
|
||||
else
|
||||
++ nFailedFr ;
|
||||
}
|
||||
else if ( nType == SRF_BEZIER) {
|
||||
PtrOwner<ISurfBezier> pSurfBezNew( GetSurfBezier( Release( pSurf))) ;
|
||||
// se ho più di un loop vuol dire che ho dei trim sulla faccia e quindi li aggiungo alla superficie di bezier
|
||||
// prima della triangolazione
|
||||
if ( ! IsNull( pSurfBezNew) && pSurfBezNew->IsValid()) {
|
||||
ON_BrepFace* onFace = onBrep->Face( i) ;
|
||||
SurfFlatRegionByContours SfrCntr ;
|
||||
for ( int k = 0 ; k < onFace->LoopCount() ; ++k )
|
||||
SfrCntr.AddCurve( ConvertBrepLoop( onFace->Loop( k))) ;
|
||||
|
||||
const ON_Surface* onSurface = onFace->SurfaceOf() ;
|
||||
// se la superficie era una superficie di rivoluzione, le eventuali curve di trim erano parametrizzate con la coordinata x in radianti,
|
||||
// e non riferita allo spazio parametrico della nurbs corrispondente ( che sarebbe una nurbs razionale, dovendo approssimare un arco di circonferenza)
|
||||
// devo quindi prelevare le curve di trim e cambiarne le coordinate per matcharle allo spazio parametrico della nurbs
|
||||
if ( const ON_RevSurface* onRevSurf = ON_RevSurface::Cast( onSurface) ) {
|
||||
for ( int k = 0 ; k < onFace->LoopCount() ; ++k ) {
|
||||
ICurve* pCrv( ConvertBrepLoop( onFace->Loop( k))) ;
|
||||
// qui devo spostare ogni punto della curva dallo spazio parametrico della superificie rev allo spazio della superficie nurbs
|
||||
ConvertCurveParam( onRevSurf, &pCrv) ;
|
||||
pCrv->Scale( GLOB_FRM, SBZ_TREG_COEFF, SBZ_TREG_COEFF, 1) ;
|
||||
SfrCntr.AddCurve( pCrv) ;
|
||||
}
|
||||
}
|
||||
else {
|
||||
for ( int k = 0 ; k < onFace->LoopCount() ; ++k ) {
|
||||
PtrOwner<ICurve> pCrv( ConvertBrepLoop( onFace->Loop( k))) ;
|
||||
pCrv->Scale( GLOB_FRM, SBZ_TREG_COEFF, SBZ_TREG_COEFF, 1) ;
|
||||
SfrCntr.AddCurve( Release( pCrv)) ;
|
||||
}
|
||||
}
|
||||
ISurfFlatRegion* sfrTrim = SfrCntr.GetSurf() ;
|
||||
// questa regione di Trim deve essere riferita al rettangolo parametrico totale ( spaz param 1x1 -> regione trim 1000x1000)
|
||||
// devo anche controllare che il sistema di riferimento dello spazio di trim totale sia giusto ( con l'angolo BottomLeft in (0,0)
|
||||
//posizonato nel primo quadrante del piano XY)
|
||||
|
||||
// questa regione di Trim deve essere riferita al rettangolo parametrico totale ( spaz param 1x1 -> regione trim 1000x1000)
|
||||
// devo anche controllare che il sistema di riferimento dello spazio di trim totale sia giusto ( con l'angolo BottomLeft in (0,0)
|
||||
//posizonato nel primo quadrante del piano XY)
|
||||
double u0,u1,v0,v1 ;
|
||||
onFace->GetDomain(0, &u0, &u1) ;
|
||||
onFace->GetDomain(1, &v0, &v1) ;
|
||||
double dScaleU = u1 - u0 ;
|
||||
double dScaleV = v1 - v0 ;
|
||||
Vector3d vToOrig( -u0, -v0, 0) ;
|
||||
sfrTrim->Translate( vToOrig) ;
|
||||
// se la superficie di partenza aveva vettori dei nodi non uniformi devo riscalare lo spazio parametrico in modo da renderli uniformi
|
||||
// applicando così la trasformazione anche alle curve di trim.
|
||||
|
||||
Vector3d vToOrig( -u0 * SBZ_TREG_COEFF, -v0 * SBZ_TREG_COEFF, 0) ;
|
||||
if ( sfrTrim != nullptr)
|
||||
sfrTrim->Translate( vToOrig) ;
|
||||
else {
|
||||
++ nFailedBTrim ;
|
||||
return vSurf ;
|
||||
}
|
||||
// se la superficie di partenza aveva vettori dei nodi non uniformi devo riscalare lo spazio parametrico in modo da renderli uniformi
|
||||
// applicando così la trasformazione anche alle curve di trim.
|
||||
ON_NurbsSurface onNurbsSurface ;
|
||||
onFace->GetNurbForm( onNurbsSurface) ;
|
||||
// rendo uniforme lo spazio parametrico nella direzione dei parametri che non lo sono
|
||||
// rendo uniforme lo spazio parametrico nella direzione dei parametri che non lo sono
|
||||
int nDegU, nDegV, nSpanU, nSpanV ;
|
||||
bool bRat, bTrim ;
|
||||
pSurfBezNew->GetInfo( nDegU, nDegV, nSpanU, nSpanV, bRat, bTrim) ;
|
||||
// devo rendere lo spazio parametrico uniforme solo se la superficie è trimmata, sennò non serve
|
||||
// per capire se la superficie sia trimmata controllo che lo spazio parametrico trimmato non coincida con tutto lo spazio parametrico
|
||||
PtrOwner<ISurfFlatRegion> pSurfParam( GetSurfFlatRegionRectangle( dScaleU - EPS_SMALL, dScaleV - EPS_SMALL)) ;
|
||||
pSurfParam->Subtract( *sfrTrim) ;
|
||||
if ( pSurfParam->IsValid())
|
||||
// devo rendere lo spazio parametrico uniforme solo se la superficie è trimmata, sennò non serve
|
||||
// per capire se la superficie sia trimmata controllo che lo spazio parametrico trimmato non coincida con tutto lo spazio parametrico
|
||||
PtrOwner<ISurfFlatRegion> pSurfParam(GetSurfFlatRegionRectangle(( dScaleU - EPS_SMALL ) * SBZ_TREG_COEFF, ( dScaleV - EPS_SMALL) * SBZ_TREG_COEFF)) ;
|
||||
// se la sottrazione tra spazio parametrico e superficie di trim è diversa da zero, allora la superficie era trimmata
|
||||
if ( sfrTrim != nullptr && pSurfParam->Subtract( *sfrTrim) && pSurfParam->IsValid()) {
|
||||
MakeUniform( &sfrTrim, onNurbsSurface, dScaleU, dScaleV) ;
|
||||
pSurfBezNew->SetTrimRegion( *sfrTrim) ;
|
||||
}
|
||||
else
|
||||
sfrTrim->Scale( GLOB_FRM, nSpanU * SBZ_TREG_COEFF / dScaleU, nSpanV * SBZ_TREG_COEFF / dScaleV, 1) ;
|
||||
pSurfBezNew->SetTrimRegion( *sfrTrim) ;
|
||||
sfrTrim->Scale( GLOB_FRM, nSpanU / dScaleU, nSpanV / dScaleV, 1) ;
|
||||
|
||||
if ( sfrTrim != nullptr)
|
||||
delete sfrTrim ;
|
||||
|
||||
if ( bRev)
|
||||
pSurfBezNew->Invert() ;
|
||||
|
||||
if ( ! bForceTriMesh)
|
||||
vSurf.emplace_back( Release( pSurfBezNew)) ;
|
||||
else
|
||||
@@ -789,6 +828,10 @@ Import3dm::ConvertBrep( const ON_Brep* onBrep, const bool bForceTriMesh)
|
||||
string sOut = "Import3dm : Failed conversion of " + to_string( nFailedBz) + " NURBS belonging to a Brep" ;
|
||||
LOG_ERROR( GetEE3Logger(), sOut.c_str()) ;
|
||||
}
|
||||
if ( nFailedBTrim != 0) {
|
||||
string sOut = "Import3dm : Failed conversion of " + to_string( nFailedBTrim) + " trims of surfaces belonging to a Brep" ;
|
||||
LOG_ERROR( GetEE3Logger(), sOut.c_str()) ;
|
||||
}
|
||||
|
||||
if ( ! stmSoup.End())
|
||||
return vSurf ;
|
||||
@@ -803,7 +846,8 @@ bool
|
||||
Import3dm::MakeUniform( ISurfFlatRegion** sfr, ON_NurbsSurface onNurbsSurface, double dScaleU, double dScaleV)
|
||||
{
|
||||
// riscalo le superfici prima di effettuare una serie di operazioni di collage
|
||||
(*sfr)->Scale( GLOB_FRM, SBZ_TREG_COEFF, SBZ_TREG_COEFF, 1) ;
|
||||
//(*sfr)->Scale( GLOB_FRM, SBZ_TREG_COEFF, SBZ_TREG_COEFF, 1) ;
|
||||
// la superficie in input arriva già scalata
|
||||
bool bRescaledU = false ;
|
||||
bool bRescaledV = false ;
|
||||
int nSpanU = 1, nSpanV = 1 ;
|
||||
@@ -928,8 +972,24 @@ Import3dm::ConvertBrepLoop( const ON_BrepLoop* onBrepLoop)
|
||||
for ( int i = 0 ; i < nTrim ; ++i) {
|
||||
ON_BrepTrim* onBrepTrim = onBrepLoop->Trim( i) ;
|
||||
ON_CurveProxy* onCurveProxy = ON_CurveProxy::Cast( onBrepTrim);
|
||||
pCrvCompo->AddCurve( ConvertCurve( onCurveProxy)) ;
|
||||
PtrOwner<ICurve> pCrv( ConvertCurve( onCurveProxy)) ;
|
||||
if ( ! pCrvCompo->AddCurve( pCrv->Clone())) {
|
||||
Point3d ptEnd ; pCrvCompo->GetEndPoint( ptEnd) ;
|
||||
pCrv->ModifyStart( ptEnd) ;
|
||||
if ( ! pCrvCompo->AddCurve( pCrv->Clone()))
|
||||
return nullptr ;
|
||||
}
|
||||
}
|
||||
|
||||
//// APPROSSIMO I BREP LOOP PER ALLEGGERIRE LE OPERAZIONI DI TRIM DELLE BEZIER
|
||||
//pCrvCompo->RemoveSmallParts( 0.1, 15) ;
|
||||
//pCrvCompo->MergeCurves( 0.1, 15) ;
|
||||
|
||||
|
||||
//PolyArc paApprox ;
|
||||
//pCrvCompo->ApproxWithArcs( 0.1, 15, paApprox) ;
|
||||
//pCrvCompo->FromPolyArc( paApprox) ;
|
||||
|
||||
return Release( pCrvCompo) ;
|
||||
}
|
||||
|
||||
@@ -1046,7 +1106,6 @@ Import3dm::ConvertExtrusion( const ON_Extrusion* onExtrusion)
|
||||
ISurfTriMesh*
|
||||
Import3dm::ConvertMesh( const ON_Mesh* onMesh)
|
||||
{
|
||||
|
||||
ON_Mesh* onMeshToConvert = onMesh->Duplicate() ;
|
||||
PtrOwner<ISurfTriMesh> pSurfTm( CreateSurfTriMesh()) ;
|
||||
if ( IsNull( pSurfTm))
|
||||
@@ -1106,6 +1165,9 @@ Import3dm::ConvertMesh( const ON_Mesh* onMesh)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
delete onMeshToConvert ;
|
||||
|
||||
pSurfTm->AdjustTopology() ;
|
||||
return Release( pSurfTm) ;
|
||||
}
|
||||
@@ -1304,3 +1366,69 @@ Import3dm::ConvertAnnotation( const ON_Annotation* onAnnot, const ON_DimStyle* o
|
||||
m_mError_count["annotation"] += 1 ;
|
||||
return vpObj ;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
bool
|
||||
Import3dm::ConvertCurveParam( const ON_RevSurface* onRevSurf, ICurve** pCrv)
|
||||
{
|
||||
PtrOwner<ICurve> pCrvNew ;
|
||||
if ( (*pCrv)->GetType() == CRV_LINE) {
|
||||
PtrOwner<ICurveLine> pCrvLine( CreateCurveLine()) ;
|
||||
double dnurbsU ;
|
||||
double dnurbsV ;
|
||||
Point3d ptStart ; (*pCrv)->GetStartPoint( ptStart) ;
|
||||
onRevSurf->GetNurbFormParameterFromSurfaceParameter( ptStart.x, ptStart.y, &dnurbsU, &dnurbsV) ;
|
||||
ptStart.Set( dnurbsU, dnurbsV, 0) ;
|
||||
Point3d ptEnd ; (*pCrv)->GetEndPoint( ptEnd) ;
|
||||
onRevSurf->GetNurbFormParameterFromSurfaceParameter( ptEnd.x, ptEnd.y, &dnurbsU, &dnurbsV) ;
|
||||
ptEnd.Set( dnurbsU, dnurbsV, 0) ;
|
||||
pCrvLine->Set( ptStart, ptEnd) ;
|
||||
pCrvNew.Set( Release( pCrvLine)) ;
|
||||
}
|
||||
else if ( (*pCrv)->GetType() == CRV_ARC) {
|
||||
double dnurbsU ;
|
||||
double dnurbsV ;
|
||||
Point3d ptStart ; (*pCrv)->GetStartPoint( ptStart) ;
|
||||
onRevSurf->GetNurbFormParameterFromSurfaceParameter( ptStart.x, ptStart.y, &dnurbsU, &dnurbsV) ;
|
||||
ptStart.Set( dnurbsU, dnurbsV, 0) ;
|
||||
Point3d ptEnd ; (*pCrv)->GetEndPoint( ptEnd) ;
|
||||
onRevSurf->GetNurbFormParameterFromSurfaceParameter( ptEnd.x, ptEnd.y, &dnurbsU, &dnurbsV) ;
|
||||
ptEnd.Set( dnurbsU, dnurbsV, 0) ;
|
||||
Vector3d vtDir, vtN ;
|
||||
(*pCrv)->GetStartDir( vtDir) ;
|
||||
ICurveArc* pCrvArcOrig = GetCurveArc( (*pCrv)) ;
|
||||
vtN = pCrvArcOrig->GetNormVersor( ) ;
|
||||
PtrOwner<ICurveArc> pCrvArc( CreateCurveArc()) ;
|
||||
pCrvArc->Set2PVN( ptStart, ptEnd, vtDir, vtN) ;
|
||||
pCrvNew.Set( Release( pCrvArc)) ;
|
||||
}
|
||||
else if ( (*pCrv)->GetType() == CRV_BEZIER) {
|
||||
double dnurbsU ;
|
||||
double dnurbsV ;
|
||||
PtrOwner<ICurveBezier> pCrvBez( GetCurveBezier( (*pCrv))) ;
|
||||
int nDeg = pCrvBez->GetDegree() ;
|
||||
int nCV = nDeg + 1 ;
|
||||
for ( int i = 0 ; i < nCV ; ++i) {
|
||||
Point3d ptNew = pCrvBez->GetControlPoint( i) ;
|
||||
onRevSurf->GetNurbFormParameterFromSurfaceParameter( ptNew.x, ptNew.y, &dnurbsU, &dnurbsV) ;
|
||||
ptNew.Set( dnurbsU, dnurbsV, 0) ;
|
||||
// sto cambiando le coordinate dei CP nella curva, mentre i pesi non sono da modificare
|
||||
pCrvBez->SetControlPoint( i, ptNew) ;
|
||||
}
|
||||
pCrvNew.Set( pCrvBez) ;
|
||||
}
|
||||
else if ( (*pCrv)->GetType() == CRV_COMPO) {
|
||||
PtrOwner<ICurveComposite> pCrvCompo( GetCurveComposite( (*pCrv))) ;
|
||||
PtrOwner<ICurveComposite> pCrvCompoNew( CreateCurveComposite()) ;
|
||||
for ( const ICurve* pCrvSimpleOrig = pCrvCompo->GetFirstCurve() ; pCrvSimpleOrig != nullptr ; pCrvSimpleOrig = pCrvCompo->GetNextCurve()) {
|
||||
ICurve* pCrvSimple( pCrvSimpleOrig->Clone()) ;
|
||||
ConvertCurveParam( onRevSurf, &pCrvSimple) ;
|
||||
pCrvCompoNew->AddCurve( pCrvSimple) ;
|
||||
}
|
||||
pCrvNew.Set( pCrvCompoNew) ;
|
||||
}
|
||||
|
||||
(*pCrv) = Release( pCrvNew) ;
|
||||
|
||||
return true ;
|
||||
}
|
||||
|
||||
@@ -53,6 +53,7 @@ class Import3dm : public IImport3dm
|
||||
ISURFPOVECTOR ConvertBrep( const ON_Brep* onBrep, const bool bForceTriMesh) ;
|
||||
ICurve* ConvertBrepLoop( const ON_BrepLoop* onBrepLoop) ;
|
||||
bool MakeUniform( ISurfFlatRegion** sfr, ON_NurbsSurface onNurbsSurface, double dScaleU, double dScaleV) ;
|
||||
bool ConvertCurveParam( const ON_RevSurface* onRevSurf, ICurve** pCrv) ;
|
||||
|
||||
private :
|
||||
IGeomDB* m_pGDB ;
|
||||
|
||||
Reference in New Issue
Block a user