MrLapa
11-12-2008 22:26:15
now my problem is how to manage the collision between objects.
I saw some tutorials,but i dont understand much of what i have to do.
I 'd like to do a simple project with a crate that fall down on a plane and manage the collision.
I do tha plane and the crate that fall down with the gravity...but now i dont know which function i have to use to manage the collision between this 2 objects.
The code now is:
I know there is a function like this:
but if i dont understand bad,this only check if two body are linked(in this case return false) or are in colliosion(and in this case return true)...but i would like to know what i have to do after this to make the crate bouncing on the plane.
I saw some tutorials,but i dont understand much of what i have to do.
I 'd like to do a simple project with a crate that fall down on a plane and manage the collision.
I do tha plane and the crate that fall down with the gravity...but now i dont know which function i have to use to manage the collision between this 2 objects.
The code now is:
#include "ExampleApplication.h"
OgreOde::World *mWorld;
OgreOde::Space *mSpace;
OgreOde::StepHandler *mStepper;
class TutorialFrameListener : public ExampleFrameListener, public OIS::MouseListener, public OIS::KeyListener
{
public:
TutorialFrameListener(RenderWindow* win, Camera* cam)
: ExampleFrameListener(win, cam, true, true)
{
// Populate the camera containers
mCamNode = cam->getParentSceneNode();
// set the rotation and move speed
//mRotate = 0.13;
mMove = 250;
// continue rendering
mContinue = true;
//setta questa classe come ascoltatore di mouse e tastiera
mMouse->setEventCallback(this);
mKeyboard->setEventCallback(this);
//settiamo la direzione iniziale verso l'origine
mDirection = Vector3::ZERO;
}
bool frameStarted(const FrameEvent &evt)
{
if(mMouse)
mMouse->capture();
if(mKeyboard)
mKeyboard->capture();
//applica i movimenti fatti tramite tastiera
mCamNode->translate(mDirection * evt.timeSinceLastFrame, Node::TS_LOCAL);
Ogre::Real time = 0.1;
if (mStepper->step(time))
{
mWorld->synchronise();
}
return mContinue;
}
// MouseListener
bool mouseMoved(const OIS::MouseEvent &e)
{
return true;
}
bool mousePressed(const OIS::MouseEvent &e, OIS::MouseButtonID id)
{
return true;
}
bool mouseReleased(const OIS::MouseEvent &e, OIS::MouseButtonID id) { return true; }
// KeyListener
bool keyPressed(const OIS::KeyEvent &e)
{
switch (e.key)
{
//con il tasto ESC chiude il programma
case OIS::KC_ESCAPE:
mContinue = false;
break;
//movimenti tastiera
case OIS::KC_UP:
case OIS::KC_W:
mDirection.z = -mMove;
break;
case OIS::KC_DOWN:
case OIS::KC_S:
mDirection.z = mMove;
break;
case OIS::KC_LEFT:
case OIS::KC_A:
mDirection.x = -mMove;
break;
case OIS::KC_RIGHT:
case OIS::KC_D:
mDirection.x = mMove;
break;
case OIS::KC_PGDOWN:
case OIS::KC_E:
mDirection.y = -mMove;
break;
case OIS::KC_PGUP:
case OIS::KC_Q:
mDirection.y = mMove;
break;
default:
break;
}
return mContinue;
}
bool keyReleased(const OIS::KeyEvent &e)
{
//annullare i cambiamenti dopo che il pulsante è rilasciato...se nn messo,continua sempre in quella direzione
switch (e.key)
{
case OIS::KC_UP:
case OIS::KC_W:
mDirection.z = 0;
break;
case OIS::KC_DOWN:
case OIS::KC_S:
mDirection.z = 0;
break;
case OIS::KC_LEFT:
case OIS::KC_A:
mDirection.x = 0;
break;
case OIS::KC_RIGHT:
case OIS::KC_D:
mDirection.x = 0;
break;
case OIS::KC_PGDOWN:
case OIS::KC_E:
mDirection.y = 0;
break;
case OIS::KC_PGUP:
case OIS::KC_Q:
mDirection.y = 0;
break;
default:
break;
} // switch
return true;
}
protected:
Real mRotate; // The rotate constant
Real mMove; // The movement constant
SceneManager *mSceneMgr; // The current SceneManager
SceneNode *mCamNode; // The SceneNode the camera is currently attached to
bool mContinue; // Whether to continue rendering or not
Vector3 mDirection; // Value to move in the correct direction
};
class TutorialApplication : public ExampleApplication,public OgreOde::CollisionListener
{
protected:
OgreOde::InfinitePlaneGeometry *mGround;
OgreOde::Body *mBody;
OgreOde::Geometry *mGeom;
OgreOde::BoxMass mMass;
Ogre::SceneNode *mNode;
Ogre::Entity *mEntity;
public:
TutorialApplication()
{
}
~TutorialApplication()
{
}
void createCamera(void)
{
// create camera, but leave at default position
mCamera = mSceneMgr->createCamera("PlayerCam");
mCamera->setNearClipDistance(5);
}
void createFrameListener(void)
{
// Create the FrameListener
mFrameListener = new TutorialFrameListener(mWindow, mCamera);
mRoot->addFrameListener(mFrameListener);
// Show the frame stats overlay
mFrameListener->showDebugOverlay(true);
}
void createScene(void)
{
/*la gerarchia è SCENEMANAGER...SCENENODE...ENTITY*/
//settaggio luce di ambiente...R,G,B da 0 ad 1
mSceneMgr->setAmbientLight( ColourValue( 1, 1, 1 ) );
//attacco camera allo SceneNode
// Create the scene node
SceneNode *node = mSceneMgr->getRootSceneNode()->createChildSceneNode("CamNode1", Vector3(0, 80, 300));
// Create the pitch node
//node = node->createChildSceneNode("PitchNode1");
node->attachObject(mCamera);
//INIZIO PARTE MOTORE FISICO
mWorld = new OgreOde::World(mSceneMgr);
mWorld->setGravity(Ogre::Vector3(0,-9.80665,0));
mWorld->setCFM(10e-5);
mWorld->setERP(0.8);
mWorld->setAutoSleep(true);
mWorld->setAutoSleepAverageSamplesCount(10);
mWorld->setContactCorrectionVelocity(1.0);
mSpace = mWorld->getDefaultSpace();
const Ogre::Real _time_step = 0.5;
const Ogre::Real time_scale = Ogre::Real(1.7);
const Ogre::Real max_frame_time = Ogre::Real(1.0 / 4);
mStepper = new OgreOde::StepHandler(mWorld, OgreOde::StepHandler::QuickStep,_time_step, max_frame_time,
time_scale);
mGround = new OgreOde::InfinitePlaneGeometry(Plane(Ogre::Vector3(0,1,0),0), mWorld, mWorld->getDefaultSpace());
// Use a load of meshes to represent the floor
int i = 0;
StaticGeometry* s;
s = mSceneMgr->createStaticGeometry("StaticFloor");
s->setRegionDimensions(Ogre::Vector3(160.0, 100.0, 160.0));
// Set the region origin so the center is at 0 world
s->setOrigin(Ogre::Vector3::ZERO);
for (Real z = -80.0;z <= 80.0;z += 20.0)
{
for (Real x = -80.0;x <= 80.0;x += 20.0)
{
String name = String("Ground") + StringConverter::toString(i++);
Entity* entity = mSceneMgr->createEntity(name, "plane.mesh");
entity->setQueryFlags (1<<4);
entity->setUserObject(mGround);
entity->setCastShadows(false);
s->addEntity(entity, Ogre::Vector3(x,0,z));
}
}
s->build();
mEntity = mSceneMgr->createEntity("crate","crate.mesh");
mEntity->setQueryFlags (1<<2);
mNode = mSceneMgr->getRootSceneNode()->createChildSceneNode("crate");
mNode->attachObject(mEntity);
//mEntity->setNormaliseNormals(true);
mEntity->setCastShadows(true);
mBody = new OgreOde::Body(mWorld);
mNode->attachObject(mBody);
Vector3 size(10.0,10.0,10.0);
OgreOde::BoxMass mMass(0.5,size);
mMass.setDensity(5.0,size);
mGeom = (OgreOde::Geometry*)new OgreOde::BoxGeometry(size, mWorld, mSpace);
mNode->setScale(size.x * 0.1,size.y * 0.1,size.z * 0.1);
mBody->setMass(mMass);
mGeom->setBody(mBody);
mEntity->setUserObject(mGeom);
mBody->setOrientation(Quaternion(Radian(5.0),Ogre::Vector3(0,0,0)));
mBody->setPosition(Vector3(0,120,-20));
}
};
//MAIN
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
#define WIN32_LEAN_AND_MEAN
#include "windows.h"
INT WINAPI WinMain( HINSTANCE hInst, HINSTANCE, LPSTR strCmdLine, INT )
#else
int main(int argc, char **argv)
#endif
{
// Create application object
TutorialApplication app;
try {
app.go();
} catch( Exception& e ) {
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
MessageBox( NULL, e.what(), "An exception has occurred!", MB_OK | MB_ICONERROR | MB_TASKMODAL);
#else
fprintf(stderr, "An exception has occurred: %s\n",
e.what());
#endif
}
return 0;
}
I know there is a function like this:
bool collision(OgreOde::Contact* contact)
{
// Check for collisions between things that are connected and ignore them
OgreOde::Geometry * const g1 = contact->getFirstGeometry();
OgreOde::Geometry * const g2 = contact->getSecondGeometry();
if (g1 && g2)
{
const OgreOde::Body * const b1 = g1->getBody();
const OgreOde::Body * const b2 = g2->getBody();
//if connected ignore them
if (b1 && b2 && OgreOde::Joint::areConnected(b1, b2))
return false;
}
// Set the friction at the contact
contact->setCoulombFriction(OgreOde::Utility::Infinity);
contact->setBouncyness(0.1);
// Yes, this collision is valid
return true;
}
but if i dont understand bad,this only check if two body are linked(in this case return false) or are in colliosion(and in this case return true)...but i would like to know what i have to do after this to make the crate bouncing on the plane.