Raycast from bottom of body to detect floor collision

Post Reply
Pacha
Posts: 26
Joined: Sat Jun 15, 2013 2:29 am

Raycast from bottom of body to detect floor collision

Post by Pacha »

This probably is a simple question, I made a working ray casting from the center of my btRigidBody object, but it always hits itself (as it is casted from the center).

What would be the best approach to use a ray cast from the bottom part of my body down the Y-axis? As I want to know if my body is touching the floor.

I want to do this because I want to apply a certain velocity (simulating a jump) when a key is pressed, and I want to do this only if my body is touching something below.

Thanks!
Tau
Posts: 25
Joined: Tue May 01, 2012 11:52 am

Re: Raycast from bottom of body to detect floor collision

Post by Tau »

You should look at CharacterDemo.

Code: Select all

class ClosestNotMe : public btCollisionWorld::ClosestRayResultCallback
	{
	public:
		ClosestNotMe (btRigidBody* me) : btCollisionWorld::ClosestRayResultCallback(btVector3(0.0, 0.0, 0.0), btVector3(0.0, 0.0, 0.0))
		{
			m_me = me;
		}

		virtual btScalar addSingleResult(btCollisionWorld::LocalRayResult& rayResult,bool normalInWorldSpace)
		{
			if (rayResult.m_collisionObject == m_me)
				return 1.0;

			return ClosestRayResultCallback::addSingleResult (rayResult, normalInWorldSpace);
		}
	protected:
		btRigidBody* m_me;
	};

	ClosestNotMe rayCallback(m_rigidBody);
Norbert
Posts: 2
Joined: Sat Aug 16, 2014 10:00 pm
Location: Netherlands

Re: Raycast from bottom of body to detect floor collision

Post by Norbert »

I hope it's okay that I'm bumping this thread. I'm trying to accomplish the exact same thing Pacha wanted, namely to only allow jumping when the btRigidBody is touching something below. Since Bullet's real-time simulation isn't 100% accurate, I cannot use btRigidBody->getCenterOfMassPosition().getY(). After all, when I land on y=2, Bullet first gives an approximation (like y=1.872293) and then slowly works its way up (or, sometimes, down) to the actual value.

My question: can someone supplement Tau's remarks with more information? The code Tau pasted appears to be from DynamicCharacterController.cpp (of the CharacterDemo). I have trouble understanding what other parts of that code I would need to get what I want. Should I attach a callback to operations or to the btRigidBody? "ClosestNotMe rayCallback(m_rigidBody);" by itself won't be enough.
TeKilla
Posts: 3
Joined: Thu Aug 14, 2014 7:35 am

Re: Raycast from bottom of body to detect floor collision

Post by TeKilla »

I had this problem and solved it simply by retrieving the btRigidBody hitted.
When you have a hit, just check if RayCallback.m_collisionObject is different than your character rigidbody.
If not, then do a raycast which start at the end of your previous raycast and check again.

if hit
--if m_collisionObject != me
----return true // collision happend with something
--else //i hit myself
----raycast from the end of the current raycast
Norbert
Posts: 2
Joined: Sat Aug 16, 2014 10:00 pm
Location: Netherlands

Re: Raycast from bottom of body to detect floor collision

Post by Norbert »

Hi TeKilla, thanks for trying to help me.

By your "if hit" pseudocode, do you mean RayCallback.hasHit(), preceded by a btDiscreteDynamicsWorld.rayTest (From, To, RayCallback); ?

If so, would I need to create a btCollisionWorld::ClosestRayResultCallback RayCallback (From, To); ?

If so, would the From be btRigidBody *btPlayer; btPlayer->getCenterOfMassPosition(); ?

What exactly would the To vector be?
I have several thousand objects that function as floors, should I loop through them?
If so, would the loop be something like this:
for (list<btRigidBody *>::Iterator Iterator = Objects.begin(); Iterator != Objects.end(); ++Iterator) { /* use *Iterator */ }

The actual hit check in the loop, will it be like this:
if (RayCallback.m_collisionObject != btPlayer) { /* hit! maybe use RayCallback.hitPointWorld in some way? */ }

Also, how do I know the /bottom/ of btPlayer is touching the other object?
And what if the player is touching the left of an L shaped object whose _ is a floor but its | is a wall that shouldn't trigger a hit?
Post Reply