ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/libgender/oct.C
(Generate patch)

Comparing libgender/oct.C (file contents):
Revision 1.22 by root, Wed Oct 6 02:04:03 2004 UTC vs.
Revision 1.39 by root, Sat Oct 9 16:37:31 2004 UTC

2 2
3#include <vector> 3#include <vector>
4 4
5using namespace std; 5using namespace std;
6 6
7#define GL_GLEXT_PROTOTYPES
8#include <GL/gl.h> 7#include <GL/gl.h>
9 8
10#include "oct.h" 9#include "oct.h"
11#include "view.h" 10#include "view.h"
12#include "entity.h" 11#include "entity.h"
13
14vector<GLuint> occ_query_objects;
15
16static GLuint begin_occ_query ()
17{
18 GLuint id;
19
20 if (occ_query_objects.size ())
21 {
22 id = *(occ_query_objects.end () - 1);
23 occ_query_objects.pop_back ();
24 }
25 else
26 glGenQueriesARB (1, &id);
27
28 glBeginQueryARB (GL_SAMPLES_PASSED, id);
29 return id;
30}
31
32#define end_occ_query() glEndQueryARB (GL_SAMPLES_PASSED);
33
34static GLuint occ_query_result (GLuint id)
35{
36 GLuint count;
37
38 glGetQueryObjectuivARB (id, GL_QUERY_RESULT, &count);
39 occ_query_objects.push_back (id);
40
41 return count;
42}
43 12
44octant world(0, sector (SOFFS_MIN, SOFFS_MIN, SOFFS_MIN), MAXEXTENT); 13octant world(0, sector (SOFFS_MIN, SOFFS_MIN, SOFFS_MIN), MAXEXTENT);
45 14
46octant::octant (octant *parent, const sector &orig, uoffs extent) 15octant::octant (octant *parent, const sector &orig, uoffs extent)
47: parent(parent), orig(orig), extent(extent) 16: parent(parent), orig(orig), extent(extent)
54{ 23{
55 for (fill = 8; fill--; ) 24 for (fill = 8; fill--; )
56 delete sub[fill]; 25 delete sub[fill];
57} 26}
58 27
59static bool overlap (const sector &o1, uoffs ea, const box &bbox) 28static bool overlap (const sector &o1, uoffs ea, const sector &a, const sector &b)
60{ 29{
61 sector a2, b2;
62
63 ea /= 2; 30 ea /= 2;
64 31
65 a2.x = o1.x + ea; 32 sector center_1 = o1 + ea;
66 a2.y = o1.y + ea; 33 sector size_2 = b - a;
67 a2.z = o1.z + ea; 34 sector center_2 = a + size_2 / 2;
68
69 b2.x = (bbox.a.x + bbox.b.x) / 2;
70 b2.y = (bbox.a.y + bbox.b.y) / 2;
71 b2.z = (bbox.a.z + bbox.b.z) / 2;
72 35
73 return abs (a2.x - b2.x) <= ea + (bbox.b.x - bbox.a.x) 36 return abs (center_1 - center_2) <= ea + size_2;
74 && abs (a2.y - b2.y) <= ea + (bbox.b.y - bbox.a.y)
75 && abs (a2.z - b2.z) <= ea + (bbox.b.z - bbox.a.z);
76} 37}
77 38
78void octant::add (entity_base *e) 39void octant::add (entity *e)
79{ 40{
80 box bbox = translate (e->bbox, e->orig, sector (0, 0, 0)); 41 const sector &a = e->a;
42 const sector &b = e->b;
81 43
82 uoffs size = max (abs (bbox.b.x - bbox.a.x),
83 max (abs (bbox.b.y - bbox.a.y),
84 abs (bbox.b.z - bbox.a.z)));
85
86 if (overlap (orig, extent, bbox)) 44 if (overlap (orig, extent, a, b))
87 { 45 {
88 uoffs extent2 = extent / 2; 46 uoffs extent2 = extent / 2;
47 uoffs size = max (abs (b - a));
89 48
90 if (size > extent2 || !extent2) 49 if (size > extent2 || !extent2)
91 { 50 {
92 push_back (e); 51 push_back (e);
93 e->o.push_back (this); 52 e->o.push_back (this);
96 55
97 for (int i = 8; i--; ) 56 for (int i = 8; i--; )
98 { 57 {
99 sector s = orig; 58 sector s = orig;
100 s.offset (i, extent2); 59 s.offset (i, extent2);
60
101 if (overlap (s, extent2, bbox)) 61 if (overlap (s, extent2, a, b))
102 { 62 {
103 if (!sub[i]) 63 if (!sub[i])
104 sub[i] = new octant (this, s, extent2); 64 sub[i] = new octant (this, s, extent2);
105 65
106 sub[i]->add (e); 66 sub[i]->add (e);
107 } 67 }
108 } 68 }
109 } 69 }
110} 70}
111 71
112void octant::remove (entity_base *e) 72void octant::remove (entity *e)
113{ 73{
114} 74}
115 75
116void octant::detect_visibility (view &ctx) 76void octant::detect_visibility (view &ctx)
117{ 77{
118 visibility_state &vs = ctx.vismap[this]; 78 visibility_state &vs = ctx.vismap[this];
119 79
120 if (vs.generation != ctx.generation) 80 if (vs.generation != ctx.generation)
121 vs.visibility = visibility_state::UNKNOWN; 81 vs.visibility = visibility_state::UNKNOWN;
122 82
123 const sector &cam = ctx.orig; 83 if (orig <= ctx.orig && ctx.orig <= orig + extent)
124 if (cam.x >= orig.x && cam.x <= orig.x + extent
125 && cam.y >= orig.y && cam.y <= orig.y + extent
126 && cam.z >= orig.z && cam.z <= orig.z + extent)
127 { 84 {
128 vs.visibility = visibility_state::PARTIAL; 85 vs.visibility = visibility_state::PARTIAL;
129 vs.generation = ctx.generation; 86 vs.generation = ctx.generation;
130 } 87 }
131 else 88 else
132 { 89 {
133 point center ( 90 GLfloat extent2 = 0.5F * (GLfloat)extent;
134 orig.x + (soffs)extent / 2 - cam.x, 91 point center = point (orig) + extent2 - point (ctx.orig);
135 orig.y + (soffs)extent / 2 - cam.y,
136 orig.z + (soffs)extent / 2 - cam.z
137 );
138 92
139 GLfloat dia = (0.5 * sqrtf (3))*(GLfloat)extent; 93 GLfloat rad = ctx.diagfact * extent2;
140 94
141 if (ctx.frustum.t.distance (center) < -dia) return; 95 if (ctx.frustum.t.distance (center) < -rad) return;
142 if (ctx.frustum.b.distance (center) < -dia) return; 96 if (ctx.frustum.b.distance (center) < -rad) return;
143 if (ctx.frustum.l.distance (center) < -dia) return; 97 if (ctx.frustum.l.distance (center) < -rad) return;
144 if (ctx.frustum.r.distance (center) < -dia) return; 98 if (ctx.frustum.r.distance (center) < -rad) return;
145 if (ctx.frustum.n.distance (center) < -dia) return; 99 if (ctx.frustum.n.distance (center) < -rad) return;
146 if (ctx.frustum.f.distance (center) < -dia) return; 100
101 GLfloat fd = ctx.frustum.f.distance (center);
102
103 if (fd < -rad)
104 {
105 if (fd < -rad * 3.F)
106 return;
107
108 ctx.farlist.push_back (this);
109 return;
110 }
147 } 111 }
112
113 if (vs.visibility == visibility_state::UNKNOWN)
114 vs.visibility = visibility_state::FULL;
148 115
149 if (size ()) 116 if (size ())
150 ctx.vislist.push_back (this); 117 ctx.vislist.push_back (this);
151 118
152 // node to start with 119 // node to start with
171 138
172void octant::display (view &ctx) 139void octant::display (view &ctx)
173{ 140{
174#if 0 141#if 0
175 glBegin (GL_LINES); 142 glBegin (GL_LINES);
176 sector s = orig; 143 sector s = orig - ctx.orig;
177 s.x -= ctx.orig.x;
178 s.y -= ctx.orig.y;
179 s.z -= ctx.orig.z;
180 vec3 clr(0, 0.8, 0); 144 vec3 clr(0, 0.8, 0);
181 glMaterialfv (GL_FRONT_AND_BACK, GL_DIFFUSE, (const GLfloat*)&clr); 145 glMaterialfv (GL_FRONT_AND_BACK, GL_DIFFUSE, (const GLfloat*)&clr);
182 146
183 for (int i = 8; i--; ) 147 for (int i = 8; i--; )
184 for (int ji = 3; ji--; ) 148 for (int ji = 3; ji--; )
194 s.z + !!(j & 4) * extent); 158 s.z + !!(j & 4) * extent);
195 } 159 }
196 } 160 }
197 161
198 glEnd (); 162 glEnd ();
199 glDisable(GL_COLOR_MATERIAL);
200#endif 163#endif
201 164
202 GLuint i = begin_occ_query ();
203 for (iterator i = end (); i != begin (); ) 165 for (iterator i = end (); i != begin (); )
204 (*--i)->display (ctx); 166 (*--i)->display (ctx);
205 end_occ_query ();
206} 167}
207 168
169void octant::draw_bbox (view &ctx)
170{
171 sector s = orig - ctx.orig;
208 172
173 gl::draw_box (ctx, s, s + extent);
174}
209 175
176void octant::event (occ_query &ev)
177{
178 if (ev.r <= 5)
179 return;
180
181 //ev.v.vismap[this].visibility = visibility_state::FULL;
182 ev.v.far = ev.v.near + ev.v.frustum.n.distance (orig);
183 printf ("OCT(%x,%x,%x+%x) samples %d\n", orig.x, orig.y, orig.z, extent, ev.r);
184}
185

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines