Browse Source

Setup objects from TombRaider in their constructor

Thomas Buck 10 years ago
parent
commit
36ece5eb87
12 changed files with 632 additions and 753 deletions
  1. 4
    0
      ChangeLog.md
  2. 3
    0
      include/Game.h
  3. 26
    29
      include/Room.h
  4. 4
    1
      include/Sprite.h
  5. 1
    1
      include/ViewVolume.h
  6. 2
    2
      include/math/math.h
  7. 12
    586
      src/Game.cpp
  8. 13
    8
      src/Render.cpp
  9. 491
    105
      src/Room.cpp
  10. 73
    18
      src/Sprite.cpp
  11. 1
    1
      src/ViewVolume.cpp
  12. 2
    2
      src/math/math.cpp

+ 4
- 0
ChangeLog.md View File

@@ -2,6 +2,10 @@
2 2
 
3 3
 ## OpenRaider (0.1.3) xythobuz <xythobuz@xythobuz.de>
4 4
 
5
+    [ 20140505 ]
6
+    * Moved setup of Room, Portal, Box, Sector, ... into their
7
+      Constructors.
8
+
5 9
     [ 20140504 ]
6 10
     * Forcing use of new Room and Sprite classes in World.
7 11
     * Rewrote Sprite loading code in Game

+ 3
- 0
include/Game.h View File

@@ -38,6 +38,9 @@ public:
38 38
 
39 39
     void handleMouseMotion(int xrel, int yrel);
40 40
 
41
+    unsigned int getTextureStart();
42
+    unsigned int getTextureOffset();
43
+
41 44
     //! \fixme should be private
42 45
     entity_t *mLara;
43 46
 

+ 26
- 29
include/Room.h View File

@@ -11,8 +11,10 @@
11 11
 #include <vector>
12 12
 #include <memory>
13 13
 #include "math/math.h"
14
+#include "math/Matrix.h"
14 15
 #include "Mesh.h"
15 16
 #include "Sprite.h"
17
+#include "TombRaider.h"
16 18
 
17 19
 class Light {
18 20
 public:
@@ -25,20 +27,27 @@ public:
25 27
         typeDirectional = 3  //!< Directional light
26 28
     } LightType;
27 29
 
28
-    Light(vec4_t pos, vec3_t dir, vec_t att, vec4_t color, vec_t cutoff, LightType type);
30
+    Light(TombRaider &tr, unsigned int room, unsigned int index);
29 31
 
30
-//private:
31
-    vec4_t mPos; //! Light position in 3 space
32
-    vec3_t mDir; //! Light direction
33
-    vec_t mAtt;
34
-    vec4_t mColor; //! Color of light
35
-    vec_t mCutoff; //! Fade out distance
36
-    LightType mType; //! Type of light
32
+    void getPos(vec4_t p);
33
+    void getDir(vec3_t d);
34
+    vec_t getAtt();
35
+    void getColor(vec4_t c);
36
+    vec_t getCutoff();
37
+    LightType getType();
38
+
39
+private:
40
+    vec4_t pos; //! Light position in 3 space
41
+    vec3_t dir; //! Light direction
42
+    vec_t att;
43
+    vec4_t color; //! Color of light
44
+    vec_t cutoff; //! Fade out distance
45
+    LightType type; //! Type of light
37 46
 };
38 47
 
