2

I am developing a game using jbox2d in conjunction with jBox2d for android. I would like to detect if user touches a particular dynamic body among various bodies in my world. I have tried iterating over all the bodies and find one of my interest but it didnt work for me. Please help Heres what I did :

@Override
public boolean ccTouchesEnded(MotionEvent event)
{
    CGPoint location = CCDirector.sharedDirector().convertToGL(CGPoint.ccp(event.getX(), 
            event.getY()));

    for(Body b = _world.getBodyList();b.getType()==BodyType.DYNAMIC; b.getNext())
    {
        CCSprite sprite = (CCSprite)b.getUserData();
        if(sprite!=null && sprite instanceof CCSprite)
        {
            CGRect body_rect = sprite.getBoundingBox();
            if(body_rect.contains(location.x, location.y))
            {
                Log.i("body touched","<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
                expandAndStopBody(b);
                break;
            }

        }   
    }
return true;
}

After the touch, system continues to print GC_CONCURRENT freed 1649K, 14% free 11130K/12935K, paused 1ms+2ms and everything goes to hung like state.

rahil008
  • 173
  • 1
  • 7

2 Answers2

1

To check if a body is touched you can the method queryAABB of world object. I try to rearrange your code to use the method:

// to avoid creation every time you touch the screen
private QueryCallback qc=new QueryCallback() {

    @Override
    public boolean reportFixture(Fixture fixture) {
            if (fixture.getBody()!=null) 
            {
                    Body b=fixture.getBody();
                    CCSprite sprite = (CCSprite)b.getUserData();
                    Log.i("body touched","<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");           
                    expandAndStopBody(b);
            }
            return false;
    }
};

private AABB aabb;

@Override
public boolean ccTouchesEnded(MotionEvent event)
{
    CGPoint location = CCDirector.sharedDirector().convertToGL(CGPoint.ccp(event.getX(), event.getY()));

    // define a bounding box with width and height of 0.4f
    aabb=new AABB(new Vec2(location.x-0.2f, location.y-0.2f),new Vec2(location.x+0.2f, location.y+0.2f));               
    _world.queryAABB(qc, aabb);            

    return true;
}

I try to reduce garbage collector, but something has to be instanziate to. More info on http://www.iforce2d.net/b2dtut/world-querying

xcesco
  • 4,690
  • 4
  • 34
  • 65
0

You should check to make sure the body is not null in your list, e.g.

for ( Body b = world.getBodyList(); b!=null; b = b.getNext() )
{
    // do something
}

Not sure if this will solve the hang, but should do.

SolidRegardless
  • 427
  • 3
  • 17
  • writing b = b.getNext() instead of simply b.getnext() solves the "hang" problem but now the behaviour is weird. Besides the body that was touched, some other random bodies behave as if they were touched too. Dont know whats happening but may be the way I am adding multiple bodies into world is causing the probs. I have called the code to add a body inside a loop. Is it wrong to do so? Also, please throw some light on b = b.getNext() magic. Thanks – rahil008 Oct 20 '12 at 08:46
  • The magic is actually b != null, because it exits the loop when it has reached the end of the list (linked lists convention). When the end has been reached, b will be equal to null. With regards to your other issue, I would recommend posting the problem on either the Cocos2d forum or the jBox2d forum. It is a very specialised question, that I think the audience from those forums would be better equipped to help. – SolidRegardless Oct 20 '12 at 16:15