ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/libgender/util.h
Revision: 1.61
Committed: Tue Nov 23 18:32:39 2004 UTC (19 years, 6 months ago) by root
Content type: text/plain
Branch: MAIN
Changes since 1.60: +14 -48 lines
Log Message:
*** empty log message ***

File Contents

# User Rev Content
1 root 1.1 #ifndef UTIL_H
2     #define UTIL_H
3    
4 root 1.7 #include <cmath>
5 root 1.27 #include <cfloat>
6 root 1.39 #include <cstdlib>
7 root 1.1 #include <vector>
8 root 1.22 #include <string>
9 root 1.1
10 root 1.37 #include "opengl.h"
11 root 1.18
12 root 1.37 #include <SDL/SDL_image.h>
13 root 1.30
14 root 1.1 using namespace std;
15 root 1.18
16 root 1.36 typedef long long soffs; // 32 bit
17     typedef unsigned long long uoffs;
18 root 1.39 #define OFFS_BITS 63
19 root 1.36 #define SOFFS_MIN (soffs)-(1LL << (OFFS_BITS - 2))
20     #define SOFFS_MAX (soffs)+(1LL << (OFFS_BITS - 2))
21     #define MAXEXTENT (1ULL << (OFFS_BITS - 1))
22 root 1.1
23 root 1.39 #define ABS(n) ((n) < 0 ? -(n) : (n))
24    
25 root 1.37 struct sector
26     {
27 root 1.32 soffs x, y, z;
28    
29     sector (soffs x, soffs y, soffs z) : x(x), y(y), z(z) { };
30     sector (soffs xyz = 0) : x(xyz), y(xyz), z(xyz) { };
31     };
32    
33     inline sector operator +(const sector &a, const sector &b)
34     {
35     return sector (a.x + b.x, a.y + b.y, a.z + b.z);
36     }
37    
38     inline sector operator -(const sector &a, const sector &b)
39     {
40     return sector (a.x - b.x, a.y - b.y, a.z - b.z);
41     }
42    
43     inline sector operator /(const sector &a, soffs b)
44     {
45     return sector (a.x / b, a.y / b, a.z / b);
46     }
47    
48 root 1.40 inline sector operator >>(const sector &a, unsigned int b)
49     {
50     return sector (a.x >> b, a.y >> b, a.z >> b);
51     }
52    
53 root 1.32 inline bool operator <=(const sector &a, const sector &b)
54     {
55     return a.x <= b.x && a.y <= b.y && a.z <= b.z;
56     }
57    
58     inline soffs max (const sector &a)
59     {
60     return max (a.x, max (a.y, a.z));
61     }
62    
63     inline sector translate (const sector &p, const sector &src, const sector &dst)
64     {
65     return p + (dst - src);
66     }
67    
68     inline sector abs (const sector &s)
69     {
70 root 1.39 return sector (ABS (s.x), ABS (s.y), ABS (s.z));
71 root 1.32 }
72 root 1.1
73 root 1.51 struct vec2
74     {
75     GLfloat x, y;
76     vec2 () { };
77     vec2 (GLfloat s) : x(s), y(s) { };
78     vec2 (GLfloat x, GLfloat y) : x(x), y(y) { };
79     };
80    
81 root 1.57 inline const vec2 operator +(const vec2 &a, const vec2 &b)
82     {
83     return vec2 (a.x + b.x, a.y + b.y);
84     }
85    
86     inline const vec2 operator -(const vec2 &a, const vec2 &b)
87     {
88     return vec2 (a.x - b.x, a.y - b.y);
89     }
90    
91 root 1.37 struct vec3
92     {
93 root 1.1 GLfloat x, y, z;
94     vec3 () { };
95 root 1.32 vec3 (GLfloat s) : x(s), y(s), z(s) { };
96 root 1.1 vec3 (GLfloat x, GLfloat y, GLfloat z) : x(x), y(y), z(z) { };
97 root 1.32 vec3 (const sector &s) : x(s.x), y(s.y), z(s.z) { };
98 root 1.1
99     const vec3 operator -() const
100     { return vec3 (-x, -y, -z); }
101     };
102    
103     const vec3 normalize (const vec3 &v);
104     const vec3 cross (const vec3 &a, const vec3 &b);
105 root 1.6
106     inline const vec3 operator *(const vec3 &a, GLfloat s)
107     {
108     return vec3 (a.x * s, a.y * s, a.z * s);
109     }
110    
111 root 1.27 inline const vec3 operator +(const vec3 &a, const vec3 &b)
112     {
113     return vec3 (a.x + b.x, a.y + b.y, a.z + b.z);
114     }
115    
116     inline const vec3 operator -(const vec3 &a, const vec3 &b)
117     {
118     return vec3 (a.x - b.x, a.y - b.y, a.z - b.z);
119     }
120    
121 root 1.6 inline GLfloat dot (const vec3 &a, const vec3 &b)
122     {
123     return a.x * b.x + a.y * b.y + a.z * b.z;
124     }
125    
126 root 1.45 // squared length
127     inline const GLfloat length2 (const vec3 &v)
128 root 1.6 {
129 root 1.45 return dot (v, v);
130     }
131    
132     inline const GLfloat length (const vec3 &v)
133     {
134     return sqrtf (length2 (v));
135 root 1.6 }
136 root 1.1
137 root 1.10 typedef vec3 point;
138 root 1.51
139     struct vec4
140     {
141     GLfloat x, y, z, w;
142     vec4 () { };
143     vec4 (GLfloat s) : x(s), y(s), z(s), w(s) { };
144     vec4 (GLfloat x, GLfloat y, GLfloat z, GLfloat w) : x(x), y(y), z(z), w(w) { };
145 root 1.53 vec4 (const vec3 &v, GLfloat w = 1.F) : x(v.x), y(v.y), z(v.z), w(w) { };
146 root 1.51 };
147 root 1.10
148     // a generic plane
149 root 1.37 struct plane
150     {
151 root 1.10 vec3 n;
152     GLfloat d;
153    
154     plane () { };
155     plane (GLfloat a, GLfloat b, GLfloat c, GLfloat d);
156     };
157 root 1.45
158     inline GLfloat distance (const plane &a, const point &p)
159     {
160     return dot (a.n, p) + a.d;
161     }
162    
163     struct sphere {
164     point p;
165     GLfloat r;
166    
167     sphere () { };
168     sphere (const point &p, GLfloat r) : p(p), r(r) { };
169     };
170    
171     inline bool overlap (const sphere &a, const sphere &b)
172     {
173     GLfloat d = a.r + b.r;
174    
175     return length2 (a.p - b.p) <= d * d;
176     }
177    
178     struct cone {
179     point p;
180     vec3 a; // axis
181 root 1.47 GLfloat f, fs1, fc2; // angle
182 root 1.45
183     cone () { };
184     cone (const point &p, const vec3 &a, GLfloat f)
185     : p(p), a(a), f(f)
186     {
187 root 1.46 fs1 = 1.F / sinf (f);
188 root 1.47 fc2 = cosf (f); fc2 *= fc2;
189 root 1.45 };
190     };
191    
192     inline bool overlap (const cone &c, const sphere &s)
193     {
194 root 1.46 vec3 d = s.p - c.p + c.a * (s.r * c.fs1);
195 root 1.47 GLfloat dd = dot (c.a, d);
196 root 1.58 return dd > 0.F && dd * dd >= length2 (d) * c.fc2;
197 root 1.45 }
198 root 1.10
199     void renormalize (sector &s, point &p);
200    
201 root 1.37 struct colour
202     {
203 root 1.40 GLubyte r, g, b, a;
204     colour (GLfloat r = 1., GLfloat g = 1., GLfloat b = 1., GLfloat a = 1.)
205     : r(GLubyte (r * 255.F + .5F))
206     , g(GLubyte (g * 255.F + .5F))
207     , b(GLubyte (b * 255.F + .5F))
208     , a(GLubyte (a * 255.F + .5F))
209     {
210     }
211 root 1.10 };
212 root 1.5
213 root 1.40 struct tex2
214 root 1.37 {
215 root 1.1 GLfloat s, t;
216 root 1.40 tex2 () { };
217     tex2 (GLfloat s, GLfloat t) : s(s), t(t) { };
218 root 1.1 };
219 root 1.57
220     inline const tex2 operator +(const tex2 &a, const tex2 &b)
221     {
222     return tex2 (a.s + b.s, a.t + b.t);
223     }
224    
225     inline const tex2 operator -(const tex2 &a, const tex2 &b)
226     {
227     return tex2 (a.s - b.s, a.t - b.t);
228     }
229    
230     inline const tex2 operator *(const tex2 &a, GLfloat s)
231     {
232     return tex2 (a.s * s, a.t * s);
233     }
234 root 1.1
235 root 1.52 template<typename vectype> class vector_traits { };
236    
237     template<>
238     struct vector_traits<vec2>
239     {
240     typedef GLfloat basetype;
241     static const int dimension () { return 2; }
242     };
243    
244     template<>
245     struct vector_traits<vec3>
246     {
247     typedef GLfloat basetype;
248     static const int dimension () { return 3; }
249     };
250    
251     template<>
252     struct vector_traits<vec4>
253     {
254     typedef GLfloat basetype;
255     static const int dimension () { return 4; }
256     };
257    
258     template<>
259     struct vector_traits<tex2>
260     {
261     typedef GLfloat basetype;
262     static const int dimension () { return 2; }
263     };
264    
265     template<>
266     struct vector_traits<colour>
267     {
268     typedef GLubyte basetype;
269     static const int dimension () { return 4; }
270     };
271    
272 root 1.37 struct box
273     {
274 root 1.27 point a, b;
275 root 1.8
276     box() { };
277 root 1.1
278     void reset ()
279     {
280 root 1.27 a = point ( FLT_MAX, FLT_MAX, FLT_MAX);
281     b = point (-FLT_MAX, -FLT_MAX, -FLT_MAX);
282 root 1.1 }
283    
284     void add (const box &o);
285     void add (const point &p);
286     };
287 root 1.5
288 root 1.27 struct entity;
289     struct geometry;
290 root 1.20 struct view;
291 root 1.32 struct octant;
292 root 1.7
293 root 1.37 extern struct timer
294     {
295 root 1.7 static double now;
296     static double diff;
297 root 1.44 static double fps;
298 root 1.7
299     static void frame ();
300     timer ();
301     } timer;
302 root 1.11
303 root 1.13 /*
304 root 1.11 #define MAX_EVENT_TYPES 10
305     enum event_type { TIMER_EV };
306 root 1.37 struct event
307     {
308 root 1.11 event_type type;
309     };
310    
311     typedef callback1<void, event&> event_cb;
312    
313 root 1.37 class skedjuhlar
314     {
315 root 1.11 public:
316     // only 10 types for now
317     private:
318     vector <list<event_cb> > event_lists;
319    
320     public:
321     skedjuhlar () {
322     event_lists.resize (MAX_EVENT_TYPES, list<event_cb>());
323     }
324    
325     void register_event_cb (const event_type &t, const event_cb &e) {
326     event_lists[t].push_back (e);
327     };
328     void send_event (event &e) {
329     list<event_cb> &l = event_lists[e.type];
330     for (list<event_cb>::iterator it = l.begin (); it != l.end (); it++) {
331     (*it)(e);
332     }
333     };
334     void check_events () {
335     while (!events.empty ()) {
336     event &e = events.pop_front ();
337     list<event_cb> &l = event_lists[e->name];
338     for (list<event_cb>::iterator it = l.begin (); it !+ l.end (); it++) {
339     (*it)(e);
340     }
341     delete e; // ugly slow? hai hai..... 183G
342     }
343     }
344     };
345    
346     extern skedjuhlar main_scheduler;
347 root 1.13 */
348 root 1.22
349 root 1.37 namespace gl
350     {
351 root 1.41 #ifdef DEBUG
352     void errchk (const char *name, const char *args, const char *file, int line);
353     #endif
354    
355 root 1.40 struct vertex_v3f
356     {
357 root 1.56 point v; // vertex
358 root 1.40
359     vertex_v3f () { };
360 root 1.56 vertex_v3f (point v) : v(v) { };
361 root 1.40 };
362    
363     struct vertex_t2f_n3f_v3f
364     {
365     tex2 t; // texture
366     vec3 n; // normal
367 root 1.56 point v; // vertex
368 root 1.40
369 root 1.48 vertex_t2f_n3f_v3f () { }
370 root 1.56 vertex_t2f_n3f_v3f (point v, vec3 n, tex2 t = tex2()) : v(v), n(n), t(t) { }
371     };
372 root 1.40
373 root 1.56 template<typename unused> class type_traits { };
374    
375     template<> struct type_traits<GLfloat > { static const GLenum glenum () { return GL_FLOAT; } };
376     template<> struct type_traits<GLdouble> { static const GLenum glenum () { return GL_DOUBLE; } };
377     template<> struct type_traits<GLint > { static const GLenum glenum () { return GL_INT; } };
378     template<> struct type_traits<GLuint > { static const GLenum glenum () { return GL_UNSIGNED_INT; } };
379     template<> struct type_traits<GLshort > { static const GLenum glenum () { return GL_SHORT; } };
380     template<> struct type_traits<GLushort> { static const GLenum glenum () { return GL_UNSIGNED_SHORT; } };
381     template<> struct type_traits<GLbyte > { static const GLenum glenum () { return GL_BYTE; } };
382     template<> struct type_traits<GLubyte > { static const GLenum glenum () { return GL_UNSIGNED_BYTE; } };
383     template<> struct type_traits<vertex_v3f > { static const GLenum glenum () { return GL_V3F; } };
384     template<> struct type_traits<vertex_t2f_n3f_v3f> { static const GLenum glenum () { return GL_T2F_N3F_V3F; } };
385    
386     template<GLenum unused> class enum_traits { };
387    
388     template<> struct enum_traits<GL_FLOAT > { typedef GLfloat type; };
389     template<> struct enum_traits<GL_DOUBLE > { typedef GLdouble type; };
390     template<> struct enum_traits<GL_INT > { typedef GLint type; };
391     template<> struct enum_traits<GL_UNSIGNED_INT > { typedef GLuint type; };
392     template<> struct enum_traits<GL_SHORT > { typedef GLshort type; };
393     template<> struct enum_traits<GL_UNSIGNED_SHORT> { typedef GLushort type; };
394     template<> struct enum_traits<GL_BYTE > { typedef GLbyte type; };
395     template<> struct enum_traits<GL_UNSIGNED_BYTE > { typedef GLubyte type; };
396     template<> struct enum_traits<GL_V3F > { typedef vertex_v3f type; };
397     template<> struct enum_traits<GL_T2F_N3F_V3F > { typedef vertex_t2f_n3f_v3f type; };
398 root 1.34
399 root 1.56 // deprecated:
400 root 1.49 GLsizei format_stride (GLenum format);
401     GLsizei format_offset_p (GLenum format);
402     GLsizei format_offset_n (GLenum format);
403     GLsizei format_offset_t (GLenum format);
404    
405 root 1.41 struct matrix
406     {
407     GLfloat data[4][4];
408    
409     const GLfloat operator ()(int i, int j) const { return data[j][i]; };
410     GLfloat &operator ()(int i, int j) { return data[j][i]; };
411    
412     operator GLfloat *() { return &data[0][0]; }
413    
414     void diagonal (GLfloat v);
415     void clear () { diagonal (0.F); };
416     void identity () { diagonal (1.F); };
417    
418     void print (); // ugly
419    
420 root 1.54 static matrix translation (const vec3 &v);
421     static matrix rotation (GLfloat degrees, const vec3 &axis);
422     static matrix scaling (GLfloat sx, GLfloat sy, GLfloat sz, GLfloat w = 1.F);
423 root 1.41
424     matrix () { };
425     matrix (GLfloat diag) { diagonal (diag); };
426     };
427    
428 root 1.54 matrix operator *(const matrix &a, const matrix &b);
429     vec3 operator *(const matrix &a, const vec3 &v);
430 root 1.40
431 root 1.48 template<GLenum target>
432 root 1.56 struct vertex_buffer_object
433     {
434 root 1.40 GLuint buffer;
435     GLenum format;
436 root 1.52 GLsizei count;
437 root 1.56 GLsizei size;
438 root 1.40
439 root 1.48 bool alloc ()
440 root 1.40 {
441 root 1.48 if (buffer)
442     return false;
443    
444     glGenBuffersARB (1, &buffer);
445     return true;
446 root 1.40 }
447    
448 root 1.48 void bind ()
449 root 1.40 {
450     glBindBufferARB (target, buffer);
451     }
452    
453 root 1.56 template<class basetype>
454     void set (const basetype *d, GLsizei count, GLenum usage = GL_STATIC_DRAW_ARB)
455 root 1.40 {
456     alloc ();
457 root 1.56 format = type_traits<basetype>::glenum ();
458 root 1.52 this->count = count;
459 root 1.56 size = sizeof (basetype);
460 root 1.55 vertex_buffer_object::bind ();
461 root 1.56 glBufferDataARB (target, count * this->size, d, usage);
462 root 1.40 }
463    
464 root 1.48 template<class data>
465     void set (const vector<data> &d, GLenum usage = GL_STATIC_DRAW_ARB)
466 root 1.40 {
467 root 1.48 set (&d[0], d.size (), usage);
468 root 1.40 }
469    
470 root 1.56 template<typename basetype>
471     void set (GLsizei count, GLenum usage = GL_DYNAMIC_DRAW_ARB)
472 root 1.55 {
473     alloc ();
474 root 1.56 format = type_traits<basetype>::glenum ();
475     this->count = count;
476     size = sizeof (basetype);
477 root 1.55 vertex_buffer_object::bind ();
478 root 1.56 glBufferDataARB (target, this->count * size, 0, usage);
479 root 1.55 }
480    
481     void *map (GLenum access = GL_WRITE_ONLY)
482     {
483     vertex_buffer_object::bind ();
484     return glMapBufferARB (target, access);
485     }
486    
487     void unmap ()
488     {
489     vertex_buffer_object::bind ();
490     glUnmapBuffer (target);
491     }
492    
493 root 1.54 vertex_buffer_object ()
494 root 1.40 : buffer(0)
495     {
496     }
497    
498 root 1.54 ~vertex_buffer_object ()
499 root 1.40 {
500 root 1.48 if (buffer)
501     glDeleteBuffersARB (1, &buffer);
502 root 1.40 }
503    
504     operator GLint ()
505     {
506     return buffer;
507     }
508     };
509    
510 root 1.56 struct vertex_buffer : vertex_buffer_object<GL_ARRAY_BUFFER_ARB>
511     {
512 root 1.48 void bind ()
513     {
514 root 1.54 vertex_buffer_object<GL_ARRAY_BUFFER_ARB>::bind ();
515 root 1.56 glInterleavedArrays (format, 0, 0);
516 root 1.48 }
517    
518     void draw (GLenum mode, GLint first, GLsizei count)
519     {
520     bind ();
521     glDrawArrays (mode, first, count);
522     }
523     };
524    
525 root 1.56 struct index_buffer : vertex_buffer_object<GL_ELEMENT_ARRAY_BUFFER_ARB>
526     {
527 root 1.48 void draw (GLenum mode, GLint first, GLsizei count)
528     {
529     bind ();
530 root 1.56 glDrawElements (mode, count, format, (GLvoid *)((char *)0 + first * size)); // only SHORT supported :( // first //D//TODO
531 root 1.48 }
532     };
533    
534     void draw_bbox (const sector &a, const sector &b);
535 root 1.49
536 root 1.60 GLuint load_texture (SDL_Surface *surface, GLfloat *texcoord);
537 root 1.31 }
538    
539 root 1.61 template<typename idtype = unsigned int>
540     struct idpool
541 root 1.60 {
542 root 1.61 typedef idtype type;
543     vector<idtype> free;
544     idtype next;
545 root 1.60
546 root 1.61 idpool ();
547     idtype get ();
548     void put (idtype &i);
549 root 1.60 };
550    
551 root 1.61 template<class value, typename idtype = unsigned int>
552 root 1.60 struct idmap
553     {
554 root 1.61 vector<value *> map;
555 root 1.60
556 root 1.61 idpool<idtype> &ctx;
557 root 1.60
558 root 1.61 idmap (idpool<idtype> &ctx)
559 root 1.60 : ctx (ctx)
560     {
561     }
562    
563     ~idmap ()
564     {
565     }
566    
567 root 1.61 #if 0
568 root 1.60 value *&operator [](const base &k)
569     {
570     }
571 root 1.61 #endif
572 root 1.60 };
573 root 1.27
574 root 1.1 #endif
575