00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "stdmeshimporter.h"
00023 #include <salt/gmath.h>
00024 #include <sstream>
00025
00026 #include <zeitgeist/logserver/logserver.h>
00027 using namespace zeitgeist;
00028 using namespace oxygen;
00029 using namespace boost;
00030 using namespace salt;
00031 using namespace std;
00032
00033 StdMeshImporter::StdMeshImporter() : MeshImporter()
00034 {
00035 }
00036
00037 StdMeshImporter::~StdMeshImporter()
00038 {
00039 }
00040
00041 static const string gSphereStr = "StdUnitSphere";
00042 static const string gBoxStr = "StdUnitBox";
00043 static const string gCCylinderStr = "StdCCylinder";
00044
00045 shared_ptr<TriMesh>
00046 StdMeshImporter::ImportMesh(const std::string& name,const ParameterList& parameter)
00047 {
00048 if (name == gSphereStr)
00049 {
00050 return UnitSphereMesh();
00051 }
00052
00053 if (name == gBoxStr)
00054 {
00055 return UnitBoxMesh();
00056 }
00057
00058 if (name == gCCylinderStr)
00059 {
00060 return UnitCCylinder(parameter);
00061 }
00062
00063 return shared_ptr<TriMesh>();
00064 }
00065
00066
00067
00068
00069
00070
00071 static const int gNumSphereVertices = 114;
00072 static const int gNumSphereFaces = 224;
00073
00074 static float gSphereVertices[gNumSphereVertices*3] =
00075 {
00076 0.0000f,0.0000f,1.0000f, 0.0000f,0.3827f,0.9239f, -0.1464f,0.3536f,0.9239f,
00077 -0.2706f,0.2706f,0.9239f, -0.3536f,0.1464f,0.9239f, -0.3827f,0.0000f,0.9239f,
00078 -0.3536f,-0.1464f,0.9239f, -0.2706f,-0.2706f,0.9239f, -0.1464f,-0.3536f,0.9239f,
00079 0.0000f,-0.3827f,0.9239f, 0.1464f,-0.3536f,0.9239f, 0.2706f,-0.2706f,0.9239f,
00080 0.3536f,-0.1464f,0.9239f, 0.3827f,0.0000f,0.9239f, 0.3536f,0.1464f,0.9239f,
00081 0.2706f,0.2706f,0.9239f, 0.1464f,0.3536f,0.9239f, 0.0000f,0.7071f,0.7071f,
00082 -0.2706f,0.6533f,0.7071f, -0.5000f,0.5000f,0.7071f, -0.6533f,0.2706f,0.7071f,
00083 -0.7071f,0.0000f,0.7071f, -0.6533f,-0.2706f,0.7071f, -0.5000f,-0.5000f,0.7071f,
00084 -0.2706f,-0.6533f,0.7071f, 0.0000f,-0.7071f,0.7071f, 0.2706f,-0.6533f,0.7071f,
00085 0.5000f,-0.5000f,0.7071f, 0.6533f,-0.2706f,0.7071f, 0.7071f,0.0000f,0.7071f,
00086 0.6533f,0.2706f,0.7071f, 0.5000f,0.5000f,0.7071f, 0.2706f,0.6533f,0.7071f,
00087 0.0000f,0.9239f,0.3827f, -0.3536f,0.8536f,0.3827f, -0.6533f,0.6533f,0.3827f,
00088 -0.8536f,0.3536f,0.3827f, -0.9239f,0.0000f,0.3827f, -0.8536f,-0.3536f,0.3827f,
00089 -0.6533f,-0.6533f,0.3827f, -0.3536f,-0.8536f,0.3827f, 0.0000f,-0.9239f,0.3827f,
00090 0.3536f,-0.8536f,0.3827f, 0.6533f,-0.6533f,0.3827f, 0.8536f,-0.3536f,0.3827f,
00091 0.9239f,0.0000f,0.3827f, 0.8536f,0.3536f,0.3827f, 0.6533f,0.6533f,0.3827f,
00092 0.3536f,0.8536f,0.3827f, 0.0000f,1.0000f,0.0000f, -0.3827f,0.9239f,0.0000f,
00093 -0.7071f,0.7071f,0.0000f, -0.9239f,0.3827f,0.0000f, -1.0000f,0.0000f,0.0000f,
00094 -0.9239f,-0.3827f,0.0000f, -0.7071f,-0.7071f,0.0000f, -0.3827f,-0.9239f,0.0000f,
00095 0.0000f,-1.0000f,0.0000f, 0.3827f,-0.9239f,0.0000f, 0.7071f,-0.7071f,0.0000f,
00096 0.9239f,-0.3827f,0.0000f, 1.0000f,0.0000f,0.0000f, 0.9239f,0.3827f,0.0000f,
00097 0.7071f,0.7071f,0.0000f, 0.3827f,0.9239f,0.0000f, 0.0000f,0.9239f,-0.3827f,
00098 -0.3536f,0.8536f,-0.3827f, -0.6533f,0.6533f,-0.3827f, -0.8536f,0.3536f,-0.3827f,
00099 -0.9239f,0.0000f,-0.3827f, -0.8536f,-0.3536f,-0.3827f, -0.6533f,-0.6533f,-0.3827f,
00100 -0.3536f,-0.8536f,-0.3827f, 0.0000f,-0.9239f,-0.3827f, 0.3536f,-0.8536f,-0.3827f,
00101 0.6533f,-0.6533f,-0.3827f, 0.8536f,-0.3536f,-0.3827f, 0.9239f,0.0000f,-0.3827f,
00102 0.8536f,0.3536f,-0.3827f, 0.6533f,0.6533f,-0.3827f, 0.3536f,0.8536f,-0.3827f,
00103 0.0000f,0.7071f,-0.7071f, -0.2706f,0.6533f,-0.7071f, -0.5000f,0.5000f,-0.7071f,
00104 -0.6533f,0.2706f,-0.7071f, -0.7071f,0.0000f,-0.7071f, -0.6533f,-0.2706f,-0.7071f,
00105 -0.5000f,-0.5000f,-0.7071f, -0.2706f,-0.6533f,-0.7071f, 0.0000f,-0.7071f,-0.7071f,
00106 0.2706f,-0.6533f,-0.7071f, 0.5000f,-0.5000f,-0.7071f, 0.6533f,-0.2706f,-0.7071f,
00107 0.7071f,0.0000f,-0.7071f, 0.6533f,0.2706f,-0.7071f, 0.5000f,0.5000f,-0.7071f,
00108 0.2706f,0.6533f,-0.7071f, 0.0000f,0.3827f,-0.9239f, -0.1464f,0.3536f,-0.9239f,
00109 -0.2706f,0.2706f,-0.9239f, -0.3536f,0.1464f,-0.9239f, -0.3827f,0.0000f,-0.9239f,
00110 -0.3536f,-0.1464f,-0.9239f, -0.2706f,-0.2706f,-0.9239f, -0.1464f,-0.3536f,-0.9239f,
00111 0.0000f,-0.3827f,-0.9239f, 0.1464f,-0.3536f,-0.9239f, 0.2706f,-0.2706f,-0.9239f,
00112 0.3536f,-0.1464f,-0.9239f, 0.3827f,0.0000f,-0.9239f, 0.3536f,0.1464f,-0.9239f,
00113 0.2706f,0.2706f,-0.9239f, 0.1464f,0.3536f,-0.9239f, 0.0000f,0.0000f,-1.0000f
00114 };
00115
00116 static unsigned int gSphereFaces[gNumSphereFaces*3] =
00117 {
00118 0,1,2, 0,2,3, 0,3,4, 0,4,5, 0,5,6, 0,6,7, 0,7,8, 0,8,9, 0,9,10,
00119 0,10,11, 0,11,12, 0,12,13, 0,13,14, 0,14,15, 0,15,16, 0,16,1, 1,17,18, 1,18,2,
00120 2,18,19, 2,19,3, 3,19,20, 3,20,4, 4,20,21, 4,21,5, 5,21,22, 5,22,6, 6,22,23,
00121 6,23,7, 7,23,24, 7,24,8, 8,24,25, 8,25,9, 9,25,26, 9,26,10, 10,26,27, 10,27,11,
00122 11,27,28, 11,28,12, 12,28,29, 12,29,13, 13,29,30, 13,30,14, 14,30,31, 14,31,15, 15,31,32,
00123 15,32,16, 16,32,17, 16,17,1, 17,33,34, 17,34,18, 18,34,35, 18,35,19, 19,35,36, 19,36,20,
00124 20,36,37, 20,37,21, 21,37,38, 21,38,22, 22,38,39, 22,39,23, 23,39,40, 23,40,24, 24,40,41,
00125 24,41,25, 25,41,42, 25,42,26, 26,42,43, 26,43,27, 27,43,44, 27,44,28, 28,44,45, 28,45,29,
00126 29,45,46, 29,46,30, 30,46,47, 30,47,31, 31,47,48, 31,48,32, 32,48,33, 32,33,17, 33,49,50,
00127 33,50,34, 34,50,51, 34,51,35, 35,51,52, 35,52,36, 36,52,53, 36,53,37, 37,53,54, 37,54,38,
00128 38,54,55, 38,55,39, 39,55,56, 39,56,40, 40,56,57, 40,57,41, 41,57,58, 41,58,42, 42,58,59,
00129 42,59,43, 43,59,60, 43,60,44, 44,60,61, 44,61,45, 45,61,62, 45,62,46, 46,62,63, 46,63,47,
00130 47,63,64, 47,64,48, 48,64,49, 48,49,33, 49,65,66, 49,66,50, 50,66,67, 50,67,51, 51,67,68,
00131 51,68,52, 52,68,69, 52,69,53, 53,69,70, 53,70,54, 54,70,71, 54,71,55, 55,71,72, 55,72,56,
00132 56,72,73, 56,73,57, 57,73,74, 57,74,58, 58,74,75, 58,75,59, 59,75,76, 59,76,60, 60,76,77,
00133 60,77,61, 61,77,78, 61,78,62, 62,78,79, 62,79,63, 63,79,80, 63,80,64, 64,80,65, 64,65,49,
00134 65,81,82, 65,82,66, 66,82,83, 66,83,67, 67,83,84, 67,84,68, 68,84,85, 68,85,69, 69,85,86,
00135 69,86,70, 70,86,87, 70,87,71, 71,87,88, 71,88,72, 72,88,89, 72,89,73, 73,89,90, 73,90,74,
00136 74,90,91, 74,91,75, 75,91,92, 75,92,76, 76,92,93, 76,93,77, 77,93,94, 77,94,78, 78,94,95,
00137 78,95,79, 79,95,96, 79,96,80, 80,96,81, 80,81,65, 81,97,98, 81,98,82, 82,98,99, 82,99,83,
00138 83,99,100, 83,100,84, 84,100,101, 84,101,85, 85,101,102, 85,102,86, 86,102,103, 86,103,87, 87,103,104,
00139 87,104,88, 88,104,105, 88,105,89, 89,105,106, 89,106,90, 90,106,107, 90,107,91, 91,107,108, 91,108,92,
00140 92,108,109, 92,109,93, 93,109,110, 93,110,94, 94,110,111, 94,111,95, 95,111,112, 95,112,96, 96,112,97,
00141 96,97,81, 113,98,97, 113,99,98, 113,100,99, 113,101,100, 113,102,101, 113,103,102, 113,104,103, 113,105,104,
00142 113,106,105, 113,107,106, 113,108,107, 113,109,108, 113,110,109, 113,111,110, 113,112,111, 113,97,112
00143 };
00144
00145 shared_ptr<TriMesh> StdMeshImporter::UnitSphereMesh()
00146 {
00147 shared_ptr<TriMesh> mesh(new TriMesh());
00148
00149 shared_array<float> pos(new float[gNumSphereVertices*3]);
00150 memcpy(pos.get(),gSphereVertices,gNumSphereVertices*3*sizeof(float));
00151 mesh->SetPos(pos,gNumSphereVertices);
00152
00153
00154
00155 mesh->SetNormals(pos);
00156
00157 shared_ptr<IndexBuffer> idx(new IndexBuffer());
00158 idx->Cache(gNumSphereFaces*3,gSphereFaces);
00159 mesh->AddFace(idx);
00160
00161 return mesh;
00162 }
00163
00164
00165
00166
00167
00168 static const int gNumBoxVertices = 24;
00169 static const int gNumBoxFaces = 12;
00170
00171 static float gBoxVertices[gNumBoxVertices*3] =
00172 {
00173 -0.5f,-0.5f,0.5f, 0.5f,-0.5f, 0.5f, 0.5f,0.5f,0.5f,
00174 -0.5f,0.5f,0.5f, -0.5f,-0.5f,-0.5f, -0.5f,0.5f,-0.5f,
00175 0.5f,0.5f,-0.5f, 0.5f,-0.5f,-0.5f, -0.5f,0.5f,-0.5f,
00176 -0.5f,0.5f,0.5f, 0.5f,0.5f,0.5f, 0.5f,0.5f,-0.5f,
00177 -0.5f,-0.5f,-0.5f, 0.5f,-0.5f,-0.5f, 0.5f,-0.5f,0.5f,
00178 -0.5f,-0.5f,0.5f, 0.5f,-0.5f,-0.5f, 0.5f,0.5f,-0.5f,
00179 0.5f,0.5f,0.5f, 0.5f,-0.5f,0.5f, -0.5f,-0.5f,-0.5f,
00180 -0.5f,-0.5f,0.5f, -0.5f,0.5f,0.5f, -0.5f,0.5f,-0.5f
00181 };
00182
00183 static float gBoxNormals[gNumBoxVertices*3] =
00184 {
00185 0.0f,0.0f,1.0f, 0.0f,0.0f,1.0f, 0.0f,0.0f,1.0f,
00186 0.0f,0.0f,1.0f, 0.0f,0.0f,-1.0f, 0.0f,0.0f,-1.0f,
00187 0.0f,0.0f,-1.0f, 0.0f,0.0f,-1.0f, 0.0f,1.0f,0.0f,
00188 0.0f,1.0f,0.0f, 0.0f,1.0f,0.0f, 0.0f,1.0f,0.0f,
00189 0.0f,-1.0f,0.0f, 0.0f,-1.0f,0.0f, 0.0f,-1.0f,0.0f,
00190 0.0f,-1.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,0.0f,0.0f,
00191 1.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, -1.0f,0.0f,0.0f,
00192 -1.0f,0.0f,0.0f, -1.0f,0.0f,0.0f, -1.0f,0.0f,0.0f
00193 };
00194
00195 static float gBoxTexCoords[gNumBoxVertices*3] =
00196 {
00197 0.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f,
00198 0.0f,1.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f,
00199 0.0f,1.0f,0.0f, 0.0f,0.0f,0.0f, 0.0f,1.0f,0.0f,
00200 0.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f,
00201 1.0f,1.0f,0.0f, 0.0f,1.0f,0.0f, 0.0f,0.0f,0.0f,
00202 1.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f,
00203 0.0f,1.0f,0.0f, 0.0f,0.0f,0.0f, 0.0f,0.0f,0.0f,
00204 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f, 0.0f,1.0f,0.0f
00205 };
00206
00207 static unsigned int gBoxFaces[gNumSphereFaces*3] =
00208 {
00209 0,1,2, 0,2,3, 4,5,6, 4,6,7, 8,9,10, 8,10,11,
00210 12,13,14, 12,14,15, 16,17,18, 16,18,19,
00211 20,21,22, 20,22,23
00212 };
00213
00214 shared_ptr<TriMesh> StdMeshImporter::UnitBoxMesh()
00215 {
00216 shared_ptr<TriMesh> mesh(new TriMesh());
00217
00218 shared_array<float> pos(new float[gNumBoxVertices*3]);
00219 memcpy(pos.get(),gBoxVertices,gNumBoxVertices*3*sizeof(float));
00220 mesh->SetPos(pos,gNumBoxVertices);
00221
00222 shared_array<float> normals(new float[gNumBoxVertices*3]);
00223 memcpy(normals.get(),gBoxNormals,gNumBoxVertices*3*sizeof(float));
00224 mesh->SetNormals(normals);
00225
00226 shared_array<float> tex(new float[gNumBoxVertices*3]);
00227 memcpy(tex.get(), gBoxTexCoords,gNumBoxVertices*3*sizeof(float));
00228 mesh->SetTexCoords(tex);
00229
00230 shared_ptr<IndexBuffer> idx(new IndexBuffer());
00231 idx->Cache(gNumBoxFaces*3,gBoxFaces);
00232 mesh->AddFace(idx);
00233
00234 return mesh;
00235 }
00236
00237
00238
00239
00240 static void AddVertex(float** at, float x, float y, float z)
00241 {
00242 (**at) = x; ++(*at);
00243 (**at) = y; ++(*at);
00244 (**at) = z; ++(*at);
00245 }
00246
00247 std::string StdMeshImporter::MangleName (const string& name, const ParameterList& parameter)
00248 {
00249 if (
00250 (name != gCCylinderStr) ||
00251 (parameter.GetSize() < 2)
00252 )
00253 {
00254 return name;
00255 }
00256
00257 stringstream ss;
00258 ss << gCCylinderStr;
00259
00260 float radius;
00261 if (parameter.GetValue(parameter[0],radius))
00262 {
00263 ss << "R=" << radius;
00264 }
00265
00266 float length;
00267 if (parameter.GetValue(parameter[1],length))
00268 {
00269 ss << "L=" << length;
00270 }
00271
00272 return ss.str();
00273 }
00274
00275 shared_ptr<TriMesh> StdMeshImporter::UnitCCylinder(const ParameterList& parameter)
00276 {
00277
00278
00279
00280
00281
00282 float ccRadius = 1;
00283 float ccLength = 1;
00284
00285 GetLog()->Debug()
00286 << "(StdMeshImporter::UnitCCylinder) paramSize="
00287 << parameter.GetSize() << "\n";
00288 if (parameter.GetSize() >= 2)
00289 {
00290 parameter.GetValue(parameter[0],ccRadius);
00291 parameter.GetValue(parameter[1],ccLength);
00292 }
00293
00294
00295 const int capped_cylinder_quality = 3;
00296 const int n = capped_cylinder_quality*4;
00297
00298 int innerLoop = (n+1);
00299 int numVertices = innerLoop * 2;
00300 numVertices += (innerLoop * (n/4) * 2);
00301 numVertices += (innerLoop * (n/4) * 2);
00302
00303 shared_array<float> pos(new float[numVertices * 3]);
00304 shared_array<float> normals(new float[numVertices * 3]);
00305 float* cVert = pos.get();
00306 float* cNormal = normals.get();
00307
00308 int i,j;
00309 float tmp,nx,start_nx,start_ny;
00310
00311 float l = ccLength * 0.5;
00312 float a = g2PI / n;
00313 float sa = gSin(a);
00314 float ca = gCos(a);
00315
00316
00317
00318
00319 float ny = 1;
00320 float nz = 0;
00321
00322 for (i=0; i<=n; ++i)
00323 {
00324 AddVertex(&cNormal,ny,nz,0);
00325 AddVertex(&cVert,ny*ccRadius,nz*ccRadius,l);
00326 AddVertex(&cNormal,ny,nz,0);
00327 AddVertex(&cVert,ny*ccRadius,nz*ccRadius,-l);
00328
00329
00330 tmp = ca * ny - sa * nz;
00331 nz = sa*ny + ca*nz;
00332 ny = tmp;
00333 }
00334
00335
00336 start_nx = 0;
00337 start_ny = 1;
00338
00339 for (j=0; j<(n/4); ++j)
00340 {
00341
00342 float start_nx2 = ca*start_nx + sa*start_ny;
00343 float start_ny2 = -sa*start_nx + ca*start_ny;
00344
00345
00346 nx = start_nx;
00347 ny = start_ny;
00348 nz = 0;
00349 float nx2 = start_nx2;
00350 float ny2 = start_ny2;
00351 float nz2 = 0;
00352
00353 for (i=0; i<=n; i++)
00354 {
00355 AddVertex(&cNormal,ny2,nz2,nx2);
00356 AddVertex(&cVert,ny2*ccRadius,nz2*ccRadius,l+nx2*ccRadius);
00357 AddVertex(&cNormal,ny,nz,nx);
00358 AddVertex(&cVert,ny*ccRadius,nz*ccRadius,l+nx*ccRadius);
00359
00360
00361 tmp = ca*ny - sa*nz;
00362 nz = sa*ny + ca*nz;
00363 ny = tmp;
00364 tmp = ca*ny2- sa*nz2;
00365 nz2 = sa*ny2 + ca*nz2;
00366 ny2 = tmp;
00367 }
00368
00369 start_nx = start_nx2;
00370 start_ny = start_ny2;
00371 }
00372
00373
00374 start_nx = 0;
00375 start_ny = 1;
00376
00377 for (j=0; j<(n/4); j++)
00378 {
00379
00380 float start_nx2 = ca*start_nx - sa*start_ny;
00381 float start_ny2 = sa*start_nx + ca*start_ny;
00382
00383
00384 nx = start_nx; ny = start_ny; nz = 0;
00385 float nx2 = start_nx2;
00386 float ny2 = start_ny2;
00387 float nz2 = 0;
00388
00389 for (i=0; i<=n; i++)
00390 {
00391 AddVertex(&cNormal,ny,nz,nx);
00392 AddVertex(&cVert,ny*ccRadius,nz*ccRadius,-l+nx*ccRadius);
00393 AddVertex(&cNormal,ny2,nz2,nx2);
00394 AddVertex(&cVert,ny2*ccRadius,nz2*ccRadius,-l+nx2*ccRadius);
00395
00396 tmp = ca*ny - sa*nz;
00397 nz = sa*ny + ca*nz;
00398 ny = tmp;
00399 tmp = ca*ny2- sa*nz2;
00400 nz2 = sa*ny2 + ca*nz2;
00401 ny2 = tmp;
00402 }
00403
00404 start_nx = start_nx2;
00405 start_ny = start_ny2;
00406 }
00407
00408 shared_ptr<IndexBuffer> idx(new IndexBuffer());
00409
00410 int numFaces = (numVertices - 2);
00411 idx->EnsureFit(numFaces*3);
00412
00413 for (i=0;i<numFaces;++i)
00414 {
00415 if (i%2)
00416 {
00417 idx->Cache(i+1);
00418 idx->Cache(i);
00419 idx->Cache(i+2);
00420 } else
00421 {
00422 idx->Cache(i);
00423 idx->Cache(i+1);
00424 idx->Cache(i+2);
00425 }
00426 }
00427
00428 shared_ptr<TriMesh> mesh(new TriMesh());
00429 mesh->SetPos(pos,numVertices);
00430 mesh->SetNormals(normals);
00431 mesh->AddFace(idx);
00432 mesh->SetName(MangleName(gCCylinderStr,parameter));
00433
00434 return mesh;
00435 }
00436