source: GTP/trunk/App/Demos/Vis/FriendlyCulling/Converter/ObjConverter.cpp @ 2963

Revision 2963, 9.5 KB checked in by mattausch, 16 years ago (diff)

debug version trying to find out how to speed up app

Line 
1#include "ObjConverter.h"
2#include "gzstream.h"
3#include <iostream>
4
5
6using namespace std;
7
8
9static void LoadIndices(char *str,
10                                                const VertexArray &vertices,
11                                                const VertexArray &normals,
12                                                const vector<pair<float, float> > &texcoords,
13                                                VertexArray &faceVertices,
14                                                VertexArray &faceNormals,
15                                                vector<Texcoord> &faceTexcoords
16                                                )
17{
18        vector<char *> substrings;
19
20        char *next_token;
21
22        // extract the triples of the form v/t/n v/t/n ...
23        char *pch = strtok_s(str + 1, " ", &next_token);
24
25        while (pch != NULL)
26        {
27                substrings.push_back(pch);
28                pch = strtok_s(NULL, " ", &next_token);   
29        }
30
31        vector<int> indices;
32        vector<int> nIndices;
33        vector<int> tIndices;
34
35        //cout << "number of vertices=" << (int)vertices.size() << endl;
36
37        for (size_t i = 0; i < substrings.size(); ++ i)
38        {
39                // vertex, normal and texture indices
40                char *str = strtok_s(substrings[i], "/", &next_token);   
41                int index = (int)strtol(str, NULL, 10) - 1;
42
43                int tIndex = index;
44                int nIndex = index;
45
46                /*str = strtok_s(substrings[i], "/", &next_token);       
47                int tIndex = (int)strtol(str, NULL, 10) - 1;
48
49                str = strtok_s(substrings[i], "/", &next_token);         
50                int nIndex = (int)strtol(str, NULL, 10) - 1;
51*/
52                // store indices
53                if (index >= 0)
54                {
55                        indices.push_back(index);
56                        nIndices.push_back(nIndex);
57                        tIndices.push_back(tIndex);
58                }
59
60                // new triangle found
61                if (indices.size() > 2)
62                {
63#if 1
64                        int idx1 = 0;
65                        int idx2 = (int)indices.size() - 2;
66                        int idx3 = (int)indices.size() - 1;
67#else
68                        int idx3 = 0;
69                        int idx2 = (int)indices.size() - 2;
70                        int idx1 = (int)indices.size() - 1;
71#endif
72                        faceVertices.push_back(vertices[indices[idx1]]);
73                        faceVertices.push_back(vertices[indices[idx2]]);
74                        faceVertices.push_back(vertices[indices[idx3]]);
75       
76                        Vector3 dummy(1, 0, 0);
77                        faceNormals.push_back(dummy);
78                        faceNormals.push_back(dummy);
79                        faceNormals.push_back(dummy);
80
81                        /*
82                        const Vector3 v2 = mVertices[2] - mVertices[1];
83                        Normalize(CrossProd(v2, v1));
84
85                        faceNormals.push_back(normals[nIndices[idx1]]);
86                        faceNormals.push_back(normals[nIndices[idx2]]);
87                        faceNormals.push_back(normals[nIndices[idx3]]);
88
89                        faceTexcoords.push_back(texcoords[tIndices[idx1]]);
90                        faceTexcoords.push_back(texcoords[tIndices[idx2]]);
91                        faceTexcoords.push_back(texcoords[tIndices[idx3]]);
92                        */
93                }
94        }
95}
96
97
98ObjConverter::ObjConverter()
99{}
100
101
102ObjConverter::~ObjConverter()
103{
104        for (size_t i = 0; i < mGeometry.size(); ++ i)
105        {
106                delete [] mGeometry[i]->mVertices;
107                delete [] mGeometry[i]->mNormals;
108                delete [] mGeometry[i]->mTexcoords;
109
110                delete mGeometry[i];
111        }
112       
113        mGeometry.clear();
114}
115
116
117void ObjConverter::LoadShape(const VertexArray &faceVertices,
118                                                         const VertexArray &faceNormals,
119                                                         const vector<Texcoord> &faceTexcoords)
120{
121        int numElements = (int)faceVertices.size();
122        Geometry *geom = new Geometry();
123
124        // convert the triangles to geometry
125        geom->mVertices = new Vector3[numElements];
126        geom->mNormals = new Vector3[numElements];
127        geom->mTexcoords = new Texcoord[numElements];
128
129        geom->mVertexCount = numElements;
130        geom->mTexcoordCount = (int)faceTexcoords.size();
131
132        cout << "number of vertices=" << numElements << endl;
133
134        for (int i = 0; i < numElements; ++ i)
135        {
136                geom->mVertices[i].x = faceVertices[i].x;
137                geom->mVertices[i].y = -faceVertices[i].z;
138                geom->mVertices[i].z = faceVertices[i].y;
139
140                geom->mNormals[i].x = faceNormals[i].x;
141                geom->mNormals[i].y = -faceNormals[i].z;
142                geom->mNormals[i].z = faceNormals[i].y;
143
144                if (i <= geom->mTexcoordCount)
145                {
146                        geom->mTexcoords[i].first = faceTexcoords[i].first;
147                        geom->mTexcoords[i].second = faceTexcoords[i].second;
148                }
149        }
150
151        mGeometry.push_back(geom);
152}
153
154
155bool ObjConverter::Convert(const string &filename, const std::string &outputFilename)
156{
157        mNumShapes = 0;
158       
159        for (size_t i = 0; i < mGeometry.size(); ++ i)
160        {
161                delete [] mGeometry[i]->mVertices;
162                delete [] mGeometry[i]->mNormals;
163                delete [] mGeometry[i]->mTexcoords;
164
165                delete mGeometry[i];
166        }
167       
168        mGeometry.clear();
169
170        if (!ReadFile(filename))
171        {
172                cerr << "could not read file" << endl;
173                return false;
174        }
175
176        if (!WriteFile(outputFilename))
177        {
178                cerr << "could not write file" << endl;
179                return false;
180        }
181
182
183        return true;
184}
185
186
187bool ObjConverter::ReadFile(const string &filename)
188{
189        FILE *file;
190
191        if ((file = fopen(filename.c_str(), "r")) == NULL)
192        {       
193                return false;
194        }
195       
196        VertexArray faceVertices;
197        VertexArray faceNormals;
198        vector<Texcoord> faceTexcoords;
199
200        VertexArray vertices;
201        VertexArray normals;
202        vector<Texcoord> texcoords;
203
204        vector<int> indices;
205
206        int line = 0;
207
208        const int len = 10000;
209        char str[len];
210
211        while (fgets(str, len, file) != NULL)
212        {
213                //cout << str;
214                switch (str[0])
215                {
216                case 'v': // vertex or normal
217                        {
218                                float x, y, z;
219
220                                switch (str[1])
221                                {
222                                case 'n' :
223                                        sscanf(str + 2, "%f %f %f", &x, &y, &z);
224                                        normals.push_back(Vector3(x, y, z));
225                                        break;
226                                case 't':
227                                        sscanf(str + 2, "%f %f", &x, &y);
228                                        texcoords.push_back(pair<float, float>(x, y));
229                                        break;
230                                default:
231                                        sscanf(str + 1, "%f %f %f", &x, &y, &z);
232                                        vertices.push_back(Vector3(x, y, z));
233                                        //cout <<"v " << x << " " << y << " "<< z << " ";
234                                }
235                                break;
236                        }
237                case 'f':
238                        {
239                                //////////
240                                //-- indices in the current line
241
242                                LoadIndices(str,
243                                                vertices, normals, texcoords,
244                                                faceVertices, faceNormals, faceTexcoords);
245
246                                if (((line % 100) == 99) &&
247                                        !faceVertices.empty())
248                                {
249                                        ++ mNumShapes;
250
251                                        LoadShape(faceVertices, faceNormals, faceTexcoords);
252
253                                        faceVertices.clear();
254                                        faceNormals.clear();
255                                        faceTexcoords.clear();
256                                }
257
258                                break;
259                        }   // end face
260                case 'g':
261                        {/*
262                                if (!faceVertices.empty())
263                                {
264                                        ++ mNumShapes;
265
266                                        LoadShape(faceVertices, faceNormals, faceTexcoords);
267
268                                        faceVertices.clear();
269                                        faceNormals.clear();
270                                        faceTexcoords.clear();
271                                }*/
272                        }
273                        break;
274                default:
275                        break;
276                }
277
278                ++ line;
279        }
280
281        if (!faceVertices.empty())
282        {
283                ++ mNumShapes;
284
285                LoadShape(faceVertices, faceNormals, faceTexcoords);
286
287                faceVertices.clear();
288                faceNormals.clear();
289                faceTexcoords.clear();
290        }
291
292        fclose(file);
293       
294        return true;
295}
296
297
298void ObjConverter::WriteGeometry(ogzstream &str, Geometry *geom)
299{
300        int vertexCount = geom->mVertexCount;
301        str.write(reinterpret_cast<char *>(&vertexCount), sizeof(int));
302 
303        str.write(reinterpret_cast<char *>(geom->mVertices), sizeof(Vector3) * vertexCount);
304        str.write(reinterpret_cast<char *>(geom->mNormals), sizeof(Vector3) * vertexCount);
305
306        int texCoordCount = geom->mTexcoordCount;
307        str.write(reinterpret_cast<char *>(&texCoordCount), sizeof(int));
308
309        if (texCoordCount)
310                str.write(reinterpret_cast<char *>(geom->mTexcoords), sizeof(float) * texCoordCount * 2);
311       
312
313        ///////
314        //-- texture
315
316        int texId = -1;
317        //int texId = 0;
318        str.write(reinterpret_cast<char *>(&texId), sizeof(int));
319
320        bool alphaTestEnabled = false;
321        bool cullFaceEnabled = false;
322        //bool cullFaceEnabled = true;
323
324        str.write(reinterpret_cast<char *>(&alphaTestEnabled), sizeof(bool));
325        str.write(reinterpret_cast<char *>(&cullFaceEnabled), sizeof(bool));
326
327        // material
328        //bool hasMaterial = true;
329        bool hasMaterial = false;
330        str.write(reinterpret_cast<char *>(&hasMaterial), sizeof(bool));
331       
332        if (hasMaterial)
333        {
334                Vector3 ambient, diffuse, black;
335
336                ambient.x = ambient.y = ambient.z = 0.2f;
337                diffuse.x = diffuse.y = diffuse.z = 1.0f;
338                black.x = black.y = black.z = .0f;
339
340                // only write rgb part of the material
341                str.write(reinterpret_cast<char *>(&ambient), sizeof(Vector3));
342                str.write(reinterpret_cast<char *>(&diffuse), sizeof(Vector3));
343                str.write(reinterpret_cast<char *>(&black), sizeof(Vector3));
344                str.write(reinterpret_cast<char *>(&black), sizeof(Vector3));
345        }
346}
347
348
349bool ObjConverter::WriteFile(const string &filename)
350{
351        ogzstream ofile(filename.c_str());
352
353        if (!ofile.is_open())
354                return false;
355       
356
357        /////////
358        //-- write textures
359
360        //int textureCount = 1;
361        int textureCount = 0;
362
363        ofile.write(reinterpret_cast<char *>(&textureCount), sizeof(int));
364
365        if (textureCount > 0)
366        {
367                const string texName("wood.jpg");
368
369                int texnameSize = (int)texName.length() + 1;
370                ofile.write(reinterpret_cast<char *>(&texnameSize), sizeof(int));
371
372                ofile.write(texName.c_str(), sizeof(char) * texnameSize);
373
374                int boundS = 1;
375                int boundT = 1;
376
377                ofile.write(reinterpret_cast<char *>(&boundS), sizeof(int));
378                ofile.write(reinterpret_cast<char *>(&boundT), sizeof(int));
379        }
380
381
382        ///////////
383        //-- write shapes
384
385        ofile.write(reinterpret_cast<char *>(&mNumShapes), sizeof(int));
386
387        vector<Geometry *>::const_iterator it, it_end = mGeometry.end();
388
389        for (it = mGeometry.begin(); it != it_end; ++ it)
390        {
391                WriteGeometry(ofile, *it);
392        }
393
394
395        int entityCount = 1;
396        ofile.write(reinterpret_cast<char *>(&entityCount), sizeof(int));
397
398
399        //////////
400        //-- write single scene entity
401
402        // no transformation
403        bool hasTrafo = false;
404        ofile.write(reinterpret_cast<char *>(&hasTrafo), sizeof(bool));
405
406        // a dummy lod
407        int numLODs = 1;
408        ofile.write(reinterpret_cast<char *>(&numLODs), sizeof(int));
409
410        float dist = 0;
411        ofile.write(reinterpret_cast<char *>(&dist), sizeof(float));
412
413        ofile.write(reinterpret_cast<char *>(&mNumShapes), sizeof(int));
414
415        // all shapes belong to this scene entity
416        for (int i = 0; i < mNumShapes; ++ i)
417        {
418                int shapeId = i;
419                ofile.write(reinterpret_cast<char *>(&shapeId), sizeof(int));
420        }
421
422        return true;
423}
Note: See TracBrowser for help on using the repository browser.