Sprite Occlusion

Get help using Construct 2

Post » Sun Mar 24, 2013 9:22 pm

@sqiddster - Thanks also. Yes this is a definite risk. I have decided to change the design slightly so I don't need full object overlaps for this very reason. I'm going to use several 'sub-objects' instead which will achieve the same effect.

Posts: 16
Reputation: 732

Post » Sun Mar 24, 2013 10:17 pm

@Boomlet OK, cool.
Posts: 3,191
Reputation: 32,739

Post » Sun Mar 24, 2013 11:25 pm

Code: Select all
Global constant number TRUE  = 1
Global constant number FALSE = 0
+ Function: On function "isCovered" :
   Local number result = 0
   -> System: set result to TRUE
   + System: for "y" from 0 to rectangle.Width
      + System: for "x" from 0 to rectangle.Height
         Local number covered = 0
         Local number px = 0
         Local number py = 0
         -> System: set px to rectangle.X - rectangle.width/2  + loopindex("x")
         -> System: set py to rectangle.Y - rectangle.height/2 + loopindex("y")
         + System: Foreach circle
         + System: distance(circle.X,circle.Y,px,py) <= circle.width/2
            -> System: covered = TRUE
            -> System: stop loop  // stop the foreach
         + System: covered = FALSE
            -> System: set result to FALSE
            -> System: stop loop  // stop the "x" loop
            -> System: stop loop  // stop the "y" loop
   -> Function: set return value to result

Untested. But the idea is to sample each pixel of your rectangle and see if there's a circle for which the distance from the center of the circle to this point is lower than its radius.
I make several assumption here:
- you only have one rectangle shape in your layout
- your circle.width is exactly equal to your circle's diameter (I use width/2 for the radius)
- the origin of your rectangle and circle is in the middle

Be carefull the amount of computation will be proportionnal to rectangle.width*rectangle.height*circle.Count at worst case, which is if the rectangle is completely covered since all the loop are stopped as soon as an out of circle point is found.

If you happen to use some kind of grid snapping, you can probably lower the amount of computation since you shouldn't have to check every single point of the rectangle (but not sure)

In any case you shouldn't run this function every tick, but probably only when you drop a circle.

Also using any kind of C2's built-in overlap check isn't really reliable since a circle's collision polygon is usually an octogon and also, checking for radius is probably faster than using polygon based collision detection.

here's a working implementation:
as you can see it can get quickly slow.Yann2013-03-26 08:36:17
Last edited by Yann on Sun Sep 14, 2014 7:26 pm, edited 1 time in total.
Posts: 1,488
Reputation: 16,594

Post » Mon Mar 25, 2013 5:59 pm

@Yann - Thank you so much for this. I'm genuinely blown away that someone would go to all this effort to help out

It definitely works exactly as required and more importantly it's given me something tangible to start playing around with. If I can do anything else clever with it then I'll definitely share.

Thanks again for your help - this forum rocks
Posts: 16
Reputation: 732


Return to How do I....?

Who is online

Users browsing this forum: adventurist and 58 guests