X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/31e1bd370d2ded34d97f4824029adb924a0a58a4..69659fd770f615210efac4b4fa741b3ad6223616:/src/common/containr.cpp diff --git a/src/common/containr.cpp b/src/common/containr.cpp index d465bc0511..f2d237a36d 100644 --- a/src/common/containr.cpp +++ b/src/common/containr.cpp @@ -24,13 +24,16 @@ #pragma hdrstop #endif +#ifndef WX_PRECOMP + #include "wx/containr.h" +#endif + #ifndef WX_PRECOMP #include "wx/log.h" #include "wx/event.h" #include "wx/window.h" #include "wx/scrolbar.h" #include "wx/radiobut.h" - #include "wx/containr.h" #endif //WX_PRECOMP // trace mask for focus messages @@ -40,56 +43,52 @@ // implementation // ============================================================================ -wxControlContainer::wxControlContainer(wxWindow *winParent) +// ---------------------------------------------------------------------------- +// wxControlContainerBase +// ---------------------------------------------------------------------------- + +void wxControlContainerBase::SetCanFocus(bool acceptsFocus) { - m_winParent = winParent; - m_winLastFocused = NULL; - m_inSetFocus = false; + if ( acceptsFocus == m_acceptsFocus ) + return; + + m_acceptsFocus = acceptsFocus; + + m_winParent->SetCanFocus(m_acceptsFocus); } -bool wxControlContainer::AcceptsFocus() const +bool wxControlContainerBase::HasAnyFocusableChildren() const { - // if we're not shown or disabled, we can't accept focus - if ( m_winParent->IsShown() && m_winParent->IsEnabled() ) + const wxWindowList& children = m_winParent->GetChildren(); + for ( wxWindowList::const_iterator i = children.begin(), + end = children.end(); + i != end; + ++i ) { - // otherwise we can accept focus either if we have no children at all - // (in this case we're probably not used as a container) or only when - // at least one child will accept focus - wxWindowList::compatibility_iterator node = m_winParent->GetChildren().GetFirst(); - if ( !node ) - return true; - -#ifdef __WXMAC__ - // wxMac has eventually the two scrollbars as children, they don't count - // as real children in the algorithm mentioned above - bool hasRealChildren = false ; -#endif + const wxWindow * const child = *i; - while ( node ) - { - wxWindow *child = node->GetData(); - node = node->GetNext(); - -#ifdef __WXMAC__ - if ( m_winParent->MacIsWindowScrollbar( child ) ) - continue; - hasRealChildren = true ; -#endif - if ( child->AcceptsFocus() ) - { - return true; - } - } + if ( !m_winParent->IsClientAreaChild(child) ) + continue; -#ifdef __WXMAC__ - if ( !hasRealChildren ) - return true ; -#endif + if ( child->CanAcceptFocus() ) + return true; } return false; } +#ifndef wxHAS_NATIVE_TAB_TRAVERSAL + +// ---------------------------------------------------------------------------- +// generic wxControlContainer +// ---------------------------------------------------------------------------- + +wxControlContainer::wxControlContainer() +{ + m_winLastFocused = NULL; + m_inSetFocus = false; +} + void wxControlContainer::SetLastFocus(wxWindow *win) { // the panel itself should never get the focus at all but if it does happen @@ -132,12 +131,16 @@ void wxControlContainer::SetLastFocus(wxWindow *win) } // propagate the last focus upwards so that our parent can set focus back - // to us if it loses it now and regains later - wxWindow *parent = m_winParent->GetParent(); - if ( parent ) + // to us if it loses it now and regains later; do *not* do this if we are + // a toplevel window (e.g. wxDialog) that has another frame as its parent + if ( !m_winParent->IsTopLevel() ) { - wxChildFocusEvent eventFocus(m_winParent); - parent->GetEventHandler()->ProcessEvent(eventFocus); + wxWindow *parent = m_winParent->GetParent(); + if ( parent ) + { + wxChildFocusEvent eventFocus(m_winParent); + parent->GetEventHandler()->ProcessEvent(eventFocus); + } } } @@ -307,8 +310,15 @@ void wxControlContainer::HandleOnNavigationKey( wxNavigationKeyEvent& event ) } } - if ( bookctrl && bookctrl->GetEventHandler()->ProcessEvent(event) ) - return; + if ( bookctrl ) + { + // make sure that we don't bubble up the event again from the book + // control resulting in infinite recursion + wxNavigationKeyEvent eventCopy(event); + eventCopy.SetEventObject(m_winParent); + if ( bookctrl->GetEventHandler()->ProcessEvent(eventCopy) ) + return; + } } // there is not much to do if we don't have children and we're not @@ -497,7 +507,7 @@ void wxControlContainer::HandleOnNavigationKey( wxNavigationKeyEvent& event ) } #endif // __WXMSW__ - if ( child->AcceptsFocusFromKeyboard() ) + if ( child->CanAcceptFocusFromKeyboard() ) { // if we're setting the focus to a child panel we should prevent it // from giving it to the child which had the focus the last time @@ -638,12 +648,11 @@ bool wxSetFocusToChild(wxWindow *win, wxWindow **childLastFocused) wxWindow *child = node->GetData(); node = node->GetNext(); -#ifdef __WXMAC__ - if ( child->GetParent()->MacIsWindowScrollbar( child ) ) + // skip special windows: + if ( !win->IsClientAreaChild(child) ) continue; -#endif - - if ( child->AcceptsFocusFromKeyboard() && !child->IsTopLevel() ) + + if ( child->CanAcceptFocusFromKeyboard() && !child->IsTopLevel() ) { #ifdef __WXMSW__ // If a radiobutton is the first focusable child, search for the @@ -669,3 +678,5 @@ bool wxSetFocusToChild(wxWindow *win, wxWindow **childLastFocused) return false; } + +#endif // !wxHAS_NATIVE_TAB_TRAVERSAL