X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/e5b5af9139263dd92c3fca3153b9a69e36c8b7c8..22fec94aa95d2e1340dfa4bc7f00cea79b868977:/src/msw/window.cpp diff --git a/src/msw/window.cpp b/src/msw/window.cpp index eb18a5e6b1..89faa57b7f 100644 --- a/src/msw/window.cpp +++ b/src/msw/window.cpp @@ -93,6 +93,7 @@ #include "wx/notebook.h" #include "wx/listctrl.h" +#include "wx/dynlib.h" #include @@ -119,7 +120,7 @@ #endif #endif -#if defined(TME_LEAVE) && defined(WM_MOUSELEAVE) +#if defined(TME_LEAVE) && defined(WM_MOUSELEAVE) && wxUSE_DYNLIB_CLASS #define HAVE_TRACKMOUSEEVENT #endif // everything needed for TrackMouseEvent() @@ -1539,9 +1540,13 @@ void wxWindowMSW::Update() // drag and drop // --------------------------------------------------------------------------- +#if wxUSE_DRAG_AND_DROP || !defined(__WXWINCE__) + +#if wxUSE_STATBOX + // we need to lower the sibling static boxes so controls contained within can be // a drop target -static inline void AdjustStaticBoxZOrder(wxWindow *parent) +static void AdjustStaticBoxZOrder(wxWindow *parent) { // no sibling static boxes if we have no parent (ie TLW) if ( !parent ) @@ -1560,6 +1565,16 @@ static inline void AdjustStaticBoxZOrder(wxWindow *parent) } } +#else // !wxUSE_STATBOX + +static inline void AdjustStaticBoxZOrder(wxWindow * WXUNUSED(parent)) +{ +} + +#endif // wxUSE_STATBOX/!wxUSE_STATBOX + +#endif // drag and drop is used + #if wxUSE_DRAG_AND_DROP void wxWindowMSW::SetDropTarget(wxDropTarget *pDropTarget) { @@ -1703,7 +1718,7 @@ void wxWindowMSW::DoGetPosition(int *x, int *y) const { if ( wxTheApp->GetLayoutDirection() == wxLayout_RightToLeft ) { - // In RTL mode, we want the logical left x-coordinate, + // In RTL mode, we want the logical left x-coordinate, // which would be the physical right x-coordinate. point.x = rect.right; } @@ -2630,7 +2645,8 @@ WXLRESULT wxWindowMSW::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM l #ifdef HAVE_TRACKMOUSEEVENT case WM_MOUSELEAVE: - // filter out excess WM_MOUSELEAVE events sent after PopupMenu() (on XP at least) + // filter out excess WM_MOUSELEAVE events sent after PopupMenu() + // (on XP at least) if ( m_mouseInWindow ) { GenerateMouseLeave(); @@ -3950,6 +3966,19 @@ bool wxWindowMSW::HandlePower(WXWPARAM WXUNUSED_IN_WINCE(wParam), #endif } +bool wxWindowMSW::IsDoubleBuffered() const +{ + for ( const wxWindowMSW *wnd = this; + wnd && !wnd->IsTopLevel(); wnd = + wnd->GetParent() ) + { + if ( ::GetWindowLong(GetHwndOf(wnd), GWL_EXSTYLE) & WS_EX_COMPOSITED ) + return true; + } + + return false; +} + // --------------------------------------------------------------------------- // owner drawn stuff // --------------------------------------------------------------------------- @@ -4365,7 +4394,7 @@ void wxWindowMSW::OnPaint(wxPaintEvent& event) bool wxWindowMSW::HandleEraseBkgnd(WXHDC hdc) { - wxDCTemp dc(hdc); + wxDCTemp dc(hdc, GetClientSize()); dc.SetHDC(hdc); dc.SetWindow((wxWindow *)this); @@ -4468,11 +4497,37 @@ WXHBRUSH wxWindowMSW::MSWGetBgBrush(WXHDC hDC, WXHWND hWndToPaint) return 0; } -bool wxWindowMSW::HandlePrintClient(WXHDC WXUNUSED(hDC)) +bool wxWindowMSW::HandlePrintClient(WXHDC hDC) { - // TODO: handle wxBG_STYLE_CUSTOM and/or wxBG_STYLE_COLOUR here so when - // DrawParentThemeBackground() from uxtheme.dll is called we don't get - // the default background e.g. the border when custom drawing buttons + // we receive this message when DrawThemeParentBackground() is + // called from def window proc of several controls under XP and we + // must draw properly themed background here + // + // note that naively I'd expect filling the client rect with the + // brush returned by MSWGetBgBrush() work -- but for some reason it + // doesn't and we have to call parents MSWPrintChild() which is + // supposed to call DrawThemeBackground() with appropriate params + // + // also note that in this case lParam == PRF_CLIENT but we're + // clearly expected to paint the background and nothing else! + + if ( IsTopLevel() || InheritsBackgroundColour() ) + return false; + + // sometimes we don't want the parent to handle it at all, instead + // return whatever value this window wants + if ( !MSWShouldPropagatePrintChild() ) + return MSWPrintChild(hDC, (wxWindow *)this); + + for ( wxWindow *win = GetParent(); win; win = win->GetParent() ) + { + if ( win->MSWPrintChild(hDC, (wxWindow *)this) ) + return true; + + if ( win->IsTopLevel() || win->InheritsBackgroundColour() ) + break; + } + return false; } @@ -4879,14 +4934,41 @@ bool wxWindowMSW::HandleMouseMove(int x, int y, WXUINT flags) m_mouseInWindow = true; #ifdef HAVE_TRACKMOUSEEVENT - WinStruct trackinfo; + typedef BOOL (WINAPI *_TrackMouseEvent_t)(LPTRACKMOUSEEVENT); +#ifdef __WXWINCE__ + static const _TrackMouseEvent_t + s_pfn_TrackMouseEvent = _TrackMouseEvent; +#else // !__WXWINCE__ + static _TrackMouseEvent_t s_pfn_TrackMouseEvent; + static bool s_initDone = false; + if ( !s_initDone ) + { + wxLogNull noLog; - trackinfo.dwFlags = TME_LEAVE; - trackinfo.hwndTrack = GetHwnd(); + wxDynamicLibrary dllComCtl32(_T("comctl32.dll"), wxDL_VERBATIM); + if ( dllComCtl32.IsLoaded() ) + { + s_pfn_TrackMouseEvent = (_TrackMouseEvent_t) + dllComCtl32.GetSymbol(_T("_TrackMouseEvent")); + } + + s_initDone = true; - // Use the commctrl.h _TrackMouseEvent(), which will call the real - // TrackMouseEvent() if available or emulate it - _TrackMouseEvent(&trackinfo); + // notice that it's ok to unload comctl32.dll here as it won't + // be really unloaded, being still in use because we link to it + // statically too + } + + if ( s_pfn_TrackMouseEvent ) +#endif // __WXWINCE__/!__WXWINCE__ + { + WinStruct trackinfo; + + trackinfo.dwFlags = TME_LEAVE; + trackinfo.hwndTrack = GetHwnd(); + + (*s_pfn_TrackMouseEvent)(&trackinfo); + } #endif // HAVE_TRACKMOUSEEVENT wxMouseEvent event(wxEVT_ENTER_WINDOW); @@ -4896,7 +4978,7 @@ bool wxWindowMSW::HandleMouseMove(int x, int y, WXUINT flags) } } #ifdef HAVE_TRACKMOUSEEVENT - else + else // mouse not in window { // Check if we need to send a LEAVE event // Windows doesn't send WM_MOUSELEAVE if the mouse has been captured so