source: trunk/VUT/work/IVReader/src/ivmeshdata.cpp @ 183

Revision 183, 6.9 KB checked in by mattausch, 19 years ago (diff)

added iv-reader library, testing code, and resources

Line 
1#include "ivmeshdata.h"
2#include "IVReader.h"
3
4
5IVMeshData::IVMeshData()
6{
7        vertices = normals = texCoords = indices = normalIndices = texCoordIndices = NULL;
8        vcnt = ncnt = tcnt = icnt = nicnt = ticnt = 0;
9        roType = IV_ROT_INVALID;
10        boundingBox = NULL;
11}
12
13IVMeshData::~IVMeshData()
14{
15}
16
17void IVMeshData::collapse()
18{
19        if (indices != NULL)    delete [] indices;
20        if (vertices != NULL)   delete [] vertices;
21        if (normals != NULL)    delete [] normals;
22        if (texCoords != NULL)  delete [] texCoords;
23        if (normalIndices != NULL) delete [] normalIndices;
24        if (texCoordIndices != NULL) delete [] texCoordIndices;
25        if (boundingBox != NULL) delete boundingBox;
26        indices = vertices = normals = texCoords = normalIndices = texCoords = NULL;
27        boundingBox = NULL;
28}
29
30int IVMeshData::getSeparatorCnt(Ogre::Real *data, int end)
31{
32        int cnt = 0;
33        for (int i=0; i < end; i++) if (data[i] < 0.f) cnt++;
34        return cnt;
35}
36
37Ogre::AxisAlignedBox *IVMeshData::calcBoundingBox()
38{
39        if ((vertices == NULL) || (vcnt <=0)) return new Ogre::AxisAlignedBox(0, 0, 0, 0, 0, 0);
40        Ogre::Real x, y, z, minX, minY, minZ, maxX, maxY, maxZ;
41        minX = minY = minZ = 999999;
42        maxX = maxY = maxZ = -999999;
43        for (int i=0; i<vcnt/3; i++)
44        {
45                x = vertices[i*3];
46                if (minX > x) minX = x; if (maxX < x) maxX = x;
47                y = vertices[i*3+1];
48                if (minY > y) minY = y; if (maxY < y) maxY = y;
49                z = vertices[i*3+2];
50                if (minZ > z) minZ = z; if (maxZ < z) maxZ = z;
51        }
52        return new Ogre::AxisAlignedBox(minX, minY, minZ, maxX, maxY, maxZ);
53
54}
55
56
57Ogre::Real *IVMeshData::expandTriangleStripIndices(Ogre::Real *indices, int icnt, int *icntOut)
58{
59        if (indices[icnt-1] >= 0.0)
60                *icntOut = (icnt+1 - 3*(getSeparatorCnt(indices, icnt)+1))*3;
61        else
62                *icntOut = (icnt - 3*getSeparatorCnt(indices, icnt))*3;
63if (*icntOut < 0)
64int hoppla = 1;
65        Ogre::Real *indOut = new Ogre::Real[*icntOut];
66
67        int triangleCnt = 0, tc = 0;
68        for (int i=2; i < icnt; i++)
69        {
70                if (indices[i] >= 0)
71                {
72                        if (tc % 2 == 0)
73                        {
74                                indOut[triangleCnt*3]   = indices[i-2];
75                                indOut[triangleCnt*3+1] = indices[i-1];
76                                indOut[triangleCnt*3+2] = indices[i];
77                        }
78                        else
79                        {
80                                indOut[triangleCnt*3]   = indices[i];
81                                indOut[triangleCnt*3+1] = indices[i-1];
82                                indOut[triangleCnt*3+2] = indices[i-2];
83                        }
84                        triangleCnt++; tc++;
85                }
86                else
87                {
88                        i += 2; tc = 0;
89                }
90        }
91        return indOut;
92}       
93
94int IVMeshData::getNextFaceSize(int start)
95{
96        for (int i=start; i < icnt; i++)
97        {
98                if (indices[i] < 0.f) return i - start;
99        }
100        return icnt - start;
101}
102
103Ogre::Real *IVMeshData::expandFaceSetIndices(Ogre::Real *indices, int icnt, int *icntOut)
104{
105        if (indices[icnt-1] >= 0.0)
106                *icntOut = (icnt+1 - 3*(getSeparatorCnt(indices, icnt)+1))*3;
107        else
108                *icntOut = (icnt - 3*getSeparatorCnt(indices, icnt))*3;
109        Ogre::Real *indOut = new Ogre::Real[*icntOut];
110
111        int index = 0, size = 0;
112        for (int i=0; i < icnt; i++)
113        {
114                if ((size = getNextFaceSize(i)) < 3) break;
115                for (int j=0; j < size-2; j++)
116                {
117                        indOut[index] = indices[i]; index++;
118                        indOut[index] = indices[i+1+j]; index++;
119                        indOut[index] = indices[i+2+j]; index++;
120                }
121                i = i + size;
122        }
123        return indOut;
124}
125
126IVMeshData *IVMeshData::expand()
127{
128        using namespace Ogre;
129
130        IVMeshData *mDataOut = new IVMeshData();
131
132        mDataOut->boundingBox = calcBoundingBox();
133        if ((vertices == NULL) || (vcnt <= 0) || (indices == NULL) || (icnt <= 0))
134        {
135                if (IVReader::IVLog != NULL)
136                {
137                        std::string message = "Expand-Error: ((vertices == NULL) || (vcnt <= 0) || (indices == NULL) || (icnt <= 0))";
138                        IVReader::IVLog->logMessage(message);
139                }
140       
141                return mDataOut;
142        }
143        bool nOk, tOk, niOk, tiOk, nperv, tperv;
144        nOk = ((normals != NULL) && (ncnt > 0));
145        tOk = ((texCoords != NULL) && (tcnt > 0));
146        nperv = (ncnt == vcnt) && (nicnt != icnt);
147        tperv = (tcnt*3 == vcnt*2) && (ticnt != icnt);
148
149        if ((nOk && !nperv) || (tOk && !tperv))
150        {
151                niOk = ((normalIndices != NULL) && (nicnt == icnt));
152                tiOk = ((texCoordIndices != NULL) && (ticnt == icnt));
153
154                if (!nperv && nOk && !niOk) nOk = false;
155                if (!tperv && tOk && !tiOk) tOk = false;
156
157                int sepcnt = getSeparatorCnt(indices, icnt);
158                mDataOut->icnt = icnt;
159                mDataOut->vcnt = (icnt - sepcnt)*3;
160                mDataOut->vertices = new Real[mDataOut->vcnt];
161
162                if (nOk)
163                {
164                        mDataOut->ncnt = mDataOut->vcnt;
165                        mDataOut->normals = new Real[mDataOut->ncnt];
166                }
167                if (tOk)
168                {
169                        mDataOut->tcnt = (icnt - sepcnt)*2;
170                        mDataOut->texCoords = new Real[mDataOut->tcnt];
171                }
172                mDataOut->indices = new Real[mDataOut->icnt];
173
174                int index = 0;
175                for (int i=0; i < icnt; i++)
176                {
177                        if (indices[i] >= 0.f)
178                        {
179                                mDataOut->vertices[index*3]   = vertices[(int)indices[i]*3];
180                                mDataOut->vertices[index*3+1] = vertices[(int)indices[i]*3+1];
181                                mDataOut->vertices[index*3+2] = vertices[(int)indices[i]*3+2];
182
183                                if (nOk)
184                                {
185                                        if (nperv)
186                                        {
187                                                mDataOut->normals[index*3]   = normals[(int)indices[i]*3];
188                                                mDataOut->normals[index*3+1] = normals[(int)indices[i]*3+1];
189                                                mDataOut->normals[index*3+2] = normals[(int)indices[i]*3+2];
190                                        }
191                                        else
192                                        {
193                                                mDataOut->normals[index*3]   = normals[(int)normalIndices[i]*3];
194                                                mDataOut->normals[index*3+1] = normals[(int)normalIndices[i]*3+1];
195                                                mDataOut->normals[index*3+2] = normals[(int)normalIndices[i]*3+2];
196                                        }
197                                }
198                                if (tOk)
199                                {
200                                        if (tperv)
201                                        {
202                                                mDataOut->texCoords[index*2]   = texCoords[(int)indices[i]*2];
203                                                mDataOut->texCoords[index*2+1] = texCoords[(int)indices[i]*2+1];
204                                        }
205                                        else
206                                        {
207                                                mDataOut->texCoords[index*2]   = texCoords[(int)texCoordIndices[i]*2];
208                                                mDataOut->texCoords[index*2+1] = texCoords[(int)texCoordIndices[i]*2+1];
209                                        }
210                                }
211
212                                mDataOut->indices[i] = index;
213                                index++;
214                        }
215                        else mDataOut->indices[i] = indices[i];
216                }
217        }
218        else
219        {
220                mDataOut->icnt = icnt;
221                mDataOut->indices = new Real[mDataOut->icnt];
222                memcpy(mDataOut->indices, indices, mDataOut->icnt*sizeof(Real));
223
224                mDataOut->vcnt = vcnt;
225                mDataOut->vertices = new Real[mDataOut->vcnt];
226                memcpy(mDataOut->vertices, vertices, mDataOut->vcnt*sizeof(Real));
227
228                if (nOk)
229                {
230                        mDataOut->ncnt = ncnt;
231                        mDataOut->normals = new Real[mDataOut->ncnt];
232                        memcpy(mDataOut->normals, normals, mDataOut->ncnt*sizeof(Real));
233                }
234                if (tOk)
235                {
236                        mDataOut->tcnt = tcnt;
237                        mDataOut->texCoords = new Real[mDataOut->tcnt];
238                        memcpy(mDataOut->texCoords, texCoords, mDataOut->tcnt*sizeof(Real));
239                }
240
241        }
242
243        int icntNew = 0;
244        Real *indicesNew = NULL;
245        mDataOut->roType = roType;
246        if (mDataOut->roType == IV_ROT_TRIANGLE_STRIP) 
247        {       
248                indicesNew = expandTriangleStripIndices(mDataOut->indices, mDataOut->icnt, &icntNew);
249        }
250        else if (mDataOut->roType == IV_ROT_FACE_SET)
251        {
252                indicesNew = expandFaceSetIndices(mDataOut->indices, mDataOut->icnt, &icntNew);
253        }
254        else
255        {
256                return mDataOut;
257        }
258        delete [] mDataOut->indices;
259        mDataOut->indices = indicesNew;
260        mDataOut->icnt = icntNew;
261
262        return mDataOut;
263}
Note: See TracBrowser for help on using the repository browser.