EgtGeomKernel :
- introduzione delle nurbs periodiche; da finire.
This commit is contained in:
+110
-9
@@ -510,14 +510,7 @@ CurveToArcsPerpExtrCurve( const ICurve* pCrv, double dLinTol, double dAngTolDeg)
|
||||
bool
|
||||
NurbsCurveCanonicalize( CNurbsData& cnData)
|
||||
{
|
||||
// se periodica
|
||||
if ( cnData.bPeriodic) {
|
||||
// va trasformata in non-periodica (clamped)
|
||||
// vedere The NurbsBook di Les Piegl e Tiller
|
||||
// mancano esempi per testare
|
||||
return false ;
|
||||
}
|
||||
// se con nodi extra
|
||||
// se con nodi extra
|
||||
if ( cnData.bExtraKnotes) {
|
||||
int nKnotesNbr = int( cnData.vU.size()) ;
|
||||
if ( nKnotesNbr < 4)
|
||||
@@ -526,7 +519,91 @@ NurbsCurveCanonicalize( CNurbsData& cnData)
|
||||
for ( int i = 0 ; i < nKnotesNbr - 2 ; ++ i)
|
||||
cnData.vU[i] = cnData.vU[i+1] ;
|
||||
cnData.vU.resize( nKnotesNbr - 2) ;
|
||||
return true ;
|
||||
}
|
||||
|
||||
// se periodica
|
||||
if ( cnData.bPeriodic) {
|
||||
CNurbsData cnData_clamped ;
|
||||
// va trasformata in non-periodica (clamped)
|
||||
// bisogna aumentare la molteplicità del primo e ultimo nodo fino ad arrivare al grado della nurbs
|
||||
// e poi scartare nodi e punti fuori dalla regione clamped ( tra u_p e u_(m-p) ?)
|
||||
|
||||
// comincio ad aumentare la molteplictià della fine della curva
|
||||
int nCP = int( cnData.vCP.size()) ;
|
||||
int nU = nCP + cnData.nDeg - 1 ;
|
||||
PNTVECTOR vBC ;
|
||||
vBC.resize( cnData.nDeg + 1) ;
|
||||
DBLVECTOR vBW ;
|
||||
vBW.resize( cnData.nDeg + 1) ;
|
||||
if ( ! cnData.bRat) {
|
||||
for ( int i = 0 ; i <= cnData.nDeg ; ++ i)
|
||||
vBC[ cnData.nDeg - i] = cnData.vCP[nCP - 1 - i] ;
|
||||
}
|
||||
else {
|
||||
for ( int i = 0 ; i <= cnData.nDeg ; ++ i) {
|
||||
vBC[cnData.nDeg - i] = cnData.vCP[nCP - i] * cnData.vW[nCP - i] ;
|
||||
vBW[cnData.nDeg - i] = cnData.vW[nCP - i] ;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
double alpha ;
|
||||
int b = nU - 1 ;
|
||||
int a = b - 1 ;
|
||||
int i = b ;
|
||||
while ( abs( cnData.vU[b] - cnData.vU[b - 1]) < EPS_ZERO)
|
||||
-- b ;
|
||||
int mult = min( i - b + 1, cnData.nDeg) ; // mi aspetto che sia 1, ma comunque sarà < cnData.nDeg
|
||||
int r = cnData.nDeg - mult ;
|
||||
//// indice che si riferisce al vettore vCP
|
||||
int c = nU - cnData.nDeg + 1 ;
|
||||
// aggiusto a mano il vettore dei nodi ( aumento la molteplicità del primo valore fino a cnData.nDeg)
|
||||
double dKnot = cnData.vU[ nU - 1] ;
|
||||
cnData.vU.resize( nU + r) ;
|
||||
for ( int t = 0 ; t < r ; ++t) {
|
||||
cnData.vU[nU + t] = dKnot ;
|
||||
}
|
||||
|
||||
if ( mult < cnData.nDeg) {
|
||||
// inserisco il nodo r volte
|
||||
for ( int j = 1 ; j <= r ; ++ j) {
|
||||
int L = b - cnData.nDeg + j ;
|
||||
for ( int i = 0; i <= r - j ; ++i) {
|
||||
alpha = (cnData.vU[b] - cnData.vU[L+i])/ ( cnData.vU[i+b+1] - cnData.vU[L+i]) ;
|
||||
vBC[i] = alpha * vBC[i+1] + ( 1 - alpha) * vBC[i] ;
|
||||
if ( cnData.bRat) {
|
||||
vBW[i] = alpha * vBW[i+1] + ( 1 - alpha) * vBW[i] ;
|
||||
}
|
||||
}
|
||||
cnData.vCP[L] = vBC[0] ;
|
||||
//cnData.vCP[c+r-j-mult] = vBC[r-j] ;
|
||||
if ( cnData.bRat ) {
|
||||
cnData.vW[L] = vBW[0] ;
|
||||
//cnData.vW[c+r-j-mult] = vBW[r-j] ;
|
||||
}
|
||||
}
|
||||
}
|
||||
// aggiungo i punti ottenuti alla curva.
|
||||
cnData.vCP.resize( nCP + cnData.nDeg - mult) ;
|
||||
for ( int p = 0 ; p < cnData.nDeg - mult ; ++p) {
|
||||
cnData.vCP[ nCP + cnData.nDeg - mult - 1 - p] = vBC[cnData.nDeg - p] ;
|
||||
}
|
||||
if ( cnData.bRat ) {
|
||||
cnData.vW.resize( nCP + cnData.nDeg - mult) ;
|
||||
for ( int p = 0 ; p <= cnData.nDeg ; ++p) {
|
||||
cnData.vW[ nCP + cnData.nDeg - mult - 1 - p] = vBW[cnData.nDeg - p] ;
|
||||
}
|
||||
}
|
||||
|
||||
// aumento la molteplicità del primo punto
|
||||
|
||||
// aggiusto a mano il vettore dei nodi ( aumento la molteplicità del primo valore fino a cnData.nDeg)
|
||||
/// DA ADATTARE PER IL PRIMO
|
||||
cnData.vU.resize( nU + cnData.nDeg - mult) ;
|
||||
dKnot = cnData.vU[ nU] ;
|
||||
for ( int t = nU - 1 ; t < cnData.nDeg - mult - 1 ; ++t) {
|
||||
cnData.vU[t] = dKnot ;
|
||||
}
|
||||
}
|
||||
|
||||
return true ;
|
||||
@@ -710,6 +787,30 @@ NurbsToBezierCurve( const CNurbsData& cnData)
|
||||
}
|
||||
}
|
||||
|
||||
// se la curva ha grado 1, manca da aggiungere l'ultimo tratto
|
||||
if ( cnData.nDeg == 1 ) {
|
||||
// costruisco la curva di Bezier e la inserisco nella curva composita
|
||||
PtrOwner<ICurveBezier> pCrvBez( CreateCurveBezier()) ;
|
||||
if ( ! pCrvBez->Init( cnData.nDeg, cnData.bRat))
|
||||
return nullptr ;
|
||||
if ( ! cnData.bRat) {
|
||||
for ( int i = 0 ; i <= cnData.nDeg ; ++ i) {
|
||||
if ( ! pCrvBez->SetControlPoint( i, vBC[i]))
|
||||
return nullptr ;
|
||||
}
|
||||
}
|
||||
else {
|
||||
for ( int i = 0 ; i <= cnData.nDeg ; ++ i) {
|
||||
if ( ! pCrvBez->SetControlPoint( i, vBC[i] / vBW[i], vBW[i]))
|
||||
return nullptr ;
|
||||
}
|
||||
}
|
||||
if ( ! pCrvBez->IsAPoint()) {
|
||||
if ( ! pCrvCompo->AddCurve( Release( pCrvBez)))
|
||||
return nullptr ;
|
||||
}
|
||||
}
|
||||
|
||||
// restituisco la curva composita
|
||||
return Release( pCrvCompo) ;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user