00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #ifndef __VCGLIB_PLATONIC
00025 #define __VCGLIB_PLATONIC
00026
00027 #include<vcg/math/base.h>
00028 #include<vcg/complex/trimesh/allocate.h>
00029 #include<vcg/complex/trimesh/refine.h>
00030 #include<vcg/complex/trimesh/update/flag.h>
00031
00032 namespace vcg {
00033 namespace tri {
00044 template <class TetraMeshType>
00045 void Tetrahedron(TetraMeshType &in)
00046 {
00047 typedef TetraMeshType MeshType;
00048 typedef typename TetraMeshType::CoordType CoordType;
00049 typedef typename TetraMeshType::VertexPointer VertexPointer;
00050 typedef typename TetraMeshType::VertexIterator VertexIterator;
00051 typedef typename TetraMeshType::FaceIterator FaceIterator;
00052
00053 in.Clear();
00054 Allocator<TetraMeshType>::AddVertices(in,4);
00055 Allocator<TetraMeshType>::AddFaces(in,4);
00056
00057 VertexPointer ivp[4];
00058 VertexIterator vi=in.vert.begin();
00059 ivp[0]=&*vi;(*vi).P()=CoordType ( 1.0, 1.0, 1.0); ++vi;
00060 ivp[1]=&*vi;(*vi).P()=CoordType (-1.0, 1.0,-1.0); ++vi;
00061 ivp[2]=&*vi;(*vi).P()=CoordType (-1.0,-1.0, 1.0); ++vi;
00062 ivp[3]=&*vi;(*vi).P()=CoordType ( 1.0,-1.0,-1.0);
00063
00064 FaceIterator fi=in.face.begin();
00065 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[1]; (*fi).V(2)=ivp[2]; ++fi;
00066 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[2]; (*fi).V(2)=ivp[3]; ++fi;
00067 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[3]; (*fi).V(2)=ivp[1]; ++fi;
00068 (*fi).V(0)=ivp[3]; (*fi).V(1)=ivp[2]; (*fi).V(2)=ivp[1];
00069 }
00070
00071
00074 template <class DodMeshType>
00075 void Dodecahedron(DodMeshType & in)
00076 {
00077 typedef DodMeshType MeshType;
00078 typedef typename MeshType::CoordType CoordType;
00079 typedef typename MeshType::VertexPointer VertexPointer;
00080 typedef typename MeshType::VertexIterator VertexIterator;
00081 typedef typename MeshType::FaceIterator FaceIterator;
00082 typedef typename MeshType::ScalarType ScalarType;
00083 const int N_penta=12;
00084 const int N_points=62;
00085
00086 int penta[N_penta*3*3]=
00087 {20,11, 18, 18, 11, 8, 8, 11, 4,
00088 13,23, 4, 4, 23, 8, 8, 23, 16,
00089 13, 4, 30, 30, 4, 28, 28, 4, 11,
00090 16,34, 8, 8, 34, 18, 18, 34, 36,
00091 11,20, 28, 28, 20, 45, 45, 20, 38,
00092 13,30, 23, 23, 30, 41, 41, 30, 47,
00093 16,23, 34, 34, 23, 50, 50, 23, 41,
00094 20,18, 38, 38, 18, 52, 52, 18, 36,
00095 30,28, 47, 47, 28, 56, 56, 28, 45,
00096 50,60, 34, 34, 60, 36, 36, 60, 52,
00097 45,38, 56, 56, 38, 60, 60, 38, 52,
00098 50,41, 60, 60, 41, 56, 56, 41, 47 };
00099
00100 const ScalarType p=(1.0 + math::Sqrt(5.0)) / 2.0;
00101 const ScalarType p2=p*p;
00102 const ScalarType p3=p*p*p;
00103 ScalarType vv[N_points*3]=
00104 {
00105 0, 0, 2*p2, p2, 0, p3, p, p2, p3,
00106 0, p, p3, -p, p2, p3, -p2, 0, p3,
00107 -p, -p2, p3, 0, -p, p3, p, -p2, p3,
00108 p3, p, p2, p2, p2, p2, 0, p3, p2,
00109 -p2, p2, p2, -p3, p, p2, -p3, -p, p2,
00110 -p2, -p2, p2, 0, -p3, p2, p2, -p2, p2,
00111 p3, -p, p2, p3, 0, p, p2, p3, p,
00112 -p2, p3, p, -p3, 0, p, -p2, -p3, p,
00113 p2, -p3, p, 2*p2, 0, 0, p3, p2, 0,
00114 p, p3, 0, 0, 2*p2, 0, -p, p3, 0,
00115 -p3, p2, 0, -2*p2, 0, 0, -p3, -p2, 0,
00116 -p, -p3, 0, 0, -2*p2, 0, p, -p3, 0,
00117 p3, -p2, 0, p3, 0, -p, p2, p3, -p,
00118 -p2, p3, -p, -p3, 0, -p, -p2, -p3, -p,
00119 p2, -p3, -p, p3, p, -p2, p2, p2, -p2,
00120 0, p3, -p2, -p2, p2, -p2, -p3, p, -p2,
00121 -p3, -p, -p2, -p2, -p2, -p2, 0, -p3, -p2,
00122 p2, -p2, -p2, p3, -p, -p2, p2, 0, -p3,
00123 p, p2, -p3, 0, p, -p3, -p, p2, -p3,
00124 -p2, 0, -p3, -p, -p2, -p3, 0, -p, -p3,
00125 p, -p2, -p3, 0, 0, -2*p2
00126 };
00127 in.Clear();
00128
00129 Allocator<DodMeshType>::AddVertices(in,20+12);
00130 Allocator<DodMeshType>::AddFaces(in, 5*12);
00131
00132 int h,i,j,m=0;
00133
00134 bool used[N_points];
00135 for (i=0; i<N_points; i++) used[i]=false;
00136
00137 int reindex[20+12 *10];
00138 ScalarType xx,yy,zz, sx,sy,sz;
00139
00140 int order[5]={0,1,8,6,2};
00141 int added[12];
00142
00143 VertexIterator vi=in.vert.begin();
00144
00145 for (i=0; i<12; i++) {
00146 sx=sy=sz=0;
00147 for (int j=0; j<5; j++) {
00148 h= penta[ i*9 + order[j] ]-1;
00149 xx=vv[h*3];yy=vv[h*3+1];zz=vv[h*3+2]; sx+=xx; sy+=yy; sz+=zz;
00150 if (!used[h]) {
00151 (*vi).P()=CoordType( xx, yy, zz ); vi++;
00152 used[h]=true;
00153 reindex[ h ] = m++;
00154 }
00155 }
00156 (*vi).P()=CoordType( sx/5.0, sy/5.0, sz/5.0 ); vi++;
00157 added[ i ] = m++;
00158 }
00159
00160 std::vector<VertexPointer> index(in.vn);
00161
00162 for(j=0,vi=in.vert.begin();j<in.vn;++j,++vi) index[j] = &(*vi);
00163
00164 FaceIterator fi=in.face.begin();
00165
00166 for (i=0; i<12; i++) {
00167 for (j=0; j<5; j++){
00168 (*fi).V(0)=index[added[i] ];
00169 (*fi).V(1)=index[reindex[penta[i*9 + order[j ] ] -1 ] ];
00170 (*fi).V(2)=index[reindex[penta[i*9 + order[(j+1)%5] ] -1 ] ];
00171 if (in.HasPerFaceFlags()) {
00172
00173 (*fi).SetF(0);
00174 (*fi).SetF(2);
00175 }
00176 fi++;
00177 }
00178 }
00179 }
00180
00181 template <class OctMeshType>
00182 void Octahedron(OctMeshType &in)
00183 {
00184 typedef OctMeshType MeshType;
00185 typedef typename MeshType::CoordType CoordType;
00186 typedef typename MeshType::VertexPointer VertexPointer;
00187 typedef typename MeshType::VertexIterator VertexIterator;
00188 typedef typename MeshType::FaceIterator FaceIterator;
00189
00190 in.Clear();
00191 Allocator<OctMeshType>::AddVertices(in,6);
00192 Allocator<OctMeshType>::AddFaces(in,8);
00193
00194 VertexPointer ivp[6];
00195
00196 VertexIterator vi=in.vert.begin();
00197 ivp[0]=&*vi;(*vi).P()=CoordType ( 1, 0, 0); ++vi;
00198 ivp[1]=&*vi;(*vi).P()=CoordType ( 0, 1, 0); ++vi;
00199 ivp[2]=&*vi;(*vi).P()=CoordType ( 0, 0, 1); ++vi;
00200 ivp[3]=&*vi;(*vi).P()=CoordType (-1, 0, 0); ++vi;
00201 ivp[4]=&*vi;(*vi).P()=CoordType ( 0,-1, 0); ++vi;
00202 ivp[5]=&*vi;(*vi).P()=CoordType ( 0, 0,-1);
00203
00204 FaceIterator fi=in.face.begin();
00205 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[1]; (*fi).V(2)=ivp[2]; ++fi;
00206 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[2]; (*fi).V(2)=ivp[4]; ++fi;
00207 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[4]; (*fi).V(2)=ivp[5]; ++fi;
00208 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[5]; (*fi).V(2)=ivp[1]; ++fi;
00209 (*fi).V(0)=ivp[3]; (*fi).V(1)=ivp[1]; (*fi).V(2)=ivp[5]; ++fi;
00210 (*fi).V(0)=ivp[3]; (*fi).V(1)=ivp[5]; (*fi).V(2)=ivp[4]; ++fi;
00211 (*fi).V(0)=ivp[3]; (*fi).V(1)=ivp[4]; (*fi).V(2)=ivp[2]; ++fi;
00212 (*fi).V(0)=ivp[3]; (*fi).V(1)=ivp[2]; (*fi).V(2)=ivp[1];
00213 }
00214
00215 template <class IcoMeshType>
00216 void Icosahedron(IcoMeshType &in)
00217 {
00218 typedef IcoMeshType MeshType;
00219 typedef typename MeshType::ScalarType ScalarType;
00220 typedef typename MeshType::CoordType CoordType;
00221 typedef typename MeshType::VertexPointer VertexPointer;
00222 typedef typename MeshType::VertexIterator VertexIterator;
00223 typedef typename MeshType::FaceIterator FaceIterator;
00224
00225 ScalarType L=ScalarType((math::Sqrt(5.0)+1.0)/2.0);
00226 CoordType vv[12]={
00227 CoordType ( 0, L, 1),
00228 CoordType ( 0, L,-1),
00229 CoordType ( 0,-L, 1),
00230 CoordType ( 0,-L,-1),
00231
00232 CoordType ( L, 1, 0),
00233 CoordType ( L,-1, 0),
00234 CoordType (-L, 1, 0),
00235 CoordType (-L,-1, 0),
00236
00237 CoordType ( 1, 0, L),
00238 CoordType (-1, 0, L),
00239 CoordType ( 1, 0,-L),
00240 CoordType (-1, 0,-L)
00241 };
00242
00243 int ff[20][3]={
00244 {1,0,4},{0,1,6},{2,3,5},{3,2,7},
00245 {4,5,10},{5,4,8},{6,7,9},{7,6,11},
00246 {8,9,2},{9,8,0},{10,11,1},{11,10,3},
00247 {0,8,4},{0,6,9},{1,4,10},{1,11,6},
00248 {2,5,8},{2,9,7},{3,10,5},{3,7,11}
00249 };
00250
00251
00252 in.Clear();
00253 Allocator<IcoMeshType>::AddVertices(in,12);
00254 Allocator<IcoMeshType>::AddFaces(in,20);
00255 VertexPointer ivp[12];
00256
00257 VertexIterator vi;
00258 int i;
00259 for(i=0,vi=in.vert.begin();vi!=in.vert.end();++i,++vi){
00260 (*vi).P()=vv[i];
00261 ivp[i]=&*vi;
00262 }
00263
00264 FaceIterator fi;
00265 for(i=0,fi=in.face.begin();fi!=in.face.end();++i,++fi){
00266 (*fi).V(0)=ivp[ff[i][0]];
00267 (*fi).V(1)=ivp[ff[i][1]];
00268 (*fi).V(2)=ivp[ff[i][2]];
00269 }
00270 }
00271
00272 template <class MeshType>
00273 void Hexahedron(MeshType &in)
00274 {
00275 typedef typename MeshType::ScalarType ScalarType;
00276 typedef typename MeshType::CoordType CoordType;
00277 typedef typename MeshType::VertexPointer VertexPointer;
00278 typedef typename MeshType::VertexIterator VertexIterator;
00279 typedef typename MeshType::FaceIterator FaceIterator;
00280
00281 in.Clear();
00282 Allocator<MeshType>::AddVertices(in,8);
00283 Allocator<MeshType>::AddFaces(in,12);
00284
00285 VertexPointer ivp[8];
00286
00287 VertexIterator vi=in.vert.begin();
00288
00289 ivp[7]=&*vi;(*vi).P()=CoordType (-1,-1,-1); ++vi;
00290 ivp[6]=&*vi;(*vi).P()=CoordType ( 1,-1,-1); ++vi;
00291 ivp[5]=&*vi;(*vi).P()=CoordType (-1, 1,-1); ++vi;
00292 ivp[4]=&*vi;(*vi).P()=CoordType ( 1, 1,-1); ++vi;
00293 ivp[3]=&*vi;(*vi).P()=CoordType (-1,-1, 1); ++vi;
00294 ivp[2]=&*vi;(*vi).P()=CoordType ( 1,-1, 1); ++vi;
00295 ivp[1]=&*vi;(*vi).P()=CoordType (-1, 1, 1); ++vi;
00296 ivp[0]=&*vi;(*vi).P()=CoordType ( 1, 1, 1);
00297
00298 FaceIterator fi=in.face.begin();
00299 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[1]; (*fi).V(2)=ivp[2]; ++fi;
00300 (*fi).V(0)=ivp[3]; (*fi).V(1)=ivp[2]; (*fi).V(2)=ivp[1]; ++fi;
00301 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[2]; (*fi).V(2)=ivp[4]; ++fi;
00302 (*fi).V(0)=ivp[6]; (*fi).V(1)=ivp[4]; (*fi).V(2)=ivp[2]; ++fi;
00303 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[4]; (*fi).V(2)=ivp[1]; ++fi;
00304 (*fi).V(0)=ivp[5]; (*fi).V(1)=ivp[1]; (*fi).V(2)=ivp[4]; ++fi;
00305 (*fi).V(0)=ivp[7]; (*fi).V(1)=ivp[5]; (*fi).V(2)=ivp[6]; ++fi;
00306 (*fi).V(0)=ivp[4]; (*fi).V(1)=ivp[6]; (*fi).V(2)=ivp[5]; ++fi;
00307 (*fi).V(0)=ivp[7]; (*fi).V(1)=ivp[6]; (*fi).V(2)=ivp[3]; ++fi;
00308 (*fi).V(0)=ivp[2]; (*fi).V(1)=ivp[3]; (*fi).V(2)=ivp[6]; ++fi;
00309 (*fi).V(0)=ivp[7]; (*fi).V(1)=ivp[3]; (*fi).V(2)=ivp[5]; ++fi;
00310 (*fi).V(0)=ivp[1]; (*fi).V(1)=ivp[5]; (*fi).V(2)=ivp[3];
00311
00312 if (in.HasPerFaceFlags()) {
00313 FaceIterator fi=in.face.begin();
00314 for (int k=0; k<12; k++) {
00315 (*fi).SetF(1); fi++;
00316 }
00317 }
00318
00319 }
00320
00321 template <class MeshType>
00322 void Square(MeshType &in)
00323 {
00324 typedef typename MeshType::ScalarType ScalarType;
00325 typedef typename MeshType::CoordType CoordType;
00326 typedef typename MeshType::VertexPointer VertexPointer;
00327 typedef typename MeshType::VertexIterator VertexIterator;
00328 typedef typename MeshType::FaceIterator FaceIterator;
00329
00330 in.Clear();
00331 Allocator<MeshType>::AddVertices(in,4);
00332 Allocator<MeshType>::AddFaces(in,2);
00333
00334 VertexPointer ivp[4];
00335
00336 VertexIterator vi=in.vert.begin();
00337 ivp[0]=&*vi;(*vi).P()=CoordType ( 1, 0, 0); ++vi;
00338 ivp[1]=&*vi;(*vi).P()=CoordType ( 0, 1, 0); ++vi;
00339 ivp[2]=&*vi;(*vi).P()=CoordType (-1, 0, 0); ++vi;
00340 ivp[3]=&*vi;(*vi).P()=CoordType ( 0,-1, 0);
00341
00342 FaceIterator fi=in.face.begin();
00343 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[1]; (*fi).V(2)=ivp[2]; ++fi;
00344 (*fi).V(0)=ivp[2]; (*fi).V(1)=ivp[3]; (*fi).V(2)=ivp[0];
00345
00346 if (in.HasPerFaceFlags()) {
00347 FaceIterator fi=in.face.begin();
00348 for (int k=0; k<2; k++) {
00349 (*fi).SetF(2); fi++;
00350 }
00351 }
00352 }
00353
00354
00355
00356
00357 template <class MeshType>
00358 void Sphere(MeshType &in, const int subdiv = 3 )
00359 {
00360 typedef typename MeshType::ScalarType ScalarType;
00361 typedef typename MeshType::CoordType CoordType;
00362 typedef typename MeshType::VertexPointer VertexPointer;
00363 typedef typename MeshType::VertexIterator VertexIterator;
00364 typedef typename MeshType::FaceIterator FaceIterator;
00365 if(in.vn==0 && in.fn==0) Icosahedron(in);
00366
00367 VertexIterator vi;
00368 for(vi = in.vert.begin(); vi!=in.vert.end();++vi)
00369 vi->P().Normalize();
00370
00371 tri::UpdateFlags<MeshType>::FaceBorderFromNone(in);
00372 tri::UpdateTopology<MeshType>::FaceFace(in);
00373
00374 size_t lastsize = 0;
00375 for(int i = 0 ; i < subdiv; ++i)
00376 {
00377 Refine< MeshType, MidPoint<MeshType> >(in, MidPoint<MeshType>(&in), 0);
00378
00379 for(vi = in.vert.begin() + lastsize; vi != in.vert.end(); ++vi)
00380 vi->P().Normalize();
00381
00382 lastsize = in.vert.size();
00383 }
00384 }
00385
00386
00388 template <class MeshType>
00389 void Cone( MeshType& in,
00390 const typename MeshType::ScalarType r1,
00391 const typename MeshType::ScalarType r2,
00392 const typename MeshType::ScalarType h,
00393 const int SubDiv = 36 )
00394 {
00395 typedef typename MeshType::ScalarType ScalarType;
00396 typedef typename MeshType::CoordType CoordType;
00397 typedef typename MeshType::VertexPointer VertexPointer;
00398 typedef typename MeshType::VertexIterator VertexIterator;
00399 typedef typename MeshType::FaceIterator FaceIterator;
00400
00401 int i,b1,b2;
00402 in.Clear();
00403 int VN,FN;
00404 if(r1==0 || r2==0) {
00405 VN=SubDiv+2;
00406 FN=SubDiv*2;
00407 } else {
00408 VN=SubDiv*2+2;
00409 FN=SubDiv*4;
00410 }
00411
00412 Allocator<MeshType>::AddVertices(in,VN);
00413 Allocator<MeshType>::AddFaces(in,FN);
00414 VertexPointer *ivp = new VertexPointer[VN];
00415
00416 VertexIterator vi=in.vert.begin();
00417 ivp[0]=&*vi;(*vi).P()=CoordType ( 0,-h/2.0,0 ); ++vi;
00418 ivp[1]=&*vi;(*vi).P()=CoordType ( 0, h/2.0,0 ); ++vi;
00419
00420 b1 = b2 = 2;
00421 int cnt=2;
00422 if(r1!=0)
00423 {
00424 for(i=0;i<SubDiv;++i)
00425 {
00426 double a = math::ToRad(i*360.0/SubDiv);
00427 ivp[cnt]=&*vi; (*vi).P()= CoordType(r1*cos(a), -h/2.0, r1*sin(a)); ++vi;++cnt;
00428 }
00429 b2 += SubDiv;
00430 }
00431
00432 if(r2!=0)
00433 {
00434 for(i=0;i<SubDiv;++i)
00435 {
00436 double a = math::ToRad(i*360.0/SubDiv);
00437 ivp[cnt]=&*vi; (*vi).P()= CoordType( r2*cos(a), h/2.0, r2*sin(a)); ++vi;++cnt;
00438 }
00439 }
00440
00441 FaceIterator fi=in.face.begin();
00442
00443 if(r1!=0) for(i=0;i<SubDiv;++i,++fi) {
00444 (*fi).V(0)=ivp[0];
00445 (*fi).V(1)=ivp[b1+i];
00446 (*fi).V(2)=ivp[b1+(i+1)%SubDiv];
00447 }
00448
00449 if(r2!=0) for(i=0;i<SubDiv;++i,++fi) {
00450 (*fi).V(0)=ivp[1];
00451 (*fi).V(2)=ivp[b2+i];
00452 (*fi).V(1)=ivp[b2+(i+1)%SubDiv];
00453 }
00454
00455 if(r1==0) for(i=0;i<SubDiv;++i,++fi)
00456 {
00457 (*fi).V(0)=ivp[0];
00458 (*fi).V(1)=ivp[b2+i];
00459 (*fi).V(2)=ivp[b2+(i+1)%SubDiv];
00460 }
00461 if(r2==0) for(i=0;i<SubDiv;++i,++fi){
00462 (*fi).V(0)=ivp[1];
00463 (*fi).V(2)=ivp[b1+i];
00464 (*fi).V(1)=ivp[b1+(i+1)%SubDiv];
00465 }
00466
00467 if(r1!=0 && r2!=0)for(i=0;i<SubDiv;++i)
00468 {
00469 (*fi).V(0)=ivp[b1+i];
00470 (*fi).V(1)=ivp[b2+i];
00471 (*fi).V(2)=ivp[b2+(i+1)%SubDiv];
00472 ++fi;
00473 (*fi).V(0)=ivp[b1+i];
00474 (*fi).V(1)=ivp[b2+(i+1)%SubDiv];
00475 (*fi).V(2)=ivp[b1+(i+1)%SubDiv];
00476 ++fi;
00477 }
00478 }
00479
00480
00481 template <class MeshType >
00482 void Box(MeshType &in, const typename MeshType::BoxType & bb )
00483 {
00484 typedef typename MeshType::ScalarType ScalarType;
00485 typedef typename MeshType::CoordType CoordType;
00486 typedef typename MeshType::VertexPointer VertexPointer;
00487 typedef typename MeshType::VertexIterator VertexIterator;
00488 typedef typename MeshType::FaceIterator FaceIterator;
00489
00490 in.Clear();
00491 Allocator<MeshType>::AddVertices(in,8);
00492 Allocator<MeshType>::AddFaces(in,12);
00493
00494 VertexPointer ivp[8];
00495
00496 VertexIterator vi=in.vert.begin();
00497 ivp[0]=&*vi;(*vi).P()=CoordType (bb.min[0],bb.min[1],bb.min[2]); ++vi;
00498 ivp[1]=&*vi;(*vi).P()=CoordType (bb.max[0],bb.min[1],bb.min[2]); ++vi;
00499 ivp[2]=&*vi;(*vi).P()=CoordType (bb.min[0],bb.max[1],bb.min[2]); ++vi;
00500 ivp[3]=&*vi;(*vi).P()=CoordType (bb.max[0],bb.max[1],bb.min[2]); ++vi;
00501 ivp[4]=&*vi;(*vi).P()=CoordType (bb.min[0],bb.min[1],bb.max[2]); ++vi;
00502 ivp[5]=&*vi;(*vi).P()=CoordType (bb.max[0],bb.min[1],bb.max[2]); ++vi;
00503 ivp[6]=&*vi;(*vi).P()=CoordType (bb.min[0],bb.max[1],bb.max[2]); ++vi;
00504 ivp[7]=&*vi;(*vi).P()=CoordType (bb.max[0],bb.max[1],bb.max[2]);
00505
00506 FaceIterator fi=in.face.begin();
00507 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[1]; (*fi).V(2)=ivp[2]; ++fi;
00508 (*fi).V(0)=ivp[3]; (*fi).V(1)=ivp[2]; (*fi).V(2)=ivp[1]; ++fi;
00509 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[2]; (*fi).V(2)=ivp[4]; ++fi;
00510 (*fi).V(0)=ivp[6]; (*fi).V(1)=ivp[4]; (*fi).V(2)=ivp[2]; ++fi;
00511 (*fi).V(0)=ivp[0]; (*fi).V(1)=ivp[4]; (*fi).V(2)=ivp[1]; ++fi;
00512 (*fi).V(0)=ivp[5]; (*fi).V(1)=ivp[1]; (*fi).V(2)=ivp[4]; ++fi;
00513 (*fi).V(0)=ivp[7]; (*fi).V(1)=ivp[5]; (*fi).V(2)=ivp[6]; ++fi;
00514 (*fi).V(0)=ivp[4]; (*fi).V(1)=ivp[6]; (*fi).V(2)=ivp[5]; ++fi;
00515 (*fi).V(0)=ivp[7]; (*fi).V(1)=ivp[6]; (*fi).V(2)=ivp[3]; ++fi;
00516 (*fi).V(0)=ivp[2]; (*fi).V(1)=ivp[3]; (*fi).V(2)=ivp[6]; ++fi;
00517 (*fi).V(0)=ivp[7]; (*fi).V(1)=ivp[3]; (*fi).V(2)=ivp[5]; ++fi;
00518 (*fi).V(0)=ivp[1]; (*fi).V(1)=ivp[5]; (*fi).V(2)=ivp[3];
00519
00520 if (in.HasPerFaceFlags()) {
00521 FaceIterator fi=in.face.begin();
00522 for (int k=0; k<12; k++) {
00523 (*fi).SetF(1); fi++;
00524 }
00525 }
00526
00527 }
00528
00529
00530
00531
00532
00533
00534 template <class MeshType,class V, class F >
00535 void Build( MeshType & in, const V & v, const F & f)
00536 {
00537 typedef typename MeshType::ScalarType ScalarType;
00538 typedef typename MeshType::CoordType CoordType;
00539 typedef typename MeshType::VertexPointer VertexPointer;
00540 typedef typename MeshType::VertexIterator VertexIterator;
00541 typedef typename MeshType::FaceIterator FaceIterator;
00542
00543 Allocator<MeshType>::AddVertices(in,v.size());
00544 Allocator<MeshType>::AddFaces(in,f.size());
00545
00546 typename V::const_iterator vi;
00547
00548 typename MeshType::VertexType tv;
00549
00550 for(int i=0;i<v.size();++i)
00551 {
00552 float *vv=(float *)(&v[i]);
00553 in.vert[i].P() = CoordType( vv[0],vv[1],vv[2]);
00554 }
00555
00556 std::vector<VertexPointer> index(in.vn);
00557 VertexIterator j;
00558 int k;
00559 for(k=0,j=in.vert.begin();j!=in.vert.end();++j,++k)
00560 index[k] = &*j;
00561
00562 typename F::const_iterator fi;
00563
00564 typename MeshType::FaceType ft;
00565
00566 for(int i=0;i<f.size();++i)
00567 {
00568 int * ff=(int *)(&f[i]);
00569 assert( ff[0]>=0 );
00570 assert( ff[1]>=0 );
00571 assert( ff[2]>=0 );
00572 assert( ff[0]<in.vn );
00573 assert( ff[1]<in.vn );
00574 assert( ff[2]<in.vn );
00575 in.face[i].V(0) = &in.vert[ ff[0] ];
00576 in.face[i].V(1) = &in.vert[ ff[0] ];
00577 in.face[i].V(2) = &in.vert[ ff[0] ];
00578
00579 }
00580 }
00581
00582
00583
00584
00585
00586
00587 template <class MeshType>
00588 void Grid(MeshType & in, int w, int h, float wl, float hl, float *data)
00589 {
00590 typedef typename MeshType::CoordType CoordType;
00591 typedef typename MeshType::VertexPointer VertexPointer;
00592 typedef typename MeshType::VertexIterator VertexIterator;
00593 typedef typename MeshType::FaceIterator FaceIterator;
00594
00595 in.Clear();
00596 Allocator<MeshType>::AddVertices(in,w*h);
00597
00598
00599 float wld=wl/float(w);
00600 float hld=hl/float(h);
00601
00602 for(int i=0;i<h;++i)
00603 for(int j=0;j<w;++j)
00604 in.vert[i*w+j].P()=CoordType ( j*wld, i*hld, data[i*w+j]);
00605 FaceGrid(in,w,h);
00606 }
00607
00608
00609
00610
00611
00612 template <class MeshType>
00613 void FaceGrid(MeshType & in, int w, int h)
00614 {
00615 assert(in.vn == (int)in.vert.size());
00616 assert(in.vn >= w*h);
00617
00618 Allocator<MeshType>::AddFaces(in,(w-1)*(h-1)*2);
00619
00620
00621
00622
00623
00624
00625
00626
00627 for(int i=0;i<h-1;++i)
00628 for(int j=0;j<w-1;++j)
00629 {
00630 in.face[2*(i*(w-1)+j)+0].V(0) = &(in.vert[(i+1)*w+j+1]);
00631 in.face[2*(i*(w-1)+j)+0].V(1) = &(in.vert[(i+0)*w+j+1]);
00632 in.face[2*(i*(w-1)+j)+0].V(2) = &(in.vert[(i+0)*w+j+0]);
00633
00634 in.face[2*(i*(w-1)+j)+1].V(0) = &(in.vert[(i+0)*w+j+0]);
00635 in.face[2*(i*(w-1)+j)+1].V(1) = &(in.vert[(i+1)*w+j+0]);
00636 in.face[2*(i*(w-1)+j)+1].V(2) = &(in.vert[(i+1)*w+j+1]);
00637 }
00638
00639 if (in.HasPerFaceFlags()) {
00640 for (int k=0; k<(h-1)*(w-1)*2; k++) {
00641 in.face[k].SetF(2);
00642 }
00643 }
00644
00645 }
00646
00647
00648
00649
00650
00651
00652 template <class MeshType>
00653 void FaceGrid(MeshType & in, const std::vector<int> &grid, int w, int h)
00654 {
00655 assert(in.vn == (int)in.vert.size());
00656 assert(in.vn <= w*h);
00657
00658
00659
00660
00661
00662
00663
00664
00665
00666
00667
00668 for(int i=0;i<h-1;++i)
00669 for(int j=0;j<w-1;++j)
00670 {
00671 int V0i= grid[(i+0)*w+j+0];
00672 int V1i= grid[(i+0)*w+j+1];
00673 int V2i= grid[(i+1)*w+j+0];
00674 int V3i= grid[(i+1)*w+j+1];
00675
00676 int ndone=0;
00677 bool quad = (V0i>=0 && V1i>=0 && V2i>=0 && V3i>=0 ) && in.HasPerFaceFlags();
00678
00679 if(V0i>=0 && V2i>=0 && V3i>=0 )
00680 {
00681 typename MeshType::FaceIterator f= Allocator<MeshType>::AddFaces(in,1);
00682 f->V(0)=&(in.vert[V3i]);
00683 f->V(1)=&(in.vert[V2i]);
00684 f->V(2)=&(in.vert[V0i]);
00685 if (quad) f->SetF(2);
00686 ndone++;
00687 }
00688 if(V0i>=0 && V1i>=0 && V3i>=0 )
00689 {
00690 typename MeshType::FaceIterator f= Allocator<MeshType>::AddFaces(in,1);
00691 f->V(0)=&(in.vert[V0i]);
00692 f->V(1)=&(in.vert[V1i]);
00693 f->V(2)=&(in.vert[V3i]);
00694 if (quad) f->SetF(2);
00695 ndone++;
00696 }
00697
00698 if (ndone==0) {
00699 if(V2i>=0 && V0i>=0 && V1i>=0 )
00700 {
00701 typename MeshType::FaceIterator f= Allocator<MeshType>::AddFaces(in,1);
00702 f->V(0)=&(in.vert[V2i]);
00703 f->V(1)=&(in.vert[V0i]);
00704 f->V(2)=&(in.vert[V1i]);
00705 ndone++;
00706 }
00707 if(V1i>=0 && V3i>=0 && V2i>=0 )
00708 {
00709 typename MeshType::FaceIterator f= Allocator<MeshType>::AddFaces(in,1);
00710 f->V(0)=&(in.vert[V1i]);
00711 f->V(1)=&(in.vert[V3i]);
00712 f->V(2)=&(in.vert[V2i]);
00713 ndone++;
00714 }
00715 }
00716
00717
00718 }
00719 }
00720
00721 template <class MeshType>
00722 void Cylinder(int slices, int stacks, MeshType & m){
00723
00724 typename MeshType::VertexIterator vi = vcg::tri::Allocator<MeshType>::AddVertices(m,slices*(stacks+1));
00725 for ( int i = 0; i < stacks+1; ++i)
00726 for ( int j = 0; j < slices; ++j)
00727 {
00728 float x,y,h;
00729 x = cos( 2.0 * M_PI / slices * j);
00730 y = sin( 2.0 * M_PI / slices * j);
00731 h = 2 * i / (float)(stacks) - 1;
00732
00733 (*vi).P() = typename MeshType::CoordType(x,h,y);
00734 ++vi;
00735 }
00736
00737 typename MeshType::FaceIterator fi ;
00738 for ( int j = 0; j < stacks; ++j)
00739 for ( int i = 0; i < slices; ++i)
00740 {
00741 int a,b,c,d;
00742 a = (j+0)*slices + i;
00743 b = (j+1)*slices + i;
00744 c = (j+1)*slices + (i+1)%slices;
00745 d = (j+0)*slices + (i+1)%slices;
00746 if(((i+j)%2) == 0){
00747 fi = vcg::tri::Allocator<MeshType>::AddFaces(m,1);
00748 (*fi).V(0) = &m.vert[ a ];
00749 (*fi).V(1) = &m.vert[ b ];
00750 (*fi).V(2) = &m.vert[ c ];
00751
00752 fi = vcg::tri::Allocator<MeshType>::AddFaces(m,1);
00753 (*fi).V(0) = &m.vert[ c ];
00754 (*fi).V(1) = &m.vert[ d ];
00755 (*fi).V(2) = &m.vert[ a ];
00756 }
00757 else{
00758 fi = vcg::tri::Allocator<MeshType>::AddFaces(m,1);
00759 (*fi).V(0) = &m.vert[ b ];
00760 (*fi).V(1) = &m.vert[ c ];
00761 (*fi).V(2) = &m.vert[ d ];
00762
00763 fi = vcg::tri::Allocator<MeshType>::AddFaces(m,1);
00764 (*fi).V(0) = &m.vert[ d ];
00765 (*fi).V(1) = &m.vert[ a ];
00766 (*fi).V(2) = &m.vert[ b ];
00767
00768 }
00769 }
00770
00771 if (m.HasPerFaceFlags()) {
00772 for (typename MeshType::FaceIterator fi=m.face.begin(); fi!=m.face.end(); fi++) {
00773 (*fi).SetF(2);
00774 }
00775 }
00776
00777
00778 }
00779
00780 template <class MeshType>
00781 void GenerateCameraMesh(MeshType &in){
00782 typedef typename MeshType::CoordType MV;
00783 MV vv[52]={
00784 MV(-0.000122145 , -0.2 ,0.35),
00785 MV(0.000122145 , -0.2 ,-0.35),MV(-0.000122145 , 0.2 ,0.35),MV(0.000122145 , 0.2 ,-0.35),MV(0.999878 , -0.2 ,0.350349),MV(1.00012 , -0.2 ,-0.349651),MV(0.999878 , 0.2 ,0.350349),MV(1.00012 , 0.2 ,-0.349651),MV(1.28255 , 0.1 ,0.754205),MV(1.16539 , 0.1 ,1.03705),MV(0.88255 , 0.1 ,1.15421),
00786 MV(0.599707 , 0.1 ,1.03705),MV(0.48255 , 0.1 ,0.754205),MV(0.599707 , 0.1 ,0.471362),MV(0.88255 , 0.1 ,0.354205),MV(1.16539 , 0.1 ,0.471362),MV(1.28255 , -0.1 ,0.754205),MV(1.16539 , -0.1 ,1.03705),MV(0.88255 , -0.1 ,1.15421),MV(0.599707 , -0.1 ,1.03705),MV(0.48255 , -0.1 ,0.754205),
00787 MV(0.599707 , -0.1 ,0.471362),MV(1.16539 , -0.1 ,0.471362),MV(0.88255 , -0.1 ,0.354205),MV(3.49164e-005 , 0 ,-0.1),MV(1.74582e-005 , -0.0866025 ,-0.05),MV(-1.74582e-005 , -0.0866025 ,0.05),MV(-3.49164e-005 , 8.74228e-009 ,0.1),MV(-1.74582e-005 , 0.0866025 ,0.05),MV(1.74582e-005 , 0.0866025 ,-0.05),MV(-0.399913 , 1.99408e-022 ,-0.25014),
00788 MV(-0.399956 , -0.216506 ,-0.12514),MV(-0.400044 , -0.216506 ,0.12486),MV(-0.400087 , 2.18557e-008 ,0.24986),MV(-0.400044 , 0.216506 ,0.12486),MV(-0.399956 , 0.216506 ,-0.12514),MV(0.479764 , 0.1 ,0.754205),MV(0.362606 , 0.1 ,1.03705),MV(0.0797637 , 0.1 ,1.15421),MV(-0.203079 , 0.1 ,1.03705),MV(-0.320236 , 0.1 ,0.754205),
00789 MV(-0.203079 , 0.1 ,0.471362),MV(0.0797637 , 0.1 ,0.354205),MV(0.362606 , 0.1 ,0.471362),MV(0.479764 , -0.1 ,0.754205),MV(0.362606 , -0.1 ,1.03705),MV(0.0797637 , -0.1 ,1.15421),MV(-0.203079 , -0.1 ,1.03705),MV(-0.320236 , -0.1 ,0.754205),MV(0.0797637 , -0.1 ,0.354205),MV(0.362606 , -0.1 ,0.471362),
00790 MV(-0.203079 , -0.1 ,0.471362), };
00791 int ff[88][3]={
00792 {0,2,3},
00793 {3,1,0},{4,5,7},{7,6,4},{0,1,5},{5,4,0},{1,3,7},{7,5,1},{3,2,6},{6,7,3},{2,0,4},
00794 {4,6,2},{10,9,8},{10,12,11},{10,13,12},{10,14,13},{10,15,14},{10,8,15},{8,17,16},{8,9,17},{9,18,17},
00795 {9,10,18},{10,19,18},{10,11,19},{11,20,19},{11,12,20},{12,21,20},{12,13,21},{13,23,21},{13,14,23},{14,22,23},
00796 {14,15,22},{15,16,22},{15,8,16},{23,16,17},{23,17,18},{23,18,19},{23,19,20},{23,20,21},{23,22,16},{25,27,26},
00797 {25,28,27},{25,29,28},{25,24,29},{24,31,30},{24,25,31},{25,32,31},{25,26,32},{26,33,32},{26,27,33},{27,34,33},
00798 {27,28,34},{28,35,34},{28,29,35},{29,30,35},{29,24,30},{35,30,31},{35,31,32},{35,32,33},{35,33,34},{42,37,36},
00799 {42,38,37},{42,39,38},{42,40,39},{42,41,40},{42,36,43},{36,45,44},{36,37,45},{37,46,45},{37,38,46},{38,47,46},
00800 {38,39,47},{39,48,47},{39,40,48},{40,51,48},{40,41,51},{41,49,51},{41,42,49},{42,50,49},{42,43,50},{43,44,50},
00801 {43,36,44},{51,44,45},{51,45,46},{51,46,47},{51,47,48},{51,49,50},{51,50,44},
00802 };
00803
00804 in.Clear();
00805 Allocator<MeshType>::AddVertices(in,52);
00806 Allocator<MeshType>::AddFaces(in,88);
00807
00808 in.vn=52;in.fn=88;
00809 int i,j;
00810 for(i=0;i<in.vn;i++)
00811 in.vert[i].P()=vv[i];;
00812
00813 std::vector<typename MeshType::VertexPointer> index(in.vn);
00814
00815 typename MeshType::VertexIterator vi;
00816 for(j=0,vi=in.vert.begin();j<in.vn;++j,++vi) index[j] = &*vi;
00817 for(j=0;j<in.fn;++j)
00818 {
00819 in.face[j].V(0)=index[ff[j][0]];
00820 in.face[j].V(1)=index[ff[j][1]];
00821 in.face[j].V(2)=index[ff[j][2]];
00822 }
00823 }
00824
00826
00827 }
00828 }
00829 #endif