1 //////////////////////////////////////////////////////////////////////////////////////// 2 // 3 // Nestopia - NES/Famicom emulator written in C++ 4 // 5 // Copyright (C) 2003-2008 Martin Freij 6 // 7 // This file is part of Nestopia. 8 // 9 // Nestopia is free software; you can redistribute it and/or modify 10 // it under the terms of the GNU General Public License as published by 11 // the Free Software Foundation; either version 2 of the License, or 12 // (at your option) any later version. 13 // 14 // Nestopia is distributed in the hope that it will be useful, 15 // but WITHOUT ANY WARRANTY; without even the implied warranty of 16 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 // GNU General Public License for more details. 18 // 19 // You should have received a copy of the GNU General Public License 20 // along with Nestopia; if not, write to the Free Software 21 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 22 // 23 //////////////////////////////////////////////////////////////////////////////////////// 24 25 #ifndef NST_WINDOW_RECT_H 26 #define NST_WINDOW_RECT_H 27 28 #pragma once 29 30 #include "NstWindowPoint.hpp" 31 32 namespace Nestopia 33 { 34 namespace Window 35 { 36 struct Rect : RECT 37 { 38 Rect& ClientTransform(HWND); 39 Rect& ScreenTransform(HWND); 40 RectNestopia::Window::Rect41 Rect(int v=0) 42 { 43 left = v; 44 top = v; 45 right = v; 46 bottom = v; 47 } 48 RectNestopia::Window::Rect49 Rect(const POINT& p) 50 { 51 left = 0; 52 top = 0; 53 right = p.x; 54 bottom = p.y; 55 } 56 RectNestopia::Window::Rect57 Rect(int l,int t,int r,int b) 58 { 59 left = l; 60 top = t; 61 right = r; 62 bottom = b; 63 } 64 RectNestopia::Window::Rect65 Rect(const RECT& r) 66 { 67 left = r.left; 68 top = r.top; 69 right = r.right; 70 bottom = r.bottom; 71 } 72 SetNestopia::Window::Rect73 Rect& Set(int l,int t,int r,int b) 74 { 75 left = l; 76 top = t; 77 right = r; 78 bottom = b; 79 return *this; 80 } 81 operator =Nestopia::Window::Rect82 Rect& operator = (int v) 83 { 84 left = v; 85 top = v; 86 right = v; 87 bottom = v; 88 return *this; 89 } 90 operator =Nestopia::Window::Rect91 Rect& operator = (const POINT& p) 92 { 93 left = 0; 94 top = 0; 95 right = p.x; 96 bottom = p.y; 97 return *this; 98 } 99 operator =Nestopia::Window::Rect100 Rect& operator = (const RECT& r) 101 { 102 left = r.left; 103 top = r.top; 104 right = r.right; 105 bottom = r.bottom; 106 return *this; 107 } 108 operator ==Nestopia::Window::Rect109 bool operator == (const Rect& r) const 110 { 111 return 112 ( 113 right == r.right && 114 bottom == r.bottom && 115 left == r.left && 116 top == r.top 117 ); 118 } 119 operator !=Nestopia::Window::Rect120 bool operator != (const Rect& r) const 121 { 122 return 123 ( 124 right != r.right || 125 bottom != r.bottom || 126 left != r.left || 127 top != r.top 128 ); 129 } 130 operator !Nestopia::Window::Rect131 bool operator ! () const 132 { 133 return (right | bottom | left | top) == 0; 134 } 135 operator []Nestopia::Window::Rect136 long& operator [] (uint i) 137 { 138 return (&left)[i]; 139 } 140 operator []Nestopia::Window::Rect141 const long& operator [] (uint i) const 142 { 143 return (&left)[i]; 144 } 145 InsideNestopia::Window::Rect146 bool Inside(const Point& p) const 147 { 148 return p.x >= left && p.x < right && p.y >= top && p.y < bottom; 149 } 150 ValidNestopia::Window::Rect151 bool Valid() const 152 { 153 return left <= right && top <= bottom; 154 } 155 VisibleNestopia::Window::Rect156 bool Visible() const 157 { 158 return right - left > 0 && bottom - top > 0; 159 } 160 161 private: 162 163 class PosProxy 164 { 165 Rect& r; 166 167 public: 168 PosProxy(Rect & rect)169 PosProxy(Rect& rect) 170 : r(rect) {} 171 operator =(const Point & p)172 PosProxy& operator = (const Point& p) 173 { 174 r.right = p.x + (r.right - r.left); 175 r.bottom = p.y + (r.bottom - r.top); 176 r.left = p.x; 177 r.top = p.y; 178 return *this; 179 } 180 operator +=(const Point & p)181 PosProxy& operator += (const Point& p) 182 { 183 r.left += p.x; 184 r.top += p.y; 185 r.right += p.x; 186 r.bottom += p.y; 187 return *this; 188 } 189 operator +(const Point & p) const190 Point operator + (const Point& p) const 191 { 192 return Point( r.left + p.x, r.top + p.y ); 193 } 194 operator -=(const Point & p)195 PosProxy& operator -= (const Point& p) 196 { 197 r.left -= p.x; 198 r.top -= p.y; 199 r.right -= p.x; 200 r.bottom -= p.y; 201 return *this; 202 } 203 operator -(const Point & p) const204 Point operator - (const Point& p) const 205 { 206 return Point( r.left - p.x, r.top - p.y ); 207 } 208 operator Point() const209 operator Point () const 210 { 211 return Point(r.left,r.top); 212 } 213 }; 214 215 class WidthHeightProxy 216 { 217 long* p; 218 219 public: 220 WidthHeightProxy(long * point)221 WidthHeightProxy(long* point) 222 : p(point) {} 223 operator =(int xy)224 WidthHeightProxy& operator = (int xy) 225 { 226 p[2] = p[0] + xy; 227 return *this; 228 } 229 operator +=(int xy)230 WidthHeightProxy& operator += (int xy) 231 { 232 p[2] += xy; 233 return *this; 234 } 235 operator +(int xy) const236 int operator + (int xy) const 237 { 238 return p[2] - p[0] + xy; 239 } 240 operator -=(int xy)241 WidthHeightProxy& operator -= (int xy) 242 { 243 p[2] -= xy; 244 return *this; 245 } 246 operator -(int xy) const247 int operator - (int xy) const 248 { 249 return p[2] - p[0] - xy; 250 } 251 operator int() const252 operator int () const 253 { 254 return p[2] - p[0]; 255 } 256 }; 257 258 class SizeProxy 259 { 260 Rect& r; 261 262 public: 263 SizeProxy(Rect & rect)264 SizeProxy(Rect& rect) 265 : r(rect) {} 266 operator =(const Point & p)267 SizeProxy& operator = (const Point& p) 268 { 269 r.right = r.left + p.x; 270 r.bottom = r.top + p.y; 271 return *this; 272 } 273 operator +=(const Point & p)274 SizeProxy& operator += (const Point& p) 275 { 276 r.right += p.x; 277 r.bottom += p.y; 278 return *this; 279 } 280 operator +(const Point & p) const281 Point operator + (const Point& p) const 282 { 283 return Point 284 ( 285 (r.right - r.left) + p.x, 286 (r.bottom - r.top) + p.y 287 ); 288 } 289 operator -=(const Point & p)290 SizeProxy& operator -= (const Point& p) 291 { 292 r.right -= p.x; 293 r.bottom -= p.y; 294 return *this; 295 } 296 operator -(const Point & p) const297 Point operator - (const Point& p) const 298 { 299 return Point 300 ( 301 (r.right - r.left) - p.x, 302 (r.bottom - r.top) - p.y 303 ); 304 } 305 operator Point() const306 operator Point () const 307 { 308 return Point 309 ( 310 r.right - r.left, 311 r.bottom - r.top 312 ); 313 } 314 }; 315 316 class CenterProxy 317 { 318 Rect& r; 319 320 public: 321 CenterProxy(Rect & rect)322 CenterProxy(Rect& rect) 323 : r(rect) {} 324 operator =(const Point & p)325 CenterProxy& operator = (const Point& p) 326 { 327 const Point size 328 ( 329 r.right - r.left, 330 r.bottom - r.top 331 ); 332 333 r.left = p.x - (size.x / 2); 334 r.right = p.x + (size.x / 2) + (size.x % 2); 335 r.top = p.y - (size.y / 2); 336 r.bottom = p.y + (size.y / 2) + (size.y % 2); 337 338 return *this; 339 } 340 operator Point() const341 operator Point () const 342 { 343 return Point 344 ( 345 r.left + ((r.right - r.left) / 2), 346 r.top + ((r.bottom - r.top) / 2) 347 ); 348 } 349 }; 350 351 public: 352 PositionNestopia::Window::Rect353 PosProxy Position() 354 { 355 return *this; 356 } 357 PositionNestopia::Window::Rect358 Point Position() const 359 { 360 return Point( left, top ); 361 } 362 SizeNestopia::Window::Rect363 SizeProxy Size() 364 { 365 return *this; 366 } 367 SizeNestopia::Window::Rect368 Point Size() const 369 { 370 return Point( right - left, bottom - top ); 371 } 372 CenterNestopia::Window::Rect373 CenterProxy Center() 374 { 375 return *this; 376 } 377 CenterNestopia::Window::Rect378 Point Center() const 379 { 380 return Point 381 ( 382 left + ((right - left) / 2), 383 top + ((bottom - top) / 2) 384 ); 385 } 386 CornerNestopia::Window::Rect387 Point& Corner() 388 { 389 return reinterpret_cast<Point&>(right); 390 } 391 CornerNestopia::Window::Rect392 const Point& Corner() const 393 { 394 return reinterpret_cast<const Point&>(right); 395 } 396 WidthNestopia::Window::Rect397 WidthHeightProxy Width() 398 { 399 return &left; 400 } 401 WidthNestopia::Window::Rect402 int Width() const 403 { 404 return right - left; 405 } 406 HeightNestopia::Window::Rect407 WidthHeightProxy Height() 408 { 409 return ⊤ 410 } 411 HeightNestopia::Window::Rect412 int Height() const 413 { 414 return bottom - top; 415 } 416 operator <Nestopia::Window::Rect417 bool operator < (const Rect& r) const { return Width() * Height() < r.Width() * r.Height(); } operator >Nestopia::Window::Rect418 bool operator > (const Rect& r) const { return Width() * Height() > r.Width() * r.Height(); } operator <=Nestopia::Window::Rect419 bool operator <= (const Rect& r) const { return Width() * Height() <= r.Width() * r.Height(); } operator >=Nestopia::Window::Rect420 bool operator >= (const Rect& r) const { return Width() * Height() >= r.Width() * r.Height(); } 421 operator *Nestopia::Window::Rect422 Rect operator * (const Rect& r) const 423 { 424 return Rect 425 ( 426 left * r.left, 427 top * r.top, 428 right * r.right, 429 bottom * r.bottom 430 ); 431 } 432 operator *Nestopia::Window::Rect433 Rect operator * (const long v) const 434 { 435 return Rect 436 ( 437 left * v, 438 top * v, 439 right * v, 440 bottom * v 441 ); 442 } 443 operator *Nestopia::Window::Rect444 Rect operator * (const Point& p) const 445 { 446 return Rect 447 ( 448 left * p.x, 449 top * p.y, 450 right * p.x, 451 bottom * p.y 452 ); 453 } 454 operator /Nestopia::Window::Rect455 Rect operator / (const long v) const 456 { 457 return Rect 458 ( 459 left / v, 460 top / v, 461 right / v, 462 bottom / v 463 ); 464 } 465 operator /Nestopia::Window::Rect466 Rect operator / (const Point& p) const 467 { 468 return Rect 469 ( 470 left / p.x, 471 top / p.y, 472 right / p.x, 473 bottom / p.y 474 ); 475 } 476 477 struct Window; 478 }; 479 480 struct Rect::Window : Rect 481 { WindowNestopia::Window::Rect::Window482 Window(HWND hWnd) 483 { 484 ::GetWindowRect( hWnd, this ); 485 } 486 }; 487 } 488 } 489 490 #endif 491