Crazy Eddie's GUI System  0.8.4
 All Classes Namespaces Functions Variables Typedefs Enumerations Enumerator Friends Pages
Rect.h
1 /***********************************************************************
2  created: 14/2/2011
3  author: Martin Preisler (reworked from code by Paul D Turner)
4 
5  purpose: Defines 'Rect' class
6 *************************************************************************/
7 /***************************************************************************
8  * Copyright (C) 2004 - 2011 Paul D Turner & The CEGUI Development Team
9  *
10  * Permission is hereby granted, free of charge, to any person obtaining
11  * a copy of this software and associated documentation files (the
12  * "Software"), to deal in the Software without restriction, including
13  * without limitation the rights to use, copy, modify, merge, publish,
14  * distribute, sublicense, and/or sell copies of the Software, and to
15  * permit persons to whom the Software is furnished to do so, subject to
16  * the following conditions:
17  *
18  * The above copyright notice and this permission notice shall be
19  * included in all copies or substantial portions of the Software.
20  *
21  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
22  * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
23  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
24  * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
25  * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
26  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
27  * OTHER DEALINGS IN THE SOFTWARE.
28  ***************************************************************************/
29 #ifndef _CEGUIRect_h_
30 #define _CEGUIRect_h_
31 
32 #include "CEGUI/Vector.h"
33 #include "CEGUI/Size.h"
34 
35 // Start of CEGUI namespace section
36 namespace CEGUI
37 {
42 template<typename T>
43 class Rect:
44  public AllocatedObject<Rect<T> >
45 {
46 public:
47  typedef T value_type;
48 
49  inline Rect()
50  {}
51 
52  inline Rect(const T& left, const T& top, const T& right, const T& bottom):
53  d_min(left, top),
54  d_max(right, bottom)
55  {}
56 
57  inline Rect(const Vector2<T>& min, const Vector2<T>& max):
58  d_min(min),
59  d_max(max)
60  {}
61 
62  inline Rect(const Vector2<T>& pos, const Size<T>& size):
63  d_min(pos),
64  d_max(pos + Vector2<T>(size.d_width, size.d_height))
65  {}
66 
67  inline Rect(const Rect& r):
68  d_min(r.d_min),
69  d_max(r.d_max)
70  {}
71 
72  inline Rect& operator=(const Rect& rhs)
73  {
74  d_min = rhs.d_min;
75  d_max = rhs.d_max;
76 
77  return *this;
78  }
79 
80  inline void left(const T& v)
81  {
82  d_min.d_x = v;
83  }
84 
85  inline const T& left() const
86  {
87  return d_min.d_x;
88  }
89 
90  inline void top(const T& v)
91  {
92  d_min.d_y = v;
93  }
94 
95  inline const T& top() const
96  {
97  return d_min.d_y;
98  }
99 
100  inline void right(const T& v)
101  {
102  d_max.d_x = v;
103  }
104 
105  inline const T& right() const
106  {
107  return d_max.d_x;
108  }
109 
110  inline void bottom(const T& v)
111  {
112  d_max.d_y = v;
113  }
114 
115  inline const T& bottom() const
116  {
117  return d_max.d_y;
118  }
119 
124  void setPosition(const Vector2<T>& min)
125  {
126  const Size<T> size = getSize();
127  d_min = min;
128  setSize(size);
129  }
130 
135  const Vector2<T>& getPosition() const
136  {
137  return d_min;
138  }
139 
140  void setSize(const Size<T>& size)
141  {
142  d_max = d_min + Vector2<T>(size.d_width, size.d_height);
143  }
144 
149  inline Size<T> getSize() const
150  {
151  return Size<T>(getWidth(), getHeight());
152  }
153 
154  void setWidth(const T& w)
155  {
156  d_max.d_x = d_min.d_x + w;
157  }
158 
163  inline T getWidth() const
164  {
165  return d_max.d_x - d_min.d_x;
166  }
167 
168  void setHeight(const T& h)
169  {
170  d_max.d_y = d_min.d_y + h;
171  }
172 
177  inline T getHeight() const
178  {
179  return d_max.d_y - d_min.d_y;
180  }
181 
190  inline Rect getIntersection(const Rect& rect) const
191  {
192  if ((d_max.d_x > rect.d_min.d_x) &&
193  (d_min.d_x < rect.d_max.d_x) &&
194  (d_max.d_y > rect.d_min.d_y) &&
195  (d_min.d_y < rect.d_max.d_y))
196  {
197  Rect ret;
198 
199  // fill in ret with the intersection
200  ret.d_min.d_x = (d_min.d_x > rect.d_min.d_x) ? d_min.d_x : rect.d_min.d_x;
201  ret.d_max.d_x = (d_max.d_x < rect.d_max.d_x) ? d_max.d_x : rect.d_max.d_x;
202  ret.d_min.d_y = (d_min.d_y > rect.d_min.d_y) ? d_min.d_y : rect.d_min.d_y;
203  ret.d_max.d_y = (d_max.d_y < rect.d_max.d_y) ? d_max.d_y : rect.d_max.d_y;
204 
205  return ret;
206  }
207  else
208  {
209  return Rect(0.0f, 0.0f, 0.0f, 0.0f);
210  }
211  }
212 
223  inline void offset(const Vector2<T>& v)
224  {
225  d_min += v;
226  d_max += v;
227  }
228 
239  inline bool isPointInRect(const Vector2<T>& v) const
240  {
241  if ((d_min.d_x > v.d_x) ||
242  (d_max.d_x <= v.d_x) ||
243  (d_min.d_y > v.d_y) ||
244  (d_max.d_y <= v.d_y))
245  {
246  return false;
247  }
248 
249  return true;
250  }
251 
252 
263  void constrainSizeMax(const Size<T>& size)
264  {
265  if (getWidth() > size.d_width)
266  {
267  setWidth(size.d_width);
268  }
269 
270  if (getHeight() > size.d_height)
271  {
272  setHeight(size.d_height);
273  }
274  }
275 
276 
287  void constrainSizeMin(const Size<T>& size)
288  {
289  if (getWidth() < size.d_width)
290  {
291  setWidth(size.d_width);
292  }
293 
294  if (getHeight() < size.d_height)
295  {
296  setHeight(size.d_height);
297  }
298  }
299 
300 
314  void constrainSize(const Size<T>& max_sz, const Size<T>& min_sz)
315  {
316  Size<T> curr_sz(getSize());
317 
318  if (curr_sz.d_width > max_sz.d_width)
319  {
320  setWidth(max_sz.d_width);
321  }
322  else if (curr_sz.d_width < min_sz.d_width)
323  {
324  setWidth(min_sz.d_width);
325  }
326 
327  if (curr_sz.d_height > max_sz.d_height)
328  {
329  setHeight(max_sz.d_height);
330  }
331  else if (curr_sz.d_height < min_sz.d_height)
332  {
333  setHeight(min_sz.d_height);
334  }
335  }
336 
337 
338  /*************************************************************************
339  Operators
340  *************************************************************************/
341  inline bool operator==(const Rect& rhs) const
342  {
343  return ((d_min == rhs.d_min) && (d_max == rhs.d_max));
344  }
345 
346  inline bool operator!=(const Rect& rhs) const
347  {
348  return !operator==(rhs);
349  }
350 
351  inline Rect operator*(T scalar) const
352  {
353  return Rect(d_min * scalar, d_max * scalar);
354  }
355 
356  const Rect& operator*=(T scalar)
357  {
358  d_min *= scalar;
359  d_max *= scalar;
360  return *this;
361  }
362 
363  Rect operator+(const Rect& r) const
364  {
365  return Rect(d_min + r.d_min, d_max + r.d_max);
366  }
367 
368  inline friend std::ostream& operator << (std::ostream& s, const Rect& v)
369  {
370  s << "CEGUI::Rect<" << typeid(T).name() << ">(" << v.d_min.d_x << ", " << v.d_min.d_y << ", " << v.d_max.d_x << ", " << v.d_max.d_y << ")";
371  return s;
372  }
373 
375  inline static Rect zero()
376  {
377  return Rect(Vector2<T>::zero(), Size<T>::zero());
378  }
379 
380  /*************************************************************************
381  Data Fields
382  *************************************************************************/
383  Vector2<T> d_min;
384  Vector2<T> d_max;
385 
386  // d_min.d_x is former d_left
387  // d_min.d_y is former d_top
388  // d_max.d_x is former d_right
389  // d_max.d_y is former d_bottom
390 };
391 
392 // the main reason for this is to keep C++ API in sync with other languages
393 typedef Rect<float> Rectf;
394 
395 // we need to allow URect to be multiplied by floats, this is the most elegant way to do that
396 inline Rect<UDim> operator * (const Rect<UDim>& v, const float c)
397 {
398  return Rect<UDim>(v.d_min * c, v.d_max * c);
399 }
400 
401 typedef Rect<UDim> URect;
402 
403 } // End of CEGUI namespace section
404 
405 
406 #endif // end of guard _CEGUIRect_h_
407