From b10141db0f63429111f6c82c85ccb921723b5b82 Mon Sep 17 00:00:00 2001 From: sanine Date: Fri, 25 Feb 2022 10:03:47 -0600 Subject: add square:divide() function --- city/geometry-test.lua | 37 +++++++++++++++++++++++++++++++++++++ city/geometry.lua | 20 ++++++++++++++++++++ 2 files changed, 57 insertions(+) diff --git a/city/geometry-test.lua b/city/geometry-test.lua index f85bec0..74ddb3a 100644 --- a/city/geometry-test.lua +++ b/city/geometry-test.lua @@ -93,3 +93,40 @@ test( end end ) + +test( + 'subdivide a square', + function() + local center = geom.point(2, 2) + local square = geom.square(center, 4) + + local children = square:divide() + assert( + #children == 4, + string.format( + 'incorrect number of children: %d', + #children + ) + ) + + local aa = children[1] + assert(aa.center.x == 1) + assert(aa.center.y == 1) + assert(aa.span == 2) + + local ba = children[2] + assert(ba.center.x == 3) + assert(ba.center.y == 1) + assert(ba.span == 2) + + local ab = children[3] + assert(ab.center.x == 1) + assert(ab.center.y == 3) + assert(ab.span == 2) + + local bb = children[4] + assert(bb.center.x == 3) + assert(bb.center.y == 3) + assert(bb.span == 2) + end +) diff --git a/city/geometry.lua b/city/geometry.lua index 1632393..13088d1 100644 --- a/city/geometry.lua +++ b/city/geometry.lua @@ -47,6 +47,9 @@ geom.square = class{ axis_range = function(c, r) return {min=c-r, max=c+r} end, + -- returns true if a point is inside of the square + -- and false otherwise + -- (x/y mininum exclusive, maximum inclusive) contains = function(self, point) local x_overlap = (point.x > self.x.min) and (point.x <= self.x.max) @@ -57,6 +60,23 @@ geom.square = class{ return true end return false + end, + + -- return an array of four squares covering the same + -- area as their parent + divide = function(self) + local this = getmetatable(self).__index + + local x = self.center.x + local y = self.center.y + local d = self.span / 4 + + return { + this(geom.point(x-d, y-d), d*2), + this(geom.point(x+d, y-d), d*2), + this(geom.point(x-d, y+d), d*2), + this(geom.point(x+d, y+d), d*2), + } end } -- cgit v1.2.1