[Bf-blender-cvs] [39330a3e622] fracture_modifier: reworked the trigger system to work in narrowphase of bullet (more exact shapes)

Martin Felke noreply at git.blender.org
Wed Aug 9 22:18:12 CEST 2017


Commit: 39330a3e622ba3e6dafdcc91290794f8e4db1c1d
Author: Martin Felke
Date:   Wed Aug 9 22:18:03 2017 +0200
Branches: fracture_modifier
https://developer.blender.org/rB39330a3e622ba3e6dafdcc91290794f8e4db1c1d

reworked the trigger system to work in narrowphase of bullet (more exact shapes)

===================================================================

M	intern/rigidbody/rb_bullet_api.cpp
M	release/scripts/startup/bl_ui/properties_physics_rigidbody.py
M	source/blender/blenkernel/intern/rigidbody.c

===================================================================

diff --git a/intern/rigidbody/rb_bullet_api.cpp b/intern/rigidbody/rb_bullet_api.cpp
index 1ef84bd92c8..ef6941bd5a5 100644
--- a/intern/rigidbody/rb_bullet_api.cpp
+++ b/intern/rigidbody/rb_bullet_api.cpp
@@ -723,20 +723,15 @@ struct rbFilterCallback : public btOverlapFilterCallback
 		this->callback = callback;
 	}
 
-	virtual bool needBroadphaseCollision(btBroadphaseProxy *proxy0, btBroadphaseProxy *proxy1) const
+	bool check_collision(rbRigidBody* rb0, rbRigidBody* rb1, bool collides) const
 	{
-		rbRigidBody *rb0 = (rbRigidBody *)((btFractureBody *)proxy0->m_clientObject)->getUserPointer();
-		rbRigidBody *rb1 = (rbRigidBody *)((btFractureBody *)proxy1->m_clientObject)->getUserPointer();
-		
-		bool collides;
-		collides = (proxy0->m_collisionFilterGroup & proxy1->m_collisionFilterMask) != 0;
-		collides = collides && (proxy1->m_collisionFilterGroup & proxy0->m_collisionFilterMask);
 		if (!rb0 || !rb1)
 			return collides;
 
 		collides = collides && (rb0->col_groups & rb1->col_groups);
 		if (this->callback != NULL) {
 			int result = 0;
+#if 0
 			//cast ray from centroid of 1 rigidbody to another, do this only for mesh shapes (all other can use standard bbox)
 			int stype0 = rb0->body->getCollisionShape()->getShapeType();
 			int stype1 = rb1->body->getCollisionShape()->getShapeType();
@@ -806,10 +801,29 @@ struct rbFilterCallback : public btOverlapFilterCallback
 			}
 
 			collides = collides && (bool)result;
+#endif
+			result = this->callback(rb0->world->blenderWorld, rb0->meshIsland, rb1->meshIsland, rb0->blenderOb, rb1->blenderOb);
+			collides = collides && (bool)result;
 		}
-		
+
 		return collides;
 	}
+
+	virtual bool needBroadphaseCollision(btBroadphaseProxy *proxy0, btBroadphaseProxy *proxy1) const
+	{
+		//rbRigidBody *rb0 = (rbRigidBody *)((btFractureBody *)proxy0->m_clientObject)->getUserPointer();
+		//rbRigidBody *rb1 = (rbRigidBody *)((btFractureBody *)proxy1->m_clientObject)->getUserPointer();
+		
+		bool collides;
+		collides = (proxy0->m_collisionFilterGroup &
+		           (proxy1->m_collisionFilterMask | btBroadphaseProxy::StaticFilter |
+		            btBroadphaseProxy::KinematicFilter)) != 0;
+		collides = collides && (proxy1->m_collisionFilterGroup &
+		           (proxy0->m_collisionFilterMask | btBroadphaseProxy::StaticFilter |
+		            btBroadphaseProxy::KinematicFilter));
+
+		return collides; //this->check_collision(rb0, rb1, collides);
+	}
 };
 
 static inline void copy_quat_btquat(float quat[4], const btQuaternion &btquat)
@@ -892,6 +906,33 @@ static void idCallback(void *userPtr, int* objectId, int* shardId)
 	}
 }
 
