-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathrectangle.c
87 lines (69 loc) · 2.22 KB
/
rectangle.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
#include <stdlib.h>
#include <stdbool.h>
#include "rectangle.h"
Rectangle rectangle_intersect(const Rectangle *a, const Rectangle *b)
{
int x1 = (a->x > b->x) ? a->x : b->x;
int x2 = ((a->x + a->width) < (b->x + b->width)) ? (a->x + a->width) : (b->x + b->width);
int y1 = (a->y > b->y) ? a->y : b->y;
int y2 = ((a->y + a->height) < (b->y + b->height)) ? (a->y + a->height) : (b->y + b->height);
return (Rectangle){x1, y1, x2 - x1, y2 - y1};
}
RectangleArray rectangle_subtract(const Rectangle *a, const Rectangle *b)
{
RectangleArray result = {NULL, 0};
Rectangle intersection = rectangle_intersect(a, b);
if (rectangle_is_invalid(&intersection))
{
result.rectangles = malloc(sizeof(Rectangle));
result.rectangles[0] = *a;
result.size = 1;
return result;
}
result.rectangles = malloc(4 * sizeof(Rectangle));
result.size = 0;
if (a->y < b->y)
{
result.rectangles[result.size++] = (Rectangle){a->x, a->y, a->width, b->y - a->y};
}
if (a->y + a->height > b->y + b->height)
{
result.rectangles[result.size++] = (Rectangle){a->x, b->y + b->height, a->width, a->y + a->height - (b->y + b->height)};
}
if (a->x < b->x)
{
result.rectangles[result.size++] = (Rectangle){a->x, b->y, b->x - a->x, b->height};
}
if (a->x + a->width > b->x + b->width)
{
result.rectangles[result.size++] = (Rectangle){b->x + b->width, b->y, a->x + a->width - (b->x + b->width), b->height};
}
return result;
}
bool rectangle_is_invalid(const Rectangle *p)
{
return p->x < 0 || p->y < 0 || p->width < 0 || p->height < 0;
}
bool rectangle_equals(const Rectangle *a, const Rectangle *b)
{
return a->x == b->x && a->y == b->y && a->width == b->width && a->height == b->height;
}
Rectangle rectangle_normalize(const Rectangle *r)
{
Rectangle result = *r;
if (result.width < 0)
{
result.width *= -1;
result.x -= result.width;
}
if (result.height < 0)
{
result.height *= -1;
result.y -= result.height;
}
return result;
}
Rectangle rectangle_pad(const Rectangle *r, int p)
{
return (Rectangle){r->x - p, r->y - p, r->width + 2 * p, r->height + 2 * p};
}