1 /*
2     GL-117
3     Copyright 2001, 2002 Thomas A. Drexl aka heptargon
4 
5     This file is part of GL-117.
6 
7     GL-117 is free software; you can redistribute it and/or modify
8     it under the terms of the GNU General Public License as published by
9     the Free Software Foundation; either version 2 of the License, or
10     (at your option) any later version.
11 
12     GL-117 is distributed in the hope that it will be useful,
13     but WITHOUT ANY WARRANTY; without even the implied warranty of
14     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15     GNU General Public License for more details.
16 
17     You should have received a copy of the GNU General Public License
18     along with GL-117; if not, write to the Free Software
19     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
20 */
21 
22 /* This file includes the memory representation of any 3D model. */
23 
24 #ifndef IS_MODEL_H
25 #define IS_MODEL_H
26 
27 #include "common.h" // ok
28 
29 #include "vertexarray.h" // ok
30 
31 /* Currently models are normalized to the (-1,-1,-1)-(1,1,1) cube and static!
32    The model represents the "class" description of a static model's geometry and colors.
33    It is "instanciated" using a DynamicObj which has a reference to the model,
34    scaling, rotation, translation, physical attributes...
35    A model consists of several objects.
36    Objects consist of vertices, quads, triangles, and one material. */
37 
38 // CColor stores color information
39 class CColor
40 {
41   public:
42   unsigned char c [4]; // color information as vector, 32 bpp (floats would be faster for the vertex arrays)
43   CColor ();
44   CColor (CColor *col);
45   CColor (short cr, short cg, short cb);
46   CColor (short cr, short cg, short cb, short ca);
47   ~CColor ();
48   void setColor (CColor *col);
49   void setColor (short cr, short cg, short cb, short ca);
50   void setColor (short cr, short cg, short cb);
51   bool isEqual (CColor *col); // compare colors
52   void take (CColor *col); // copy data from col
53 };
54 
55 // CTexture loads and stores a texture to memory
56 // To use a texture, it must be loaded and added to the OpenGL texture list using
57 //   gl->genTextureTGA();
58 // instead of this class!
59 class CTexture
60 {
61   public:
62   unsigned char *data; // texture color data as array, 32 bpp (RGBA? => see tga loader)
63   char name [256]; // texture file name
64   bool mipmap; // mipmapping on/off depending on gluBuildMipmaps
65   int textureID; // texture ID of native GL code
66   int width, height;
67   // average values to substitute textured quads by colors for LOD:
68   float texlight; // average of texture's overall brightness
69   float texred; // average of texture's red
70   float texgreen; // average of texture's green
71   float texblue; // average of texture's blue
72   int quality; // texture quality of native GL code
73   bool alpha; // alpha blending necessary
74   CTexture ();
75   ~CTexture ();
76   int loadFromTGA (char *fname, int quality, int alphatype, int mipmap); // called via gl->genTextureTGA()
77   void getColor (CColor *c, int x, int y); // color of a special pixel
78 };
79 
80 // CVector3 stores the components of a 3D vector (x,y,z)
81 class CVector3
82 {
83   public:
84   float x, y, z; // coordinates, float on most systems faster than double
85   CVector3 ();
86   CVector3 (float x, float y, float z);
87   CVector3 (CVector3 *v);
88   void set (float x, float y, float z);
89   void neg ();
90   void add (CVector3 *v);
91   void sub (CVector3 *v);
92   void mul (float fac);
93   void crossproduct (CVector3 *v);
94   float dotproduct (CVector3 *v);
95   float length ();
96   void norm ();
97   bool isEqual (CVector3 *v); // exactly equal in memory (no sense for comparisons)
98   bool isEqual (CVector3 *v, float tol); // numerically equal, use a tolerance like 1E-8
99   void take (CVector3 *v); // copy data from v
100 };
101 
102 // CVector2 stores the components of a 2D vector, for texture purpose
103 class CVector2
104 {
105   public:
106   float x, y; // coordinates
107   void take (CVector2 *v); // copy data from v
108   bool isEqual (CVector2 *v); // exactly equal in memory (no sense for comparisons)
109   bool isEqual (CVector2 *v, float tol); // numerically equal, use a tolerance like 1E-8
110 };
111 
112 // CVertex represents a vertex which may take inforamtion about color, location, normal, texture, number of surrounding triangles
113 class CVertex
114 {
115   public:
116   int triangles; // number of triangles this vertex belongs to
117   CColor color; // color, used when displayed without textures
118   CVector3 vector; // coordinates
119   CVector3 normal; // normal vector interpolated of all surrounding triangles
120   CVector2 tex; // 2D texture coordinates
121   CVertex ();
122   CVertex (CVertex *v);
123   void addNormal (CVector3 *n); // the normal vector of a vertex can be calculated as average of all adjacent plane normals
124   void addColor (CColor *c); // the color of a vertex can be calculated as average of all adjacent plane colors
125   void take (CVertex *v); // copy data from v
126 };
127 
128 extern double pitab; // pi=atan(1)
129 extern float sintab [360], costab [360]; // table for sine, cosine functions (obsolete, use COS(), SIN() instead)
130 
131 // CRotation stores one (x,y,z)-rotation
132 class CRotation
133 {
134   private:
135   float rot [3] [3]; // rotation matrix
136   public:
137   short a, b, c; // rotation angles for each plane of the carthesian cosy
138   CRotation ();
139   ~CRotation ();
140   void setAngles (short a, short b, short c);
141   void addAngles (short a, short b, short c);
142   void calcRotation ();
143   float rotateX (CVector3 *v);
144   float rotateY (CVector3 *v);
145   float rotateZ (CVector3 *v);
146   float getsintab (int a);
147   float getcostabntab (int a);
148   void take (CRotation *r);
149 };
150 
151 // CTriangle stores references to the vertices of the triangle/face
152 class CTriangle
153 {
154   public:
155   CVertex *v [3]; // references to the three vertices
156   void getNormal (CVector3 *n);
157   void setVertices (CVertex *a, CVertex *b, CVertex *c);
158 };
159 
160 // CQuad stores references to the vertices of the quad/square/face
161 class CQuad
162 {
163   public:
164   CVertex *v [4]; // references to the four vertices
165   void getNormal (CVector3 *n);
166   void setVertices (CVertex *a, CVertex *b, CVertex *c, CVertex *d);
167 };
168 
169 // CMaterial stores the name, filename, color, and texture of a material
170 class CMaterial
171 {
172   public:
173   char name [255]; // unique name
174   char filename [255]; // unique file name
175   CColor color; // uniform color
176   CTexture *texture; // reference to a texture (or NULL if there is no texture)
177   float utile; // tiling coordinates
178   float vtile;
179   float uoffset; // texture offsets (the importer must calculate u/v due to offsets)
180   float voffset;
181   float uscale; // texture scaling (the importer must calculate u/v due to scaling)
182   float vscale;
183   float wrot; // rotation in degree (the importer must calculate u/v due to wrot)
184   CMaterial ();
185 };
186 
187 // CObject stores the material, vertices, and faces (triangles, quads) of an object
188 class CObject
189 {
190   public:
191   Uint16 numVertices;
192   Uint16 numTriangles;
193   Uint16 numQuads;
194   Uint16 numTexVertex;
195   CMaterial *material; // an object has one unique material
196   bool hasTexture; // an object can have one unique texture
197   char name [255]; // unique object name
198   CVertex *vertex; // vertex list
199   CTriangle *triangle; // triangle list
200   CQuad *quad; // quad list
201   CObject ();
202   ~CObject ();
203   int addVertex (CVertex *w); // used to construct objects
204   void setColor (CColor *col);
205 };
206 
207 // CModel stores the materials and objects of a model, the data structure is optimized for 3DS files
208 class CModel
209 {
210   private:
211   // all private members are only used "temporarily" at runtime!
212   int rotcol; // very special for flickering light sources, e.g. the engine's bright yellow color is rotated
213   float light_ambient [4]; // special light source attributes
214   float light_diffuse [4];
215   float light_ambient2 [4];
216   float light_diffuse2 [4];
217   CVector3 tlnull;
218   CRotation rotnull;
219   VertexArray *va; // using a vertex array means more memory, but better performance
220 
221   public:
222   char name [20]; // unique model name like "GL-117"
223   int shading; // shading can be set to FLAT (0) or SMOOTH/GOURAUD (1)
224   Uint16 numObjects; // number of objects (which have a unique material)
225   Uint16 numMaterials; // number of materials (should be the same as the number of objects)
226   bool displaylist; // enable using a display list
227   CMaterial *material [100]; // materials, at most 100 (these are only pointers)
228   CObject *object [100]; // objects, at most 100 (these are only pointers)
229   bool nolight; // do not use light?
230   bool alpha; // use alpha blending?
231   int numRefpoints; // reference points for missiles
232   CVector3 *refpoint; // obsolete
233   float scale, scalex, scaley, scalez; // overall scaling of original 3DS coords
234   // Note: the model is stored to (-1,-1,-1)-(1,1,1) in RAM, the SpaceObj tells about the scaling of a model
235   float cubex, cubey, cubez; // surrounding cube (or radius of sphere) for simplified collision detection
236   int list1, list2, list3; // display lists already generated for each type of draw() method
237 
238   CModel ();
239   void setName (char *name);
240   void addMaterial (CMaterial *material);
241   void addObject (CObject *object);
242   void addRefPoint (CVector3 *tl);
243   ~CModel ();
244   void setColor (CColor *col);
245   void drawVertexNormals (CObject *cm, float zoom);
246   int rotateColor (int n);
247   void scaleTexture (float fx, float fy);
248   // the drawing methods take the following parameters:
249   // tl+tl2=translation, rot=rotation, lum=luminance (default 1.0), explode=radial translation (default 0)
250   // draw everything
251   void draw (CVector3 *tl, CVector3 *tl2, CRotation *rot, float zoom, float lum, int explode);
252   // draw without GL lighting
253   void draw2 (CVector3 *tl, CVector3 *tl2, CRotation *rot, float zoom, int explode);
254   // draw without textures
255   void draw3 (CVector3 *tl, CVector3 *tl2, CRotation *rot, float zoom, int explode);
256   // draw without textures, different luminance
257   void draw3 (CVector3 *tl, CVector3 *tl2, CRotation *rot, float zoom, float lum, int explode);
258 };
259 
260 // CSphere represents an ellipsoid according to the CModel data structure
261 class CSphere : public CModel
262 {
263   private:
264   int random (int n);
265   public:
266   int segments; // segments on lateral angle, doubled for longitudinal angle
267   float radius;
268   float dx, dy, dz; // ellipsoid measures in the carthesian cosy
269   CSphere ();
270   CSphere (float radius, int segments, float dx, float dy, float dz);
271   ~CSphere ();
272   void init (float radius, int segments);
273   void init (float radius, int segments, float dx, float dy, float dz, int randomized);
274   void invertNormals (); // point outside/inside
275   void setNorthPoleColor (CColor *c, float w); // see setPoleColor, phi=0, theta=90
276   void setSouthPoleColor (CColor *c, float w);
277   void setPoleColor (int phi, int theta, CColor *c, float w); // shade color over any pole
278 };
279 
280 // Part of an ellipsoid
281 class CSpherePart : public CModel
282 {
283   public:
284   int segments; // segments on lateral angle, doubled for longitudinal angle
285   float radius;
286   CSpherePart ();
287   CSpherePart (float radius, int segments, float phi);
288   ~CSpherePart ();
289   void init (float radius, int segments);
290   void init (float radius, int segments, float phi);
291   void setNorthPoleColor (CColor *c, float w); // see setPoleColor, phi=0, theta=90
292   void setSouthPoleColor (CColor *c, float w);
293   void setPoleColor (int phi, int theta, CColor *c, float w); // shade color over any pole
294 };
295 
296 // More models could be added here, esp. for importing complex non-polygonal formats (obj, wrl)
297 
298 #endif
299