Ever want 2D, colliding GUIs?

So do many. Lots of people turn to implementing Axis-Aligned Bounding-Boxes (AABB). That works… for some things. Any time it’s not as simple as “we’ve got lots and lots of rectangles that don’t rotate”, you have a use-case for SAT. SAT stands for “Separating Axis Theorem”, or as I like to call it, “Simple Can You Draw Line Theorem” (we’ll stick with the former).

Basically, pretend you’ve got 2 polygons, right? Convex ones. Shine a light on them, mentally. Look at the shadow. Congrats! You just projected a 2D object into 1D. “wtf does this mean?” you might be wondering. It means that you did math! The very most important math in SAT. Basically, you have to pretend we have 2 polygons, and we shine lights on them. If you ever see a gap between the shadows, where light got through, it means they’re not colliding! Easy as that.

You can do something similar in real life. First, get two objects that are both polygons (no circles allowed), preferably around the same height. Put them on a flat surface next to a wall. Now, turn off the lights, and shine a flashlight from the side onto them. Do this in many directions. You should be able to find one (or many) directions that the shadows don’t intersect! That means, by SAT, they don’t intersect.

SAT is this concept: “project” the 2D polygons onto a 1D line, and if those lines intersect, do it again with a different direction. There are only a few directions you HAVE to check, though: the “normals” of the faces. To find out what that means, check out Axis’ post here. Once you get the normals, project the shape using that axis, and check if the line produced by that are intersecting. You have to check all the normals, and if upon viewing all the normals, they still aren’t deemed “not colliding”, it’s 100% certain that they are colliding and you can return true.

I made a thing in Love2D to show this. Here’s a link to that.This has all the info and more, plus the Lua files. A .love is a renamed zip file.

Oh gosh, I hope you optimized it to be a AABB-OBB SAT collision, by transforming one rectangle into the object space of the other, if not, you’re doing it wrong

That’s OBB collision, not SAT collision. OBB only works for rectangles, while SAT works for all convex polygons (see the example using a rectangle and a pentagon). If I were to use OBB, I’d only be able to use rectangles, which is a :(.

Also, I totally didn’t make a typo in the subject line. I definitely was tired and I’m definitely not editing it.

Roblox frames are only rectangles, so it’s actually a plus, and you could have a separate SAT Collision for polygons, it’s a legit performance boost to have a AABB-OBB SAT collision function on hand, you can do sooo many manual optimizations with it :DDD

You’re not restricted to only rectangles in ROBLOX. What I’m working on next it taking the vertices of a polygon and decomposing it into triangles to represent it with ImageLabels. Also, it’s true that you could implement OBB to go with SAT for optimizations in rectangle-rectangle collision, but it’s just a SAT implementation with no need of OBB. Rectangles are handled perfectly well with SAT.

They are handled perfectly well with a normal SAT check, but about half as efficient as one optimized for rectangles