-
-
Notifications
You must be signed in to change notification settings - Fork 6.3k
Commit
… to Memphiz for figuring this out
- Loading branch information
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -27,6 +27,8 @@ | |
#else | ||
#define XBMC_FORCE_INLINE | ||
#endif | ||
|
||
#include <vector> | ||
#include <algorithm> | ||
|
||
class CPoint | ||
|
@@ -154,6 +156,192 @@ class CRect | |
return Width() * Height(); | ||
}; | ||
|
||
std::vector<CRect> SubtractRect(CRect splitterRect) | ||
{ | ||
#define ADD_RECT_ABOVE_INTERSECTION(add) \ | ||
{ \ | ||
add = CRect(x1, y1, x2, intersection.y1);\ | ||
newRectaglesList.push_back(add);\ | ||
} | ||
#define ADD_RECT_BELOW_INTERSECTION(add) \ | ||
{\ | ||
add = CRect(x1, intersection.y2, x2, y2);\ | ||
newRectaglesList.push_back(add);\ | ||
} | ||
#define ADD_RECT_LEFT_OF_INTERSECTION(add) \ | ||
{\ | ||
add = CRect(x1, intersection.y1, intersection.x1, intersection.y2);\ | ||
newRectaglesList.push_back(add);\ | ||
} | ||
#define ADD_RECT_RIGHT_OF_INTERSECTION(add) \ | ||
{\ | ||
add = CRect(intersection.x2, intersection.y1, x2, intersection.y2);\ | ||
newRectaglesList.push_back(add);\ | ||
} | ||
|
||
std::vector<CRect> newRectaglesList; | ||
CRect intersection = splitterRect.Intersect(*this); | ||
|
||
if (!intersection.IsEmpty()) | ||
{ | ||
CRect add; | ||
// intersection rect upper edge | ||
if (intersection.y1 == y1) // y starts with baserect | ||
{ | ||
// intersection rect lower edge | ||
if (intersection.y2 == y2) // y goes down to baserect | ||
{ | ||
if (intersection.x1 == x1) // x starts with baserect | ||
{ | ||
if (intersection.x2 == x2) // x ends with baserect | ||
{ // result 100% covered | ||
// add nothing | ||
} | ||
else // x ends in baserect | ||
{ // results in 1 rect | ||
ADD_RECT_RIGHT_OF_INTERSECTION(add); | ||
} | ||
} | ||
else // x starts in baserect | ||
{ | ||
if (intersection.x2 == x2) // x ends with baserect | ||
{ // results in 1 rect | ||
ADD_RECT_LEFT_OF_INTERSECTION(add); | ||
} | ||
else // x ends in baserect | ||
{ //results in 2 rects | ||
ADD_RECT_LEFT_OF_INTERSECTION(add); | ||
ADD_RECT_RIGHT_OF_INTERSECTION(add); | ||
} | ||
} | ||
} | ||
else // y ends in baserect | ||
{ | ||
if (intersection.x1 == x1) // x starts with baserect | ||
{ | ||
if (intersection.x2 == x2) // x ends with baserect | ||
{ //results in 1 rect, below intersection | ||
ADD_RECT_BELOW_INTERSECTION(add); | ||
} | ||
else // x ends in baserect | ||
{ // results in 2 rects | ||
ADD_RECT_BELOW_INTERSECTION(add); | ||
ADD_RECT_RIGHT_OF_INTERSECTION(add); | ||
} | ||
} | ||
else // x starts in baserect | ||
{ | ||
if (intersection.x2 == x2) // x ends with baserect | ||
{ //results in 2 rects | ||
ADD_RECT_BELOW_INTERSECTION(add); | ||
ADD_RECT_LEFT_OF_INTERSECTION(add); | ||
} | ||
else // x ends in baserect | ||
{ //results in 3 rects | ||
ADD_RECT_BELOW_INTERSECTION(add); | ||
ADD_RECT_LEFT_OF_INTERSECTION(add); | ||
ADD_RECT_RIGHT_OF_INTERSECTION(add); | ||
} | ||
} | ||
} | ||
} | ||
else // y starts in baserect | ||
{ | ||
// intersection rect lower edge | ||
if (intersection.y2 == y2) // y goes down to baserect | ||
{ | ||
if (intersection.x1 == x1) // xstarts with baserect | ||
{ | ||
if (intersection.x2 == x2) // x ends with baserect | ||
{ //results in 1 rect above intersection | ||
ADD_RECT_ABOVE_INTERSECTION(add); | ||
} | ||
else // x ends in baserect | ||
{ // results in 2 rects | ||
ADD_RECT_ABOVE_INTERSECTION(add); | ||
ADD_RECT_RIGHT_OF_INTERSECTION(add); | ||
} | ||
} | ||
else // x starts in baserect | ||
{ | ||
if (intersection.x2 == x2) // x ends with baserect | ||
{ // results in 2 rects | ||
ADD_RECT_ABOVE_INTERSECTION(add); | ||
ADD_RECT_LEFT_OF_INTERSECTION(add); | ||
} | ||
else // x ends in baserect | ||
{ // results in 3 rects | ||
ADD_RECT_ABOVE_INTERSECTION(add); | ||
ADD_RECT_LEFT_OF_INTERSECTION(add); | ||
ADD_RECT_RIGHT_OF_INTERSECTION(add); | ||
} | ||
} | ||
} | ||
else // y ends in baserect | ||
{ | ||
if (intersection.x1 == x1) // x starts with baserect | ||
{ | ||
if (intersection.x2 == x2) // x ends with baserect | ||
{ // results in 2 rects | ||
ADD_RECT_ABOVE_INTERSECTION(add); | ||
ADD_RECT_BELOW_INTERSECTION(add); | ||
} | ||
else // x ends in baserect | ||
{ // results in 3 rects | ||
ADD_RECT_ABOVE_INTERSECTION(add); | ||
ADD_RECT_BELOW_INTERSECTION(add); | ||
ADD_RECT_RIGHT_OF_INTERSECTION(add); | ||
} | ||
} | ||
else // x starts in baserect | ||
{ | ||
if (intersection.x2 == x2) // x ends with baserect | ||
{ // results in 3 rects | ||
ADD_RECT_ABOVE_INTERSECTION(add); | ||
ADD_RECT_BELOW_INTERSECTION(add); | ||
ADD_RECT_LEFT_OF_INTERSECTION(add); | ||
} | ||
else // x ends in baserect | ||
{ // results in 4 rects | ||
ADD_RECT_ABOVE_INTERSECTION(add); | ||
ADD_RECT_BELOW_INTERSECTION(add); | ||
ADD_RECT_LEFT_OF_INTERSECTION(add); | ||
ADD_RECT_RIGHT_OF_INTERSECTION(add); | ||
} | ||
} | ||
} | ||
} | ||
} | ||
else | ||
{ | ||
newRectaglesList.push_back(*this); | ||
} | ||
|
||
return newRectaglesList; | ||
} | ||
This comment has been minimized.
Sorry, something went wrong.
This comment has been minimized.
Sorry, something went wrong.
This comment has been minimized.
Sorry, something went wrong.
jmarshallnz
via email
Contributor
|
||
|
||
std::vector<CRect> SubtractRects(std::vector<CRect> intersectionList) | ||
{ | ||
std::vector<CRect> fragmentsList; | ||
fragmentsList.push_back(*this); | ||
|
||
for (std::vector<CRect>::iterator splitter = intersectionList.begin(); splitter != intersectionList.end(); ++splitter) | ||
{ | ||
std::vector<CRect> toAddList; | ||
|
||
for (std::vector<CRect>::iterator fragment = fragmentsList.begin(); fragment != fragmentsList.end(); ++fragment) | ||
{ | ||
std::vector<CRect> newFragmentsList = fragment->SubtractRect(*splitter); | ||
toAddList.insert(toAddList.end(), newFragmentsList.begin(), newFragmentsList.end()); | ||
} | ||
|
||
fragmentsList.clear(); | ||
fragmentsList.insert(fragmentsList.end(), toAddList.begin(), toAddList.end()); | ||
} | ||
|
||
return fragmentsList; | ||
} | ||
|
||
bool operator !=(const CRect &rect) const | ||
{ | ||
if (x1 != rect.x1) return true; | ||
|
Correct me if I'm wrong, but you could make this much less code by generating the 4 outside rects and then intersecting them with the current rect, throwing away anything where the intersection is empty.