X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/e58dab20ce995856303154a367bcca904066525c..37e188eaaa67c45f386845b374d2f11a250fb1a0:/src/os2/button.cpp diff --git a/src/os2/button.cpp b/src/os2/button.cpp index ab27b61602..0dfafaa3b3 100644 --- a/src/os2/button.cpp +++ b/src/os2/button.cpp @@ -1,5 +1,5 @@ ///////////////////////////////////////////////////////////////////////////// -// Name: button.cpp +// Name: src/os2/button.cpp // Purpose: wxButton // Author: David Webster // Modified by: @@ -12,16 +12,20 @@ // For compilers that support precompilation, includes "wx.h". #include "wx/wxprec.h" +#include "wx/button.h" + #ifndef WX_PRECOMP - #include "wx/button.h" + #include "wx/app.h" #include "wx/brush.h" #include "wx/panel.h" #include "wx/bmpbuttn.h" #include "wx/settings.h" #include "wx/dcscreen.h" #include "wx/scrolwin.h" + #include "wx/toplevel.h" #endif +#include "wx/stockitem.h" #include "wx/os2/private.h" #define BUTTON_HEIGHT_FROM_CHAR_HEIGHT(cy) (11*EDIT_HEIGHT_FROM_CHAR_HEIGHT(cy)/10) @@ -39,19 +43,21 @@ IMPLEMENT_DYNAMIC_CLASS(wxButton, wxControl) // Button -bool wxButton::Create( - wxWindow* pParent -, wxWindowID vId -, const wxString& rsLabel -, const wxPoint& rPos -, const wxSize& rSize -, long lStyle -#if wxUSE_VALIDATORS -, const wxValidator& rValidator -#endif -, const wxString& rsName -) +bool wxButton::Create( wxWindow* pParent, + wxWindowID vId, + const wxString& rsLbl, + const wxPoint& rPos, + const wxSize& rSize, + long lStyle, + const wxValidator& rValidator, + const wxString& rsName) { + wxString rsLabel(rsLbl); + if (rsLabel.empty() && wxIsStockID(vId)) + rsLabel = wxGetStockLabel(vId); + + wxString sLabel = ::wxPMTextToLabel(rsLabel); + SetName(rsName); #if wxUSE_VALIDATORS SetValidator(rValidator); @@ -71,18 +77,10 @@ bool wxButton::Create( // if (m_windowStyle & wxCLIP_SIBLINGS ) lStyle |= WS_CLIPSIBLINGS; - // - // If the parent is a scrolled window the controls must - // have this style or they will overlap the scrollbars - // - if (pParent) - if (pParent->IsKindOf(CLASSINFO(wxScrolledWindow)) || - pParent->IsKindOf(CLASSINFO(wxGenericScrolledWindow))) - lStyle |= WS_CLIPSIBLINGS; m_hWnd = (WXHWND)::WinCreateWindow( GetHwndOf(pParent) // Parent handle ,WC_BUTTON // A Button class window - ,(PSZ)rsLabel.c_str() // Button text + ,sLabel.c_str() // Button text ,lStyle // Button style ,0, 0, 0, 0 // Location and size ,GetHwndOf(pParent) // Owner handle @@ -93,34 +91,42 @@ bool wxButton::Create( ); if (m_hWnd == 0) { - return FALSE; + return false; } // // Subclass again for purposes of dialog editing mode // SubclassWin(m_hWnd); - SetFont(*wxSMALL_FONT); + wxFont* pButtonFont = new wxFont( 8 + ,wxSWISS + ,wxNORMAL + ,wxNORMAL + ); + SetFont(*pButtonFont); + SetXComp(0); + SetYComp(0); SetSize( rPos.x ,rPos.y ,rSize.x ,rSize.y ); - return TRUE; + delete pButtonFont; + return true; } // end of wxButton::Create wxButton::~wxButton() { - wxPanel* pPanel = wxDynamicCast(GetParent(), wxPanel); + wxTopLevelWindow *tlw = wxDynamicCast(wxGetTopLevelParent(this), wxTopLevelWindow); - if (pPanel) + if (tlw) { - if (pPanel->GetDefaultItem() == this) + if (tlw->GetDefaultItem() == this) { // // Don't leave the panel with invalid default item // - pPanel->SetDefaultItem(NULL); + tlw->SetDefaultItem(NULL); } } } // end of wxButton::~wxButton @@ -135,6 +141,7 @@ wxSize wxButton::DoGetBestSize() const int nWidthButton; int nWidthChar; int nHeightChar; + wxFont vFont = (wxFont)GetFont(); GetTextExtent( rsLabel ,&nWidthButton @@ -144,7 +151,7 @@ wxSize wxButton::DoGetBestSize() const wxGetCharSize( GetHWND() ,&nWidthChar ,&nHeightChar - ,(wxFont*)&GetFont() + ,&vFont ); // @@ -160,15 +167,21 @@ wxSize wxButton::DoGetBestSize() const // // Need a little extra to make it look right // - nHeightButton += nHeightChar/1.5; + nHeightButton += (int)(nHeightChar/1.5); - wxSize vSize = GetDefaultSize(); + if (!HasFlag(wxBU_EXACTFIT)) + { + wxSize vSize = GetDefaultSize(); - if (nWidthButton > vSize.x) - vSize.x = nWidthButton; - if (nHeightButton > vSize.y) - vSize.y = nHeightButton; - return vSize; + if (nWidthButton > vSize.x) + vSize.x = nWidthButton; + if (nHeightButton > vSize.y) + vSize.y = nHeightButton; + return vSize; + } + return wxSize( nWidthButton + ,nHeightButton + ); } // end of wxButton::DoGetBestSize /* static */ @@ -218,34 +231,84 @@ bool wxButton::SendClickEvent() return ProcessCommand(vEvent); } // end of wxButton::SendClickEvent -void wxButton::SetDefault() +wxWindow *wxButton::SetDefault() { - wxWindow* pParent = GetParent(); - wxButton* pBtnOldDefault = NULL; - wxPanel* pPanel = wxDynamicCast(pParent, wxPanel); - long lStyle = 0L; + // + // Set this one as the default button both for wxWidgets and Windows + // + wxWindow* pWinOldDefault = wxButtonBase::SetDefault(); - if (pParent) - { - wxWindow* pWinOldDefault = pParent->SetDefaultItem(this); + SetDefaultStyle( wxDynamicCast(pWinOldDefault, wxButton), false); + SetDefaultStyle( this, true ); - pBtnOldDefault = wxDynamicCast(pWinOldDefault, wxButton); - } - if (pBtnOldDefault && pBtnOldDefault != this) + return pWinOldDefault; +} // end of wxButton::SetDefault + +void wxButton::SetTmpDefault() +{ + wxTopLevelWindow *tlw = wxDynamicCast(wxGetTopLevelParent(this), wxTopLevelWindow); + + wxCHECK_RET( tlw, wxT("button without top level window?") ); + + wxWindow* pWinOldDefault = tlw->GetDefaultItem(); + + tlw->SetTmpDefaultItem(this); + SetDefaultStyle( wxDynamicCast(pWinOldDefault, wxButton), false); + SetDefaultStyle( this, true ); +} // end of wxButton::SetTmpDefault + +void wxButton::UnsetTmpDefault() +{ + wxTopLevelWindow *tlw = wxDynamicCast(wxGetTopLevelParent(this), wxTopLevelWindow); + + wxCHECK_RET( tlw, wxT("button without top level window?") ); + + tlw->SetTmpDefaultItem(NULL); + + wxWindow* pWinOldDefault = tlw->GetDefaultItem(); + + SetDefaultStyle( this, false ); + SetDefaultStyle( wxDynamicCast(pWinOldDefault, wxButton), true ); +} // end of wxButton::UnsetTmpDefault + +void wxButton::SetDefaultStyle( + wxButton* pBtn +, bool bOn +) +{ + long lStyle; + // + // We may be called with NULL pointer -- simpler to do the check here than + // in the caller which does wxDynamicCast() + // + if (!pBtn) + return; + + // + // First, let DefDlgProc() know about the new default button + // + if (bOn) { - // - // Remove the BS_DEFPUSHBUTTON style from the other button - // - lStyle = ::WinQueryWindowULong(GetHwndOf(pBtnOldDefault), QWL_STYLE); + if (!wxTheApp->IsActive()) + return; // - // Don't do it with the owner drawn buttons because it will reset - // BS_OWNERDRAW style bit too (BS_OWNERDRAW & BS_DEFPUSHBUTTON != 0)! + // In OS/2 the dialog/panel doesn't really know it has a default + // button, the default button simply has that style. We'll just + // simulate by setting focus to it // + pBtn->SetFocus(); + } + lStyle = ::WinQueryWindowULong(GetHwndOf(pBtn), QWL_STYLE); + if (!(lStyle & BS_DEFAULT) == bOn) + { if ((lStyle & BS_USERBUTTON) != BS_USERBUTTON) { - lStyle &= ~BS_DEFAULT; - ::WinSetWindowULong(GetHwndOf(pBtnOldDefault), QWL_STYLE, lStyle); + if (bOn) + lStyle |= BS_DEFAULT; + else + lStyle &= ~BS_DEFAULT; + ::WinSetWindowULong(GetHwndOf(pBtn), QWL_STYLE, lStyle); } else { @@ -253,31 +316,18 @@ void wxButton::SetDefault() // Redraw the button - it will notice itself that it's not the // default one any longer // - pBtnOldDefault->Refresh(); + pBtn->Refresh(); } } - - // - // Set this button as the default - // - lStyle = ::WinQueryWindowULong(GetHwnd(), QWL_STYLE); - if ((lStyle & BS_USERBUTTON) != BS_USERBUTTON) - { - lStyle != BS_DEFAULT; - ::WinSetWindowULong(GetHwnd(), QWL_STYLE, lStyle); - } -} // end of wxButton::SetDefault +} // end of wxButton::UpdateDefaultStyle // ---------------------------------------------------------------------------- // event/message handlers // ---------------------------------------------------------------------------- -bool wxButton::OS2Command( - WXUINT uParam -, WXWORD wId -) +bool wxButton::OS2Command(WXUINT uParam, WXWORD WXUNUSED(wId)) { - bool bProcessed = FALSE; + bool bProcessed = false; switch (uParam) { @@ -286,21 +336,20 @@ bool wxButton::OS2Command( bProcessed = SendClickEvent(); break; } + return bProcessed; } // end of wxButton::OS2Command -WXHBRUSH wxButton::OnCtlColor( - WXHDC pDC -, WXHWND pWnd -, WXUINT nCtlColor -, WXUINT uMessage -, WXWPARAM wParam -, WXLPARAM lParam -) +WXHBRUSH wxButton::OnCtlColor( WXHDC WXUNUSED(pDC), + WXHWND WXUNUSED(pWnd), + WXUINT WXUNUSED(nCtlColor), + WXUINT WXUNUSED(uMessage), + WXWPARAM WXUNUSED(wParam), + WXLPARAM WXUNUSED(lParam) ) { - wxBrush* pBackgroundBrush = wxTheBrushList->FindOrCreateBrush( GetBackgroundColour() - ,wxSOLID - ); + wxBrush* pBackgroundBrush = wxTheBrushList->FindOrCreateBrush( GetBackgroundColour() + ,wxSOLID + ); return (WXHBRUSH)pBackgroundBrush->GetResourceHandle(); } // end of wxButton::OnCtlColor @@ -318,21 +367,44 @@ void wxButton::MakeOwnerDrawn() lStyle |= BS_USERBUTTON; ::WinSetWindowULong(GetHwnd(), QWL_STYLE, lStyle); } -} // end of wxCButton::MakeOwnerDrawn +} // end of wxButton::MakeOwnerDrawn -MRESULT wxButton::WindowProc( - WXUINT uMsg -, WXWPARAM wParam -, WXLPARAM lParam -) +WXDWORD wxButton::OS2GetStyle( + long lStyle +, WXDWORD* pdwExstyle +) const { // - // When we receive focus, we want to become the default button in our - // parent panel + // Buttons never have an external border, they draw their own one + // + WXDWORD dwStyle = wxControl::OS2GetStyle( (lStyle & ~wxBORDER_MASK) | wxBORDER_NONE + ,pdwExstyle + ); + + // + // We must use WS_CLIPSIBLINGS with the buttons or they would draw over + // each other in any resizeable dialog which has more than one button in + // the bottom + // + dwStyle |= WS_CLIPSIBLINGS; + return dwStyle; +} // end of wxButton::OS2GetStyle + +MRESULT wxButton::WindowProc( WXUINT uMsg, + WXWPARAM wParam, + WXLPARAM lParam ) +{ + // + // When we receive focus, we want to temporary become the default button in + // our parent panel so that pressing "Enter" would activate us -- and when + // losing it we should restore the previous default button as well // if (uMsg == WM_SETFOCUS) { - SetDefault(); + if (SHORT1FROMMP(lParam) == TRUE) + SetTmpDefault(); + else + UnsetTmpDefault(); // // Let the default processign take place too @@ -362,5 +434,4 @@ MRESULT wxButton::WindowProc( ,wParam ,lParam )); -} // end of wxW indowProc - +} // end of wxWindowProc