I've posted my collision code here for starters, removing all the game specific stuff so you can see how I've iterated through the collisions for anything important. Added more comments but feel free to ask questions.
It's important to know that when everything was made, the body Ids were stored in globals (array for balls and gScenery.xxx for other stuff). I didn't store the fixtures so you have to work back to get them for the collisions(I have no performance issues so I haven't finetuned this).
arrBall(n).hit is the time of last collision. I use this to filter out multiple reactions to the same collision. I found that one collision of 2 balls could trigger 2 or 3 collisions at 60 FPS.
function checkCollisions()
for n = 1 to g.numBalls
` *** Process all active balls, no need to waste time on inactive ones
if arrBall(n).state > cBALLINACTIVE
` *** For each ball get any contacts. This initialises a list of contacts
b2FindBodyContacts arrBall(n).body
contact = b2GetContact()
` *** Iterate through the list of contacts for any relevant ones
while contact > 0
` *** Get the contact details. "Touching" means a true contact, not just proximity
` *** Then, we have to find the second contact, could be Body A or B
` ** Use a little jiggery pokery to get the second body
if b2GetContactIsTouching()
fixture = b2GetContactFixtureA()
body = b2GetFixtureBody(fixture)
if body = arrBall(n).body
fixture = b2GetContactFixtureB()
body = b2GetFixtureBody(fixture)
endif
` *** Process Balls in Play
` *** Active Bodies can be on the ramp (nothing to do other than wait for it to come into play)
` *** or in play
if arrBall(n).state > cBALLONRAMP
` *** Hit the floor? ***
if body = gScenery.floor and arrBall(n).hit < Hitimer() - 100
` *** Process the floor hit - destroy or reduce ball level
` *** Some nice explosion effects and sounds
` *** ...
` *** ...
exit
endif
` *** Hit the Score Wall? ***
if body = gScenery.scoreWall
` *** Nice explosion, add to score, inactivate ball
exit
endif
` * Hit another ball?
` *** Iterate through the balls to see if we have a ball <> ball collision
` *** make sure each ball only processed once (ignore collison registered on 2nd ball)
if arrBall(n).hit < Hitimer() - 100
for m = n + 1 to g.numBalls
if body = arrBall(m).body
` *** nice explosion, change ball level and colour
` *** sound effects
exit
endif
next m
endif
` *** Process balls on Ramp
else
` * Hit the Slide?
` *** Put ball intop play. Increase restitution to "bouncy"
if body = gScenery.slide and arrBall(n).state = cBALLONRAMP
b2SetFixtureRestitution arrBall(n).fixture, g.ballRestitution
arrBall(n).state = cBALLINPLAY
exit
endif
endif : ` END IF BALLINPLAY
endif
contact = b2GetContact()
endwhile
endif
next n
endfunction
