From a798e0e0ffe327b405206a561538e88d1e8db7da Mon Sep 17 00:00:00 2001 From: Mathias Gumz Date: Sat, 19 Mar 2011 14:56:45 +0100 Subject: added RectangleUtil::overlapRectangles() + test cases --- src/RectangleUtil.hh | 44 +++++++++++++++++++++++++++++++++ src/tests/testRectangleUtil.cc | 55 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 99 insertions(+) diff --git a/src/RectangleUtil.hh b/src/RectangleUtil.hh index 88c3a33..9725e63 100644 --- a/src/RectangleUtil.hh +++ b/src/RectangleUtil.hh @@ -24,6 +24,50 @@ bool insideBorder(const RectangleLike& rect, y < rect.y() + (int)rect.height() + border_width; } + + +/* + * Determines if rectangle 'a' overlaps rectangle 'b' + * @returns true if 'a' overlaps 'b' + * + * outside overlap situations + * + * a----a a----a a--------a b--------b + * | | b----b | b-+--b | b----b | | a----a | + * a----a | | a--+-a | | | | | | | | | + * b----b b----b | b----b | | a----a | + * a--------a b--------b + * + */ + +inline bool overlapRectangles( + int ax, int ay, int awidth, int aheight, + int bx, int by, int bwidth, int bheight) { + + bool do_not_overlap = + ax > (bx + bwidth) + || bx > (ax + awidth) + || ay > (by + bheight) + || by > (ay + aheight); + + return !do_not_overlap; +} + + +/* + * Determines if rectangle 'a' overlaps rectangle 'b' + * @param a - rectangle a + * @param b - rectangle b + * @returns true if 'a' overlaps 'b' + */ +template +bool overlapRectangles(const RectangleLikeA& a, const RectangleLikeB& b) { + + return overlapRectangles( + a.x(), a.y(), a.width(), a.height(), + b.x(), b.y(), b.width(), b.height()); +} + } // namespace RectangleUtil diff --git a/src/tests/testRectangleUtil.cc b/src/tests/testRectangleUtil.cc index f10b6af..2da2a4e 100644 --- a/src/tests/testRectangleUtil.cc +++ b/src/tests/testRectangleUtil.cc @@ -55,12 +55,67 @@ int test_insideBorder() { return 0; } +int test_overlapRectangles() { + printf("testing RectangleUtil::overlapRectangles()\n"); + + struct _t { + struct Rect a; + struct Rect b; + int truth; + }; + + struct _test { + bool operator()(const Rect& a, const Rect& b, int truth, int i) { + + int result = RectangleUtil::overlapRectangles(a, b); + + printf(" %d: [%2d %2d]-[%2d %2d] %s [%2d %2d]-[%2d %2d]: %s\n", + i, + a.x(), a.y(), + a.x() + (int)a.width(), + a.y() + (int)a.height(), + result ? "overlaps" : "does not overlap", + b.x(), b.y(), + b.x() + (int)b.width(), + b.y() + (int)b.height(), + result == truth ? "ok" : "failed"); + return result == truth; + } + }; + + const _t tests[] = { + + { { 0, 0, 8, 8 }, { 0, 0, 8, 8 }, true }, // b equals a + { { 0, 0, 8, 8 }, { 3, 3, 3, 3 }, true }, // b completely inside a + { { 0, 0, 8, 8 }, { 4, 4, 8, 8 }, true }, // b overlaps a in one corner + { { 0, 0, 8, 8 }, { 4,-1, 2, 9 }, true }, // b overlaps a in the middle + + { { 0, 0, 8, 8 }, { -8, 0, 5, 8 }, false }, // b completely left from a + { { 0, 0, 8, 8 }, { 9, 0, 5, 8 }, false }, // b completely right from a + { { 0, 0, 8, 8 }, { 0,-9, 5, 8 }, false }, // b completely down below a + { { 0, 0, 8, 8 }, { 0, 9, 5, 8 }, false }, // b completely up above a + }; + + + + _test test; + int i; + for (i = 0; i < sizeof(tests)/sizeof(_t); ++i) { + test(tests[i].a, tests[i].b, tests[i].truth, i); + test(tests[i].b, tests[i].a, tests[i].truth, i); + } + + printf("done.\n"); + + return 0; +} int main(int argc, char **argv) { test_insideBorder(); + test_overlapRectangles(); return 0; } -- cgit v0.11.2