From a82afab363d472b412823d645091ced8a60b6c14 Mon Sep 17 00:00:00 2001 From: Vadim Zeitlin Date: Thu, 13 Oct 2011 12:45:56 +0000 Subject: [PATCH 1/1] Implement SetShape() for wxPopupWindow in wxGTK. Move SetShape() implementation from wxTopLevelWindow to wxNonOwnedWindow so that wxPopupWindow, which also inherits from the latter, could use it as well. This makes it possible to have popup windows with irregular shapes in wxGTK as well as in wxMSW and wxOSX. git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@69408 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775 --- Makefile.in | 21 +++++++++ build/bakefiles/files.bkl | 2 + include/wx/gtk/nonownedwnd.h | 35 ++++++++++++++ include/wx/gtk/toplevel.h | 5 -- include/wx/nonownedwnd.h | 5 +- src/gtk/nonownedwnd.cpp | 91 ++++++++++++++++++++++++++++++++++++ src/gtk/toplevel.cpp | 45 ------------------ 7 files changed, 152 insertions(+), 52 deletions(-) create mode 100644 include/wx/gtk/nonownedwnd.h create mode 100644 src/gtk/nonownedwnd.cpp diff --git a/Makefile.in b/Makefile.in index 6c5ce7a403..fb031f6d7c 100644 --- a/Makefile.in +++ b/Makefile.in @@ -2607,6 +2607,7 @@ COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_LOWLEVEL_HDR = \ wx/gtk/font.h \ wx/gtk/filehistory.h \ wx/gtk/minifram.h \ + wx/gtk/nonownedwnd.h \ wx/gtk/pen.h \ wx/gtk/popupwin.h \ wx/gtk/private/win_gtk.h \ @@ -5042,6 +5043,7 @@ COND_TOOLKIT_GTK_TOOLKIT_VERSION_2___LOWLEVEL_SRC_OBJECTS = \ monodll_gtk_font.o \ monodll_gtk_sockgtk.o \ monodll_gtk_minifram.o \ + monodll_gtk_nonownedwnd.o \ monodll_gtk_pen.o \ monodll_gtk_popupwin.o \ monodll_private.o \ @@ -5924,6 +5926,7 @@ COND_TOOLKIT_GTK_TOOLKIT_VERSION_2___LOWLEVEL_SRC_OBJECTS_1 = \ monodll_gtk_font.o \ monodll_gtk_sockgtk.o \ monodll_gtk_minifram.o \ + monodll_gtk_nonownedwnd.o \ monodll_gtk_pen.o \ monodll_gtk_popupwin.o \ monodll_private.o \ @@ -6994,6 +6997,7 @@ COND_TOOLKIT_GTK_TOOLKIT_VERSION_2___LOWLEVEL_SRC_OBJECTS_2 = \ monolib_gtk_font.o \ monolib_gtk_sockgtk.o \ monolib_gtk_minifram.o \ + monolib_gtk_nonownedwnd.o \ monolib_gtk_pen.o \ monolib_gtk_popupwin.o \ monolib_private.o \ @@ -7876,6 +7880,7 @@ COND_TOOLKIT_GTK_TOOLKIT_VERSION_2___LOWLEVEL_SRC_OBJECTS_3 = \ monolib_gtk_font.o \ monolib_gtk_sockgtk.o \ monolib_gtk_minifram.o \ + monolib_gtk_nonownedwnd.o \ monolib_gtk_pen.o \ monolib_gtk_popupwin.o \ monolib_private.o \ @@ -9125,6 +9130,7 @@ COND_TOOLKIT_GTK_TOOLKIT_VERSION_2___LOWLEVEL_SRC_OBJECTS_4 = \ coredll_gtk_font.o \ coredll_gtk_sockgtk.o \ coredll_gtk_minifram.o \ + coredll_gtk_nonownedwnd.o \ coredll_gtk_pen.o \ coredll_gtk_popupwin.o \ coredll_private.o \ @@ -10007,6 +10013,7 @@ COND_TOOLKIT_GTK_TOOLKIT_VERSION_2___LOWLEVEL_SRC_OBJECTS_5 = \ coredll_gtk_font.o \ coredll_gtk_sockgtk.o \ coredll_gtk_minifram.o \ + coredll_gtk_nonownedwnd.o \ coredll_gtk_pen.o \ coredll_gtk_popupwin.o \ coredll_private.o \ @@ -10717,6 +10724,7 @@ COND_TOOLKIT_GTK_TOOLKIT_VERSION_2___LOWLEVEL_SRC_OBJECTS_6 = \ corelib_gtk_font.o \ corelib_gtk_sockgtk.o \ corelib_gtk_minifram.o \ + corelib_gtk_nonownedwnd.o \ corelib_gtk_pen.o \ corelib_gtk_popupwin.o \ corelib_private.o \ @@ -11599,6 +11607,7 @@ COND_TOOLKIT_GTK_TOOLKIT_VERSION_2___LOWLEVEL_SRC_OBJECTS_7 = \ corelib_gtk_font.o \ corelib_gtk_sockgtk.o \ corelib_gtk_minifram.o \ + corelib_gtk_nonownedwnd.o \ corelib_gtk_pen.o \ corelib_gtk_popupwin.o \ corelib_private.o \ @@ -18081,6 +18090,9 @@ monodll_sound_sdl.o: $(srcdir)/src/unix/sound_sdl.cpp $(MONODLL_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@monodll_gtk_minifram.o: $(srcdir)/src/gtk/minifram.cpp $(MONODLL_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/gtk/minifram.cpp +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@monodll_gtk_nonownedwnd.o: $(srcdir)/src/gtk/nonownedwnd.cpp $(MONODLL_ODEP) +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/gtk/nonownedwnd.cpp + @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@monodll_gtk_pen.o: $(srcdir)/src/gtk/pen.cpp $(MONODLL_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/gtk/pen.cpp @@ -23451,6 +23463,9 @@ monolib_sound_sdl.o: $(srcdir)/src/unix/sound_sdl.cpp $(MONOLIB_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@monolib_gtk_minifram.o: $(srcdir)/src/gtk/minifram.cpp $(MONOLIB_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/gtk/minifram.cpp +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@monolib_gtk_nonownedwnd.o: $(srcdir)/src/gtk/nonownedwnd.cpp $(MONOLIB_ODEP) +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/gtk/nonownedwnd.cpp + @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@monolib_gtk_pen.o: $(srcdir)/src/gtk/pen.cpp $(MONOLIB_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/gtk/pen.cpp @@ -28980,6 +28995,9 @@ coredll_win32.o: $(srcdir)/src/univ/themes/win32.cpp $(COREDLL_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@coredll_gtk_minifram.o: $(srcdir)/src/gtk/minifram.cpp $(COREDLL_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(COREDLL_CXXFLAGS) $(srcdir)/src/gtk/minifram.cpp +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@coredll_gtk_nonownedwnd.o: $(srcdir)/src/gtk/nonownedwnd.cpp $(COREDLL_ODEP) +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(COREDLL_CXXFLAGS) $(srcdir)/src/gtk/nonownedwnd.cpp + @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@coredll_gtk_pen.o: $(srcdir)/src/gtk/pen.cpp $(COREDLL_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(COREDLL_CXXFLAGS) $(srcdir)/src/gtk/pen.cpp @@ -32991,6 +33009,9 @@ corelib_win32.o: $(srcdir)/src/univ/themes/win32.cpp $(CORELIB_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@corelib_gtk_minifram.o: $(srcdir)/src/gtk/minifram.cpp $(CORELIB_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(CORELIB_CXXFLAGS) $(srcdir)/src/gtk/minifram.cpp +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@corelib_gtk_nonownedwnd.o: $(srcdir)/src/gtk/nonownedwnd.cpp $(CORELIB_ODEP) +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(CORELIB_CXXFLAGS) $(srcdir)/src/gtk/nonownedwnd.cpp + @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@corelib_gtk_pen.o: $(srcdir)/src/gtk/pen.cpp $(CORELIB_ODEP) @COND_TOOLKIT_GTK_TOOLKIT_VERSION_2_USE_GUI_1@ $(CXXC) -c -o $@ $(CORELIB_CXXFLAGS) $(srcdir)/src/gtk/pen.cpp diff --git a/build/bakefiles/files.bkl b/build/bakefiles/files.bkl index 96b214b1bb..1e73c71304 100644 --- a/build/bakefiles/files.bkl +++ b/build/bakefiles/files.bkl @@ -1094,6 +1094,7 @@ IMPORTANT: please read docs/tech/tn0016.txt before modifying this file! src/gtk/font.cpp src/gtk/sockgtk.cpp src/gtk/minifram.cpp + src/gtk/nonownedwnd.cpp src/gtk/pen.cpp src/gtk/popupwin.cpp src/gtk/private.cpp @@ -1131,6 +1132,7 @@ IMPORTANT: please read docs/tech/tn0016.txt before modifying this file! wx/gtk/font.h wx/gtk/filehistory.h wx/gtk/minifram.h + wx/gtk/nonownedwnd.h wx/gtk/pen.h wx/gtk/popupwin.h wx/gtk/private/win_gtk.h diff --git a/include/wx/gtk/nonownedwnd.h b/include/wx/gtk/nonownedwnd.h new file mode 100644 index 0000000000..a722e27606 --- /dev/null +++ b/include/wx/gtk/nonownedwnd.h @@ -0,0 +1,35 @@ +/////////////////////////////////////////////////////////////////////////////// +// Name: wx/gtk/nonownedwnd.h +// Purpose: wxGTK-specific wxNonOwnedWindow declaration. +// Author: Vadim Zeitlin +// Created: 2011-10-12 +// RCS-ID: $Id: wxhead.h,v 1.12 2010-04-22 12:44:51 zeitlin Exp $ +// Copyright: (c) 2011 Vadim Zeitlin +// Licence: wxWindows licence +/////////////////////////////////////////////////////////////////////////////// + +#ifndef _WX_GTK_NONOWNEDWND_H_ +#define _WX_GTK_NONOWNEDWND_H_ + +// ---------------------------------------------------------------------------- +// wxNonOwnedWindow contains code common to wx{Popup,TopLevel}Window in wxGTK. +// ---------------------------------------------------------------------------- + +class WXDLLIMPEXP_CORE wxNonOwnedWindow : public wxNonOwnedWindowBase +{ +public: + wxNonOwnedWindow() { } + + virtual bool SetShape(const wxRegion& region); + + // Overridden to actually set the shape when the window becomes realized. + virtual void GTKHandleRealized(); + +private: + // If valid, defines the custom shape of the window. + wxRegion m_shape; + + wxDECLARE_NO_COPY_CLASS(wxNonOwnedWindow); +}; + +#endif // _WX_GTK_NONOWNEDWND_H_ diff --git a/include/wx/gtk/toplevel.h b/include/wx/gtk/toplevel.h index a84cf8a87e..d7b19d6409 100644 --- a/include/wx/gtk/toplevel.h +++ b/include/wx/gtk/toplevel.h @@ -57,8 +57,6 @@ public: virtual bool ShowFullScreen(bool show, long style = wxFULLSCREEN_ALL); virtual bool IsFullScreen() const { return m_fsIsShowing; }; - virtual bool SetShape(const wxRegion& region); - virtual void RequestUserAttention(int flags = wxUSER_ATTENTION_INFO); virtual void SetWindowStyleFlag( long style ); @@ -113,9 +111,6 @@ public: // size of WM decorations wxSize m_decorSize; - // shape of the frame - wxRegion m_shape; - // private gtk_timeout_add result for mimicing wxUSER_ATTENTION_INFO and // wxUSER_ATTENTION_ERROR difference, -2 for no hint, -1 for ERROR hint, rest for GtkTimeout handle. int m_urgency_hint; diff --git a/include/wx/nonownedwnd.h b/include/wx/nonownedwnd.h index 8029419765..6f32d2304e 100644 --- a/include/wx/nonownedwnd.h +++ b/include/wx/nonownedwnd.h @@ -30,14 +30,15 @@ public: #if defined(__WXDFB__) #include "wx/dfb/nonownedwnd.h" +#elif defined(__WXGTK__) + #include "wx/gtk/nonownedwnd.h" #elif defined(__WXMAC__) #include "wx/osx/nonownedwnd.h" #elif defined(__WXMSW__) #include "wx/msw/nonownedwnd.h" #else // No special class needed in other ports, they can derive both wxTLW and - // wxPopupWindow directly from wxWindow and don't implement SetShape() (at - // least at this level, wxGTK does do it in wxTLW). + // wxPopupWindow directly from wxWindow and don't implement SetShape(). class wxNonOwnedWindow : public wxNonOwnedWindowBase { }; diff --git a/src/gtk/nonownedwnd.cpp b/src/gtk/nonownedwnd.cpp new file mode 100644 index 0000000000..20f05258e3 --- /dev/null +++ b/src/gtk/nonownedwnd.cpp @@ -0,0 +1,91 @@ +/////////////////////////////////////////////////////////////////////////////// +// Name: src/gtk/nonownedwnd.cpp +// Purpose: wxGTK implementation of wxNonOwnedWindow. +// Author: Vadim Zeitlin +// Created: 2011-10-12 +// RCS-ID: $Id: wxhead.cpp,v 1.11 2010-04-22 12:44:51 zeitlin Exp $ +// Copyright: (c) 2011 Vadim Zeitlin +// Licence: wxWindows licence +/////////////////////////////////////////////////////////////////////////////// + +// ============================================================================ +// declarations +// ============================================================================ + +// ---------------------------------------------------------------------------- +// headers +// ---------------------------------------------------------------------------- + +// for compilers that support precompilation, includes "wx.h". +#include "wx/wxprec.h" + +#ifdef __BORLANDC__ + #pragma hdrstop +#endif + +#ifndef WX_PRECOMP + #include "wx/string.h" +#endif // WX_PRECOMP + +#include "wx/gtk/private.h" + +#include + +namespace +{ + +// helper +bool do_shape_combine_region(GdkWindow* window, const wxRegion& region) +{ + if (window) + { + if (region.IsEmpty()) + { + gdk_window_shape_combine_mask(window, NULL, 0, 0); + } + else + { + gdk_window_shape_combine_region(window, region.GetRegion(), 0, 0); + return true; + } + } + return false; +} + +} // anonymous namespace + + +// ============================================================================ +// wxNonOwnedWindow implementation +// ============================================================================ + +void wxNonOwnedWindow::GTKHandleRealized() +{ + wxNonOwnedWindowBase::GTKHandleRealized(); + + if (HasFlag(wxFRAME_SHAPED)) + SetShape(m_shape); +} + +bool wxNonOwnedWindow::SetShape(const wxRegion& region) +{ + wxCHECK_MSG( HasFlag(wxFRAME_SHAPED), false, + wxT("Shaped windows must be created with the wxFRAME_SHAPED style.")); + + if ( gtk_widget_get_realized(m_widget) ) + { + if ( m_wxwindow ) + do_shape_combine_region(gtk_widget_get_window(m_wxwindow), region); + + return do_shape_combine_region(gtk_widget_get_window(m_widget), region); + } + else // not realized yet + { + // store the shape to set, it will be really set once we're realized + m_shape = region; + + // we don't know if we're going to succeed or fail, be optimistic by + // default + return true; + } +} diff --git a/src/gtk/toplevel.cpp b/src/gtk/toplevel.cpp index eed18cf06c..1e1c3bcc39 100644 --- a/src/gtk/toplevel.cpp +++ b/src/gtk/toplevel.cpp @@ -328,9 +328,6 @@ void wxTopLevelWindowGTK::GTKHandleRealized() const wxIconBundle& icons = GetIcons(); if (icons.GetIconCount()) SetIcons(icons); - - if (HasFlag(wxFRAME_SHAPED)) - SetShape(m_shape); // it will really set the window shape now } //----------------------------------------------------------------------------- @@ -1321,48 +1318,6 @@ void wxTopLevelWindowGTK::RemoveGrab() } -// helper -static bool do_shape_combine_region(GdkWindow* window, const wxRegion& region) -{ - if (window) - { - if (region.IsEmpty()) - { - gdk_window_shape_combine_mask(window, NULL, 0, 0); - } - else - { - gdk_window_shape_combine_region(window, region.GetRegion(), 0, 0); - return true; - } - } - return false; -} - - -bool wxTopLevelWindowGTK::SetShape(const wxRegion& region) -{ - wxCHECK_MSG( HasFlag(wxFRAME_SHAPED), false, - wxT("Shaped windows must be created with the wxFRAME_SHAPED style.")); - - if ( gtk_widget_get_realized(m_widget) ) - { - if ( m_wxwindow ) - do_shape_combine_region(gtk_widget_get_window(m_wxwindow), region); - - return do_shape_combine_region(gtk_widget_get_window(m_widget), region); - } - else // not realized yet - { - // store the shape to set, it will be really set once we're realized - m_shape = region; - - // we don't know if we're going to succeed or fail, be optimistic by - // default - return true; - } -} - bool wxTopLevelWindowGTK::IsActive() { return (this == (wxTopLevelWindowGTK*)g_activeFrame); -- 2.45.2