Main Menu

Collison and maps question

Started by thefrog, November 17, 2007, 05:04:44 AM

Previous topic - Next topic

thefrog

Hi guys,

I currently trying to write a small game, Lunar lander type, where the ship moves and rotates in a map (like caves)

http://labarette.free.fr/Screenshot.jpg

I used Mappy and the Mappyloader

I need precise collision detection.
If I understand right I need to create a collision map wich is the "outline" of the current map.

I tried using kevin's MakeCollisionWorldFromMap function, but it doesn't seem to work (maybe it's only for simple square tiles)

Is there a tool for doing this outline job ?

Otherwise I think it would be easier to forget the map, and construct it in the program using sprites, wich would permit
perfect collison, don't you think ?

Thanks for your help.




kevin

#1
   Personally, despite a little extra setup  i'd use vector 99.99999% of the time.   As in a vector world, rendering and collision are effectively two separate issues.   This is not the case with pixel collisions.

  Now there's a number of ways to solve such issues thought,  but it's not without some overhead .  Which namely come in the form of  increasing rendering cost and/or increasing the size of the memory foot of the application.  

   Here's a few more ideas to get you started.

   

Image Hit Sprite Pixels


       If collisions are not limited to  screen space (they can occur outside of the visible portion of the world),  then one straight forward approach is to calculate the  bounding region the sprite is currently located at. Convert this area to from world space coordinates to Map / Level  coordinates (if the map is being drawn at position 0,0 the it's just a matter of dividing the coordinates by the Maps Blk width/height).   This will give you a rectangle shape of the tiles the sprite may be intersecting upon the Level.     Then we just run through each tile and compare it back to the sprite in the question, using ImageHitSpritePixels.   Transparent tiles can be ignored, so assuming the blank area of the map are transparent tiles, you'll only be checking for a handful of intersections.    

     Another approach in PB1.7x revisions the built a entity from the overlapping tile region and just compare that as per SpriteHit
           


Map Caching


       If collisions are to only occur within screen space (or just outside it),  then  an extension of the previous idea could be implement a two pass rendering approach.  Pass one renders the Map to a screen sized (or just larger then the screen) image.   Then to detect collisions we can either manually compare the image against the sprites in question, or make a sprite that uses this image (which we'll call our map sprite) and then check if that sprite hits any of the other sprites.   It's better to perform a reversed detections when using  SpriteHit for example.  

       This will work and it's basically how the scramble example (See your PlayBasic/Projects/Games folder).  However we're assuming that the Map gfx and Screen sized Image are FX surfaces. If they're not then this means lots of pixel fetching video access.  I.e.  SLOW!

       If I was using this approach i'd have two copies of the Map blks in memory.  One in normal video format and one in FX format.    I'd use the video formatted  map (which is what it defaults to) for rendering to the screen and FX map for collision purposes.   Those will a keen eye, might have already hit upon something that this approach allows.

     Firstly,   By using two maps,  the second map doesn't have to use the same pixel data as the visible map.  As such you can use it as collision mask.   Which would allow you to fine tune the collision and avoid the 'black pixel' false positives.  Which can make some games too frustrating to bother playing.

     The secondly is that the collision map could be a different size (scaled up or down)  if you wanted.  So you can fine tune the amount of  time it takes to render maps to the collision image and perform impacts upon the map when it's drawn to the image and converted to a sprite.  As per above.




All Sprite Solution


      As you're already mentioned, you could do away with maps entirely and use an all sprite solution.  Clearly it's not advisable to turn every tile into a separate sprite and run collision upon them in world space.  So caching clumps of tiles or segments of the scenery into tiles is the way to go.   The latter is simplest solution but isn't very memory friendly.   Where you could just pre-draw the map and cut it up into chucks.  This would be ok for small worlds say around  twice the size of the screen, but any larger and you're really going to be eating massive amounts of memory.

     What I'd probably do is use a variation of the previous caching idea.  And as such convert rows of tiles into a series of image strips,( than make sprites from them to do collision) or perhaps make a series of 'rect sized images (perhaps 2 or 3 times the size of a tile and do it that way.      By segmenting, you can help reduce the comparison overhead.  Since If the collision image/sprite is the full size of the screen, then  by definition every sprite will end up being compared do it.   The more sprites the more overhead.  
     

     We've really only touched the surface, but there's enough to get you started..




thefrog

Ok thanks for all this info

I will read all this with attention and see what's the best solution for me.

ATLUS

But possible do card with miscellaneous size tiles???