+class CollisionFilterDispatcher : public btCollisionDispatcher
+{
+	public:
+		virtual bool needsCollision(const btCollisionObject *body0, const btCollisionObject *body1);
+		rbFilterCallback *filterCallback;
+		CollisionFilterDispatcher(btDefaultCollisionConfiguration *configuration, rbFilterCallback* callback);
+};
+
+CollisionFilterDispatcher::CollisionFilterDispatcher(btDefaultCollisionConfiguration* configuration, rbFilterCallback *callback)
+    :btCollisionDispatcher(configuration)
+{
+	this->filterCallback = callback;
+}
+
+bool CollisionFilterDispatcher::needsCollision(const btCollisionObject *body0, const btCollisionObject *body1)
+{
+	rbRigidBody *rb0 = (rbRigidBody *)((btFractureBody *)body0)->getUserPointer();
+	rbRigidBody *rb1 = (rbRigidBody *)((btFractureBody *)body1)->getUserPointer();
+
+	if (this->filterCallback)
+	{
+		return this->filterCallback->check_collision(rb0, rb1, true);
+	}
+
+	return true;
+}
+
 //yuck, but need a handle for the world somewhere for collision callback...
 rbDynamicsWorld *RB_dworld_new(const float gravity[3], void* blenderWorld, void* blenderScene, int (*callback)(void *, void *, void *, void *, void *),
 							   void (*contactCallback)(rbContactPoint* cp, void *bworld), void (*idCallbackOut)(void*, void*, int*, int*),
@@ -901,13 +942,12 @@ rbDynamicsWorld *RB_dworld_new(const float gravity[3], void* blenderWorld, void*
 	
 	/* collision detection/handling */
 	world->collisionConfiguration = new btDefaultCollisionConfiguration();
-	
-	world->dispatcher = new btCollisionDispatcher(world->collisionConfiguration);
+
+	world->filterCallback = new rbFilterCallback(callback);
+	world->dispatcher = new CollisionFilterDispatcher(world->collisionConfiguration, (rbFilterCallback*)world->filterCallback);
 	btGImpactCollisionAlgorithm::registerAlgorithm((btCollisionDispatcher *)world->dispatcher);
 	
 	world->pairCache = new btDbvtBroadphase();
-	
-	world->filterCallback = new rbFilterCallback(callback);
 	world->pairCache->getOverlappingPairCache()->setOverlapFilterCallback(world->filterCallback);
 
 	/* constraint solving */
diff --git a/release/scripts/startup/bl_ui/properties_physics_rigidbody.py b/release/scripts/startup/bl_ui/properties_physics_rigidbody.py
index fd6fa2223df..961fbdc6bf9 100644
--- a/release/scripts/startup/bl_ui/properties_physics_rigidbody.py
+++ b/release/scripts/startup/bl_ui/properties_physics_rigidbody.py
@@ -81,7 +81,7 @@ class PHYSICS_PT_rigid_body_trigger_advanced(PHYSICS_PT_rigidbody_panel, Panel):
         row.prop(rbo, "dynamic_trigger")
         row = layout.row()
         row.prop(rbo, "plastic_dissolve")
-        row.prop(rbo, "is_anti_trigger")
+        row.prop(rbo, "is_anti_trigger", text="Stop Trigger")
 
 class PHYSICS_PT_rigid_body_collisions(PHYSICS_PT_rigidbody_panel, Panel):
     bl_label = "Rigid Body Collisions"
diff --git a/source/blender/blenkernel/intern/rigidbody.c b/source/blender/blenkernel/intern/rigidbody.c
index 34705ed569e..a6f010b824e 100644
--- a/source/blender/blenkernel/intern/rigidbody.c
+++ b/source/blender/blenkernel/intern/rigidbody.c
@@ -1273,9 +1273,10 @@ void BKE_rigidbody_validate_sim_shard(RigidBodyWorld *rbw, MeshIsland *mi, Objec
 		BKE_rigidbody_validate_sim_shard_shape(mi, ob, true);
 	
 	if (rbo->physics_object) {
-		if (rebuild == false || mi->rigidbody->flag & RBO_FLAG_KINEMATIC_REBUILD)
+		if (rebuild == false /*|| mi->rigidbody->flag & RBO_FLAG_KINEMATIC_REBUILD*/)
 			RB_dworld_remove_body(rbw->physics_world, rbo->physics_object);
 	}
+
 	if (!rbo->physics_object || rebuild) {
 		float size[3];
 
@@ -1349,6 +1350,12 @@ void BKE_rigidbody_validate_sim_shard(RigidBodyWorld *rbw, MeshIsland *mi, Objec
 			}
 		}
 	}
+	else if (mi->rigidbody->flag & RBO_FLAG_KINEMATIC_REBUILD )
+	{
+		RB_body_deactivate(rbo->physics_object);
+		RB_body_set_mass(rbo->physics_object, 0.0f);
+		RB_body_set_kinematic_state(rbo->physics_object, true);
+	}
 
 	if (rbw && rbw->physics_world && rbo->physics_object)
 	{
@@ -1356,7 +1363,7 @@ void BKE_rigidbody_validate_sim_shard(RigidBodyWorld *rbw, MeshIsland *mi, Objec
 	}
 
 	rbo->flag &= ~RBO_FLAG_NEEDS_VALIDATE;
-	rbo->flag &= ~RBO_FLAG_KINEMATIC_REBUILD;
+	//rbo->flag &= ~RBO_FLAG_KINEMATIC_REBUILD;
 }
 
 
@@ -1444,6 +1451,12 @@ static void rigidbody_validate_sim_object(RigidBodyWorld *rbw, Object *ob, bool
 			}
 		}
 	}
