1 /*	Public domain	*/
2 
3 #ifndef _AGAR_GUI_GEOMETRY_H_
4 #define _AGAR_GUI_GEOMETRY_H_
5 #include <agar/gui/begin.h>
6 
7 /* Integer point */
8 typedef struct ag_point {
9 	int x, y;
10 } AG_Point;
11 
12 /* Integer rectangle from coordinate and dimensions */
13 typedef struct ag_rect {
14 	int x, y;
15 	int w, h;
16 } AG_Rect;
17 
18 /* Integer rectangle with computed extrema. */
19 typedef struct ag_rect2 {
20 	int x1, y1;
21 	int w, h;
22 	int x2, y2;
23 } AG_Rect2;
24 
25 /* Clipping rectangle */
26 typedef struct ag_clip_rect {
27 	AG_Rect r;		/* Integer coordinates */
28 	double eqns[4][4];	/* Computed plane equations (GL) */
29 } AG_ClipRect;
30 
31 /* Texture coordinates */
32 typedef struct ag_texcoord {
33 	float x, y, w, h;
34 } AG_TexCoord;
35 
36 __BEGIN_DECLS
37 
38 AG_Rect  AG_ReadRect(AG_DataSource *);
39 void     AG_WriteRect(AG_DataSource *, AG_Rect);
40 
41 #define  AG_ReadRect2(ds)    AG_RectToRect2(AG_ReadRect(ds))
42 #define  AG_WriteRect2(ds,r) AG_WriteRect(ds, AG_Rect2ToRect(r))
43 
44 /* Return a Point at x,y. */
45 static __inline__ AG_Point
AG_POINT(int x,int y)46 AG_POINT(int x, int y)
47 {
48 	AG_Point pt;
49 	pt.x = x;
50 	pt.y = y;
51 	return (pt);
52 }
53 
54 /* Return a Rect of dimensions w,h at position x,y. */
55 static __inline__ AG_Rect
AG_RECT(int x,int y,int w,int h)56 AG_RECT(int x, int y, int w, int h)
57 {
58 	AG_Rect r;
59 	r.x = x;
60 	r.y = y;
61 	r.w = w;
62 	r.h = h;
63 	return (r);
64 }
65 
66 /* Return a Rect2 of dimensions w,h at position x,y. */
67 static __inline__ AG_Rect2
AG_RECT2(int x,int y,int w,int h)68 AG_RECT2(int x, int y, int w, int h)
69 {
70 	AG_Rect2 r;
71 	r.x1 = x;
72 	r.y1 = y;
73 	r.w = w;
74 	r.h = h;
75 	r.x2 = x+w;
76 	r.y2 = y+h;
77 	return (r);
78 }
79 
80 /* Convert a Rect2 to a Rect. */
81 static __inline__ AG_Rect
AG_Rect2ToRect(AG_Rect2 r2)82 AG_Rect2ToRect(AG_Rect2 r2)
83 {
84 	AG_Rect r;
85 	r.x = r2.x1;
86 	r.y = r2.y1;
87 	r.w = r2.w;
88 	r.h = r2.h;
89 	return (r);
90 }
91 
92 /* Resize a Rect. */
93 static __inline__ void
AG_RectSize(AG_Rect * r,int w,int h)94 AG_RectSize(AG_Rect *r, int w, int h)
95 {
96 	r->w = w;
97 	r->h = h;
98 }
99 
100 /* Resize a Rect2. */
101 static __inline__ void
AG_RectSize2(AG_Rect2 * r,int w,int h)102 AG_RectSize2(AG_Rect2 *r, int w, int h)
103 {
104 	r->w = w;
105 	r->x2 = r->x1+w;
106 	r->h = h;
107 	r->y2 = r->y1+h;
108 }
109 
110 /* Translate a Rect. */
111 static __inline__ void
AG_RectTranslate(AG_Rect * r,int x,int y)112 AG_RectTranslate(AG_Rect *r, int x, int y)
113 {
114 	r->x += x;
115 	r->y += y;
116 }
117 
118 /* Translate a Rect2. */
119 static __inline__ void
AG_RectTranslate2(AG_Rect2 * r,int x,int y)120 AG_RectTranslate2(AG_Rect2 *r, int x, int y)
121 {
122 	r->x1 += x;
123 	r->y1 += y;
124 	r->x2 += x;
125 	r->y2 += y;
126 }
127 
128 /* Convert a Rect to a Rect2. */
129 static __inline__ AG_Rect2
AG_RectToRect2(AG_Rect r)130 AG_RectToRect2(AG_Rect r)
131 {
132 	AG_Rect2 r2;
133 	r2.x1 = r.x;
134 	r2.y1 = r.y;
135 	r2.w = r.w;
136 	r2.h = r.h;
137 	r2.x2 = r.x+r.w;
138 	r2.y2 = r.y+r.h;
139 	return (r2);
140 }
141 
142 /* Return the intersection of two Rect's. */
143 static __inline__ AG_Rect
AG_RectIntersect(const AG_Rect * a,const AG_Rect * b)144 AG_RectIntersect(const AG_Rect *a, const AG_Rect *b)
145 {
146 	AG_Rect x;
147 
148 	x.x = AG_MAX(a->x, b->x);
149 	x.y = AG_MAX(a->y, b->y);
150 	x.w = AG_MIN((a->x+a->w), (b->x+b->w)) - x.x;
151 	x.h = AG_MIN((a->y+a->h), (b->y+b->h)) - x.y;
152 	if (x.w < 0) { x.w = 0; }
153 	if (x.h < 0) { x.h = 0; }
154 	return (x);
155 }
156 
157 /* Return the intersection of two Rect2's. */
158 static __inline__ AG_Rect2
AG_RectIntersect2(const AG_Rect2 * a,const AG_Rect2 * b)159 AG_RectIntersect2(const AG_Rect2 *a, const AG_Rect2 *b)
160 {
161 	AG_Rect2 rx;
162 
163 	rx.x1 = AG_MAX(a->x1, b->x1);
164 	rx.y1 = AG_MAX(a->y1, b->y1);
165 	rx.w = AG_MIN(a->x2, b->x2) - rx.x1;
166 	if (rx.w < 0) { rx.w = 0; }
167 	rx.h = AG_MIN(a->y2, b->y2) - rx.y1;
168 	if (rx.h < 0) { rx.h = 0; }
169 	rx.x2 = rx.x1 + rx.w;
170 	rx.y2 = rx.y1 + rx.h;
171 	return (rx);
172 }
173 
174 /* Test whether two Rect's are the same. */
175 static __inline__ int
AG_RectCompare(const AG_Rect * a,const AG_Rect * b)176 AG_RectCompare(const AG_Rect *a, const AG_Rect *b)
177 {
178 	return (a->x == b->x &&
179 	        a->y == b->y &&
180 		a->w == b->w &&
181 		a->h == b->h) ? 0:1;
182 }
183 
184 /* Test whether two Rect2's are the same. */
185 static __inline__ int
AG_RectCompare2(const AG_Rect2 * a,const AG_Rect2 * b)186 AG_RectCompare2(const AG_Rect2 *a, const AG_Rect2 *b)
187 {
188 	return (a->x1 == b->x1 &&
189 	        a->y1 == b->y1 &&
190 		a->w == b->w &&
191 		a->h == b->h) ? 0:1;
192 }
193 
194 /* Test whether a point intersects a Rect. */
195 static __inline__ int
AG_RectInside(const AG_Rect * r,int x,int y)196 AG_RectInside(const AG_Rect *r, int x, int y)
197 {
198 	return (x >= r->x &&
199 	        y >= r->y &&
200 		x < r->x+r->w &&
201 		y < r->y+r->h);
202 }
203 
204 /* Test whether a point intersects a Rect2. */
205 static __inline__ int
AG_RectInside2(const AG_Rect2 * r,int x,int y)206 AG_RectInside2(const AG_Rect2 *r, int x, int y)
207 {
208 	return (x >= r->x1 &&
209 	        y >= r->y1 &&
210 		x < r->x2 &&
211 		y < r->y2);
212 }
213 __END_DECLS
214 
215 #if defined(_AGAR_INTERNAL) || defined(_USE_AGAR_GUI_GEOMETRY)
216 # define POINT(x,y)	AG_POINT((x),(y))
217 # define RECT(x,y,w,h)	AG_RECT((x),(y),(w),(h))
218 #endif
219 
220 #include <agar/gui/close.h>
221 #endif /* _AGAR_GUI_GEOMETRY_H_ */
222