32PStatCollector CollisionInvSphere::_volume_pcollector(
"Collision Volumes:CollisionInvSphere");
33PStatCollector CollisionInvSphere::_test_pcollector(
"Collision Tests:CollisionInvSphere");
41 return new CollisionInvSphere(*
this);
49 report_undefined_from_intersection(get_type());
59 return _volume_pcollector;
68 return _test_pcollector;
74void CollisionInvSphere::
75output(std::ostream &out)
const {
76 out <<
"invsphere, c (" << get_center() <<
"), r " << get_radius();
83compute_internal_bounds()
const {
86 return new OmniBoundingVolume();
94 const CollisionSphere *sphere;
95 DCAST_INTO_R(sphere, entry.
get_from(),
nullptr);
98 const LMatrix4 &wrt_mat = wrt_space->get_mat();
100 LPoint3 from_center = sphere->get_center() * wrt_mat;
101 LVector3 from_radius_v =
102 LVector3(sphere->get_radius(), 0.0f, 0.0f) * wrt_mat;
103 PN_stdfloat from_radius = length(from_radius_v);
105 LPoint3 into_center = get_center();
106 PN_stdfloat into_radius = get_radius();
108 LVector3 vec = from_center - into_center;
109 PN_stdfloat dist2 = dot(vec, vec);
110 if (dist2 < (into_radius - from_radius) * (into_radius - from_radius)) {
115 if (collide_cat.is_debug()) {
120 PT(CollisionEntry) new_entry =
new CollisionEntry(entry);
122 LVector3 surface_normal;
123 PN_stdfloat vec_length = vec.length();
124 if (IS_NEARLY_ZERO(vec_length)) {
128 surface_normal.set(1.0, 0.0, 0.0);
130 surface_normal = vec / -vec_length;
135 new_entry->set_surface_normal(normal);
136 new_entry->set_surface_point(into_center - surface_normal * into_radius);
137 new_entry->set_interior_point(from_center - surface_normal * from_radius);
147 const CollisionLine *line;
148 DCAST_INTO_R(line, entry.
get_from(),
nullptr);
151 const LMatrix4 &wrt_mat = wrt_space->get_mat();
153 LPoint3 from_origin = line->get_origin() * wrt_mat;
154 LVector3 from_direction = line->get_direction() * wrt_mat;
157 if (!intersects_line(t1, t2, from_origin, from_direction, 0.0f)) {
163 if (collide_cat.is_debug()) {
168 PT(CollisionEntry) new_entry =
new CollisionEntry(entry);
170 LPoint3 into_intersection_point = from_origin + t2 * from_direction;
171 new_entry->set_surface_point(into_intersection_point);
176 LVector3 normal = into_intersection_point - get_center();
178 new_entry->set_surface_normal(-normal);
189 const CollisionRay *ray;
190 DCAST_INTO_R(ray, entry.
get_from(),
nullptr);
193 const LMatrix4 &wrt_mat = wrt_space->get_mat();
195 LPoint3 from_origin = ray->get_origin() * wrt_mat;
196 LVector3 from_direction = ray->get_direction() * wrt_mat;
199 if (!intersects_line(t1, t2, from_origin, from_direction, 0.0f)) {
204 t2 = std::max(t2, 0.0);
206 if (collide_cat.is_debug()) {
211 PT(CollisionEntry) new_entry =
new CollisionEntry(entry);
213 LPoint3 into_intersection_point;
214 into_intersection_point = from_origin + t2 * from_direction;
215 new_entry->set_surface_point(into_intersection_point);
220 LVector3 normal = into_intersection_point - get_center();
222 new_entry->set_surface_normal(-normal);
232test_intersection_from_segment(
const CollisionEntry &entry)
const {
233 const CollisionSegment *segment;
234 DCAST_INTO_R(segment, entry.
get_from(),
nullptr);
237 const LMatrix4 &wrt_mat = wrt_space->get_mat();
239 LPoint3 from_a = segment->get_point_a() * wrt_mat;
240 LPoint3 from_b = segment->get_point_b() * wrt_mat;
241 LVector3 from_direction = from_b - from_a;
244 if (!intersects_line(t1, t2, from_a, from_direction, 0.0f)) {
255 }
else if (t1 >= 1.0) {
259 }
else if (t2 <= 1.0) {
261 t = std::min(t2, 1.0);
263 }
else if (t1 >= 0.0) {
265 t = std::max(t1, 0.0);
274 if (collide_cat.is_debug()) {
279 PT(CollisionEntry) new_entry =
new CollisionEntry(entry);
281 LPoint3 into_intersection_point = from_a + t * from_direction;
282 new_entry->set_surface_point(into_intersection_point);
287 LVector3 normal = into_intersection_point - get_center();
289 new_entry->set_surface_normal(-normal);
299test_intersection_from_capsule(
const CollisionEntry &entry)
const {
300 const CollisionCapsule *capsule;
301 DCAST_INTO_R(capsule, entry.
get_from(),
nullptr);
304 const LMatrix4 &wrt_mat = wrt_space->get_mat();
306 LPoint3 from_a = capsule->get_point_a() * wrt_mat;
307 LPoint3 from_b = capsule->get_point_b() * wrt_mat;
309 LVector3 from_radius_v =
310 LVector3(capsule->get_radius(), 0.0f, 0.0f) * wrt_mat;
311 PN_stdfloat from_radius = from_radius_v.length();
313 LPoint3 center = get_center();
314 PN_stdfloat radius = get_radius();
317 PN_stdfloat dist_a = (from_a - center).length();
318 PN_stdfloat dist_b = (from_b - center).length();
319 if (dist_b > dist_a) {
326 if (dist_a < radius - from_radius) {
330 if (collide_cat.is_debug()) {
335 PT(CollisionEntry) new_entry =
new CollisionEntry(entry);
337 LVector3 normal = center - from_a;
339 new_entry->set_surface_point(get_center() - normal * radius);
340 new_entry->set_interior_point(from_a - normal * from_radius);
345 new_entry->set_surface_normal(normal);
356 const CollisionBox *box;
357 DCAST_INTO_R(box, entry.
get_from(),
nullptr);
360 const LMatrix4 &wrt_mat = wrt_space->get_mat();
362 LPoint3 center = get_center();
363 PN_stdfloat radius_sq = get_radius();
364 radius_sq *= radius_sq;
369 PN_stdfloat max_dist_sq = -1.0;
370 LPoint3 deepest_vertex;
372 for (
int i = 0; i < 8; ++i) {
373 LPoint3 point = wrt_mat.xform_point(box->
get_point(i));
375 PN_stdfloat dist_sq = (point - center).length_squared();
376 if (dist_sq > max_dist_sq) {
377 deepest_vertex = point;
378 max_dist_sq = dist_sq;
382 if (max_dist_sq < radius_sq) {
388 if (collide_cat.is_debug()) {
394 PT(CollisionEntry) new_entry =
new CollisionEntry(entry);
397 new_entry->set_interior_point(deepest_vertex);
400 LVector3 normal = center - deepest_vertex;
402 new_entry->set_surface_point(center - normal * get_radius());
403 new_entry->set_surface_normal(
414void CollisionInvSphere::
416 if (collide_cat.is_debug()) {
418 <<
"Recomputing viz for " << *
this <<
"\n";
421 static const int num_slices = 16;
422 static const int num_stacks = 8;
424 PT(GeomVertexData) vdata =
new GeomVertexData
427 GeomVertexWriter vertex(vdata, InternalName::get_vertex());
429 PT(GeomTristrips) strip =
new GeomTristrips(Geom::UH_static);
430 for (
int sl = 0; sl < num_slices; ++sl) {
431 PN_stdfloat longitude0 = (PN_stdfloat)sl / (PN_stdfloat)num_slices;
432 PN_stdfloat longitude1 = (PN_stdfloat)(sl + 1) / (PN_stdfloat)num_slices;
433 vertex.add_data3(compute_point(0.0, longitude0));
434 for (
int st = 1; st < num_stacks; ++st) {
435 PN_stdfloat latitude = (PN_stdfloat)st / (PN_stdfloat)num_stacks;
436 vertex.add_data3(compute_point(latitude, longitude1));
437 vertex.add_data3(compute_point(latitude, longitude0));
439 vertex.add_data3(compute_point(1.0, longitude0));
441 strip->add_next_vertices(num_stacks * 2);
442 strip->close_primitive();
445 PT(Geom) geom =
new Geom(vdata);
446 geom->add_primitive(strip);
448 _viz_geom->add_geom(geom, get_solid_viz_state());
478 me->fillin(scan, manager);
487void CollisionInvSphere::
489 CollisionSphere::fillin(scan, manager);
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
void parse_params(const FactoryParams ¶ms, DatagramIterator &scan, BamReader *&manager)
Takes in a FactoryParams, passed from a WritableFactory into any TypedWritable's make function,...
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
This is the fundamental interface for extracting binary objects from a Bam file, as generated by a Ba...
static WritableFactory * get_factory()
Returns the global WritableFactory for generating TypedWritable objects.
This is the fundamental interface for writing binary objects to a Bam file, to be extracted later by ...
This is an abstract class for any volume in any sense which can be said to define the locality of ref...
LPoint3 get_point(int n) const
Returns the nth vertex of the OBB.
Defines a single collision event.
get_from_node_path
Returns the NodePath that represents the CollisionNode that contains the CollisionSolid that triggere...
get_into_node_path
Returns the NodePath that represents the specific CollisionNode or GeomNode instance that was collide...
get_from
Returns the CollisionSolid pointer for the particular solid that triggered this collision.
An inverted sphere: this is a sphere whose collision surface is the inside surface of the sphere.
static void register_with_read_factory()
Factory method to generate a CollisionInvSphere object.
virtual void write_datagram(BamWriter *manager, Datagram &me)
Function to write the important information in the particular object to a Datagram.
virtual PStatCollector & get_test_pcollector()
Returns a PStatCollector that is used to count the number of intersection tests made against a solid ...
virtual PStatCollector & get_volume_pcollector()
Returns a PStatCollector that is used to count the number of bounding volume tests made against a sol...
The abstract base class for all things that can collide with other things in the world,...
bool has_effective_normal() const
Returns true if a special normal was set by set_effective_normal(), false otherwise.
const LVector3 & get_effective_normal() const
Returns the normal that was set by set_effective_normal().
get_respect_effective_normal
See set_respect_effective_normal().
virtual void write_datagram(BamWriter *manager, Datagram &me)
Function to write the important information in the particular object to a Datagram.
A class to retrieve the individual data elements previously stored in a Datagram.
An ordered list of data elements, formatted in memory for transmission over a socket or writing to a ...
An instance of this class is passed to the Factory when requesting it to do its business and construc...
void register_factory(TypeHandle handle, CreateFunc *func, void *user_data=nullptr)
Registers a new kind of thing the Factory will be able to create.
A lightweight class that represents a single element that may be timed and/or counted via stats.
TypeHandle is the identifier used to differentiate C++ class types.
Base class for objects that can be written to and read from Bam files.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.