Custom Render Loop

cgpauli

24-06-2010 21:56:04

Hi,

i am trying to get OgreNewt running in a simple game with a custom render loop (because i'm using Qt), but somehow it doesn't work. What i do is i create a very simple test scene with only one primitive on which i apply gravity via the Ogre::Body->setStandardForceCallback() function. Then i call Ogre::World->setUpdateFPS(100, 5) once, although i'm not entirely sure what it does. I also call mNewtWorld->update(timediffSec) each frame, where timediffSec is the time in seconds since the last frame. But the primitive doesn't move :-(. If i use the same scene with the Ogre::ExampleApplication and a frame listener like in Demo01_Basics, it works. I would gratly appreciate if somebody could give me a hint how i can use OgreNewt correctly with a custom render loop!

Below the relevant part of my createScene-function:

mNewtWorld = new OgreNewt::World();

Ogre::Entity* floor;
Ogre::SceneNode* floornode;
floor = mSceneMgr->createEntity("Floor1", "cylinder.mesh" );

floornode = mSceneMgr->getRootSceneNode()->createChildSceneNode( "FloorNode1" );
floornode->attachObject( floor );
floor->setMaterialName( "Simple/BeachStones" );
floor->setCastShadows( false );

// okay, the basic mesh is loaded. now let's decide the size of the object, and scale the node.
Ogre::Vector3 size(5,2.5,2.5);
floornode->setScale( size );

// here's where we make a collision shape for the physics. note that we use the same size as
// above.
OgreNewt::ConvexCollisionPtr col = OgreNewt::ConvexCollisionPtr(new OgreNewt::CollisionPrimitives::Cylinder(mNewtWorld, 2.5, 5, 0));

// now we make a new rigid body based on this collision shape.
OgreNewt::Body* body = new OgreNewt::Body( mNewtWorld, col );

Ogre::Vector3 inertia, offset;
col->calculateInertialMatrix(inertia, offset);

body->setMassMatrix( 10.0, 10.0*inertia );
body->setCenterOfMass(offset);

// this is a standard callback that simply add a gravitational force (-9.8*mass) to the body.
body->setStandardForceCallback();

body->attachNode( floornode );
body->setPositionOrientation( Ogre::Vector3(0.0,-10.0,-20.0), Ogre::Quaternion::IDENTITY );

mNewtWorld->setUpdateFPS(100, 5);


Thank you for your help!

SFCBias

24-06-2010 23:29:08

Are you certain that World::update is being called every frame? Also try using a normal CollisionPtr rather than a ConvexCollisionPtr. Other than that I would probably need to see the render loop.

cgpauli

25-06-2010 17:23:11

Are you certain that World::update is being called every frame? Also try using a normal CollisionPtr rather than a ConvexCollisionPtr. Other than that I would probably need to see the render loop.

Thank you for your answer SFCBias! My render loop looks like this:

void OgreView::renderFrame()
{
unsigned long currentTime = mOgreTime->getMicrosecondsCPU();
int timediff = (int)(currentTime-mLastFrameTime);
double timediffSec = timediff/1000000.0;
mLastFrameTime = currentTime;

qDebug()<<mNewtWorld->update(timediffSec)<<" "<<timediffSec;
QtOgreWidget::renderFrame();
}


I call World::update() just before i call the renderFrame() routine of my base class (within the qDebug()-expression). It normally returns an int value of 2 or 3 with a timediffSec of about 0.02. My render loop is called by a Qt-Timer, with about 60 fps. The renderFrame()-routine of my base-class looks like this:

void QtOgreWidget::renderFrame()
{
mRoot->renderOneFrame();
}


I dont think it can be the ConvexCollisionPtr, since if use exactly the same createScene-code in the ogre example-application-framework without custom render loop, it does work.

Thank you so much for your help!

kallaspriit

25-06-2010 19:16:20

If it returs 2/3 or something like this, the world was updated these amount of times. Check out my MinimalOgreNewt application demo, it uses a custom loop, perhaps you spot your problem.

cgpauli

25-06-2010 20:45:31

Thanks, i will have a look at that demo!