Tuesday, April 8, 2014

Using Box2D on Cocos2dx

Box2D is an open source C++ engine for simulating rigid bodies in 2D.

This does not pretend to be an exhaustive tutorial about using Box2D, there is a lot of information about that already. I will try to show you the biggest mistake i made when using it and that took me a while to figure out: using the PTM_RATIO.

There will be 2 worlds: a graphic world and a physics simulation world.
When you are working on the graphic world you will have everything on terms of pixels, so you need to define a "pixel to meter ratio". This ratio will allow the worlds to communicate.

You can define a couple macros on C++ like this:

#define PTM_RATIO 50
#define WORLD_TO_SCREEN(n) ((n) * PTM_RATIO) //macro to convert meters to pixels.
#define SCREEN_TO_WORLD(n) ((n) / PTM_RATIO) //macro to convert pixels to meters.

You have to remember to use those macros when sending info from a world to another.

You can send info to the physics world:

myBodyDef.position = b2Vec2(SCREEN_TO_WORLD(mySprite->getPositionX()), SCREEN_TO_WORLD(mySprite->getPositionY()));

You will need a method to update your graphics world, and inside it you will move your graphics depending on the output of the physics world. Remember to scale them back:


mySprite->setPosition(WORLD_TO_SCREEN(myBody->GetPosition().x), WORLD_TO_SCREEN(myBody->GetPosition().y));

The third option you will have is to set some variables to the physics world. If you have them in pixels you can use a macro, but if you have them directly on MKS system (the system Box2D uses by default) you can send them directly:

world = new b2World(b2Vec2(0.0f, -9.8f)); //Sets a gravity of 9.8m/s^2

Box2D is designed to work efficiently with objects ranging from 0.1m to 10m. You can scale them back in your graphics world as much as you want, but remember to use the values in that range in the physics world.

Have fun using Box2D...it is amazing!!! :)

No comments:

Post a Comment