5
\$\begingroup\$

How do I import and attach a PNG or GIF to a shape in Box2dWeb?

The best resource I could find online is at: http://www.jeremyhubble.com/box2d.html

However, this "tutorial" doesn't give much explanation about how images are actually used. So it is clearly possible, but I can't get the userData trick to work.

\$\endgroup\$
9
\$\begingroup\$

You are generally responsible for rendering the state of your box2d world - the "userData trick" you refer to is not really to do with the box2d framework.

userData is a placeholder for arbitrary data that you want to associate to a body. This could be anything - a string, function, object, etc. This data is typically used to help you render your world during the update loop, which is exactly what the resource you linked to does - If you look at the processObjects function it uses the imgsrc value to create an Image object and draws it onto the canvas at the correct location. (This isn't really a good idea because the image is created once per object per iteration - I would suggest it should only be created once)

Here's a quick sample that shows how you can use a PNG to represent a box2d object - you'll need an 50x50px image called "image.png" and the box2web javascript file from the project site in the same folder as the html.

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <title></title>
</head>
<body>
    <canvas id="canvas" width="1024" height="700" />

    <!-- Get this from the box2dweb project site -->
    <script type="text/javascript" src="Box2dWeb-2.1.a.3.min.js"></script>

    <script type="text/javascript">
    var CANVAS_WIDTH = 1024, CANVAS_HEIGHT = 700, SCALE = 30;

    var b2Vec2 = Box2D.Common.Math.b2Vec2
            , b2BodyDef = Box2D.Dynamics.b2BodyDef
            , b2Body = Box2D.Dynamics.b2Body
            , b2FixtureDef = Box2D.Dynamics.b2FixtureDef
            , b2Fixture = Box2D.Dynamics.b2Fixture
            , b2World = Box2D.Dynamics.b2World
            , b2MassData = Box2D.Collision.Shapes.b2MassData
            , b2PolygonShape = Box2D.Collision.Shapes.b2PolygonShape
            , b2CircleShape = Box2D.Collision.Shapes.b2CircleShape
            , b2DebugDraw = Box2D.Dynamics.b2DebugDraw;

    var canvas = document.getElementById("canvas");
    var context = canvas.getContext("2d");

    var world = new b2World(new b2Vec2(0, 2), true);

    // Create some objects in the world
    var fixDef = new b2FixtureDef();
    fixDef.density = 1.0;
    fixDef.friction = 0.5;
    fixDef.restitution = 1;
    var bodyDef = new b2BodyDef();

    for (var i = 0; i < 40; i++) {
        bodyDef.type = b2Body.b2_dynamicBody;
        bodyDef.position.Set((Math.random() * 400) / SCALE, (Math.random() * 400) / SCALE);
        bodyDef.linearVelocity.Set((Math.random() * 12) + 2, (Math.random() * 12) + 2);

        fixDef.shape = new b2PolygonShape();
        fixDef.shape.SetAsBox(25 / SCALE, 25 / SCALE);
        world.CreateBody(bodyDef).CreateFixture(fixDef);
    }

    // This is where you load the image data - make it a 50px x 50px image
    // You should use some sort of pre-loader to make sure the image is loaded prior to 
    // using it.
    var image = new Image();
    image.src = "image.png";

    // Set up the game loop - you might want to look into using window.requestAnimationFrame
    // or some variation of that.
    window.setInterval(gameLoop, 1000 / 60);

    function gameLoop() {
        // Update the box2d world
        world.Step(1 / 60, 8, 3);
        world.ClearForces();

        context.clearRect(0, 0, CANVAS_WIDTH, CANVAS_HEIGHT);

        for (b = world.GetBodyList() ; b; b = b.GetNext()) {
            if (b.GetType() == b2Body.b2_dynamicBody) {
                var pos = b.GetPosition();

                context.save();
                context.translate(pos.x * SCALE, pos.y * SCALE);
                context.rotate(b.GetAngle());
                context.drawImage(image, -25, -25);
                context.restore();
            }
        }
    }

    </script>
</body>
</html>

Hope that helps!

\$\endgroup\$
4
  • 1
    \$\begingroup\$ You are a god! I really appreciate your help. This gives me a great starting point and moving forward I think Cocos2d may be the best solution for a more advanced project. \$\endgroup\$
    – VinLucero
    Apr 25 '12 at 21:29
  • \$\begingroup\$ I read several tutorials, and reverse engineered so many box2d examples when all it took to learn was play with your short and simple code. \$\endgroup\$ Jul 24 '12 at 3:44
  • \$\begingroup\$ Glad I could help! \$\endgroup\$ Jul 24 '12 at 9:32
  • \$\begingroup\$ I found this file and I cannot get it to work. I download the Box2dWeb file and saved it as a .js (javascript) file. What should I do next. I am new to the Box2dWeb code. \$\endgroup\$
    – user45402
    Jun 25 '14 at 15:33
1
\$\begingroup\$

Maybe this can help too. Have a look. http://codingowl.com/readblog.php?blogid=134

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.