00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061 #include "guichan/widget.hpp"
00062
00063 #include "guichan/actionlistener.hpp"
00064 #include "guichan/basiccontainer.hpp"
00065 #include "guichan/defaultfont.hpp"
00066 #include "guichan/exception.hpp"
00067 #include "guichan/focushandler.hpp"
00068 #include "guichan/keyinput.hpp"
00069 #include "guichan/keylistener.hpp"
00070 #include "guichan/mouseinput.hpp"
00071 #include "guichan/mouselistener.hpp"
00072
00073
00074 namespace gcn
00075 {
00076 Font* Widget::mGlobalFont = NULL;
00077 DefaultFont Widget::mDefaultFont;
00078 std::list<Widget*> Widget::mWidgets;
00079
00080 Widget::Widget()
00081 {
00082 mParent = NULL;
00083 mForegroundColor = Color(0x000000);
00084 mBackgroundColor = Color(0xffffff);
00085 mBaseColor = Color(0x808090);
00086 mBorderSize = 0;
00087 mFocusHandler = NULL;
00088 mFocusable = false;
00089 mClickTimeStamp = 0;
00090 mClickCount = 0;
00091 mHasMouse = false;
00092 mVisible = true;
00093 mTabIn = true;
00094 mTabOut = true;
00095 mEnabled = true;
00096 mClickButton = 0;
00097
00098 mCurrentFont = NULL;
00099 mWidgets.push_back(this);
00100 }
00101
00102 Widget::~Widget()
00103 {
00104 if (getParent() != NULL)
00105 {
00106 getParent()->_announceDeath(this);
00107 }
00108
00109 _setFocusHandler(NULL);
00110
00111 mWidgets.remove(this);
00112 }
00113
00114 void Widget::_setParent(BasicContainer* parent)
00115 {
00116 mParent = parent;
00117 }
00118
00119 BasicContainer* Widget::getParent() const
00120 {
00121 return mParent;
00122 }
00123
00124 void Widget::setWidth(int width)
00125 {
00126 mDimension.width = width;
00127 }
00128
00129 int Widget::getWidth() const
00130 {
00131 return mDimension.width;
00132 }
00133
00134 void Widget::setHeight(int height)
00135 {
00136 mDimension.height = height;
00137 }
00138
00139 int Widget::getHeight() const
00140 {
00141 return mDimension.height;
00142 }
00143
00144 void Widget::setX(int x)
00145 {
00146 mDimension.x = x;
00147 }
00148
00149 int Widget::getX() const
00150 {
00151 return mDimension.x;
00152 }
00153
00154 void Widget::setY(int y)
00155 {
00156 mDimension.y = y;
00157 }
00158
00159 int Widget::getY() const
00160 {
00161 return mDimension.y;
00162 }
00163
00164 void Widget::setPosition(int x, int y)
00165 {
00166 mDimension.x = x;
00167 mDimension.y = y;
00168 }
00169
00170 void Widget::setDimension(const Rectangle& dimension)
00171 {
00172 mDimension = dimension;
00173 }
00174
00175 void Widget::setBorderSize(unsigned int borderSize)
00176 {
00177 mBorderSize = borderSize;
00178 }
00179
00180 unsigned int Widget::getBorderSize() const
00181 {
00182 return mBorderSize;
00183 }
00184
00185 const Rectangle& Widget::getDimension() const
00186 {
00187 return mDimension;
00188 }
00189
00190 const std::string& Widget::getEventId() const
00191 {
00192 return mEventId;
00193 }
00194
00195 void Widget::setEventId(const std::string& eventId)
00196 {
00197 mEventId = eventId;
00198 }
00199
00200 bool Widget::isFocused() const
00201 {
00202 if (!mFocusHandler)
00203 {
00204 return false;
00205 }
00206
00207 return (mFocusHandler->isFocused(this));
00208 }
00209
00210 bool Widget::hasMouse() const
00211 {
00212 return mHasMouse;
00213 }
00214
00215 void Widget::setFocusable(bool focusable)
00216 {
00217 if (!focusable && isFocused())
00218 {
00219 mFocusHandler->focusNone();
00220 }
00221
00222 mFocusable = focusable;
00223 }
00224
00225 bool Widget::isFocusable() const
00226 {
00227 return mFocusable && isVisible() && isEnabled();
00228 }
00229
00230 void Widget::requestFocus()
00231 {
00232 if (mFocusHandler == NULL)
00233 {
00234 throw GCN_EXCEPTION("No focushandler set (did you add the widget to the gui?).");
00235 }
00236
00237 if (isFocusable())
00238 {
00239 mFocusHandler->requestFocus(this);
00240 }
00241 }
00242
00243 void Widget::requestMoveToTop()
00244 {
00245 if (mParent)
00246 {
00247 mParent->moveToTop(this);
00248 }
00249 }
00250
00251 void Widget::requestMoveToBottom()
00252 {
00253 if (mParent)
00254 {
00255 mParent->moveToBottom(this);
00256 }
00257 }
00258
00259 void Widget::setVisible(bool visible)
00260 {
00261 if (!visible && isFocused())
00262 {
00263 mFocusHandler->focusNone();
00264 }
00265 mVisible = visible;
00266 }
00267
00268 bool Widget::isVisible() const
00269 {
00270 if (getParent() == NULL)
00271 {
00272 return mVisible;
00273 }
00274 else
00275 {
00276 return mVisible && getParent()->isVisible();
00277 }
00278 }
00279
00280 void Widget::setBaseColor(const Color& color)
00281 {
00282 mBaseColor = color;
00283 }
00284
00285 const Color& Widget::getBaseColor() const
00286 {
00287 return mBaseColor;
00288 }
00289
00290 void Widget::setForegroundColor(const Color& color)
00291 {
00292 mForegroundColor = color;
00293 }
00294
00295 const Color& Widget::getForegroundColor() const
00296 {
00297 return mForegroundColor;
00298 }
00299
00300 void Widget::setBackgroundColor(const Color& color)
00301 {
00302 mBackgroundColor = color;
00303 }
00304
00305 const Color& Widget::getBackgroundColor() const
00306 {
00307 return mBackgroundColor;
00308 }
00309
00310 void Widget::_setFocusHandler(FocusHandler* focusHandler)
00311 {
00312 if (mFocusHandler)
00313 {
00314 releaseModalFocus();
00315 mFocusHandler->remove(this);
00316 }
00317
00318 if (focusHandler)
00319 {
00320 focusHandler->add(this);
00321 }
00322
00323 mFocusHandler = focusHandler;
00324 }
00325
00326 FocusHandler* Widget::_getFocusHandler()
00327 {
00328 return mFocusHandler;
00329 }
00330
00331 void Widget::addActionListener(ActionListener* actionListener)
00332 {
00333 mActionListeners.push_back(actionListener);
00334 }
00335
00336 void Widget::removeActionListener(ActionListener* actionListener)
00337 {
00338 mActionListeners.remove(actionListener);
00339 }
00340
00341 void Widget::addKeyListener(KeyListener* keyListener)
00342 {
00343 mKeyListeners.push_back(keyListener);
00344 }
00345
00346 void Widget::removeKeyListener(KeyListener* keyListener)
00347 {
00348 mKeyListeners.remove(keyListener);
00349 }
00350
00351 void Widget::addMouseListener(MouseListener* mouseListener)
00352 {
00353 mMouseListeners.push_back(mouseListener);
00354 }
00355
00356 void Widget::removeMouseListener(MouseListener* mouseListener)
00357 {
00358 mMouseListeners.remove(mouseListener);
00359 }
00360
00361 void Widget::_mouseInputMessage(const MouseInput& mouseInput)
00362 {
00363 if (mFocusHandler == NULL)
00364 {
00365 throw GCN_EXCEPTION("No focushandler set (did you add the widget to the gui?).");
00366 }
00367
00368 if (!mEnabled || (mFocusHandler->getModalFocused() != NULL &&
00369 !hasModalFocus()))
00370 {
00371 return;
00372 }
00373
00374 int x = mouseInput.x;
00375 int y = mouseInput.y;
00376 int b = mouseInput.getButton();
00377 int ts = mouseInput.getTimeStamp();
00378
00379 MouseListenerIterator iter;
00380
00381 switch(mouseInput.getType())
00382 {
00383 case MouseInput::MOTION:
00384 for (iter = mMouseListeners.begin(); iter != mMouseListeners.end(); ++iter)
00385 {
00386 (*iter)->mouseMotion(x, y);
00387 }
00388 break;
00389
00390 case MouseInput::PRESS:
00391 if (hasMouse())
00392 {
00393 requestFocus();
00394 mFocusHandler->requestDrag(this);
00395 }
00396
00397 if (b != MouseInput::WHEEL_UP && b != MouseInput::WHEEL_DOWN)
00398 {
00399
00400 for (iter = mMouseListeners.begin(); iter != mMouseListeners.end(); ++iter)
00401 {
00402 (*iter)->mousePress(x, y, b);
00403 }
00404
00405 if (hasMouse())
00406 {
00407 if (ts - mClickTimeStamp < 300 && mClickButton == b)
00408 {
00409 mClickCount++;
00410 }
00411 else
00412 {
00413 mClickCount = 0;
00414 }
00415 mClickButton = b;
00416 mClickTimeStamp = ts;
00417 }
00418 else
00419 {
00420 mClickButton = 0;
00421 }
00422 }
00423 else if (b == MouseInput::WHEEL_UP)
00424 {
00425 for (iter = mMouseListeners.begin(); iter != mMouseListeners.end(); ++iter)
00426 {
00427 (*iter)->mouseWheelUp(x, y);
00428 }
00429 }
00430 else
00431 {
00432 for (iter = mMouseListeners.begin(); iter != mMouseListeners.end(); ++iter)
00433 {
00434 (*iter)->mouseWheelDown(x, y);
00435 }
00436 }
00437 break;
00438
00439 case MouseInput::RELEASE:
00440 if (isDragged())
00441 {
00442 mFocusHandler->dragNone();
00443 }
00444
00445 if (b != MouseInput::WHEEL_UP && b != MouseInput::WHEEL_DOWN)
00446 {
00447 for (iter = mMouseListeners.begin(); iter != mMouseListeners.end(); ++iter)
00448 {
00449 (*iter)->mouseRelease(x, y, b);
00450 }
00451 }
00452
00453 if (mHasMouse)
00454 {
00455 if (b == mClickButton)
00456 {
00457 for (iter = mMouseListeners.begin(); iter != mMouseListeners.end(); ++iter)
00458 {
00459 (*iter)->mouseClick(x, y, b, mClickCount + 1);
00460 }
00461 }
00462 else
00463 {
00464 mClickButton = 0;
00465 mClickCount = 0;
00466 }
00467 }
00468 else
00469 {
00470 mClickCount = 0;
00471 mClickTimeStamp = 0;
00472 }
00473 break;
00474 }
00475 }
00476
00477 void Widget::_keyInputMessage(const KeyInput& keyInput)
00478 {
00479 if (mFocusHandler == NULL)
00480 {
00481 throw GCN_EXCEPTION("No focushandler set (did you add the widget to the gui?).");
00482 }
00483
00484 if (!mEnabled || (mFocusHandler->getModalFocused() != NULL &&
00485 !hasModalFocus()))
00486 {
00487 return;
00488 }
00489
00490 KeyListenerIterator iter;
00491
00492 switch(keyInput.getType())
00493 {
00494 case KeyInput::PRESS:
00495 for (iter = mKeyListeners.begin(); iter != mKeyListeners.end(); ++iter)
00496 {
00497 (*iter)->keyPress(keyInput.getKey());
00498 }
00499 break;
00500
00501 case KeyInput::RELEASE:
00502 for (iter = mKeyListeners.begin(); iter != mKeyListeners.end(); ++iter)
00503 {
00504 (*iter)->keyRelease(keyInput.getKey());
00505 }
00506 break;
00507 }
00508 }
00509
00510 void Widget::_mouseInMessage()
00511 {
00512 if (!mEnabled)
00513 {
00514 return;
00515 }
00516
00517 mHasMouse = true;
00518
00519 MouseListenerIterator iter;
00520 for (iter = mMouseListeners.begin(); iter != mMouseListeners.end(); ++iter)
00521 {
00522 (*iter)->mouseIn();
00523 }
00524 }
00525
00526 void Widget::_mouseOutMessage()
00527 {
00528 mHasMouse = false;
00529
00530 MouseListenerIterator iter;
00531 for (iter = mMouseListeners.begin(); iter != mMouseListeners.end(); ++iter)
00532 {
00533 (*iter)->mouseOut();
00534 }
00535 }
00536
00537 void Widget::getAbsolutePosition(int& x, int& y) const
00538 {
00539 if (getParent() == NULL)
00540 {
00541 x = mDimension.x;
00542 y = mDimension.y;
00543 return;
00544 }
00545
00546 int parentX;
00547 int parentY;
00548
00549 getParent()->getAbsolutePosition(parentX, parentY);
00550
00551 x = parentX + mDimension.x + getParent()->getChildrenArea().x;
00552 y = parentY + mDimension.y + getParent()->getChildrenArea().y;
00553 }
00554
00555 void Widget::generateAction()
00556 {
00557 ActionListenerIterator iter;
00558 for (iter = mActionListeners.begin(); iter != mActionListeners.end(); ++iter)
00559 {
00560 (*iter)->action(mEventId, this);
00561 }
00562 }
00563
00564 Font* Widget::getFont() const
00565 {
00566 if (mCurrentFont == NULL)
00567 {
00568 if (mGlobalFont == NULL)
00569 {
00570 return &mDefaultFont;
00571 }
00572
00573 return mGlobalFont;
00574 }
00575
00576 return mCurrentFont;
00577 }
00578
00579 void Widget::setGlobalFont(Font* font)
00580 {
00581 mGlobalFont = font;
00582
00583 std::list<Widget*>::iterator iter;
00584 for (iter = mWidgets.begin(); iter != mWidgets.end(); ++iter)
00585 {
00586 if ((*iter)->mCurrentFont == NULL)
00587 {
00588 (*iter)->fontChanged();
00589 }
00590 }
00591 }
00592
00593 void Widget::setFont(Font* font)
00594 {
00595 mCurrentFont = font;
00596 fontChanged();
00597 }
00598
00599 bool Widget::widgetExists(const Widget* widget)
00600 {
00601 bool result = false;
00602
00603 std::list<Widget*>::iterator iter;
00604 for (iter = mWidgets.begin(); iter != mWidgets.end(); ++iter)
00605 {
00606 if (*iter == widget)
00607 {
00608 return true;
00609 }
00610 }
00611
00612 return result;
00613 }
00614
00615 bool Widget::isTabInEnabled() const
00616 {
00617 return mTabIn;
00618 }
00619
00620 void Widget::setTabInEnabled(bool enabled)
00621 {
00622 mTabIn = enabled;
00623 }
00624
00625 bool Widget::isTabOutEnabled() const
00626 {
00627 return mTabOut;
00628 }
00629
00630 void Widget::setTabOutEnabled(bool enabled)
00631 {
00632 mTabOut = enabled;
00633 }
00634
00635 void Widget::setSize(int width, int height)
00636 {
00637 setWidth(width);
00638 setHeight(height);
00639 }
00640
00641 void Widget::setEnabled(bool enabled)
00642 {
00643 mEnabled = enabled;
00644 }
00645
00646 bool Widget::isEnabled() const
00647 {
00648 return mEnabled && isVisible();
00649 }
00650
00651 bool Widget::isDragged() const
00652 {
00653 if (mFocusHandler == NULL)
00654 {
00655 throw GCN_EXCEPTION("No focushandler set (did you add the widget to the gui?).");
00656 }
00657
00658 return mFocusHandler->isDragged(this);
00659 }
00660
00661 void Widget::requestModalFocus()
00662 {
00663 if (mFocusHandler == NULL)
00664 {
00665 throw GCN_EXCEPTION("No focushandler set (did you add the widget to the gui?).");
00666 }
00667
00668 mFocusHandler->requestModalFocus(this);
00669 }
00670
00671 void Widget::releaseModalFocus()
00672 {
00673 if (mFocusHandler == NULL)
00674 {
00675 return;
00676 }
00677
00678 mFocusHandler->releaseModalFocus(this);
00679 }
00680
00681 bool Widget::hasModalFocus() const
00682 {
00683 if (mFocusHandler == NULL)
00684 {
00685 throw GCN_EXCEPTION("No focushandler set (did you add the widget to the gui?).");
00686 }
00687
00688 if (getParent() != NULL)
00689 {
00690 return (mFocusHandler->getModalFocused() == this) || getParent()->hasModalFocus();
00691 }
00692
00693 return mFocusHandler->getModalFocused() == this;
00694 }
00695 }