39 48
 class StaticModel {
40 49
 public:
41
-    StaticModel(int _index, vec_t _yaw, vec3_t _pos);
50
+    StaticModel(TombRaider &tr, unsigned int room, unsigned int i);
42 51
     void display();
43 52
 
44 53
     // Compares distance to ViewVolume for depth sorting
@@ -55,7 +64,7 @@ private:
55 64
 
56 65
 class Portal {
57 66
 public:
58
-    Portal(vec3_t _vertices[4], vec3_t _normal, int _adjoiningRoom);
67
+    Portal(TombRaider &tr, unsigned int room, unsigned int index, Matrix &transform);
59 68
 
60 69
     void getVertices(vec3_t vert[4]);
61 70
     int getAdjoiningRoom();
@@ -68,7 +77,7 @@ private:
68 77
 
69 78
 class Box {
70 79
 public:
71
-    Box(vec3_t _a, vec3_t _b, vec3_t _c, vec3_t _d);
80
+    Box(TombRaider &tr, unsigned int room, unsigned int index);
72 81
 
73 82
 private:
74 83
     vec3_t a;
@@ -79,7 +88,7 @@ private:
79 88
 
80 89
 class Sector {
81 90
 public:
82
-    Sector(vec_t _floor, vec_t _ceiling, bool _wall);
91
+    Sector(TombRaider &tr, unsigned int room, unsigned int index);
83 92
     vec_t getFloor();
84 93
     vec_t getCeiling();
85 94
     bool isWall();
@@ -96,64 +105,53 @@ typedef enum {
96 105
 
97 106
 class Room {
98 107
 public:
99
-    Room(int _id);
108
+    Room(TombRaider &tr, unsigned int index);
100 109
     ~Room();
101 110
 
102 111
     void setFlags(unsigned int f);
103 112
     unsigned int getFlags();
104 113
 
105
-    void setNumXSectors(unsigned int n);
106 114
     unsigned int getNumXSectors();
107 115
 
108
-    void setNumZSectors(unsigned int n);
109 116
     unsigned int getNumZSectors();
110 117
 
111
-    void setPos(vec3_t p);
112 118
     void getPos(vec3_t p);
113 119
 
114 120
     void getBoundingBox(vec3_t box[2]);
115
-    void setBoundingBox(vec3_t box[2]);
116 121
     bool inBox(vec_t x, vec_t y, vec_t z);
117 122
     bool inBoxPlane(vec_t x, vec_t z);
118 123
 
119 124
     unsigned int sizeAdjacentRooms();
120 125
     int getAdjacentRoom(unsigned int index);
121
-    void addAdjacentRoom(int r);
122 126
 
123 127
     unsigned int sizePortals();
124 128
     Portal &getPortal(unsigned int index);
125
-    void addPortal(Portal &p);
126 129
 
127 130
     unsigned int sizeSectors();
128 131
     Sector &getSector(unsigned int index);
129
-    void addSector(Sector &s);
130 132
 
131 133
     unsigned int sizeBox();
132 134
     Box &getBox(unsigned int index);
133
-    void addBox(Box &b);
134 135
 
135 136
     unsigned int sizeModels();
136 137
     StaticModel &getModel(unsigned int index);
137
-    void addModel(StaticModel &m);
138 138
     void sortModels();
139 139
 
140 140
     unsigned int sizeLights();
141 141
     Light &getLight(unsigned int index);
142
-    void addLight(Light &l);
143 142
 
144 143
     unsigned int sizeSprites();
145 144
     Sprite &getSprite(unsigned int index);
146
-    void addSprite(Sprite &s);
147 145
 
148 146
     Mesh &getMesh();
149 147
 
150 148
 private:
151
-    int id;
152 149
     unsigned int flags;
153 150
     unsigned int numXSectors;
154 151
     unsigned int numZSectors;
155 152
     vec3_t pos;
156 153
     vec3_t bbox[2];
154
+    Mesh mesh;
157 155
 
158 156
     std::vector<int> adjacentRooms;
159 157
     std::vector<Sprite *> sprites;
@@ -161,11 +159,10 @@ private:
161 159
     std::vector<Portal *> portals;
162 160
     std::vector<Box *> boxes;
163 161
     std::vector<Sector *> sectors;
162
+    std::vector<Light *> lights;
164 163
 
165
-    // Was previously stored in RenderRoom
166
-    //vec_t dist;                  //!< Distance to near plane, move to room?
167
-    std::vector<Light *> lights; //!< List of lights in this room
168
-    Mesh mesh;                   //!< OpenGL mesh that represents this room
164
+    // Was used for "depth sorting" render list, but never assigned...?!
165
+    //vec_t dist; // Distance to near plane, move to room?
169 166
 };
170 167
 
171 168
 #endif

+ 4
- 1
include/Sprite.h View File

@@ -9,10 +9,12 @@
9 9
 #define _SPRITE_H_
10 10
 
11 11
 #include "math/math.h"
12
+#include "TombRaider.h"
12 13
 
13 14
 class Sprite {
14 15
 public:
15
-    Sprite(vec3_t _vertex[4], vec2_t _texel[4], vec3_t _pos, vec_t _radius, int _texture);
16
+    Sprite(TombRaider &tr, unsigned int room, unsigned int index);
17
+    Sprite(TombRaider &tr, unsigned int item, unsigned int sequence, unsigned int index);
16 18
     void display();
17 19
 
18 20
 private:
@@ -25,6 +27,7 @@ private:
25 27
 
26 28
 class SpriteSequence {
27 29
 public:
30
+    SpriteSequence(TombRaider &tr, unsigned int item, unsigned int sequence);
28 31
     ~SpriteSequence();
29 32
 
30 33
     void add(Sprite &s);

+ 1
- 1
include/ViewVolume.h View File

@@ -134,7 +134,7 @@ public:
134 134
      * \param max maximum point of a valid abstract bounding box
135 135
      * \returns distance to abstract box bounding volume
136 136
      */
137
-    vec_t getDistToBboxFromNear(vec3_t min, vec3_t max);
137
+    vec_t getDistToBboxFromNear(const vec3_t min, const vec3_t max);
138 138
 
139 139
     /*!
140 140
      * \brief Get a copy of the view volume

+ 2
- 2
include/math/math.h View File

@@ -51,7 +51,7 @@ int intersectionLinePolygon(vec3_t intersect, vec3_t p1, vec3_t p2, vec3_t *poly
51 51
  * \param b Second point
52 52
  * \returns distance/length
53 53
  */
54
-vec_t distance(vec3_t a, vec3_t b);
54
+vec_t distance(const vec3_t a, const vec3_t b);
55 55
 
56 56
 /*!
57 57
  * \brief Calculates the midpoint between two points / of a line segment
@@ -59,7 +59,7 @@ vec_t distance(vec3_t a, vec3_t b);
59 59
  * \param b Second point
60 60
  * \param mid Midpoint will be stored here
61 61
  */
62
-void midpoint(vec3_t a, vec3_t b, vec3_t mid);
62
+void midpoint(const vec3_t a, const vec3_t b, vec3_t mid);
63 63
 
64 64
 /*!
65 65
  * \brief Calculates a pseudo-random number

+ 12
- 586
src/Game.cpp View File

@@ -22,13 +22,6 @@
22 22
 
23 23
 #include "games/TombRaider1.h"
24 24
 
25
-// Old Code compatibility
26
-#define TexelScale 256.0f
27
-
28
-#ifndef EXPERIMENTAL_UNIFIED_ROOM_GEOMETERY
29
-#define TextureLimit 24
30
-#endif
31
-
32 25
 #ifdef EXPERIMENTAL
33 26
 std::vector<unsigned int> gColorTextureHACK;
34 27
 #endif
@@ -50,6 +43,14 @@ Game::~Game() {
50 43
     destroy();
51 44
 }
52 45
 
46
+unsigned int Game::getTextureStart() {
47
+    return mTextureStart;
48
+}
49
+
50
+unsigned int Game::getTextureOffset() {
51
+    return mTextureOffset;
52
+}
53
+
53 54
 int Game::initialize() {
54 55
     // Enable Renderer
55 56
     mTextureStart = getRender().initTextures(getOpenRaider().mDataDir);
@@ -170,600 +171,25 @@ void Game::handleMouseMotion(int xrel, int yrel) {
170 171
 }
171 172
 
172 173
 void Game::processSprites() {
173
-    float scale = 4.0f;
174
-    tr2_item_t *item = mTombRaider.Item();
175
-    tr2_sprite_texture_t *spriteTextures = mTombRaider.Sprite();
176
-    tr2_sprite_sequence_t *spriteSequence = mTombRaider.SpriteSequence();
177
-
178 174
     printf("Processing sprites: ");
179
-
180 175
     for (int i = 0; i < (mTombRaider.NumItems() - 1); i++) {
181
-        if ((mTombRaider.Engine() == TR_VERSION_1) && (item[i].intensity1 == -1))
176
+        if ((mTombRaider.Engine() == TR_VERSION_1) && (mTombRaider.Item()[i].intensity1 == -1))
182 177
             continue;
183 178
 
184
-        int id = item[i].object_id;
185 179
         for (int j = 0; j < mTombRaider.NumSpriteSequences(); j++) {
186
-            if (spriteSequence[j].object_id == id) {
187
-                SpriteSequence &sequence = *new SpriteSequence();
188
-                for (int k = 0; k < (-spriteSequence[j].negative_length); k++) {
189
-                    tr2_sprite_texture_t *sprite = &spriteTextures[spriteSequence[j].offset];
190
-
191
-                    int width = sprite->width >> 8;
192
-                    int height = sprite->height >> 8;
193
-                    int x = sprite->x;
194
-                    int y = sprite->y;
195
-                    int width2 = (int)(width * scale);
196
-                    int height2 = (int)(height * scale);
197
-
198
-                    vec3_t vertex[4];
199
-                    vec2_t texel[4];
200
-                    vec3_t pos;
201
-
202
-                    // For vising use
203
-                    pos[0] = item[i].x;
204
-                    pos[1] = item[i].y;
205
-                    pos[2] = item[i].z;
206
-
207
-                    vertex[0][0] = -width2 / 2.0f;
208
-                    vertex[1][0] = -width2 / 2.0f;
209
-                    vertex[2][0] = width2 / 2.0f;
210
-                    vertex[3][0] = width2 / 2.0f;
211
-
212
-                    vertex[0][1] = 0;
213
-                    vertex[1][1] = -height2;
214
-                    vertex[2][1] = -height2;
215
-                    vertex[3][1] = 0;
216
-
217
-                    vertex[0][2] = 0;
218
-                    vertex[1][2] = 0;
219
-                    vertex[2][2] = 0;
220
-                    vertex[3][2] = 0;
221
-
222
-                    texel[3][0] = (vec_t)(x+width)/TexelScale;
223
-                    texel[3][1] = (vec_t)(y+height)/TexelScale;
224
-
225
-                    texel[2][0] = (vec_t)(x+width)/TexelScale;
226
-                    texel[2][1] = (vec_t)(y)/TexelScale;
227
-
228
-                    texel[1][0] = (vec_t)(x) /TexelScale;
229
-                    texel[1][1] = (vec_t)(y) /TexelScale;
230
-
231
-                    texel[0][0] = (vec_t)(x) / TexelScale;
232
-                    texel[0][1] = (vec_t)(y+height)/TexelScale;
233
-
234
-                    sequence.add(*new Sprite(vertex, texel, pos, width2 / 2.0f, sprite->tile + mTextureStart));
235
-
236
-                    //printf(".");
237
-                    //fflush(stdout);
238
-                }
239
-                getWorld().addSprite(sequence);
240
-            }
180
+            if (mTombRaider.SpriteSequence()[j].object_id == mTombRaider.Item()[i].object_id)
181
+                getWorld().addSprite(*new SpriteSequence(mTombRaider, i, j));
241 182
         }
242 183
     }
243
-
244 184
     printf("Done! Found %d sprites.\n", mTombRaider.NumSpriteSequences());
245 185
 }
246 186
 
247 187
 void Game::processRooms() {
248 188
     printf("Processing rooms: ");
249
-
250 189
     for (int index = 0; index < mTombRaider.NumRooms(); index++) {
251
-        Matrix transform;
252
-        Room &room = *new Room(index);
253
-        getWorld().addRoom(room);
254
-
255
-        if (!mTombRaider.isRoomValid(index)) {
256
-            getConsole().print("WARNING: Handling invalid vertex array in room");
257
-            //printf("x");
258
-            //fflush(stdout);
259
-            //return; // ?
260
-            continue;
261
-        }
262
-
263
-        unsigned int flags;
264
-        vec3_t pos;
265
-        vec3_t bbox[2];
266
-        mTombRaider.getRoomInfo(index, &flags, pos, bbox[0], bbox[1]);
267
-        room.setFlags(flags);
268
-        room.setPos(pos);
269
-
270
-        // Adjust positioning for OR world coordinate translation
271
-        bbox[0][0] += pos[0];
272
-        bbox[1][0] += pos[0];
273
-        bbox[0][2] += pos[2];
274
-        bbox[1][2] += pos[2];
275
-
276
-        room.setBoundingBox(bbox);
277
-
278
-        // Mongoose 2002.04.03, Setup 3D transform
279
-        transform.setIdentity();
280
-        transform.translate(pos);
281
-
282
-        // Setup portals
283
-        float portalVertices[12];
284
-        unsigned int count = mTombRaider.getRoomPortalCount(index);
285
-
286
-        // Current room is always first
287
-        room.addAdjacentRoom(index);
288
-
289
-        for (unsigned int i = 0; i < count; i++) {
290
-            vec3_t vertices[4];
291
-            vec3_t normal;
292
-            int adjoiningRoom;
293
-            mTombRaider.getRoomPortal(index, i, &adjoiningRoom, normal, portalVertices);
294
-            for (unsigned int j = 0; j < 4; ++j) {
295
-                vertices[j][0] = portalVertices[j*3];
296
-                vertices[j][1] = portalVertices[j*3+1];
297
-                vertices[j][2] = portalVertices[j*3+2];
298
-
299
-                // Relative coors in vis portals
300
-                transform.multiply3v(vertices[j], vertices[j]);
301
-            }
302
-            Portal &portal = *new Portal(vertices, normal, adjoiningRoom);
303
-            room.addPortal(portal);
304
-            room.addAdjacentRoom(adjoiningRoom);
305
-        }
306
-
307
-        // Physics/gameplay use /////////////////////////////
308
-
309
-        //! \fixme Use more of sector structure, boxes, and floordata
310
-
311
-        // List of sectors in this room
312
-        unsigned int numXSectors, numZSectors;
313
-        count = mTombRaider.getRoomSectorCount(index, &numZSectors, &numXSectors);
314
-        room.setNumXSectors(numXSectors);
315
-        room.setNumZSectors(numZSectors);
316
-        for (unsigned int i = 0; i < count; i++) {
317
-            unsigned int sectorFlags;
318
-            int floorDataIndex, boxIndex, roomBelow, roomAbove;
319
-            vec_t floor, ceiling;
320
-            bool wall = false;
321
-
322
-            mTombRaider.getRoomSector(index, i, &sectorFlags,
323
-                    &ceiling, &floor, &floorDataIndex, &boxIndex,
324
-                    &roomBelow, &roomAbove);
325
-
326
-            if (sectorFlags & tombraiderSector_wall)
327
-                wall = true;
328
-
329
-            room.addSector(*new Sector(floor, ceiling, wall));
330
-        }
331
-
332
-        // Setup collision boxes
333
-        //! fixme Should use sectors, but this is a test
334
-        count = mTombRaider.getRoomBoxCount(index);
335
-
336
-        //! fixme Only to be done only on room[0]?  I don't think so...
337
-        for (unsigned int i = 0; !index && i < count; i++) {
338
-            vec3_t a, b, c, d;
339
-            mTombRaider.getRoomBox(index, i, a, b, c, d);
340
-            room.addBox(*new Box(a, b, c, d));
341
-        }
342
-
343
-        // Setup room lights /////////////////////////////////////
344
-        count = mTombRaider.getRoomLightCount(index);
345
-
346
-        for (unsigned int i = 0; i < count; i++) {
347
-            unsigned int lightFlags, lightType;
348
-            vec4_t position;
349
-            vec3_t dir;
350
-            vec_t att;
351
-            vec4_t color;
352
-            vec_t cutoff;
353
-            Light::LightType type;
354
-
355
-            mTombRaider.getRoomLight(index, i, position, color,
356
-                    dir, &att, &cutoff, &lightType, &lightFlags);
357
-
358
-            switch (lightType) {
359
-                case tombraiderLight_typeDirectional:
360
-                    type = Light::typeDirectional;
361
-                    break;
362
-                case tombraiderLight_typeSpot:
363
-                    type = Light::typeSpot;
364
-                    break;
365
-                case tombraiderLight_typePoint:
366
-                default:
367
-                    type = Light::typePoint;
368
-            }
369
-
370
-            room.addLight(*new Light(position, dir, att, color, cutoff, type));
371
-
372
-            //! \todo Light flags?
373
-        }
374
-
375
-        // Room geometery //////////////////////////////////
376
-
377
-//#define EXPERIMENTAL_UNIFIED_ROOM_GEOMETERY
378
-#ifdef EXPERIMENTAL_UNIFIED_ROOM_GEOMETERY
379
-        unsigned int vertexCount, normalCount, colorCount, triCount;
380
-        vec_t *vertexArray;
381
-        vec_t *normalArray;
382
-        vec_t *colorArray;
383
-        unsigned int *indices, *flags;
384
-        float *texCoords;
385
-        int *textures;
386
-
387
-        mTombRaider.getRoomVertexArrays(index,
388
-                &vertexCount, &vertexArray,
389
-                &normalCount, &normalArray,
390
-                &colorCount, &colorArray);
391
-
392
-        room.getMesh().bufferVertexArray(vertexCount, (vec_t *)vertexArray);
393
-        room.getMesh().bufferNormalArray(normalCount, (vec_t *)normalArray);
394
-        room.getMesh().bufferColorArray(vertexCount, (vec_t *)colorArray);
395
-
396
-        mTombRaider.getRoomTriangles(index, mTextureStart,
397
-                &triCount, &indices, &texCoords, &textures,
398
-                &flags);
399
-
400
-        room.getMesh().bufferTriangles(triCount, indices, texCoords, textures, flags);
401
-#else
402
-        float rgba[4];
403
-        float xyz[3];
404
-
405
-        count = mTombRaider.getRoomVertexCount(index);
406
-        room.getMesh().allocateVertices(count);
407
-        room.getMesh().allocateNormals(0); // count
408
-        room.getMesh().allocateColors(count);
409
-
410
-        for (unsigned int i = 0; i < count; ++i)
411
-        {
412
-            mTombRaider.getRoomVertex(index, i, xyz, rgba);
413
-
414
-            room.getMesh().setVertex(i, xyz[0], xyz[1], xyz[2]);
415
-            room.getMesh().setColor(i, rgba);
416
-        }
417
-
418
-        // Mongoose 2002.06.09, Setup allocation of meshes and polygons
419
-        // Counters ( Textured polygon lists are allocated per texture)
420
-        //          ( Textures are mapped to these meshes )
421
-        int triangle_counter[TextureLimit];
422
-        int triangle_counter_alpha[TextureLimit];
423
-        int rectangle_counter[TextureLimit];
424
-        int rectangle_counter_alpha[TextureLimit];
425
-        int tris_mesh_map[TextureLimit];
426
-        int rect_mesh_map[TextureLimit];
427
-
428
-        for (unsigned int i = 0; i < TextureLimit; ++i)
429
-        {
430
-            triangle_counter[i]        = 0;
431
-            triangle_counter_alpha[i]  = 0;
432
-            rectangle_counter[i]       = 0;
433
-            rectangle_counter_alpha[i] = 0;
434
-
435
-            tris_mesh_map[i] = -1;
436
-            rect_mesh_map[i] = -1;
437
-        }
438
-
439
-        unsigned int numTris = 0;
440
-        unsigned int numQuads = 0;
441
-
442
-        int texture;
443
-        unsigned int r, t, q, v;
444
-        unsigned int indices[4];
445
-        float texCoords[8];
446
-
447
-        count = mTombRaider.getRoomTriangleCount(index);
448
-
449
-        // Mongoose 2002.08.15, Presort by alpha and texture and setup mapping
450
-        for (t = 0; t < count; ++t)
451
-        {
452
-            mTombRaider.getRoomTriangle(index, t,
453
-                    indices, texCoords, &texture, &flags);
454
-
455
-            texture += mTextureStart;
456
-
457
-            if (texture > (int)TextureLimit)
458
-            {
459
-                getConsole().print("Handling bad room[%i].tris[%i].texture = %i",
460
-                        index, t, texture);
461
-                texture = TextureLimit - 1;
462
-            }
463
-
464
-            // Counters set up polygon allocation
465
-            if (flags & tombraiderFace_Alpha ||
466
-                    flags & tombraiderFace_PartialAlpha)
467
-            {
468
-                triangle_counter_alpha[texture] += 1;
469
-            }
470
-            else
471
-            {
472
-                triangle_counter[texture] += 1;
473
-            }
474
-
475
-            // Counter sets up texture id to mesh id mapping
476
-            if (tris_mesh_map[texture] == -1)
477
-            {
478
-                tris_mesh_map[texture] = ++numTris;
479
-            }
480
-        }
481
-
482
-        count = mTombRaider.getRoomRectangleCount(index);
483
-
484
-        for (r = 0; r < count; ++r)
485
-        {
486
-            mTombRaider.getRoomRectangle(index, r,
487
-                    indices, texCoords, &texture, &flags);
488
-
489
-            texture += mTextureStart;
490
-
491
-            if (texture > (int)TextureLimit)
492
-            {
493
-                getConsole().print("Handling bad room[%i].quad[%i].texture = %i",
494
-                        index, r, texture);
495
-                texture = TextureLimit - 1;
496
-            }
497
-
498
-            if (flags & tombraiderFace_Alpha ||
499
-                    flags & tombraiderFace_PartialAlpha)
500
-            {
501
-                rectangle_counter_alpha[texture] += 1;
502
-            }
503
-            else
504
-            {
505
-                rectangle_counter[texture] += 1;
506
-            }
507
-
508
-            if (rect_mesh_map[texture] == -1)
509
-            {
510
-                rect_mesh_map[texture] = ++numQuads;
511
-            }
512
-        }
513
-
514
-        // Allocate indexed polygon meshes
515
-        room.getMesh().allocateTriangles(numTris);
516
-        room.getMesh().allocateRectangles(numQuads);
517
-
518
-        for (unsigned int i = 0, j = 0; i < TextureLimit; ++i)
519
-        {
520
-            if (tris_mesh_map[i] > 0)
521
-            {
522
-                j = tris_mesh_map[i] - 1;
523
-
524
-                t = triangle_counter[i];
525
-
526
-                room.getMesh().mTris[j].texture = i;
527
-#ifdef MULTITEXTURE
528
-                room.getMesh().mTris[j].bumpmap = gMapTex2Bump[i];
529
-#endif
530
-                room.getMesh().mTris[j].cnum_triangles = 0;
531
-                room.getMesh().mTris[j].num_triangles = 0;
532
-                room.getMesh().mTris[j].cnum_alpha_triangles = 0;
533
-                room.getMesh().mTris[j].num_alpha_triangles = 0;
534
-                room.getMesh().mTris[j].triangles = 0x0;
535
-                room.getMesh().mTris[j].alpha_triangles = 0x0;
536
-                room.getMesh().mTris[j].texcoors = 0x0;
537
-                room.getMesh().mTris[j].texcoors2 = 0x0;
538
-
539
-                if (t > 0)
540
-                {
541
-                    room.getMesh().mTris[j].num_triangles = t;
542
-                    room.getMesh().mTris[j].triangles = new unsigned int[t*3];
543
-                    room.getMesh().mTris[j].num_texcoors = t * 3;
544
-                    room.getMesh().mTris[j].texcoors = new vec2_t[t * 3];
545
-                }
546
-
547
-                t = triangle_counter_alpha[i];
548
-
549
-                if (t > 0)
550
-                {
551
-                    room.getMesh().mTris[j].num_alpha_triangles = t;
552
-                    room.getMesh().mTris[j].alpha_triangles = new unsigned int[t*3];
553
-                    room.getMesh().mTris[j].num_texcoors2 = t * 3;
554
-                    room.getMesh().mTris[j].texcoors2 = new vec2_t[t * 3];
555
-                }
556
-            }
557
-
558
-            ///////////////////////////////////////////
559
-
560
-            if (rect_mesh_map[i] > 0)
561
-            {
562
-                j = rect_mesh_map[i] - 1;
563
-
564
-                r = rectangle_counter[i];
565
-
566
-                room.getMesh().mQuads[j].texture = i;
567
-#ifdef MULTITEXTURE
568
-                room.getMesh().mQuads[j].bumpmap = gMapTex2Bump[i];
569
-#endif
570
-                room.getMesh().mQuads[j].cnum_quads = 0;
571
-                room.getMesh().mQuads[j].num_quads = 0;
572
-                room.getMesh().mQuads[j].cnum_alpha_quads = 0;
573
-                room.getMesh().mQuads[j].num_alpha_quads = 0;
574
-                room.getMesh().mQuads[j].quads = 0x0;
575
-                room.getMesh().mQuads[j].alpha_quads = 0x0;
576
-                room.getMesh().mQuads[j].texcoors = 0x0;
577
-                room.getMesh().mQuads[j].texcoors2 = 0x0;
578
-
579
-                if (r > 0)
580
-                {
581
-                    room.getMesh().mQuads[j].num_quads = r;
582
-                    room.getMesh().mQuads[j].quads = new unsigned int[r*4];
583
-                    room.getMesh().mQuads[j].num_texcoors = r * 4;
584
-                    room.getMesh().mQuads[j].texcoors = new vec2_t[r * 4];
585
-                }
586
-
587
-                r = rectangle_counter_alpha[i];
588
-
589
-                if (r > 0)
590
-                {
591
-                    room.getMesh().mQuads[j].num_alpha_quads = r;
592
-                    room.getMesh().mQuads[j].alpha_quads = new unsigned int[r*4];
593
-                    room.getMesh().mQuads[j].num_texcoors2 = r * 4;
594
-                    room.getMesh().mQuads[j].texcoors2 = new vec2_t[r * 4];
595
-                }
596
-            }
597
-        }
598
-
599
-        // Generate textured triangles
600
-        count = mTombRaider.getRoomTriangleCount(index);
601
-
602
-        for (t = 0; t < count; ++t)
603
-        {
604
-            mTombRaider.getRoomTriangle(index, t,
605
-                    indices, texCoords, &texture, &flags);
606
-
607
-            // Adjust texture id using mTextureStart to map into
608
-            // correct textures
609
-            texture += mTextureStart;
610
-
611
-            unsigned int j = tris_mesh_map[texture] - 1;
612
-
613
-            // Setup per vertex
614
-            for (unsigned int i = 0; i < 3; ++i)
615
-            {
616
-                // Get vertex index {(0, a), (1, b), (2, c)}
617
-                v = indices[i];
618
-
619
-                if ((flags & tombraiderFace_Alpha ||
620
-                            flags & tombraiderFace_PartialAlpha) &&
621
-                        room.getMesh().mTris[j].num_alpha_triangles > 0)
622
-                {
623
-                    q = room.getMesh().mTris[j].cnum_alpha_triangles*3+i;
624
-
625
-                    room.getMesh().mTris[j].alpha_triangles[q] = v;
626
-
627
-                    room.getMesh().mTris[j].texcoors2[q][0] = texCoords[i*2];
628
-                    room.getMesh().mTris[j].texcoors2[q][1] = texCoords[i*2+1];
629
-                }
630
-                else if (room.getMesh().mTris[j].num_triangles > 0)
631
-                {
632
-                    q = room.getMesh().mTris[j].cnum_triangles*3+i;
633
-
634
-                    room.getMesh().mTris[j].triangles[q] = v;
635
-
636
-                    room.getMesh().mTris[j].texcoors[q][0] = texCoords[i*2];
637
-                    room.getMesh().mTris[j].texcoors[q][1] = texCoords[i*2+1];
638
-                }
639
-
640
-                // Partial alpha hack
641
-                if (flags & tombraiderFace_PartialAlpha)
642
-                {
643
-                    //room.getMesh().colors[v].rgba[3] = 0.45;
644
-                }
645
-            }
646
-
647
-            if (flags & tombraiderFace_Alpha ||
648
-                    flags & tombraiderFace_PartialAlpha)
649
-            {
650
-                room.getMesh().mTris[j].cnum_alpha_triangles++;
651
-            }
652
-            else
653
-            {
654
-                room.getMesh().mTris[j].cnum_triangles++;
655
-            }
656
-        }
657
-
658
-        // Generate textured quads
659
-        count = mTombRaider.getRoomRectangleCount(index);
660
-
661
-        for (r = 0; r < count; ++r)
662
-        {
663
-            mTombRaider.getRoomRectangle(index, r,
664
-                    indices, texCoords, &texture, &flags);
665
-
666
-            // Adjust texture id using mTextureStart to map into
667
-            // correct textures
668
-            texture += mTextureStart;
669
-
670
-            if (texture > (int)TextureLimit)
671
-            {
672
-                texture = TextureLimit - 1;
673
-            }
674
-
675
-            unsigned int j = rect_mesh_map[texture] - 1;
676
-
677
-            if (room.getMesh().mQuads[j].num_quads <= 0 &&
678
-                    room.getMesh().mQuads[j].num_alpha_quads <= 0)
679
-                continue;
680
-
681
-            // Setup per vertex
682
-            for (unsigned int i = 0; i < 4; ++i)
683
-            {
684
-                // Get vertex index {(0, a), (1, b), (2, c), (3, d)}
685
-                v = indices[i];
686
-
687
-                if ((flags & tombraiderFace_Alpha ||
688
-                            flags & tombraiderFace_PartialAlpha) &&
689
-                        room.getMesh().mQuads[j].num_alpha_quads > 0)
690
-                {
691
-                    q = room.getMesh().mQuads[j].cnum_alpha_quads*4+i;
692
-
693
-                    room.getMesh().mQuads[j].alpha_quads[q] = v;
694
-
695
-                    room.getMesh().mQuads[j].texcoors2[q][0] = texCoords[i*2];
696
-                    room.getMesh().mQuads[j].texcoors2[q][1] = texCoords[i*2+1];
697
-                }
698
-                else if (room.getMesh().mQuads[j].num_quads > 0)
699
-                {
700
-                    q = room.getMesh().mQuads[j].cnum_quads*4+i;
701
-
702
-                    room.getMesh().mQuads[j].quads[q] = v;
703
-
704
-                    room.getMesh().mQuads[j].texcoors[q][0] = texCoords[i*2];
705
-                    room.getMesh().mQuads[j].texcoors[q][1] = texCoords[i*2+1];
706
-                }
707
-
708
-                // Partial alpha hack
709
-                if (flags & tombraiderFace_PartialAlpha)
710
-                {
711
-                    //rRoom->mesh.colors[v].rgba[3] = 0.45;
712
-                }
713
-            }
714
-
715
-            if (flags & tombraiderFace_Alpha ||
716
-                    flags & tombraiderFace_PartialAlpha)
717
-            {
718
-                room.getMesh().mQuads[j].cnum_alpha_quads++;
719
-            }
720
-            else
721
-            {
722
-                room.getMesh().mQuads[j].cnum_quads++;
723
-            }
724
-        }
725
-#endif
726
-
727
-        // Room models
728
-        count = mTombRaider.getRoomModelCount(index);
729
-        for (unsigned int i = 0; i < count; i++) {
730
-            int ind;
731
-            vec_t yaw;
732
-            vec3_t position;
733
-            mTombRaider.getRoomModel(index, i, &ind, position, &yaw);
734
-            room.addModel(*new StaticModel(ind, yaw, position));
735
-        }
736
-
737
-        // Room sprites
738
-        count = mTombRaider.getRoomSpriteCount(index);
739
-        for (unsigned int i = 0; i < count; i++) {
740
-            float spriteVertices[12];
741
-            float spriteTexCoords[8];
742
-            vec3_t vertex[4];
743
-            vec2_t texel[4];
744
-            vec3_t position;
745
-            int tex;
746
-
747
-            mTombRaider.getRoomSprite(index, i,
748
-                    10.0f, &tex, position, spriteVertices, spriteTexCoords);
749
-
750
-            tex += mTextureStart; // OpenRaider preloads some textures
751
-
752
-            for (unsigned int j = 0; j < 12; j++)
753
-                vertex[j / 3][j % 3] = spriteVertices[j];
754
-
755
-            for (unsigned int j = 0; j < 8; j++)
756
-                texel[j / 2][j % 2] = spriteTexCoords[j];
757
-
758
-            room.addSprite(*new Sprite(vertex, texel, position, 0.0f, tex)); //! \fixme radius 0??
759
-        }
760
-
190
+        Room &room = *new Room(mTombRaider, index);
761 191
         getWorld().addRoom(room);
762
-
763
-        //printf(".");
764
-        //fflush(stdout);
765 192
     }
766
-
767 193
     printf("Done! Found %d rooms.\n", mTombRaider.NumRooms());
768 194
 }
769 195
 

+ 13
- 8
src/Render.cpp View File

@@ -197,16 +197,21 @@ void lightRoom(Room &room)
197 197
     for (unsigned int i = 0; i < room.sizeLights(); ++i)
198 198
     {
199 199
         Light &light = room.getLight(i);
200
+        vec4_t pos, color;
201
+        vec3_t dir;
202
+        light.getPos(pos);
203
+        light.getColor(color);
204
+        light.getDir(dir);
200 205
 
201 206
         glEnable(GL_LIGHT0 + i);
202 207
 
203
-        switch (light.mType)
208
+        switch (light.getType())
204 209
         {
205 210
             case Light::typeSpot:
206
-                glLightf(GL_LIGHT0 + i,  GL_SPOT_CUTOFF,    light.mCutoff);
207
-                glLightfv(GL_LIGHT0 + i, GL_POSITION,       light.mPos);
208
-                glLightfv(GL_LIGHT0 + i, GL_SPOT_DIRECTION, light.mDir);
209
-                glLightfv(GL_LIGHT0 + i, GL_DIFFUSE,        light.mColor);
211
+                glLightf(GL_LIGHT0 + i,  GL_SPOT_CUTOFF,    light.getCutoff());
212
+                glLightfv(GL_LIGHT0 + i, GL_POSITION,       pos);
213
+                glLightfv(GL_LIGHT0 + i, GL_SPOT_DIRECTION, dir);
214
+                glLightfv(GL_LIGHT0 + i, GL_DIFFUSE,        color);
210 215
                 break;
211 216
             case Light::typePoint:
212 217
             case Light::typeDirectional:
@@ -214,10 +219,10 @@ void lightRoom(Room &room)
214 219
 
215 220
                 // GL_QUADRATIC_ATTENUATION
216 221
                 // GL_LINEAR_ATTENUATION
217
-                glLightf(GL_LIGHT0 + i, GL_LINEAR_ATTENUATION, light.mAtt);
222
+                glLightf(GL_LIGHT0 + i, GL_LINEAR_ATTENUATION, light.getAtt());
218 223
 
219
-                glLightfv(GL_LIGHT0 + i, GL_DIFFUSE, light.mColor); // GL_DIFFUSE
220
-                glLightfv(GL_LIGHT0 + i, GL_POSITION, light.mPos);
224
+                glLightfv(GL_LIGHT0 + i, GL_DIFFUSE, color); // GL_DIFFUSE
225
+                glLightfv(GL_LIGHT0 + i, GL_POSITION, pos);
221 226
                 break;
222 227
         }
223 228
     }

+ 491
- 105
src/Room.cpp View File

@@ -19,23 +19,65 @@
19 19
 #include "main.h"
20 20
 #include "Room.h"
21 21
 
22
-Light::Light(vec4_t pos, vec3_t dir, vec_t att, vec4_t color, vec_t cutoff, LightType type) {
23
-    for (unsigned int i = 0; i < 4; i++) {
24
-        mPos[i] = pos[i];
25
-        mColor[i] = color[i];
26
-        if (i < 3)
27
-            mDir[i] = dir[i];
22
+#ifndef EXPERIMENTAL_UNIFIED_ROOM_GEOMETERY
23
+#define TextureLimit 24
24
+#endif
25
+
26
+Light::Light(TombRaider &tr, unsigned int room, unsigned int index) {
27
+    unsigned int lightFlags, lightType;
28
+
29
+    tr.getRoomLight(room, index, pos, color,
30
+            dir, &att, &cutoff, &lightType, &lightFlags);
31
+
32
+    switch (lightType) {
33
+        case tombraiderLight_typeDirectional:
34
+            type = Light::typeDirectional;
35
+            break;
36
+        case tombraiderLight_typeSpot:
37
+            type = Light::typeSpot;
38
+            break;
39
+        case tombraiderLight_typePoint:
40
+        default:
41
+            type = Light::typePoint;
28 42
     }
29
-    mAtt = att;
30
-    mCutoff = cutoff;
31
-    mType = type;
43
+
44
+    //! \todo Light flags?
32 45
 }
33 46
 
34
-StaticModel::StaticModel(int _index, vec_t _yaw, vec3_t _pos) {
35
-    index = _index;
36
-    yaw = _yaw;
37
-    for (unsigned int i = 0; i < 3; i++)
38
-        pos[i] = _pos[i];
47
+void Light::getPos(vec4_t p) {
48
+    p[0] = pos[0];
49
+    p[1] = pos[1];
50
+    p[2] = pos[2];
51
+    p[3] = pos[3];
52
+}
53
+
54
+void Light::getDir(vec3_t d) {
55
+    d[0] = dir[0];
56
+    d[1] = dir[1];
57
+    d[2] = dir[2];
58
+}
59
+
60
+vec_t Light::getAtt() {
61
+    return att;
62
+}
63
+
64
+void Light::getColor(vec4_t c) {
65
+    c[0] = color[0];
66
+    c[1] = color[1];
67
+    c[2] = color[2];
68
+    c[3] = color[3];
69
+}
70
+
71
+vec_t Light::getCutoff() {
72
+    return cutoff;
73
+}
74
+
75
+Light::LightType Light::getType() {
76
+    return type;
77
+}
78
+
79
+StaticModel::StaticModel(TombRaider &tr, unsigned int room, unsigned int i) {
80
+    tr.getRoomModel(room, i, &index, pos, &yaw);
39 81
 }
40 82
 
41 83
 void StaticModel::display() {
@@ -64,15 +106,17 @@ bool StaticModel::operator<(const StaticModel &other) {
64 106
     return (distA < distB);
65 107
 }
66 108
 
67
-Portal::Portal(vec3_t _vertices[4], vec3_t _normal, int _adjoiningRoom) {
68
-    for (unsigned int i = 0; i < 3; i++) {
69
-        vertices[0][i] = _vertices[0][i];
70
-        vertices[1][i] = _vertices[1][i];
71
-        vertices[2][i] = _vertices[2][i];
72
-        vertices[3][i] = _vertices[3][i];
73
-        normal[i] = _normal[i];
109
+Portal::Portal(TombRaider &tr, unsigned int room, unsigned int index, Matrix &transform) {
110
+    float portalVertices[12];
111
+    tr.getRoomPortal(room, index, &adjoiningRoom, normal, portalVertices);
112
+    for (unsigned int j = 0; j < 4; ++j) {
113
+        vertices[j][0] = portalVertices[j*3];
114
+        vertices[j][1] = portalVertices[j*3+1];
115
+        vertices[j][2] = portalVertices[j*3+2];
116
+
117
+        // Relative coors in vis portals
118
+        transform.multiply3v(vertices[j], vertices[j]);
74 119
     }
75
-    adjoiningRoom = _adjoiningRoom;
76 120
 }
77 121
 
78 122
 void Portal::getVertices(vec3_t vert[4]) {
@@ -87,19 +131,19 @@ int Portal::getAdjoiningRoom() {
87 131
     return adjoiningRoom;
88 132
 }
89 133
 
90
-Box::Box(vec3_t _a, vec3_t _b, vec3_t _c, vec3_t _d) {
91
-    for (unsigned int i = 0; i < 3; i++) {
92
-        a[i] = _a[i];
93
-        b[i] = _b[i];
94
-        c[i] = _c[i];
95
-        d[i] = _d[i];
96
-    }
134
+Box::Box(TombRaider &tr, unsigned int room, unsigned int index) {
135
+    tr.getRoomBox(room, index, a, b, c, d);
97 136
 }
98 137
 
99
-Sector::Sector(vec_t _floor, vec_t _ceiling, bool _wall) {
100
-    floor = _floor;
101
-    ceiling = _ceiling;
102
-    wall = _wall;
138
+Sector::Sector(TombRaider &tr, unsigned int room, unsigned int index) {
139
+    unsigned int sectorFlags;
140
+    int floorDataIndex, boxIndex, roomBelow, roomAbove;
141
+
142
+    tr.getRoomSector(room, index, &sectorFlags,
143
+            &ceiling, &floor, &floorDataIndex, &boxIndex,
144
+            &roomBelow, &roomAbove);
145
+
146
+    wall = (sectorFlags & tombraiderSector_wall);
103 147
 }
104 148
 
105 149
 vec_t Sector::getFloor() {
@@ -114,68 +158,444 @@ bool Sector::isWall() {
114 158
     return wall;
115 159
 }
116 160
 
117
-Room::Room(int _id) {
118
-    id = _id;
119
-    flags = 0;
120
-    numXSectors = 0;
121
-    numZSectors = 0;
122
-    pos[0] = pos[1] = pos[2] = 0.0f;
123
-    bbox[0][0] = bbox[0][1] = bbox[0][2] = 0.0f;
124
-    bbox[1][0] = bbox[1][1] = bbox[1][2] = 0.0f;
125
-}
161
+Room::Room(TombRaider &tr, unsigned int index) {
162
+    Matrix transform;
126 163
 
127
-Room::~Room() {
128
-    unsigned long i;
164
+    if (!tr.isRoomValid(index)) {
165
+        getConsole().print("WARNING: Handling invalid vertex array in room");
166
+        //printf("x");
167
+        //fflush(stdout);
168
+        return;
169
+    }
129 170
 
130
-    for (i = 0; i < sprites.size(); i++)
131
-        delete sprites[i];
171
+    tr.getRoomInfo(index, &flags, pos, bbox[0], bbox[1]);
132 172
 
133
-    for (i = 0; i < models.size(); i++)
134
-        delete models[i];
173
+    // Adjust positioning for OR world coordinate translation
174
+    bbox[0][0] += pos[0];
175
+    bbox[1][0] += pos[0];
176
+    bbox[0][2] += pos[2];
177
+    bbox[1][2] += pos[2];
135 178
 
136
-    for (i = 0; i < portals.size(); i++)
137
-        delete portals[i];
179
+    // Mongoose 2002.04.03, Setup 3D transform
180
+    transform.setIdentity();
181
+    transform.translate(pos);
138 182
 
139
-    for (i = 0; i < boxes.size(); i++)
140
-        delete boxes[i];
183
+    // Current room is always first
184
+    adjacentRooms.push_back(index);
141 185
 
142
-    for (i = 0; i < sectors.size(); i++)
143
-        delete sectors[i];
186
+    // Setup portals
187
+    unsigned int count = tr.getRoomPortalCount(index);
188
+    for (unsigned int i = 0; i < count; i++) {
189
+        portals.push_back(new Portal(tr, index, i, transform));
190
+        adjacentRooms.push_back(portals.back()->getAdjoiningRoom());
191
+    }
144 192
 
145
-    for (i = 0; i < lights.size(); i++) {
146
-        delete lights[i];
193
+    //! \fixme Use more of sector structure, boxes, and floordata
194
+
195
+    // List of sectors in this room
196
+    count = tr.getRoomSectorCount(index, &numZSectors, &numXSectors);
197
+    for (unsigned int i = 0; i < count; i++)
198
+        sectors.push_back(new Sector(tr, index, i));
199
+
200
+    // Setup collision boxes
201
+    //! fixme Should use sectors, but this is a test
202
+    count = tr.getRoomBoxCount(index);
203
+    for (unsigned int i = 0; i < count; i++)
204
+        boxes.push_back(new Box(tr, index, i));
205
+
206
+    // Setup room lights
207
+    count = tr.getRoomLightCount(index);
208
+    for (unsigned int i = 0; i < count; i++)
209
+        lights.push_back(new Light(tr, index, i));
210
+
211
+    // Room models
212
+    count = tr.getRoomModelCount(index);
213
+    for (unsigned int i = 0; i < count; i++)
214
+        models.push_back(new StaticModel(tr, index, i));
215
+
216
+    // Room sprites
217
+    count = tr.getRoomSpriteCount(index);
218
+    for (unsigned int i = 0; i < count; i++)
219
+        sprites.push_back(new Sprite(tr, index, i));
220
+
221
+//#define EXPERIMENTAL_UNIFIED_ROOM_GEOMETERY
222
+#ifdef EXPERIMENTAL_UNIFIED_ROOM_GEOMETERY
223
+    unsigned int vertexCount, normalCount, colorCount, triCount;
224
+    vec_t *vertexArray;
225
+    vec_t *normalArray;
226
+    vec_t *colorArray;
227
+    unsigned int *indices, *flags;
228
+    float *texCoords;
229
+    int *textures;
230
+
231
+    tr.getRoomVertexArrays(index,
232
+            &vertexCount, &vertexArray,
233
+            &normalCount, &normalArray,
234
+            &colorCount, &colorArray);
235
+
236
+    mesh.bufferVertexArray(vertexCount, (vec_t *)vertexArray);
237
+    mesh.bufferNormalArray(normalCount, (vec_t *)normalArray);
238
+    mesh.bufferColorArray(vertexCount, (vec_t *)colorArray);
239
+
240
+    tr.getRoomTriangles(index, getGame().getTextureStart(),
241
+            &triCount, &indices, &texCoords, &textures,
242
+            &flags);
243
+
244
+    mesh.bufferTriangles(triCount, indices, texCoords, textures, flags);
245
+#else
246
+    float rgba[4];
247
+    float xyz[3];
248
+
249
+    count = tr.getRoomVertexCount(index);
250
+    mesh.allocateVertices(count);
251
+    mesh.allocateNormals(0); // count
252
+    mesh.allocateColors(count);
253
+
254
+    for (unsigned int i = 0; i < count; ++i)
255
+    {
256
+        tr.getRoomVertex(index, i, xyz, rgba);
257
+
258
+        mesh.setVertex(i, xyz[0], xyz[1], xyz[2]);
259
+        mesh.setColor(i, rgba);
147 260
     }
261
+
262
+    // Mongoose 2002.06.09, Setup allocation of meshes and polygons
263
+    // Counters ( Textured polygon lists are allocated per texture)
264
+    //          ( Textures are mapped to these meshes )
265
+    int triangle_counter[TextureLimit];
266
+    int triangle_counter_alpha[TextureLimit];
267
+    int rectangle_counter[TextureLimit];
268
+    int rectangle_counter_alpha[TextureLimit];
269
+    int tris_mesh_map[TextureLimit];
270
+    int rect_mesh_map[TextureLimit];
271
+
272
+    for (unsigned int i = 0; i < TextureLimit; ++i)
273
+    {
274
+        triangle_counter[i]        = 0;
275
+        triangle_counter_alpha[i]  = 0;
276
+        rectangle_counter[i]       = 0;
277
+        rectangle_counter_alpha[i] = 0;
278
+
279
+        tris_mesh_map[i] = -1;
280
+        rect_mesh_map[i] = -1;
281
+    }
282
+
283
+    unsigned int numTris = 0;
284
+    unsigned int numQuads = 0;
285
+
286
+    int texture;
287
+    unsigned int r, t, q, v;
288
+    unsigned int indices[4];
289
+    float texCoords[8];
290
+
291
+    count = tr.getRoomTriangleCount(index);
292
+
293
+    // Mongoose 2002.08.15, Presort by alpha and texture and setup mapping
294
+    for (t = 0; t < count; ++t)
295
+    {
296
+        tr.getRoomTriangle(index, t,
297
+                indices, texCoords, &texture, &flags);
298
+
299
+        texture += getGame().getTextureStart();
300
+
301
+        if (texture > (int)TextureLimit)
302
+        {
303
+            getConsole().print("Handling bad room[%i].tris[%i].texture = %i",
304
+                    index, t, texture);
305
+            texture = TextureLimit - 1;
306
+        }
307
+
308
+        // Counters set up polygon allocation
309
+        if (flags & tombraiderFace_Alpha ||
310
+                flags & tombraiderFace_PartialAlpha)
311
+        {
312
+            triangle_counter_alpha[texture] += 1;
313
+        }
314
+        else
315
+        {
316
+            triangle_counter[texture] += 1;
317
+        }
318
+
319
+        // Counter sets up texture id to mesh id mapping
320
+        if (tris_mesh_map[texture] == -1)
321
+        {
322
+            tris_mesh_map[texture] = ++numTris;
323
+        }
324
+    }
325
+
326
+    count = tr.getRoomRectangleCount(index);
327
+
328
+    for (r = 0; r < count; ++r)
329
+    {
330
+        tr.getRoomRectangle(index, r,
331
+                indices, texCoords, &texture, &flags);
332
+
333
+        texture += getGame().getTextureStart();
334
+
335
+        if (texture > (int)TextureLimit)
336
+        {
337
+            getConsole().print("Handling bad room[%i].quad[%i].texture = %i",
338
+                    index, r, texture);
339
+            texture = TextureLimit - 1;
340
+        }
341
+
342
+        if (flags & tombraiderFace_Alpha ||
343
+                flags & tombraiderFace_PartialAlpha)
344
+        {
345
+            rectangle_counter_alpha[texture] += 1;
346
+        }
347
+        else
348
+        {
349
+            rectangle_counter[texture] += 1;
350
+        }
351
+
352
+        if (rect_mesh_map[texture] == -1)
353
+        {
354
+            rect_mesh_map[texture] = ++numQuads;
355
+        }
356
+    }
357
+
358
+    // Allocate indexed polygon meshes
359
+    mesh.allocateTriangles(numTris);
360
+    mesh.allocateRectangles(numQuads);
361
+
362
+    for (unsigned int i = 0, j = 0; i < TextureLimit; ++i)
363
+    {
364
+        if (tris_mesh_map[i] > 0)
365
+        {
366
+            j = tris_mesh_map[i] - 1;
367
+
368
+            t = triangle_counter[i];
369
+
370
+            mesh.mTris[j].texture = i;
371
+#ifdef MULTITEXTURE
372
+            mesh.mTris[j].bumpmap = gMapTex2Bump[i];
373
+#endif
374
+            mesh.mTris[j].cnum_triangles = 0;
375
+            mesh.mTris[j].num_triangles = 0;
376
+            mesh.mTris[j].cnum_alpha_triangles = 0;
377
+            mesh.mTris[j].num_alpha_triangles = 0;
378
+            mesh.mTris[j].triangles = 0x0;
379
+            mesh.mTris[j].alpha_triangles = 0x0;
380
+            mesh.mTris[j].texcoors = 0x0;
381
+            mesh.mTris[j].texcoors2 = 0x0;
382
+
383
+            if (t > 0)
384
+            {
385
+                mesh.mTris[j].num_triangles = t;
386
+                mesh.mTris[j].triangles = new unsigned int[t*3];
387
+                mesh.mTris[j].num_texcoors = t * 3;
388
+                mesh.mTris[j].texcoors = new vec2_t[t * 3];
389
+            }
390
+
391
+            t = triangle_counter_alpha[i];
392
+
393
+            if (t > 0)
394
+            {
395
+                mesh.mTris[j].num_alpha_triangles = t;
396
+                mesh.mTris[j].alpha_triangles = new unsigned int[t*3];
397
+                mesh.mTris[j].num_texcoors2 = t * 3;
398
+                mesh.mTris[j].texcoors2 = new vec2_t[t * 3];
399
+            }
400
+        }
401
+
402
+        ///////////////////////////////////////////
403
+
404
+        if (rect_mesh_map[i] > 0)
405
+        {
406
+            j = rect_mesh_map[i] - 1;
407
+
408
+            r = rectangle_counter[i];
409
+
410
+            mesh.mQuads[j].texture = i;
411
+#ifdef MULTITEXTURE
412
+            mesh.mQuads[j].bumpmap = gMapTex2Bump[i];
413
+#endif
414
+            mesh.mQuads[j].cnum_quads = 0;
415
+            mesh.mQuads[j].num_quads = 0;
416
+            mesh.mQuads[j].cnum_alpha_quads = 0;
417
+            mesh.mQuads[j].num_alpha_quads = 0;
418
+            mesh.mQuads[j].quads = 0x0;
419
+            mesh.mQuads[j].alpha_quads = 0x0;
420
+            mesh.mQuads[j].texcoors = 0x0;
421
+            mesh.mQuads[j].texcoors2 = 0x0;
422
+
423
+            if (r > 0)
424
+            {
425
+                mesh.mQuads[j].num_quads = r;
426
+                mesh.mQuads[j].quads = new unsigned int[r*4];
427
+                mesh.mQuads[j].num_texcoors = r * 4;
428
+                mesh.mQuads[j].texcoors = new vec2_t[r * 4];
429
+            }
430
+
431
+            r = rectangle_counter_alpha[i];
432
+
433
+            if (r > 0)
434
+            {
435
+                mesh.mQuads[j].num_alpha_quads = r;
436
+                mesh.mQuads[j].alpha_quads = new unsigned int[r*4];
437
+                mesh.mQuads[j].num_texcoors2 = r * 4;
438
+                mesh.mQuads[j].texcoors2 = new vec2_t[r * 4];
439
+            }
440
+        }
441
+    }
442
+
443
+    // Generate textured triangles
444
+    count = tr.getRoomTriangleCount(index);
445
+
446
+    for (t = 0; t < count; ++t)
447
+    {
448
+        tr.getRoomTriangle(index, t,
449
+                indices, texCoords, &texture, &flags);
450
+
451
+        // Adjust texture id using getGame().getTextureStart() to map into
452
+        // correct textures
453
+        texture += getGame().getTextureStart();
454
+
455
+        unsigned int j = tris_mesh_map[texture] - 1;
456
+
457
+        // Setup per vertex
458
+        for (unsigned int i = 0; i < 3; ++i)
459
+        {
460
+            // Get vertex index {(0, a), (1, b), (2, c)}
461
+            v = indices[i];
462
+
463
+            if ((flags & tombraiderFace_Alpha ||
464
+                        flags & tombraiderFace_PartialAlpha) &&
465
+                    mesh.mTris[j].num_alpha_triangles > 0)
466
+            {
467
+                q = mesh.mTris[j].cnum_alpha_triangles*3+i;
468
+
469
+                mesh.mTris[j].alpha_triangles[q] = v;
470
+
471
+                mesh.mTris[j].texcoors2[q][0] = texCoords[i*2];
472
+                mesh.mTris[j].texcoors2[q][1] = texCoords[i*2+1];
473
+            }
474
+            else if (mesh.mTris[j].num_triangles > 0)
475
+            {
476
+                q = mesh.mTris[j].cnum_triangles*3+i;
477
+
478
+                mesh.mTris[j].triangles[q] = v;
479
+
480
+                mesh.mTris[j].texcoors[q][0] = texCoords[i*2];
481
+                mesh.mTris[j].texcoors[q][1] = texCoords[i*2+1];
482
+            }
483
+
484
+            // Partial alpha hack
485
+            if (flags & tombraiderFace_PartialAlpha)
486
+            {
487
+                //mesh.colors[v].rgba[3] = 0.45;
488
+            }
489
+        }
490
+
491
+        if (flags & tombraiderFace_Alpha ||
492
+                flags & tombraiderFace_PartialAlpha)
493
+        {
494
+            mesh.mTris[j].cnum_alpha_triangles++;
495
+        }
496
+        else
497
+        {
498
+            mesh.mTris[j].cnum_triangles++;
499
+        }
500
+    }
501
+
502
+    // Generate textured quads
503
+    count = tr.getRoomRectangleCount(index);
504
+
505
+    for (r = 0; r < count; ++r)
506
+    {
507
+        tr.getRoomRectangle(index, r,
508
+                indices, texCoords, &texture, &flags);
509
+
510
+        // Adjust texture id using getGame().getTextureStart() to map into
511
+        // correct textures
512
+        texture += getGame().getTextureStart();
513
+
514
+        if (texture > (int)TextureLimit)
515
+        {
516
+            texture = TextureLimit - 1;
517
+        }
518
+
519
+        unsigned int j = rect_mesh_map[texture] - 1;
520
+
521
+        if (mesh.mQuads[j].num_quads <= 0 &&
522
+                mesh.mQuads[j].num_alpha_quads <= 0)
523
+            continue;
524
+
525
+        // Setup per vertex
526
+        for (unsigned int i = 0; i < 4; ++i)
527
+        {
528
+            // Get vertex index {(0, a), (1, b), (2, c), (3, d)}
529
+            v = indices[i];
530
+
531
+            if ((flags & tombraiderFace_Alpha ||
532
+                        flags & tombraiderFace_PartialAlpha) &&
533
+                    mesh.mQuads[j].num_alpha_quads > 0)
534
+            {
535
+                q = mesh.mQuads[j].cnum_alpha_quads*4+i;
536
+
537
+                mesh.mQuads[j].alpha_quads[q] = v;
538
+
539
+                mesh.mQuads[j].texcoors2[q][0] = texCoords[i*2];
540
+                mesh.mQuads[j].texcoors2[q][1] = texCoords[i*2+1];
541
+            }
542
+            else if (mesh.mQuads[j].num_quads > 0)
543
+            {
544
+                q = mesh.mQuads[j].cnum_quads*4+i;
545
+
546
+                mesh.mQuads[j].quads[q] = v;
547
+
548
+                mesh.mQuads[j].texcoors[q][0] = texCoords[i*2];
549
+                mesh.mQuads[j].texcoors[q][1] = texCoords[i*2+1];
550
+            }
551
+
552
+            // Partial alpha hack
553
+            if (flags & tombraiderFace_PartialAlpha)
554
+            {
555
+                //rRoom->mesh.colors[v].rgba[3] = 0.45;
556
+            }
557
+        }
558
+
559
+        if (flags & tombraiderFace_Alpha ||
560
+                flags & tombraiderFace_PartialAlpha)
561
+        {
562
+            mesh.mQuads[j].cnum_alpha_quads++;
563
+        }
564
+        else
565
+        {
566
+            mesh.mQuads[j].cnum_quads++;
567
+        }
568
+    }
569
+#endif
148 570
 }
149 571
 
150
-void Room::setFlags(unsigned int f) {
151
-    flags = f;
572
+#define EMPTY_VECTOR(x)     \
573
+while (!x.empty()) {        \
574
+    delete x[x.size() - 1]; \
575
+    x.pop_back();           \
152 576
 }
153 577
 
154
-unsigned int Room::getFlags() {
155
-    return flags;
578
+Room::~Room() {
579
+    EMPTY_VECTOR(sprites);
580
+    EMPTY_VECTOR(models);
581
+    EMPTY_VECTOR(portals);
582
+    EMPTY_VECTOR(boxes);
583
+    EMPTY_VECTOR(sectors);
584
+    EMPTY_VECTOR(lights);
156 585
 }
157 586
 
158
-void Room::setNumXSectors(unsigned int n) {
159
-     numXSectors = n;
587
+unsigned int Room::getFlags() {
588
+    return flags;
160 589
 }
161 590
 
162 591
 unsigned int Room::getNumXSectors() {
163 592
     return numXSectors;
164 593
 }
165 594
 
166
-void Room::setNumZSectors(unsigned int n) {
167
-    numZSectors = n;
168
-}
169
-
170 595
 unsigned int Room::getNumZSectors() {
171 596
     return numZSectors;
172 597
 }
173 598
 
174
-void Room::setPos(vec3_t p) {
175
-    for (unsigned int i = 0; i < 3; i++)
176
-        pos[i] = p[i];
177
-}
178
-
179 599
 void Room::getPos(vec3_t p) {
180 600
     for (unsigned int i = 0; i < 3; i++)
181 601
         p[i] = pos[i];
@@ -187,12 +607,6 @@ void Room::getBoundingBox(vec3_t box[2]) {
187 607
             box[i][j] = bbox[i][j];
188 608
 }
189 609
 
190
-void Room::setBoundingBox(vec3_t box[2]) {
191
-    for (unsigned int i = 0; i < 2; i++)
192
-        for (unsigned int j = 0; j < 3; j++)
193
-            bbox[i][j] = box[i][j];
194
-}
195
-
196 610
 bool Room::inBox(vec_t x, vec_t y, vec_t z) {
197 611
     return ((y > bbox[0][1]) && (y < bbox[1][1]) && inBoxPlane(x, z));
198 612
 }
@@ -211,10 +625,6 @@ int Room::getAdjacentRoom(unsigned int index) {
211 625
     return adjacentRooms.at(index);
212 626
 }
213 627
 
214
-void Room::addAdjacentRoom(int r) {
215
-    adjacentRooms.push_back(r);
216
-}
217
-
218 628
 unsigned int Room::sizePortals() {
219 629
     return portals.size();
220 630
 }
@@ -224,10 +634,6 @@ Portal &Room::getPortal(unsigned int index) {
224 634
     return *portals.at(index);
225 635
 }
226 636
 
227
-void Room::addPortal(Portal &p) {
228
-    portals.push_back(&p);
229
-}
230
-
231 637
 unsigned int Room::sizeSectors() {
232 638
     return sectors.size();
233 639
 }
@@ -237,10 +643,6 @@ Sector &Room::getSector(unsigned int index) {
237 643
     return *sectors.at(index);
238 644
 }
239 645
 
240
-void Room::addSector(Sector &s) {
241
-    sectors.push_back(&s);
242
-}
243
-
244 646
 unsigned int Room::sizeBox() {
245 647
     return boxes.size();
246 648
 }
@@ -250,10 +652,6 @@ Box &Room::getBox(unsigned int index) {
250 652
     return *boxes.at(index);
251 653
 }
252 654
 
253
-void Room::addBox(Box &b) {
254
-    boxes.push_back(&b);
255
-}
256
-
257 655
 unsigned int Room::sizeModels() {
258 656
     return models.size();
259 657
 }
@@ -263,10 +661,6 @@ StaticModel &Room::getModel(unsigned int index) {
263 661
     return *models.at(index);
264 662
 }
265 663
 
266
-void Room::addModel(StaticModel &m) {
267
-    models.push_back(&m);
268
-}
269
-
270 664
 void Room::sortModels() {
271 665
     std::sort(models.begin(), models.end());
272 666
 }
@@ -280,10 +674,6 @@ Light &Room::getLight(unsigned int index) {
280 674
     return *lights.at(index);
281 675
 }
282 676
 
283
-void Room::addLight(Light &l) {
284
-    lights.push_back(&l);
285
-}
286
-
287 677
 unsigned int Room::sizeSprites() {
288 678
     return sprites.size();
289 679
 }
@@ -293,10 +683,6 @@ Sprite &Room::getSprite(unsigned int index) {
293 683
     return *sprites.at(index);
294 684
 }
295 685
 
296
-void Room::addSprite(Sprite &s) {
297
-    sprites.push_back(&s);
298
-}
299
-
300 686
 Mesh &Room::getMesh() {
301 687
     return mesh;
302 688
 }

+ 73
- 18
src/Sprite.cpp View File

@@ -16,6 +16,11 @@
16 16
 #include "main.h"
17 17
 #include "Sprite.h"
18 18
 
19
+SpriteSequence::SpriteSequence(TombRaider &tr, unsigned int item, unsigned int sequence) {
20
+    for (int i = 0; i < (-tr.SpriteSequence()[sequence].negative_length); i++)
21
+        add(*new Sprite(tr, item, sequence, i));
22
+}
23
+
19 24
 SpriteSequence::~SpriteSequence() {
20 25
     for (unsigned int i = 0; i < sprites.size(); i++)
21 26
         delete &sprites.at(i);
@@ -33,27 +38,77 @@ Sprite &SpriteSequence::get(unsigned int index) {
33 38
     return *sprites.at(index);
34 39
 }
35 40
 
36
-Sprite::Sprite(vec3_t _vertex[4], vec2_t _texel[4], vec3_t _pos, vec_t _radius, int _texture) {
37
-    radius = _radius;
38
-    texture = _texture;
39
-    for (unsigned int i = 0; i < 3; i++) {
40
-        vertex[0][i] = _vertex[0][i];
41
-        vertex[1][i] = _vertex[1][i];
42
-        vertex[2][i] = _vertex[2][i];
43
-        vertex[3][i] = _vertex[3][i];
44
-        pos[i] = _pos[i];
45
-        if (i < 2) {
46
-            texel[0][i] = _texel[0][i];
47
-            texel[1][i] = _texel[1][i];
48
-            texel[2][i] = _texel[2][i];
49
-            texel[3][i] = _texel[3][i];
50
-        }
51
-    }
41
+Sprite::Sprite(TombRaider &tr, unsigned int item, unsigned int sequence, unsigned int index) {
42
+    tr2_item_t *i = tr.Item();
43
+    tr2_sprite_texture_t *spriteTextures = tr.Sprite();
44
+    tr2_sprite_sequence_t *spriteSequence = tr.SpriteSequence();
45
+
46
+    //! \fixme index was unused?!
47
+    tr2_sprite_texture_t *sprite = &spriteTextures[spriteSequence[sequence].offset + index];
48
+
49
+    int width = sprite->width >> 8;
50
+    int height = sprite->height >> 8;
51
+    int x = sprite->x;
52
+    int y = sprite->y;
53
+    float scale = 4.0f;
54
+    float texelScale = 256.0f;
55
+    int width2 = (int)(width * scale);
56
+    int height2 = (int)(height * scale);
57
+
58
+    // For vising use
59
+    pos[0] = i[item].x;
60
+    pos[1] = i[item].y;
61
+    pos[2] = i[item].z;
62
+
63
+    vertex[0][0] = -width2 / 2.0f;
64
+    vertex[1][0] = -width2 / 2.0f;
65
+    vertex[2][0] = width2 / 2.0f;
66
+    vertex[3][0] = width2 / 2.0f;
67
+
68
+    vertex[0][1] = 0;
69
+    vertex[1][1] = -height2;
70
+    vertex[2][1] = -height2;
71
+    vertex[3][1] = 0;
72
+
73
+    vertex[0][2] = 0;
74
+    vertex[1][2] = 0;
75
+    vertex[2][2] = 0;
76
+    vertex[3][2] = 0;
77
+
78
+    texel[3][0] = (vec_t)(x+width)/texelScale;
79
+    texel[3][1] = (vec_t)(y+height)/texelScale;
80
+
81
+    texel[2][0] = (vec_t)(x+width)/texelScale;
82
+    texel[2][1] = (vec_t)(y)/texelScale;
83
+
84
+    texel[1][0] = (vec_t)(x) /texelScale;
85
+    texel[1][1] = (vec_t)(y) /texelScale;
86
+
87
+    texel[0][0] = (vec_t)(x) / texelScale;
88
+    texel[0][1] = (vec_t)(y+height)/texelScale;
89
+
90
+    texture = sprite->tile + getGame().getTextureStart();
91
+    radius = width2 / 2.0f;
92
+}
93
+
94
+Sprite::Sprite(TombRaider &tr, unsigned int room, unsigned int index) {
95
+    float spriteVertices[12];
96
+    float spriteTexCoords[8];
97
+
98
+    tr.getRoomSprite(room, index,
99
+            10.0f, &texture, pos, spriteVertices, spriteTexCoords);
100
+
101
+    texture += getGame().getTextureStart(); // OpenRaider preloads some textures
102
+
103
+    for (unsigned int j = 0; j < 12; j++)
104
+        vertex[j / 3][j % 3] = spriteVertices[j];
105
+
106
+    for (unsigned int j = 0; j < 8; j++)
107
+        texel[j / 2][j % 2] = spriteTexCoords[j];
52 108
 }
53 109
 
54 110
 void Sprite::display() {
55
-    if (!getRender().isVisible(pos[0], pos[1], pos[2],
56
-                radius))
111
+    if (!getRender().isVisible(pos[0], pos[1], pos[2], radius))
57 112
         return;
58 113
 
59 114
     glPushMatrix();

+ 1
- 1
src/ViewVolume.cpp View File

@@ -113,7 +113,7 @@ vec_t ViewVolume::getDistToSphereFromNear(vec_t x, vec_t y, vec_t z, vec_t radiu
113 113
     return d + radius;
114 114
 }
115 115
 
116
-vec_t ViewVolume::getDistToBboxFromNear(vec3_t min, vec3_t max) {
116
+vec_t ViewVolume::getDistToBboxFromNear(const vec3_t min, const vec3_t max) {
117 117
     vec3_t center;
118 118
     vec_t d, radius;
119 119
 

+ 2
- 2
src/math/math.cpp View File

@@ -75,13 +75,13 @@ int intersectionLinePolygon(vec3_t intersect,
75 75
     return 1;
76 76
 }
77 77
 
78
-vec_t distance(vec3_t a, vec3_t b) {
78
+vec_t distance(const vec3_t a, const vec3_t b) {
79 79
     return sqrtf(((b[0] - a[0]) * (b[0] - a[0])) +
80 80
                  ((b[1] - a[1]) * (b[1] - a[1])) +
81 81
                  ((b[2] - a[2]) * (b[2] - a[2])));
82 82
 }
83 83
 
84
-void midpoint(vec3_t a, vec3_t b, vec3_t mid) {
84
+void midpoint(const vec3_t a, const vec3_t b, vec3_t mid) {
85 85
     mid[0] = (a[0] + b[0]) / 2.0f;
86 86
     mid[1] = (a[1] + b[1]) / 2.0f;
87 87
     mid[2] = (a[2] + b[2]) / 2.0f;

Loading…
Cancel
Save