0

I am working (still) on an implementation of a Chain Reaction game. I have a lot of particles bouncing around the screen, and the user can tap the screen to create a single 'sticky' particle.

When any normal particle hits the user's sticky particle, that normal particle needs to become sticky also, so anything hitting it becomes sticky, and so on (chain reaction right!)

However, the first time a normal ball collides with the user's sticky ball, the app crashes with the following error in LogCat:

Fatal signal 11 (SIGSGV) at 0x0000005c (code=1), thread 24936 (chainreaction)

Here is the function I use when a collision has been detected (I have commented the line causing the error):

    private void ParticleCollision(Contact contact)
{
    if (contact.getFixtureA().getBody().getUserData() != null &&
        contact.getFixtureB().getBody().getUserData() != null) 
    {
        final String objA = (String)contact.getFixtureA().getBody().getUserData();
        Body bodyA = contact.getFixtureA().getBody();
        final String objB = (String)contact.getFixtureB().getBody().getUserData();
        Body bodyB = contact.getFixtureB().getBody();

        // Get the body objects for each of the bodies in the collision
        Body pBody2 = objA.startsWith("particle_") ? bodyA : bodyB;
        String cud = (String)pBody2.getUserData();

        // Find the normal body in the collision in our mBodyList array                        
        for (int i=0; i < mBodyList.size(); i++)
        {
            Body b = mBodyList.get(i);
            String tud = (String)b.getUserData();

            if(cud.equals(tud))
            {
                // We have a match
                // Get the cooresponding Particle (to get it's X/Y pos)
                Particle p = mParticleList.get(i);
                float x = p.getX();
                float y = p.getY();

                // Remove the particle that collided from our Lists
                mParticleList.remove(i);
                mFixtureList.remove(i);
                mBodyList.remove(i);

                // Remove the particle from the scene and the Body from the PhysicsWorld
                mScene.detachChild(p);
                mPhysicsWorld.destroyBody(b);

                // Create a new sticky particle where the old one was
                particle = new Particle(x, y, mPurpleParticleTextureRegion, 100);
                particle.setScale(0.3f);
                mScene.attachChild(particle);

                particleFixture = PhysicsFactory.createFixtureDef(10, 0.9f, 0.1f);
                    // Using the debugger, I see that this next line is causing the error
                            particle_body = PhysicsFactory.createBoxBody(mPhysicsWorld, particle, BodyType.StaticBody, particleFixture);
                particle_body.setUserData("sticky");
                mPhysicsWorld.registerPhysicsConnector(new PhysicsConnector(particle, particle_body, true, false));

                // Save this info to the sticky particle lists
                mStickyParticleList.add(particle);
                mStickyBodyList.add(particle_body);
                mStickyFixtureList.add(particleFixture);
            }
        }
    }
}

Previously I had that code in the mPhysicsWorld.setContactListener(), in the beginContact() method, but I read that you couldn't create bodies in the ContactListener. So, I moved the code to the function you see, and I call that from the ContactListener.

Any comments or suggestions as to what I have wrong would be greatly appreciated!!

Thanks!!

  • possible duplicate of [Android Fatal signal 11 (SIGSEGV) at 0x636f7d89 (code=1). How can it be tracked down?](http://stackoverflow.com/questions/17840521/android-fatal-signal-11-sigsegv-at-0x636f7d89-code-1-how-can-it-be-tracked) – laminatefish Jun 06 '14 at 15:11
  • You can't change anything in the world inside the Step function. Create the new body after the Step function. – iforce2d Jun 06 '14 at 17:19
  • iforce2d - does that mean I can't modify bodies and fixtures inside the ContactListener? Should I instead flag the object in the contact listener and then update the body/fixture back in the LoadScene method? – user3704686 Jun 06 '14 at 18:13
  • iforce2d - if you can update your comment to be an answer, I will accept it. Thanks for the guidance!! – user3704686 Jun 06 '14 at 18:33

1 Answers1

0

You can't change anything in the world inside the Step function. You'll need to create the new body after the Step function.

The same problem happens if you try to destroy a body inside the contact listener callback, and that seems to be a much more common situation, so you could try searching for problems related to removing bodies, eg. AndEngine Sprite/Box2D Body removal crashes my program with no error/exception information?

The typical method is to have some kind of list that can be accessed from both the main loop (where Step() is called) and inside the contact listener. Make a note of what needs to be modified by adding to the list, and in the main loop immediately after the Step function, you can carry out the changes.

Community
  • 1
  • 1
iforce2d
  • 8,194
  • 3
  • 29
  • 40