Jump to content

Phaser Box2D - sprite and physic body at different location when following player


Miezel
 Share

Recommended Posts

Hello,

I'm having some issues with the sprite and physic body being at two different locations, I would like to have them staying together.

I used this Phaser example , then added a camera follow and set the bound of the camera to null (for an infinite world). 

can anyone enlight me as to why this is happening and how to fix that?

Thanks

 

var game = new Phaser.Game(800, 600, Phaser.CANVAS, 'phaser-example', { preload: preload, create: create, render: render });

function preload() {

    game.load.image('platform', 'assets/sprites/platform.png');
    game.load.image('block', 'assets/sprites/block.png');

}

var platformSprite;
var blockSprite;

function create() {
    
    game.stage.backgroundColor = '#124184';

    // Enable Box2D physics
    game.physics.startSystem(Phaser.Physics.BOX2D);
    game.physics.box2d.gravity.y = 500;
    
    // Static platform 
    platformSprite = game.add.sprite(400, 550, 'platform');
    game.physics.box2d.enable(platformSprite);
    platformSprite.body.static = true;

    // Dynamic box
    blockSprite = game.add.sprite(400, 200, 'block');
    game.physics.box2d.enable(blockSprite);
    blockSprite.body.angle = 30;
    blockSprite.body.kinetic = true;


    game.input.onDown.add(mouseDragStart, this);
    game.input.addMoveCallback(mouseDragMove, this);
    game.input.onUp.add(mouseDragEnd, this);

    game.camera.bounds = null
    game.camera.follow(blockSprite)
}

function render() {
    
    // Default color is white
        game.debug.body(platformSprite);
        game.debug.body(platformSprite.body);
    
        game.debug.body(blockSprite, 'rgb('+222+',0,'+222+')');
        
        game.debug.cameraInfo(game.camera, 500, 32);
        game.debug.spriteInfo(blockSprite, 32, 32);
        game.debug.bodyInfo(blockSprite, 32, 132);

        game.debug.pointer(game.input.mousePointer)
        game.debug.text("" + 'offset sprite to physic body: '+ blockSprite.body.offset, 2, 14, "#00ff00");
    
}

function mouseDragStart() {
    
    game.physics.box2d.mouseDragStart(game.input.mousePointer);
    
}

function mouseDragMove() {
    
    game.physics.box2d.mouseDragMove(game.input.mousePointer);
    
}

function mouseDragEnd() {
    
    game.physics.box2d.mouseDragEnd();
    
}

 

Link to comment
Share on other sites

Hi, if it is that debug rendering is delayed, I would not care. I looked into similar problem some time ago and found, that positon of sprite+body is ok, but debug rendering when using WebGL was delayed by 1 frame. When using Canvas, there was no delay.

 You are already using Canvas in your code, but I think, problem will be the same. Try to log out sprite position and body position and check if it is OK.

Link to comment
Share on other sites

@Tom AtomI think is more than a just debug rendering issue, 

my actual use case is to be able to click on a sprite texture and drag it around ( or do other stuff, like highlighting - to simulate selection)

but after dragging things around the physic body goes off 'somewhere' and I can't drag the sprite anymore ( I later added the debug rendering and saw that it was way off)

The debug info show the sprite position and the body position  to be the same and located the center of the sprite, but it is clearly not the case since I can't drag the sprite/body from that location anymore.

 

sprite and body offset bug.png

Link to comment
Share on other sites

Ok, there are at least two problems: mouse does not work, debug draw is drawn at bad position

1) mouse does not work - your mouse input is in screen coordinates, but body is positioned in world. Before you set your camera to follow, world and screen were aligned to each other. Now, you need to translate screen coordinates into world coordinates. (In fact, you can drag your object now, if you position mouse so it is at screen coords [340, 470] ... which is in the air, but it will drag create). But to make it work as expected change your mouse methods like this:

function mouseDragStart() {
    var position = new Phaser.Point();
    position.copyFrom(game.input.mousePointer.position);

    position.x += game.camera.x;
    position.y += game.camera.y;

    game.physics.box2d.mouseDragStart(position);

}

function mouseDragMove() {
    var position = new Phaser.Point();
    position.copyFrom(game.input.mousePointer.position);

    position.x += game.camera.x;
    position.y += game.camera.y;

    game.physics.box2d.mouseDragMove(position);

}

... of course, you can do it more elegant - add some method "translate", so you will not have to duplicate code

2) debug drawn at bad poisition - if you let your create fall on platform, you will notice, that y position of debug is ok, while x is bad - if you move object right, its debug shape moves opposite. So, there is somewhere bad sign for x coordinate and it is probably in some translation code similar to what we changed for mouse. In box2D plugin, there is method renderbody in file World.js (last method in file):

Phaser.Physics.Box2D.renderBody = function(context, body, color, filled)

and there you can read:

    xf.p.x += -body.game.camera.x / world.ptmRatio;
    xf.p.y -= -body.game.camera.y / world.ptmRatio;

 if you change it to:


    xf.p.x -= -body.game.camera.x / world.ptmRatio;
    xf.p.y -= -body.game.camera.y / world.ptmRatio;

then thing start work.

 Or, you can use another way of debug draw for box2D, which does not suffer from this bug - change beginning of you create mtehod to this:

    // Enable Box2D physics
    game.physics.startSystem(Phaser.Physics.BOX2D);
    game.physics.box2d.debugDraw.shapes = true;
    game.physics.box2d.debugDraw.joints = true;

and in render do this:

function render() {
    game.debug.box2dWorld();

    // Default color is white
    //game.debug.body(platformSprite);
    ////game.debug.body(platformSprite.body);

    //game.debug.body(blockSprite, 'rgb(' + 222 + ',0,' + 222 + ')');

    //game.debug.cameraInfo(game.camera, 500, 32);
    //game.debug.spriteInfo(blockSprite, 32, 32);
    //game.debug.bodyInfo(blockSprite, 32, 132);

    //game.debug.pointer(game.input.mousePointer)
    //game.debug.text("" + 'offset sprite to physic body: ' + blockSprite.body.offset, 2, 14, "#00ff00");

}

this will draw debug for all bodies and all joints.

Link to comment
Share on other sites

 Share

  • Recently Browsing   0 members

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