+	else if (rbo->flag & RBO_FLAG_KINEMATIC_REBUILD )
+	{
+		RB_body_deactivate(rbo->physics_object);
+		RB_body_set_mass(rbo->physics_object, 0.0f);
+		RB_body_set_kinematic_state(rbo->physics_object, true);
+	}
 
 	if (rbw && rbw->physics_world)
 		RB_dworld_add_body(rbw->physics_world, rbo->physics_object, rbo->col_groups, NULL, ob, rbo->meshisland_index);
@@ -3539,7 +3552,7 @@ static void rigidbody_update_sim_ob(Scene *scene, RigidBodyWorld *rbw, Object *o
 
 	/* update rigid body location and rotation for kinematic bodies */
 	if ((rbo->flag & RBO_FLAG_KINEMATIC && rbo->force_thresh == 0.0f) || (ob->flag & SELECT && G.moving & G_TRANSFORM_OBJ)) {
-		if (rbo->type == RBO_TYPE_ACTIVE || mi == NULL)
+		if (((rbo->type == RBO_TYPE_ACTIVE || mi == NULL) && (rbo->flag & RBO_FLAG_KINEMATIC_REBUILD) == 0))
 		{
 			mul_v3_v3(centr, scale);
 			mul_qt_v3(rot, centr);
@@ -3583,12 +3596,15 @@ static void rigidbody_update_sim_ob(Scene *scene, RigidBodyWorld *rbw, Object *o
 			}
 			else if (rbo->flag & RBO_FLAG_KINEMATIC)
 			{
-				/* do the same here as above, but here we needed the eff_force value to compare against threshold */
-				mul_v3_v3(centr, scale);
-				mul_qt_v3(rot, centr);
-				add_v3_v3(loc, centr);
-				RB_body_activate(rbo->physics_object);
-				RB_body_set_loc_rot(rbo->physics_object, loc, rot);
+				if ((rbo->flag & RBO_FLAG_KINEMATIC_REBUILD) == 0)
+				{   //XXXXX TODO, maybe this is wrong here
+					/* do the same here as above, but here we needed the eff_force value to compare against threshold */
+					mul_v3_v3(centr, scale);
+					mul_qt_v3(rot, centr);
+					add_v3_v3(loc, centr);
+					RB_body_activate(rbo->physics_object);
+					RB_body_set_loc_rot(rbo->physics_object, loc, rot);
+				}
 			}
 			else
 			{
@@ -3619,7 +3635,7 @@ static void validateShard(RigidBodyWorld *rbw, MeshIsland *mi, Object *ob, int r
 		return;
 	}
 
-	if (rebuild || (mi->rigidbody->flag & RBO_FLAG_KINEMATIC_REBUILD)) {
+	if (rebuild /*|| (mi->rigidbody->flag & RBO_FLAG_KINEMATIC_REBUILD)*/) {
 		/* World has been rebuilt so rebuild object */
 		BKE_rigidbody_validate_sim_shard(rbw, mi, ob, true, transfer_speed, size);
 	}
@@ -3759,12 +3775,15 @@ void BKE_deactivateRigidbody(RigidBodyOb *rbo)
 {
 	//make kinematic again (un-trigger)
 	//printf("Untrigger\n");
-	if (rbo->physics_object)
+	//if (rbo->physics_object)
 	{
-		RB_body_set_kinematic_state(rbo->physics_object, true);
-		RB_body_set_mass(rbo->physics_object, 0.0f);
+		//RB_body_set_kinematic_state(rbo->physics_object, true);
+		//RB_body_set_mass(rbo->physics_object, 0.0f);
 		//rbo->flag |= RBO_FLAG_NEEDS_VALIDATE;
-		RB_body_deactivate(rbo->physics_object);
+		//RB_body_deactivate(rbo->physics_object);
+		rbo->flag |= RBO_FLAG_KINEMATIC;
+		rbo->flag |= RBO_FLAG_KINEMATIC_REBUILD;
+		rbo->flag |= RBO_FLAG_NEEDS_VALIDATE;
 	}
 }
 
@@ -4224,8 +4243,8 @@ static bool do_update_modifier(Scene* scene, Object* ob, RigidBodyWorld *rbw, bo
 				}
 			}
 
-			if (rebuild || rbsc->mi1->rigidbody->flag & RBO_FLAG_KINEMATIC_REBUILD ||
-				rbsc->mi2->rigidbody->flag & RBO_FLAG_KINEMATIC_REBUILD) {
+			if (rebuild) { // || rbsc->mi1->rigidbody->flag & RBO_FLAG_KINEMATIC_REBUILD ||
+				//rbsc->mi2->rigidbody->flag & RBO_FLAG_KINEMATIC_REBUILD) {
 				/* World has been rebuilt 

@@ Diff output truncated at 10240 characters. @@




More information about the Bf-blender-cvs mailing list