Jump to content

How to let Spriter participate in Box2D with libGdx


Recommended Posts

Hello everyone!

 

I'm pondering on how to let a Spriter's sprite take part in B2D physics world. First of all my general question: How would you do it?

 

My thoughts so far:

First of all I used the loader/drawer of trixt0r to get to ready setup libGdx Sprites conveniently. From tis point I tried to get them taking part in physics.

 

a) My first idea was to make out of each object/box of an entity a static B2D-Body which get a rectangular shape. The rect-shape is just for simplicity - of course the don't yield perfect coillsion.

These bodies get updated each frame when the Spriter animation renders to get new x,y and rotation.

By doing this, the texture regions of the sprite are sync'ed with the body's fixture shape.

It follows a screenshot of the Spriters monster-Sprite, where all the objects (trixt0r lib for libGdx) which have textures attached to have a green bounding box around them. These Boxes are also shapes attached to B2D-Bodies (as fixture shape).

 

e7cch1.jpg

This works so far unless I want to apply force to the monster itself. The problem is that the animation itself is controlling the physics not vice versa.

I 'd want to let the monster fall down, I would have to make these by translation the coordinates of the Sprite instead of letting the Word control the position e.g.  when its no longer grounded because there is no body underneath - thus I'm loosing the a lot of the advantages of a physics sim. 

I pasted in some code for setting this up (the following iteration is based on the code of libGdxDrawer class of trixt0r except the b2d stuff) - just to get the idea.

  public static void setUpBodiesToWorld(Player player, Loader<SpriteBox2D> loader,World world) {        Iterator<Timeline.Key.Object> it = player.objectIterator();        while(it.hasNext()){            // itereation over all the objects with a libGdx-Sprite            Timeline.Key.Object object = it.next();            /* the loader is of tpe Loader<SpriteBox2d> - its like Sprite , I put just  a               public field for the body in it */            SpriteBox2D sprite = loader.get(object.ref);                        /*Setting up the fixture shape of the body - below is just an example for taking the objects-boxes a shapes for bodies */            PolygonShape box = new PolygonShape();            box.setAsBox(sprite.getWidth() / 2 * sprite.getScaleX() ,                    sprite.getHeight() / 2 * sprite.getScaleY() , vector.set(sprite.getX(), sprite.getY()),                    sprite.getRotation() * MathUtils.degRad);            BodyDef boxBodyDef = new BodyDef();            boxBodyDef.type = BodyDef.BodyType.StaticBody;                        Body body = world.createBody(boxBodyDef);            /*assigning the body and making a association between the TextureRegion and the body              When rendering the sprite, the body can be easily retrieved and positioned*/            sprite.body = body;            Fixture fixture = body.createFixture(box, 1);            fixture.setUserData(sprite);            box.dispose();        }    } 

When the libGdx-Drawer iterates over the Player and retrieves the Sprites an additional body can be retrieved and positioned.

 

b > My second guess was to draw a static form around the sprite (like the orange ellipse in the screenshot) which encompasses roughly the sprite. This shape is the bodyshape in B2D and keeps track of the curren pos and rotation.

The sprite positions accordingly to the shape - but with odd visual side effects - e.g. things which look like they should collide don't and vice versa.

 

I believe the main problem is that the physics aren't involved animating the bones and its difficult to make them behave physically afterwards.

 

What are your thoughts/Experiences?

 

Thanks david

 

 

 

 

Link to comment
Share on other sites

  • 2 weeks later...

Hi systemExklusiv,

 

the hardest part, to get Box2D working with the Spriter API is the fact, that you have to create correct joints between the sprites. If you have bones for an entity, this should be rather easy (depends on how bones are meant to work for an entity) and an automated process for creating the joints could be implemented. But if you do not know how a sprite is related to another one, you have to define the joints manually, which may cost you some time (depends on the complexity of an entity).

 

However, if you know how to connect the Box2D objects, it should not be a problem to let Box2D manipulate the sprites. The inverse kinematics part of the library does a similar thing. The current transformation of each object/bone gets read and then manipulated. The trick is, to let the player first update itself, then manipulate the transformation of each spriter object and draw the actual result to the screen. The logic would look like this:

// Update player, can actually be skipped if the box2D bodies are already initialized.player.update();// Setup box2D bodies and joints, has to be called only oncespriterBox2DFetch(player);// Simulate physicsbox2DWorld.step(1/60f, 6, 2);// Set the transformation of the spriter objects to the one of the box2D objectsspriterBox2DTransformation(player);// Draw the resultdrawer.draw(player);

I may try to add an example to the test suite for this case, this week.

 

- Trixt0r

Link to comment
Share on other sites

  • 3 months later...

Oh man, sorry for the delay! Thanks form the answer! Yeah, your idea encompasses some really complicated 'force-applying' to simulate e.g. a walking movement. One could go further this direction: create a body for each object and interconnect them with joints. update all bodies by the animation except one at the center, which position etc. will be  calculated by the physics world. All the other bodies will driven by the animation, in a way that joints are adjusted. But this seems difficult to accomplish.

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...