00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "stdafx.h"
00021
00022 #include <iostream>
00023
00024 #include "gul_types.h"
00025 #include "gul_float.h"
00026 #include "gul_vector.h"
00027 #include "guar_bincoeff.h"
00028 #include "gunu_basics.h"
00029 #include "gunu_derivatives.h"
00030
00031
00032 namespace gunu {
00033
00034 using gul::rtr;
00035 using gul::Ptr;
00036 using gul::point;
00037 using gul::point1;
00038 using gul::point2;
00039 using gul::hpoint;
00040 using gul::hpoint1;
00041 using gul::hpoint2;
00042 using gul::set;
00043 using gul::euclid;
00044 using gul::ortho;
00045 using gul::Min;
00046 using gul::Max;
00047 using gul::cross_product;
00048 using gul::normalize;
00049 using gul::rel_equal;
00050
00051
00052
00053
00054
00055 template< class T >
00056 void CalcDersBasisFuns(
00057 const T u, const int i, const int p, const int n,
00058 const Ptr< T >& U, Ptr< Ptr< T > >& ders )
00059 {
00060 T saved,temp,d;
00061 int j,k,r,s1,s2,rk,pk,j1,j2;
00062
00063 Ptr< Ptr< T > > ndu,a;
00064 Ptr< T > left,right;
00065
00066 ndu.reserve_place( reserve_stack(Ptr< T >,p+1), p+1 );
00067 for( j = 0; j < p+1; j++ )
00068 ndu[j].reserve_place( reserve_stack(T,p+1), p+1 );
00069
00070 a.reserve_place( reserve_stack(Ptr< T >,2), 2 );
00071 for( j = 0; j < 2; j++ )
00072 a[j].reserve_place( reserve_stack(T,p+1), p+1 );
00073
00074 left.reserve_place( reserve_stack(T,p+1), p+1 );
00075 right.reserve_place( reserve_stack(T,p+1), p+1 );
00076
00077 ndu[0][0] = 1.0;
00078
00079 for( j = 1; j <= p; j++ )
00080 {
00081 left[j] = u - U[i+1-j];
00082 right[j] = U[i+j]-u;
00083 saved = 0.0;
00084 for( r = 0; r < j; r++ )
00085 {
00086 ndu[j][r] = right[r+1] + left[j-r];
00087 temp = ndu[r][j-1]/ndu[j][r];
00088
00089 ndu[r][j] = saved + right[r+1]*temp;
00090 saved = left[j-r]*temp;
00091 }
00092 ndu[j][j] = saved;
00093 }
00094
00095
00096 for( j = 0; j <= p; j++ )
00097 {
00098 ders[0][j] = ndu[j][p];
00099 }
00100
00101 for( r = 0; r <= p; r++ )
00102 {
00103 s1 = 0; s2 = 1;
00104 a[0][0] = 1.0;
00105
00106 for( k = 1; k <= n; k++ )
00107 {
00108 d = 0.0;
00109 rk = r-k; pk = p-k;
00110
00111 if( r >= k )
00112 {
00113 a[s2][0] = a[s1][0] / ndu[pk+1][rk];
00114 d = a[s2][0] * ndu[rk][pk];
00115 }
00116 if( rk >= -1 )
00117 j1 = 1;
00118 else
00119 j1 = -rk;
00120 if( r-1 <= pk )
00121 j2 = k-1;
00122 else
00123 j2 = p-r;
00124
00125 for( j = j1; j <= j2; j++ )
00126 {
00127 a[s2][j] = (a[s1][j] - a[s1][j-1]) / ndu[pk+1][rk+j];
00128 d += a[s2][j] * ndu[rk+j][pk];
00129 }
00130 if( r <= pk )
00131 {
00132 a[s2][k] = -a[s1][k-1] / ndu[pk+1][r];
00133 d += a[s2][k] * ndu[r][pk];
00134 }
00135 ders[k][r] = d;
00136 j = s1; s1 = s2; s2 = j;
00137 }
00138 }
00139
00140 r = p;
00141 for( k = 1; k <= n; k++ )
00142 {
00143 for( j = 0; j <= p; j++ )
00144 ders[k][j] *= (T)r;
00145 r *= p-k;
00146 }
00147 }
00148
00149 template void CalcDersBasisFuns(
00150 const float u, const int i, const int p, const int n,
00151 const Ptr<float>& U, Ptr< Ptr<float> >& ders );
00152 template void CalcDersBasisFuns(
00153 const double u, const int i, const int p, const int n,
00154 const Ptr<double>& U, Ptr< Ptr<double> >& ders );
00155
00156
00157
00158
00159
00160
00161 template< class T, class EP >
00162 GULAPI void BSPCurveDerivatives(
00163 const T u, const int n, const int p, const gul::Ptr< T >& U,
00164 const gul::Ptr< EP >& Pw, const int d, gul::Ptr< EP >& CK )
00165 {
00166 int du,k,j,span;
00167 EP v1;
00168 Ptr< Ptr< T > > ders;
00169
00170 du = Min( d, p );
00171
00172 ders.reserve_place( reserve_stack(Ptr< T >,du+1), du+1 );
00173 for( j = 0; j <du+1; j++ )
00174 ders[j].reserve_place( reserve_stack(T,p+1), p+1 );
00175
00176 for( k = p+1; k <= d; k++ )
00177 set( CK[k], (T)0.0 );
00178
00179 span = FindSpan( u, n, p, U );
00180 CalcDersBasisFuns( u, span, p, du, U, ders );
00181
00182 for( k = 0; k <= du; k++ )
00183 {
00184 set( CK[k], (T)0.0 );
00185 for( j = 0; j <= p; j++ )
00186 {
00187 v1 = ders[k][j] * Pw[span-p+j];
00188 CK[k] = CK[k] + v1;
00189 }
00190 }
00191 }
00192
00193 template GULAPI void BSPCurveDerivatives(
00194 const float u, const int n, const int p, const Ptr< float >& U,
00195 const Ptr< point<float> >& Pw, const int d, Ptr< point<float> >& CK );
00196 template GULAPI void BSPCurveDerivatives(
00197 const double u, const int n, const int p, const Ptr< double >& U,
00198 const Ptr< point<double> >& Pw, const int d, Ptr< point<double> >& CK );
00199 template GULAPI void BSPCurveDerivatives(
00200 const float u, const int n, const int p, const Ptr< float >& U,
00201 const Ptr< point2<float> >& Pw, const int d, Ptr< point2<float> >& CK );
00202 template GULAPI void BSPCurveDerivatives(
00203 const double u, const int n, const int p, const Ptr< double >& U,
00204 const Ptr< point2<double> >& Pw, const int d, Ptr< point2<double> >& CK );
00205
00206
00207
00208
00209
00210
00211
00212 template< class T, class EP >
00213 void BSPSurfaceDerivatives(
00214 const T u, const T v,
00215 const int nu, const int pu, const Ptr< T >& U,
00216 const int nv, const int pv, const Ptr< T >& V,
00217 const Ptr< Ptr< EP > >& Pw,
00218 const int d, Ptr< Ptr< EP > >& SKL )
00219 {
00220 int du,dv,k,l,uspan,vspan,s,r,dd;
00221 EP v1;
00222 Ptr< EP > temp;
00223 Ptr< Ptr< T > > Nu,Nv;
00224
00225 du = Min( d, pu );
00226 dv = Min( d, pv );
00227
00228 Nu.reserve_place( reserve_stack(Ptr< T >,du+1), du+1 );
00229 for( k = 0; k < pu+1; k++ )
00230 Nu[k].reserve_place( reserve_stack(T,pu+1), pu+1 );
00231
00232 Nv.reserve_place( reserve_stack(Ptr< T >,dv+1), dv+1 );
00233 for( k = 0; k < pv+1; k++ )
00234 Nv[k].reserve_place( reserve_stack(T,pv+1), pv+1 );
00235
00236 temp.reserve_place( reserve_stack(EP,pv+1), pv+1 );
00237
00238 for( k = pu+1; k <= d; k++ )
00239 for( l = 0; l <= d - k; l++ )
00240 set( SKL[k][l], (T)0.0 );
00241
00242 for( l = pv+1; l <= d; l++ )
00243 for( k = 0; k <= d - l; k++ )
00244 set( SKL[k][l], (T)0.0 );
00245
00246 uspan = FindSpan( u, nu, pu, U );
00247 CalcDersBasisFuns( u, uspan, pu, du, U, Nu );
00248
00249 vspan = FindSpan( v, nv, pv, V );
00250 CalcDersBasisFuns( v, vspan, pv, dv, V, Nv );
00251
00252 for( k = 0; k <= du; k++ )
00253 {
00254 for( s = 0; s <= pv; s++ )
00255 {
00256 set( temp[s], (T)0.0 );
00257 for( r = 0; r <= pu; r++ )
00258 {
00259 v1 = Nu[k][r] * Pw[vspan-pv+s][uspan-pu+r];
00260 temp[s] = temp[s] + v1;
00261 }
00262 }
00263 dd = Min( d - k, dv );
00264 for( l = 0; l <= dd; l++ )
00265 {
00266 set( SKL[k][l], (T)0.0 );
00267 for( s = 0; s <= pv; s++ )
00268 {
00269 v1 = Nv[l][s] * temp[s];
00270 SKL[k][l] = SKL[k][l] + v1;
00271 }
00272 }
00273 }
00274 }
00275
00276 template void BSPSurfaceDerivatives(
00277 const float u, const float v,
00278 const int nu, const int pu, const Ptr< float >& U,
00279 const int nv, const int pv, const Ptr< float >& V,
00280 const Ptr< Ptr< point<float> > >& Pw,
00281 const int d, Ptr< Ptr< point<float> > >& SKL );
00282 template void BSPSurfaceDerivatives(
00283 const double u, const double v,
00284 const int nu, const int pu, const Ptr< double >& U,
00285 const int nv, const int pv, const Ptr< double >& V,
00286 const Ptr< Ptr< point<double> > >& Pw,
00287 const int d, Ptr< Ptr< point<double> > >& SKL );
00288
00289 template void BSPSurfaceDerivatives(
00290 const float u, const float v,
00291 const int nu, const int pu, const Ptr< float >& U,
00292 const int nv, const int pv, const Ptr< float >& V,
00293 const Ptr< Ptr< hpoint<float> > >& Pw,
00294 const int d, Ptr< Ptr< hpoint<float> > >& SKL );
00295 template void BSPSurfaceDerivatives(
00296 const double u, const double v,
00297 const int nu, const int pu, const Ptr< double >& U,
00298 const int nv, const int pv, const Ptr< double >& V,
00299 const Ptr< Ptr< hpoint<double> > >& Pw,
00300 const int d, Ptr< Ptr< hpoint<double> > >& SKL );
00301
00302
00303
00304
00305
00306
00307
00308 template< class T, class HP, class EP >
00309 GULAPI void CurveDerivatives(
00310 const T u, const int n, const int p,
00311 const Ptr< T >& U, const Ptr< HP >& Pw, const int d,
00312 Ptr< EP >& CK )
00313 {
00314 Ptr< HP > CKh;
00315 EP v,v1;
00316 T w0;
00317 int k,i;
00318
00319 CKh.reserve_place( reserve_stack(HP,d+1), d+1 );
00320
00321 BSPCurveDerivatives<T,HP>( u, n, p, U, Pw, d, CKh );
00322
00323 w0 = CKh[0].w;
00324
00325 for( k = 0; k <= d; k++ )
00326 {
00327 v = ortho( CKh[k] );
00328
00329 for( i = 1; i <= k; i++ )
00330 {
00331 v1 = (rtr<T>::BinCoeff(k,i) * CKh[i].w) * CK[k-i];
00332 v = v - v1;
00333 }
00334 CK[k] = ((T)1.0 / w0) * v;
00335 }
00336 }
00337
00338 template GULAPI void CurveDerivatives(
00339 const float u, const int n, const int p,
00340 const Ptr< float >& U, const Ptr< hpoint<float> >& Pw, const int d,
00341 Ptr< point<float> >& CK );
00342 template GULAPI void CurveDerivatives(
00343 const double u, const int n, const int p,
00344 const Ptr< double >& U, const Ptr< hpoint<double> >& Pw, const int d,
00345 Ptr< point<double> >& CK );
00346
00347 template GULAPI void CurveDerivatives(
00348 const float u, const int n, const int p,
00349 const Ptr< float >& U, const Ptr< hpoint2<float> >& Pw, const int d,
00350 Ptr< point2<float> >& CK );
00351 template GULAPI void CurveDerivatives(
00352 const double u, const int n, const int p,
00353 const Ptr< double >& U, const Ptr< hpoint2<double> >& Pw, const int d,
00354 Ptr< point2<double> >& CK );
00355
00356
00357
00358 #ifdef _MSC_VER
00359 template<> GULAPI void CurveDerivatives(
00360 const float u, const int n, const int p,
00361 const gul::Ptr<float>& U, const gul::Ptr<gul::point2<float> >& Pw,
00362 const int d, gul::Ptr<gul::point2<float> >& CK )
00363 {
00364 BSPCurveDerivatives(u,n,p,U,Pw,d,CK);
00365 }
00366 template<> GULAPI void CurveDerivatives(
00367 const double u, const int n, const int p,
00368 const gul::Ptr<double>& U, const gul::Ptr<gul::point2<double> >& Pw,
00369 const int d, gul::Ptr<gul::point2<double> >& CK )
00370 {
00371 BSPCurveDerivatives(u,n,p,U,Pw,d,CK);
00372 }
00373 template<> GULAPI void CurveDerivatives(
00374 const float u, const int n, const int p,
00375 const gul::Ptr<float>& U, const gul::Ptr<gul::point<float> >& Pw,
00376 const int d, gul::Ptr<gul::point<float> >& CK )
00377 {
00378 BSPCurveDerivatives(u,n,p,U,Pw,d,CK);
00379 }
00380 template<> GULAPI void CurveDerivatives(
00381 const double u, const int n, const int p,
00382 const gul::Ptr<double>& U, const gul::Ptr<gul::point<double> >& Pw,
00383 const int d, gul::Ptr<gul::point<double> >& CK )
00384 {
00385 BSPCurveDerivatives(u,n,p,U,Pw,d,CK);
00386 }
00387 #endif
00388
00389
00390
00391
00392
00393
00394
00395 template< class T, class HP, class EP >
00396 void SurfaceDerivatives(
00397 const T u, const T v,
00398 const int nu, const int pu, const Ptr< T >& U,
00399 const int nv, const int pv, const Ptr< T >& V,
00400 const Ptr< Ptr < HP > >& Pw,
00401 const int d, Ptr< Ptr < EP > >& SKL )
00402 {
00403 int i,j,k,l;
00404 EP v1,v2,vh;
00405 T w00;
00406 Ptr< Ptr < HP > > SKLh;
00407
00408 SKLh.reserve_place( reserve_stack(Ptr < HP >,d+1), d+1 );
00409 for( i = 0; i < d+1; i++ )
00410 SKLh[i].reserve_place( reserve_stack(HP,d+1), d+1 );
00411
00412 BSPSurfaceDerivatives<T,HP>( u, v, nu, pu, U, nv, pv, V, Pw, d, SKLh );
00413
00414 w00 = SKLh[0][0].w;
00415
00416 for( k = 0; k <= d; k++ )
00417 {
00418 for( l = 0; l <= d-k; l++ )
00419 {
00420 v1 = ortho( SKLh[k][l] );
00421
00422 for( j = 1; j <= l; j++ )
00423 {
00424 vh = (rtr<T>::BinCoeff(l,j) * SKLh[0][j].w) * SKL[k][l-j];
00425 v1 = v1 - vh;
00426 }
00427 for( i = 1; i <= k; i++ )
00428 {
00429 vh = (rtr<T>::BinCoeff(k,i) * SKLh[i][0].w) * SKL[k-i][l];
00430 v1 = v1 - vh;
00431
00432 set( v2, (T)0.0 );
00433 for( j = 1; j <= l; j++ )
00434 {
00435 vh = (rtr<T>::BinCoeff(l,j) * SKLh[i][j].w) * SKL[k-i][l-j];
00436 v2 = v2 + vh;
00437 }
00438 vh = rtr<T>::BinCoeff(k,i) * v2;
00439 v1 = v1 - vh;
00440 }
00441 SKL[k][l] = ((T)1.0 / w00) * v1;
00442 }
00443 }
00444 }
00445
00446 template void SurfaceDerivatives(
00447 const float u, const float v,
00448 const int nu, const int pu, const Ptr< float >& U,
00449 const int nv, const int pv, const Ptr< float >& V,
00450 const Ptr< Ptr < hpoint<float> > >& Pw,
00451 const int d, Ptr< Ptr < point<float> > >& SKL );
00452 template void SurfaceDerivatives(
00453 const double u, const double v,
00454 const int nu, const int pu, const Ptr< double >& U,
00455 const int nv, const int pv, const Ptr< double >& V,
00456 const Ptr< Ptr < hpoint<double> > >& Pw,
00457 const int d, Ptr< Ptr < point<double> > >& SKL );
00458
00459 template void SurfaceDerivatives(
00460 const float u, const float v,
00461 const int nu, const int pu, const Ptr< float >& U,
00462 const int nv, const int pv, const Ptr< float >& V,
00463 const Ptr< Ptr < hpoint1<float> > >& Pw,
00464 const int d, Ptr< Ptr < point1<float> > >& SKL );
00465 template void SurfaceDerivatives(
00466 const double u, const double v,
00467 const int nu, const int pu, const Ptr< double >& U,
00468 const int nv, const int pv, const Ptr< double >& V,
00469 const Ptr< Ptr < hpoint1<double> > >& Pw,
00470 const int d, Ptr< Ptr < point1<double> > >& SKL );
00471
00472
00473
00474
00475
00476 template< class T, class HP >
00477 void CalcNormal_U0V0(
00478 const int nu, const int pu,
00479 const int nv, const int pv,
00480 const Ptr<Ptr<HP> >& Pw, point<T> *Normal )
00481 {
00482 int i,j,k,m;
00483 point<T> v1,v2,a,b;
00484
00485 set(a,(T)0);
00486 set(b,(T)0);
00487
00488 m = Max(pu,pv);
00489
00490 for( k=0; k<m; k++ )
00491 {
00492 i=0;
00493 j=k+1;
00494
00495 while( i <= k )
00496 {
00497 if( (i <= pv) && (j <= pu) )
00498 {
00499 v1 = euclid( Pw[i][j] );
00500 v2 = euclid( Pw[i][0] );
00501 a = v1 - v2;
00502 if( !rel_equal(v1,v2,rtr<T>::zero_tol()) )
00503 {
00504 k = m;
00505 break;
00506 }
00507 }
00508 i++;
00509 j--;
00510 }
00511 }
00512
00513 for( k=0; k<m; k++ )
00514 {
00515 i=0;
00516 j=k+1;
00517
00518 while( i <= k )
00519 {
00520 if( (j <= pv) && (i <= pu) )
00521 {
00522 v1 = euclid( Pw[j][i] );
00523 v2 = euclid( Pw[0][i] );
00524 b = v1 - v2;
00525 if( !rel_equal(v1,v2,rtr<T>::zero_tol()) )
00526 {
00527 k = m;
00528 break;
00529 }
00530 }
00531 i++;
00532 j--;
00533 }
00534 }
00535
00536 v1 = cross_product( a, b );
00537 normalize( Normal, v1 );
00538 }
00539
00540 template void CalcNormal_U0V0(
00541 const int nu, const int pu,
00542 const int nv, const int pv,
00543 const Ptr< Ptr< hpoint<float> > >& Pw, point<float> *Normal );
00544 template void CalcNormal_U0V0(
00545 const int nu, const int pu,
00546 const int nv, const int pv,
00547 const Ptr< Ptr< point<float> > >& Pw, point<float> *Normal );
00548
00549 template void CalcNormal_U0V0(
00550 const int nu, const int pu,
00551 const int nv, const int pv,
00552 const Ptr< Ptr< hpoint<double> > >& Pw, point<double> *Normal );
00553 template void CalcNormal_U0V0(
00554 const int nu, const int pu,
00555 const int nv, const int pv,
00556 const Ptr< Ptr< point<double> > >& Pw, point<double> *Normal );
00557
00558
00559
00560
00561 template< class T, class HP >
00562 void CalcNormal_U1V0(
00563 const int nu, const int pu,
00564 const int nv, const int pv,
00565 const Ptr< Ptr< HP > >& Pw, point<T> *Normal )
00566 {
00567 int i,j,k,m;
00568 point<T> v1,v2,a,b;
00569
00570 set(a,(T)0);
00571 set(b,(T)0);
00572
00573 m = Max(pu,pv);
00574
00575 for( k=0; k<m; k++ )
00576 {
00577 i=0;
00578 j=k+1;
00579
00580 while( i <= k )
00581 {
00582 if( (i <= pv) && (j <= pu) )
00583 {
00584 v1 = euclid( Pw[i][nu] );
00585 v2 = euclid( Pw[i][nu-j] );
00586 a = v1 - v2;
00587 if( !rel_equal(v1,v2,rtr<T>::zero_tol()) )
00588 {
00589 k = m;
00590 break;
00591 }
00592 }
00593 i++;
00594 j--;
00595 }
00596 }
00597
00598 for( k=0; k<m; k++ )
00599 {
00600 i=0;
00601 j=k+1;
00602
00603 while( i <= k )
00604 {
00605 if( (j <= pv) && (i <= pu) )
00606 {
00607 v1 = euclid( Pw[j][nu-i] );
00608 v2 = euclid( Pw[0][nu-i] );
00609 b = v1 - v2;
00610 if( !rel_equal(v1,v2,rtr<T>::zero_tol()) )
00611 {
00612 k = m;
00613 break;
00614 }
00615 }
00616 i++;
00617 j--;
00618 }
00619 }
00620
00621 v1 = cross_product( a, b );
00622 normalize( Normal, v1 );
00623 }
00624
00625 template void CalcNormal_U1V0(
00626 const int nu, const int pu,
00627 const int nv, const int pv,
00628 const Ptr< Ptr< hpoint<float> > >& Pw, point<float> *Normal );
00629 template void CalcNormal_U1V0(
00630 const int nu, const int pu,
00631 const int nv, const int pv,
00632 const Ptr< Ptr< point<float> > >& Pw, point<float> *Normal );
00633
00634 template void CalcNormal_U1V0(
00635 const int nu, const int pu,
00636 const int nv, const int pv,
00637 const Ptr< Ptr< hpoint<double> > >& Pw, point<double> *Normal );
00638 template void CalcNormal_U1V0(
00639 const int nu, const int pu,
00640 const int nv, const int pv,
00641 const Ptr< Ptr< point<double> > >& Pw, point<double> *Normal );
00642
00643
00644
00645
00646
00647 template< class T, class HP >
00648 void CalcNormal_U0V1(
00649 const int nu, const int pu,
00650 const int nv, const int pv,
00651 const Ptr< Ptr< HP > >& Pw, point<T> *Normal )
00652 {
00653 int i,j,k,m;
00654 point<T> v1,v2,a,b;
00655
00656 set(a,(T)0);
00657 set(b,(T)0);
00658
00659 m = Max(pu,pv);
00660
00661 for( k=0; k<m; k++ )
00662 {
00663 i=0;
00664 j=k+1;
00665
00666 while( i <= k )
00667 {
00668 if( (i <= pv) && (j <= pu) )
00669 {
00670 v1 = euclid( Pw[nv-i][j] );
00671 v2 = euclid( Pw[nv-i][0] );
00672 a = v1 - v2;
00673 if( !rel_equal(v1,v2,rtr<T>::zero_tol()) )
00674 {
00675 k = m;
00676 break;
00677 }
00678 }
00679 i++;
00680 j--;
00681 }
00682 }
00683
00684 for( k=0; k<m; k++ )
00685 {
00686 i=0;
00687 j=k+1;
00688
00689 while( i <= k )
00690 {
00691 if( (j <= pv) && (i <= pu) )
00692 {
00693 v1 = euclid( Pw[nv][i] );
00694 v2 = euclid( Pw[nv-j][i] );
00695 b = v1 - v2;
00696 if( !rel_equal(v1,v2,rtr<T>::zero_tol()) )
00697 {
00698 k = m;
00699 break;
00700 }
00701 }
00702 i++;
00703 j--;
00704 }
00705 }
00706
00707 v1 = cross_product( a, b );
00708 normalize( Normal, v1 );
00709 }
00710
00711 template void CalcNormal_U0V1(
00712 const int nu, const int pu,
00713 const int nv, const int pv,
00714 const Ptr< Ptr< hpoint<float> > >& Pw, point<float> *Normal );
00715 template void CalcNormal_U0V1(
00716 const int nu, const int pu,
00717 const int nv, const int pv,
00718 const Ptr< Ptr< point<float> > >& Pw, point<float> *Normal );
00719
00720 template void CalcNormal_U0V1(
00721 const int nu, const int pu,
00722 const int nv, const int pv,
00723 const Ptr< Ptr< hpoint<double> > >& Pw, point<double> *Normal );
00724 template void CalcNormal_U0V1(
00725 const int nu, const int pu,
00726 const int nv, const int pv,
00727 const Ptr< Ptr< point<double> > >& Pw, point<double> *Normal );
00728
00729
00730
00731
00732
00733 template< class T, class HP >
00734 void CalcNormal_U1V1(
00735 const int nu, const int pu,
00736 const int nv, const int pv,
00737 const Ptr< Ptr< HP > >& Pw, point<T> *Normal )
00738 {
00739 int i,j,k,m;
00740 point<T> v1,v2,a,b;
00741
00742 set(a,(T)0);
00743 set(b,(T)0);
00744
00745 m = Max(pu,pv);
00746
00747 for( k=0; k<m; k++ )
00748 {
00749 i=0;
00750 j=k+1;
00751
00752 while( i <= k )
00753 {
00754 if( (i <= pv) && (j <= pu) )
00755 {
00756 v1 = euclid( Pw[nv-i][nu] );
00757 v2 = euclid( Pw[nv-i][nu-j] );
00758 a = v1 - v2;
00759 if( !rel_equal(v1,v2,rtr<T>::zero_tol()) )
00760 {
00761 k = m;
00762 break;
00763 }
00764 }
00765 i++;
00766 j--;
00767 }
00768 }
00769
00770 for( k=0; k<m; k++ )
00771 {
00772 i=0;
00773 j=k+1;
00774
00775 while( i <= k )
00776 {
00777 if( (j <= pv) && (i <= pu) )
00778 {
00779 v1 = euclid( Pw[nv][nu-i] );
00780 v2 = euclid( Pw[nv-j][nu-i] );
00781 b = v1 - v2;
00782 if( !rel_equal(v1,v2,rtr<T>::zero_tol()) )
00783 {
00784 k = m;
00785 break;
00786 }
00787 }
00788 i++;
00789 j--;
00790 }
00791 }
00792
00793 v1 = cross_product( a, b );
00794 normalize( Normal, v1 );
00795 }
00796
00797 template void CalcNormal_U1V1(
00798 const int nu, const int pu,
00799 const int nv, const int pv,
00800 const Ptr< Ptr< hpoint<float> > >& Pw, point<float> *Normal );
00801 template void CalcNormal_U1V1(
00802 const int nu, const int pu,
00803 const int nv, const int pv,
00804 const Ptr< Ptr< point<float> > >& Pw, point<float> *Normal );
00805
00806 template void CalcNormal_U1V1(
00807 const int nu, const int pu,
00808 const int nv, const int pv,
00809 const Ptr< Ptr< hpoint<double> > >& Pw, point<double> *Normal );
00810 template void CalcNormal_U1V1(
00811 const int nu, const int pu,
00812 const int nv, const int pv,
00813 const Ptr< Ptr< point<double> > >& Pw, point<double> *Normal );
00814
00815 }
00816
00817
00818
00819
00820
00821
00822
00823
00824
00825
00826
00827
00828