32 BoundingHexahedron(
const LFrustum &frustum,
bool is_ortho,
33 CoordinateSystem cs) {
34 if (cs == CS_default) {
35 cs = get_default_coordinate_system();
38 PN_stdfloat fs = 1.0f;
40 fs = frustum._ffar / frustum._fnear;
46 _points[0].set(frustum._l * fs, frustum._ffar, frustum._b * fs);
47 _points[1].set(frustum._r * fs, frustum._ffar, frustum._b * fs);
48 _points[2].set(frustum._r * fs, frustum._ffar, frustum._t * fs);
49 _points[3].set(frustum._l * fs, frustum._ffar, frustum._t * fs);
50 _points[4].set(frustum._l, frustum._fnear, frustum._b);
51 _points[5].set(frustum._r, frustum._fnear, frustum._b);
52 _points[6].set(frustum._r, frustum._fnear, frustum._t);
53 _points[7].set(frustum._l, frustum._fnear, frustum._t);
58 if (cs == CS_zup_right) {
62 xform(LMatrix4::convert_mat(CS_zup_right, cs));
70 BoundingHexahedron(
const LPoint3 &fll,
const LPoint3 &flr,
71 const LPoint3 &fur,
const LPoint3 &ful,
72 const LPoint3 &nll,
const LPoint3 &nlr,
73 const LPoint3 &nur,
const LPoint3 &nul) {
99 LPoint3 BoundingHexahedron::
101 nassertr(!
is_empty(), LPoint3(0.0f, 0.0f, 0.0f));
102 nassertr(!
is_infinite(), LPoint3(0.0f, 0.0f, 0.0f));
104 LPoint3 m = _points[0];
105 for (i = 1; i < num_points; i++) {
106 m.set(min(m[0], _points[i][0]),
107 min(m[1], _points[i][1]),
108 min(m[2], _points[i][2]));
116 LPoint3 BoundingHexahedron::
118 nassertr(!
is_empty(), LPoint3(0.0f, 0.0f, 0.0f));
119 nassertr(!
is_infinite(), LPoint3(0.0f, 0.0f, 0.0f));
121 LPoint3 m = _points[0];
122 for (i = 1; i < num_points; i++) {
123 m.set(max(m[0], _points[i][0]),
124 max(m[1], _points[i][1]),
125 max(m[2], _points[i][2]));
133 LPoint3 BoundingHexahedron::
134 get_approx_center()
const {
135 nassertr(!
is_empty(), LPoint3(0.0f, 0.0f, 0.0f));
136 nassertr(!
is_infinite(), LPoint3(0.0f, 0.0f, 0.0f));
143 void BoundingHexahedron::
144 xform(
const LMatrix4 &mat) {
146 for (
int i = 0; i < num_points; i++) {
147 _points[i] = _points[i] * mat;
157 void BoundingHexahedron::
158 output(std::ostream &out)
const {
160 out <<
"bhexahedron, empty";
162 out <<
"bhexahedron, infinite";
164 out <<
"bhexahedron, min " << get_min() <<
" max " << get_max();
171 void BoundingHexahedron::
172 write(std::ostream &out,
int indent_level)
const {
174 indent(out, indent_level) <<
"bhexahedron, empty\n";
176 out <<
"bhexahedron, infinite\n";
179 <<
"bhexahedron, min " << get_min() <<
" max " << get_max() <<
":\n";
181 for (i = 0; i < num_points; i++) {
182 indent(out, indent_level + 2) << _points[i] <<
"\n";
184 indent(out, indent_level + 2) <<
"centroid is " << _centroid <<
"\n";
200 bool BoundingHexahedron::
202 return other->extend_by_hexahedron(
this);
208 bool BoundingHexahedron::
212 return other->around_hexahedrons(first, last);
218 int BoundingHexahedron::
220 return other->contains_hexahedron(
this);
226 int BoundingHexahedron::
227 contains_point(
const LPoint3 &point)
const {
229 return IF_no_intersection;
232 return IF_possible | IF_some | IF_all;
237 for (
int i = 0; i < num_planes; i++) {
238 const LPlane &p = _planes[i];
239 if (p.dist_to_plane(point) > 0.0f) {
240 return IF_no_intersection;
243 return IF_possible | IF_some | IF_all;
250 int BoundingHexahedron::
251 contains_lineseg(
const LPoint3 &a,
const LPoint3 &b)
const {
253 return IF_no_intersection;
256 return IF_possible | IF_some | IF_all;
261 for (
int i = 0; i < num_planes; i++) {
262 const LPlane &p = _planes[i];
263 if (p.dist_to_plane(a) > 0.0f ||
264 p.dist_to_plane(b) > 0.0f) {
265 return IF_no_intersection;
279 int BoundingHexahedron::
285 const LPoint3 ¢er = sphere->get_center();
286 PN_stdfloat radius = sphere->get_radius();
288 int result = IF_possible | IF_some | IF_all;
290 for (
int i = 0; i < num_planes; i++) {
291 const LPlane &p = _planes[i];
292 PN_stdfloat dist = p.dist_to_plane(center);
297 return IF_no_intersection;
299 }
else if (dist > -radius) {
311 int BoundingHexahedron::
317 const LPoint3 &min = box->
get_minq();
318 const LPoint3 &max = box->
get_maxq();
319 LPoint3 center = (min + max) * 0.5f;
320 PN_stdfloat radius2 = (max - center).length_squared();
322 int result = IF_possible | IF_some | IF_all;
324 for (
int i = 0; i < num_planes; i++) {
325 const LPlane &p = _planes[i];
326 PN_stdfloat dist = p.dist_to_plane(center);
327 PN_stdfloat dist2 = dist * dist;
329 if (dist2 <= radius2) {
335 for (
int i = 0; i < 8 && (all_in || all_out) ; ++i) {
336 if (p.dist_to_plane(box->
get_point(i)) < 0.0f) {
346 return IF_no_intersection;
347 }
else if (!all_in) {
351 }
else if (dist >= 0.0f) {
353 return IF_no_intersection;
363 int BoundingHexahedron::
365 return plane->contains_hexahedron(
this) & ~IF_all;
371 int BoundingHexahedron::
374 nassertr(!hexahedron->
is_empty(), 0);
377 LPoint3 min = hexahedron->get_min();
378 LPoint3 max = hexahedron->get_max();
379 LPoint3 center = (min + max) * 0.5f;
380 PN_stdfloat radius2 = (max - center).length_squared();
382 int result = IF_possible | IF_some | IF_all;
384 for (
int i = 0; i < num_planes; i++) {
385 const LPlane &p = _planes[i];
386 PN_stdfloat dist = p.dist_to_plane(center);
387 PN_stdfloat dist2 = dist * dist;
389 if (dist >= 0.0f && dist2 > radius2) {
392 return IF_no_intersection;
398 unsigned points_out = 0;
399 for (
int i = 0; i < 8; ++i) {
400 if (p.dist_to_plane(hexahedron->
get_point(i)) > 0.0f) {
406 if (points_out != 0) {
407 if (points_out == 8) {
408 return IF_no_intersection;
421 void BoundingHexahedron::
423 _planes[0] = LPlane(_points[0], _points[3], _points[2]);
429 if (_planes[0].dist_to_plane(_centroid) > 0) {
431 _planes[0] = LPlane(_points[0], _points[2], _points[3]);
432 _planes[1] = LPlane(_points[0], _points[5], _points[1]);
433 _planes[2] = LPlane(_points[1], _points[6], _points[2]);
434 _planes[3] = LPlane(_points[2], _points[7], _points[3]);
435 _planes[4] = LPlane(_points[3], _points[4], _points[0]);
436 _planes[5] = LPlane(_points[4], _points[7], _points[6]);
440 _planes[1] = LPlane(_points[0], _points[1], _points[5]);
441 _planes[2] = LPlane(_points[1], _points[2], _points[6]);
442 _planes[3] = LPlane(_points[2], _points[3], _points[7]);
443 _planes[4] = LPlane(_points[3], _points[0], _points[4]);
444 _planes[5] = LPlane(_points[4], _points[6], _points[7]);
450 nassertv(_planes[0].dist_to_plane(_centroid) <= 0.001);
451 nassertv(_planes[1].dist_to_plane(_centroid) <= 0.001);
452 nassertv(_planes[2].dist_to_plane(_centroid) <= 0.001);
453 nassertv(_planes[3].dist_to_plane(_centroid) <= 0.001);
454 nassertv(_planes[4].dist_to_plane(_centroid) <= 0.001);
455 nassertv(_planes[5].dist_to_plane(_centroid) <= 0.001);
462 void BoundingHexahedron::
464 LPoint3 net = _points[0];
465 for (
int i = 1; i < num_points; i++) {
468 _centroid = net / (PN_stdfloat)num_points;