From: Vadim Zeitlin Date: Sun, 25 Mar 2012 17:56:04 +0000 (+0000) Subject: Implement native tab art for wxAUI in wxGTK. X-Git-Url: https://git.saurik.com/wxWidgets.git/commitdiff_plain/069358b7ccf8a82eb4d809c25ebe5a3db9db67cd?ds=inline Implement native tab art for wxAUI in wxGTK. Use native wxAuiTabArt implementation in wxGTK, it better conforms to the system style. Closes #14098. git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@71002 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775 --- diff --git a/Makefile.in b/Makefile.in index c10f4f28d5..c2fb0475c8 100644 --- a/Makefile.in +++ b/Makefile.in @@ -1841,7 +1841,8 @@ AUIDLL_OBJECTS = \ auidll_auibook.o \ auidll_auibar.o \ auidll_tabmdi.o \ - auidll_tabart.o + auidll_tabart.o \ + $(__AUI_GTK_SRC_OBJECTS_2) AUIDLL_ODEP = $(_____pch_wxprec_auidll_wx_wxprec_h_gch___depname) AUILIB_CXXFLAGS = $(__auilib_PCH_INC) -D__WX$(TOOLKIT)__ $(__WXUNIV_DEFINE_p) \ $(__DEBUG_DEFINE_p) $(__EXCEPTIONS_DEFINE_p) $(__RTTI_DEFINE_p) \ @@ -1855,7 +1856,8 @@ AUILIB_OBJECTS = \ auilib_auibook.o \ auilib_auibar.o \ auilib_tabmdi.o \ - auilib_tabart.o + auilib_tabart.o \ + $(__AUI_GTK_SRC_OBJECTS_3) AUILIB_ODEP = $(_____pch_wxprec_auilib_wx_wxprec_h_gch___depname) RIBBONDLL_CXXFLAGS = $(__ribbondll_PCH_INC) -D__WX$(TOOLKIT)__ \ $(__WXUNIV_DEFINE_p) $(__DEBUG_DEFINE_p) $(__EXCEPTIONS_DEFINE_p) \ @@ -2140,6 +2142,7 @@ COND_USE_STC_1___wxscintilla___depname = \ @COND_TOOLKIT_WINCE@OPENGL_HDR_PLATFORM = wx/msw/glcanvas.h @COND_TOOLKIT_MOTIF@OPENGL_HDR_PLATFORM = wx/x11/glcanvas.h wx/unix/glx11.h @COND_TOOLKIT_X11@OPENGL_HDR_PLATFORM = wx/x11/glcanvas.h wx/unix/glx11.h +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2@AUI_GTK_HDR = wx/aui/tabartgtk.h COND_TOOLKIT_OSX_CARBON_BASE_OSX_SRC = \ src/osx/core/mimetype.cpp \ src/osx/core/cfstring.cpp \ @@ -4201,6 +4204,7 @@ COND_USE_GUI_1_ALL_GUI_HEADERS = \ wx/aui/tabmdi.h \ wx/aui/aui.h \ wx/aui/tabart.h \ + $(AUI_GTK_HDR) \ wx/propgrid/advprops.h \ wx/propgrid/editors.h \ wx/propgrid/manager.h \ @@ -4518,6 +4522,7 @@ COND_USE_GUI_1___MONOLIB_GUI_SRC_OBJECTS = \ monodll_auibar.o \ monodll_tabmdi.o \ monodll_tabart.o \ + $(__AUI_GTK_SRC_OBJECTS) \ monodll_advprops.o \ monodll_editors.o \ monodll_manager.o \ @@ -6188,6 +6193,8 @@ COND_TOOLKIT_WINCE___ADVANCED_PLATFORM_NATIVE_SRC_OBJECTS = \ @COND_PLATFORM_UNIX_1@__WEBVIEW_SRC_PLATFORM_OBJECTS \ @COND_PLATFORM_UNIX_1@ = monodll_gtk_webview_webkit.o @COND_TOOLKIT_MSW@__WEBVIEW_SRC_PLATFORM_OBJECTS = monodll_webview_ie.o +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2@__AUI_GTK_SRC_OBJECTS \ +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2@ = monodll_tabartgtk.o @COND_PLATFORM_UNIX_1_USE_PLUGINS_0@__PLUGIN_ADV_SRC_OBJECTS \ @COND_PLATFORM_UNIX_1_USE_PLUGINS_0@ = monodll_sound_sdl.o @COND_PLATFORM_WIN32_1@__monodll___win32rc = monodll_version_rc.o @@ -6413,6 +6420,7 @@ COND_USE_GUI_1___MONOLIB_GUI_SRC_OBJECTS_1 = \ monolib_auibar.o \ monolib_tabmdi.o \ monolib_tabart.o \ + $(__AUI_GTK_SRC_OBJECTS_1) \ monolib_advprops.o \ monolib_editors.o \ monolib_manager.o \ @@ -8085,6 +8093,8 @@ COND_TOOLKIT_WINCE___ADVANCED_PLATFORM_NATIVE_SRC_OBJECTS_1 = \ @COND_PLATFORM_UNIX_1@__WEBVIEW_SRC_PLATFORM_OBJECTS_1 \ @COND_PLATFORM_UNIX_1@ = monolib_gtk_webview_webkit.o @COND_TOOLKIT_MSW@__WEBVIEW_SRC_PLATFORM_OBJECTS_1 = monolib_webview_ie.o +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2@__AUI_GTK_SRC_OBJECTS_1 \ +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2@ = monolib_tabartgtk.o @COND_PLATFORM_UNIX_1_USE_PLUGINS_0@__PLUGIN_ADV_SRC_OBJECTS_1 \ @COND_PLATFORM_UNIX_1_USE_PLUGINS_0@ = monolib_sound_sdl.o COND_MONOLITHIC_0_SHARED_1___basedll___depname = \ @@ -12469,6 +12479,8 @@ COND_USE_SOVERSOLARIS_1___auidll___so_symlinks_uninst_cmd = rm -f \ $(LIBPREFIX)wx_$(PORTNAME)$(WXUNIVNAME)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_aui-$(WX_RELEASE)$(HOST_SUFFIX).$(DLLIMP_SUFFIX) @COND_USE_SOVERSOLARIS_1@__auidll___so_symlinks_uninst_cmd = $(COND_USE_SOVERSOLARIS_1___auidll___so_symlinks_uninst_cmd) @COND_PLATFORM_WIN32_1@__auidll___win32rc = auidll_version_rc.o +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2@__AUI_GTK_SRC_OBJECTS_2 \ +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2@ = auidll_tabartgtk.o COND_MONOLITHIC_0_SHARED_0_USE_AUI_1___auilib___depname = \ $(LIBDIRNAME)/$(LIBPREFIX)wx_$(PORTNAME)$(WXUNIVNAME)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_aui-$(WX_RELEASE)$(HOST_SUFFIX)$(LIBEXT) @COND_MONOLITHIC_0_SHARED_0_USE_AUI_1@__auilib___depname = $(COND_MONOLITHIC_0_SHARED_0_USE_AUI_1___auilib___depname) @@ -12481,6 +12493,8 @@ COND_MONOLITHIC_0_SHARED_0_USE_AUI_1___auilib___depname = \ @COND_ICC_PCH_1@ ./.pch/wxprec_auilib/wx/wxprec.h.gch @COND_USE_PCH_1@_____pch_wxprec_auilib_wx_wxprec_h_gch___depname \ @COND_USE_PCH_1@ = ./.pch/wxprec_auilib/wx/wxprec.h.gch +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2@__AUI_GTK_SRC_OBJECTS_3 \ +@COND_TOOLKIT_GTK_TOOLKIT_VERSION_2@ = auilib_tabartgtk.o @COND_SHARED_1@____wxaui_namedll_DEP = $(__auidll___depname) @COND_SHARED_0@____wxaui_namelib_DEP = $(__auilib___depname) COND_MONOLITHIC_0_SHARED_1_USE_RIBBON_1___ribbondll___depname = \ @@ -17411,6 +17425,9 @@ monodll_tabmdi.o: $(srcdir)/src/aui/tabmdi.cpp $(MONODLL_ODEP) monodll_tabart.o: $(srcdir)/src/aui/tabart.cpp $(MONODLL_ODEP) $(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/aui/tabart.cpp +monodll_tabartgtk.o: $(srcdir)/src/aui/tabartgtk.cpp $(MONODLL_ODEP) + $(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/aui/tabartgtk.cpp + monodll_advprops.o: $(srcdir)/src/propgrid/advprops.cpp $(MONODLL_ODEP) $(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/propgrid/advprops.cpp @@ -22712,6 +22729,9 @@ monolib_tabmdi.o: $(srcdir)/src/aui/tabmdi.cpp $(MONOLIB_ODEP) monolib_tabart.o: $(srcdir)/src/aui/tabart.cpp $(MONOLIB_ODEP) $(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/aui/tabart.cpp +monolib_tabartgtk.o: $(srcdir)/src/aui/tabartgtk.cpp $(MONOLIB_ODEP) + $(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/aui/tabartgtk.cpp + monolib_advprops.o: $(srcdir)/src/propgrid/advprops.cpp $(MONOLIB_ODEP) $(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/propgrid/advprops.cpp @@ -36476,6 +36496,9 @@ auidll_tabmdi.o: $(srcdir)/src/aui/tabmdi.cpp $(AUIDLL_ODEP) auidll_tabart.o: $(srcdir)/src/aui/tabart.cpp $(AUIDLL_ODEP) $(CXXC) -c -o $@ $(AUIDLL_CXXFLAGS) $(srcdir)/src/aui/tabart.cpp +auidll_tabartgtk.o: $(srcdir)/src/aui/tabartgtk.cpp $(AUIDLL_ODEP) + $(CXXC) -c -o $@ $(AUIDLL_CXXFLAGS) $(srcdir)/src/aui/tabartgtk.cpp + auilib_framemanager.o: $(srcdir)/src/aui/framemanager.cpp $(AUILIB_ODEP) $(CXXC) -c -o $@ $(AUILIB_CXXFLAGS) $(srcdir)/src/aui/framemanager.cpp @@ -36497,6 +36520,9 @@ auilib_tabmdi.o: $(srcdir)/src/aui/tabmdi.cpp $(AUILIB_ODEP) auilib_tabart.o: $(srcdir)/src/aui/tabart.cpp $(AUILIB_ODEP) $(CXXC) -c -o $@ $(AUILIB_CXXFLAGS) $(srcdir)/src/aui/tabart.cpp +auilib_tabartgtk.o: $(srcdir)/src/aui/tabartgtk.cpp $(AUILIB_ODEP) + $(CXXC) -c -o $@ $(AUILIB_CXXFLAGS) $(srcdir)/src/aui/tabartgtk.cpp + ribbondll_version_rc.o: $(srcdir)/src/msw/version.rc $(RIBBONDLL_ODEP) $(WINDRES) -i$< -o$@ --define __WX$(TOOLKIT)__ $(__WXUNIV_DEFINE_p_67) $(__DEBUG_DEFINE_p_66) $(__EXCEPTIONS_DEFINE_p_65) $(__RTTI_DEFINE_p_65) $(__THREAD_DEFINE_p_65) --define WXBUILDING --define WXDLLNAME=$(WXDLLNAMEPREFIXGUI)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_ribbon$(WXCOMPILER)$(VENDORTAG)$(WXDLLVERSIONTAG) $(__RCDEFDIR_p) --include-dir $(top_srcdir)/include $(__INC_TIFF_BUILD_p_66) $(__INC_TIFF_p_66) $(__INC_JPEG_p_66) $(__INC_PNG_p_65) $(__INC_ZLIB_p_67) $(__INC_REGEX_p_65) $(__INC_EXPAT_p_65) --define WXUSINGDLL --define WXMAKINGDLL_RIBBON diff --git a/build/bakefiles/files.bkl b/build/bakefiles/files.bkl index 00ec5612cc..5f6229d86e 100644 --- a/build/bakefiles/files.bkl +++ b/build/bakefiles/files.bkl @@ -3548,6 +3548,16 @@ IMPORTANT: please read docs/tech/tn0016.txt before modifying this file! + + + src/aui/tabartgtk.cpp + + + + + wx/aui/tabartgtk.h + + src/aui/framemanager.cpp src/aui/dockart.cpp @@ -3556,6 +3566,7 @@ IMPORTANT: please read docs/tech/tn0016.txt before modifying this file! src/aui/auibar.cpp src/aui/tabmdi.cpp src/aui/tabart.cpp + $(AUI_GTK_SRC) wx/aui/framemanager.h @@ -3566,6 +3577,7 @@ IMPORTANT: please read docs/tech/tn0016.txt before modifying this file! wx/aui/tabmdi.h wx/aui/aui.h wx/aui/tabart.h + $(AUI_GTK_HDR) diff --git a/docs/changes.txt b/docs/changes.txt index 1403d36582..396dc4240f 100644 --- a/docs/changes.txt +++ b/docs/changes.txt @@ -502,6 +502,7 @@ GTK: - Fix wxNotebook best size calculation. - Implement wxDirDialog::Create() and wxFileDialog::Create() (vinayakgarg). - Fix const methods display in assert dialog (vinayakgarg). +- Implement native tab art for wxAUI (Jens Lody and Teodor Petrov). MSW: diff --git a/include/wx/aui/tabart.h b/include/wx/aui/tabart.h index e1418f2743..68a0e09118 100644 --- a/include/wx/aui/tabart.h +++ b/include/wx/aui/tabart.h @@ -275,7 +275,17 @@ protected: unsigned int m_flags; }; -#define wxAuiDefaultTabArt wxAuiGenericTabArt +#ifndef __WXUNIVERSAL__ + #if defined(__WXGTK20__) + #define wxHAS_NATIVE_TABART + #include "wx/aui/tabartgtk.h" + #define wxAuiDefaultTabArt wxAuiGtkTabArt + #endif +#endif // !__WXUNIVERSAL__ + +#ifndef wxHAS_NATIVE_TABART + #define wxAuiDefaultTabArt wxAuiGenericTabArt +#endif #endif // wxUSE_AUI diff --git a/include/wx/aui/tabartgtk.h b/include/wx/aui/tabartgtk.h new file mode 100644 index 0000000000..25f1447d91 --- /dev/null +++ b/include/wx/aui/tabartgtk.h @@ -0,0 +1,56 @@ +///////////////////////////////////////////////////////////////////////////// +// Name: include/wx/aui/tabartgtk.h +// Purpose: declaration of the wxAuiGTKTabArt +// Author: Jens Lody and Teodor Petrov +// Modified by: +// Created: 2012-03-23 +// RCS-ID: $Id:$ +// Copyright: (c) 2012 Jens Lody +// and Teodor Petrov +// Licence: wxWindows licence +///////////////////////////////////////////////////////////////////////////// + +#ifndef _WX_AUI_TABARTGTK_H_ +#define _WX_AUI_TABARTGTK_H_ + +// ---------------------------------------------------------------------------- +// headers +// ---------------------------------------------------------------------------- + +#include "wx/defs.h" + +#if wxUSE_AUI + +#include "wx/aui/tabart.h" +#include "wx/gdicmn.h" + +class wxWindow; +class wxDC; + +class WXDLLIMPEXP_AUI wxAuiGtkTabArt : public wxAuiGenericTabArt +{ +public: + wxAuiGtkTabArt(); + + virtual wxAuiTabArt* Clone(); + virtual void DrawBackground(wxDC& dc, wxWindow* wnd, const wxRect& rect); + virtual void DrawTab(wxDC& dc, + wxWindow* wnd, + const wxAuiNotebookPage& page, + const wxRect& in_rect, + int close_button_state, + wxRect* out_tab_rect, + wxRect* out_button_rect, + int* x_extent); + void DrawButton(wxDC& dc, wxWindow* wnd, const wxRect& in_rect, int bitmap_id, + int button_state, int orientation, wxRect* out_rect); + int GetBestTabCtrlSize(wxWindow* wnd, const wxAuiNotebookPageArray& pages, + const wxSize& required_bmp_size); + virtual wxSize GetTabSize(wxDC& dc, wxWindow* wnd, const wxString& caption, + const wxBitmap& bitmap, bool active, + int close_button_state, int* x_extent); +}; + +#endif // wxUSE_AUI + +#endif // _WX_AUI_TABARTGTK_H_ diff --git a/src/aui/tabartgtk.cpp b/src/aui/tabartgtk.cpp new file mode 100644 index 0000000000..7b3e6aa1f0 --- /dev/null +++ b/src/aui/tabartgtk.cpp @@ -0,0 +1,471 @@ +/////////////////////////////////////////////////////////////////////////////// +// Name: src/aui/tabartgtk.cpp +// Purpose: implementation of the wxAuiGTKTabArt +// Author: Jens Lody and Teodor Petrov +// Modified by: +// Created: 2012-03-23 +// RCS-ID: $Id:$ +// Copyright: (c) 2012 Jens Lody +// and Teodor Petrov +// Licence: wxWindows licence +/////////////////////////////////////////////////////////////////////////////// + +// ============================================================================ +// declarations +// ============================================================================ + +// ---------------------------------------------------------------------------- +// headers +// ---------------------------------------------------------------------------- + +// For compilers that support precompilation, includes "wx.h". +#include "wx/wxprec.h" + +#ifdef __BORLANDC__ + #pragma hdrstop +#endif + +#if wxUSE_AUI + +#ifndef WX_PRECOMP + #include "wx/dc.h" + #include "wx/dcclient.h" + #include "wx/settings.h" + #include "wx/image.h" +#endif + +#include "wx/gtk/dc.h" +#include "wx/gtk/private.h" + +#include + +#include "wx/aui/auibook.h" +#include "wx/aui/tabartgtk.h" +#include "wx/renderer.h" + +namespace +{ + +static int s_CloseIconSize = 16; // default size + +} + +wxAuiGtkTabArt::wxAuiGtkTabArt()//: +// m_Xthickness(0), +// m_Ythickness(0), +// m_TabHBorder(0), +// m_TabVBorder(0) + +{ +} + +wxAuiTabArt* wxAuiGtkTabArt::Clone() +{ + wxAuiGtkTabArt* clone = new wxAuiGtkTabArt(); + + clone->SetNormalFont(m_normalFont); + clone->SetSelectedFont(m_normalFont); + clone->SetMeasuringFont(m_normalFont); + + return clone; +} + +void wxAuiGtkTabArt::DrawBackground(wxDC& dc, wxWindow* WXUNUSED(wnd), const wxRect& rect) +{ + wxGTKDCImpl *impldc = (wxGTKDCImpl*) dc.GetImpl(); + GdkWindow* window = impldc->GetGDKWindow(); + + gtk_style_apply_default_background(gtk_widget_get_style(wxGTKPrivate::GetNotebookWidget()), + window, + true, + GTK_STATE_NORMAL, + NULL, + rect.x, rect.y, rect.width, rect.height); +} + +void ButtonStateAndShadow(int button_state, GtkStateType &state, GtkShadowType &shadow) +{ + + if (button_state & wxAUI_BUTTON_STATE_DISABLED) + { + state = GTK_STATE_INSENSITIVE; + shadow = GTK_SHADOW_ETCHED_IN; + } + else if (button_state & wxAUI_BUTTON_STATE_HOVER) + { + state = GTK_STATE_PRELIGHT; + shadow = GTK_SHADOW_OUT; + } + else if (button_state & wxAUI_BUTTON_STATE_PRESSED) + { + state = GTK_STATE_ACTIVE; + shadow = GTK_SHADOW_IN; + } + else + { + state = GTK_STATE_NORMAL; + shadow = GTK_SHADOW_OUT; + } +} + +wxRect DrawCloseButton(wxDC& dc, + GtkWidget *widget, + int button_state, + wxRect const &in_rect, + int orientation, + GdkRectangle* clipRect) +{ + GtkStyle *style_button = gtk_widget_get_style(wxGTKPrivate::GetButtonWidget()); + int xthickness = style_button->xthickness; + int ythickness = style_button->ythickness; + + wxBitmap bmp; + bmp.SetPixbuf(gtk_widget_render_icon(widget, GTK_STOCK_CLOSE, GTK_ICON_SIZE_SMALL_TOOLBAR, "tab")); + + if(bmp.GetWidth() != s_CloseIconSize || bmp.GetHeight() != s_CloseIconSize) + { + wxImage img = bmp.ConvertToImage(); + img.Rescale(s_CloseIconSize, s_CloseIconSize); + bmp = img; + } + + int button_size = s_CloseIconSize + 2 * xthickness; + + wxRect out_rect; + + if (orientation == wxLEFT) + out_rect.x = in_rect.x - ythickness; + else + out_rect.x = in_rect.x + in_rect.width - button_size - ythickness; + + out_rect.y = in_rect.y + (in_rect.height - button_size) / 2; + out_rect.width = button_size; + out_rect.height = button_size; + + wxGTKDCImpl *impldc = (wxGTKDCImpl*) dc.GetImpl(); + GdkWindow* window = impldc->GetGDKWindow(); + + if (button_state == wxAUI_BUTTON_STATE_HOVER) + { + gtk_paint_box(style_button, window, + GTK_STATE_PRELIGHT, GTK_SHADOW_OUT, clipRect, widget, "button", + out_rect.x, out_rect.y, out_rect.width, out_rect.height); + } + else if (button_state == wxAUI_BUTTON_STATE_PRESSED) + { + gtk_paint_box(style_button, window, + GTK_STATE_ACTIVE, GTK_SHADOW_IN, clipRect, widget, "button", + out_rect.x, out_rect.y, out_rect.width, out_rect.height); + } + + + dc.DrawBitmap(bmp, out_rect.x + xthickness, out_rect.y + ythickness, true); + + return out_rect; +} + +void wxAuiGtkTabArt::DrawTab(wxDC& dc, wxWindow* wnd, const wxAuiNotebookPage& page, + const wxRect& in_rect, int close_button_state, wxRect* out_tab_rect, + wxRect* out_button_rect, int* x_extent) +{ + GtkWidget *widget = wnd->GetHandle(); + GtkStyle *style_notebook = gtk_widget_get_style(wxGTKPrivate::GetNotebookWidget()); + + wxRect const &window_rect = wnd->GetRect(); + + int focus_width = 0; + + gtk_widget_style_get(wxGTKPrivate::GetNotebookWidget(), + "focus-line-width", &focus_width, + NULL); + + int gap_x = 0, gap_width = 0; + int tab_pos; + if (m_flags &wxAUI_NB_BOTTOM) + tab_pos = wxAUI_NB_BOTTOM; + else //if (m_flags & wxAUI_NB_TOP) {} + tab_pos = wxAUI_NB_TOP; + + // TODO: else if (m_flags &wxAUI_NB_LEFT) {} + // TODO: else if (m_flags &wxAUI_NB_RIGHT) {} + + // figure out the size of the tab + wxSize tab_size = GetTabSize(dc, wnd, page.caption, page.bitmap, + page.active, close_button_state, x_extent); + + wxRect tab_rect = in_rect; + tab_rect.width = tab_size.x; + tab_rect.height = tab_size.y; + tab_rect.y += 2 * GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder; + + if (page.active) + tab_rect.height += 2 * GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder; + // if no bitmap is set, we need a tiny correction + if (! page.bitmap.IsOk()) + tab_rect.height += 1; + + int gap_height = 6 * GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder; + int gap_y = tab_rect.y - gap_height; + + switch (tab_pos) + { + case wxAUI_NB_TOP: + tab_rect.y -= 2 * GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder; + if (!page.active) + tab_rect.y += 2 * GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder; + gap_y = tab_rect.y + tab_rect.height; + // fall through + case wxAUI_NB_BOTTOM: + gap_x = tab_rect.x - GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_vborder / 2; + gap_width = tab_rect.width; + break; + } + tab_rect.y += GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder / 2; + gap_y += GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder / 2; + + int padding = focus_width + GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder; + + int clip_width = tab_rect.width; + if (tab_rect.x + tab_rect.width > in_rect.x + in_rect.width) + clip_width = (in_rect.x + in_rect.width) - tab_rect.x; + + dc.SetClippingRegion(tab_rect.x, tab_rect.y - GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_vborder, clip_width, tab_rect.height + GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_vborder); + + GdkRectangle area; + area.x = tab_rect.x - GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_vborder; + area.y = tab_rect.y - 2 * GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder; + area.width = clip_width + GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_vborder; + area.height = tab_rect.height + 2 * GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_hborder; + + wxGTKDCImpl *impldc = (wxGTKDCImpl*) dc.GetImpl(); + GdkWindow* window = impldc->GetGDKWindow(); + + if (tab_pos == wxAUI_NB_BOTTOM) + { + if (page.active) + { + gtk_paint_box_gap(style_notebook, window, GTK_STATE_NORMAL, GTK_SHADOW_OUT, + NULL, widget, + const_cast("notebook"), + window_rect.x, gap_y, + window_rect.width, gap_height, + GTK_POS_BOTTOM, gap_x , gap_width); + } + gtk_paint_extension(style_notebook, window, + page.active ? GTK_STATE_NORMAL : GTK_STATE_ACTIVE, GTK_SHADOW_OUT, + &area, widget, + const_cast("tab"), + tab_rect.x, tab_rect.y, + tab_rect.width, tab_rect.height, + GTK_POS_TOP); + } + else + { + if (page.active) + { + gtk_paint_box_gap(style_notebook, window, GTK_STATE_NORMAL, GTK_SHADOW_OUT, + NULL, widget, + const_cast("notebook"), + window_rect.x, gap_y, + window_rect.width, gap_height, + GTK_POS_TOP, gap_x , gap_width); + } + gtk_paint_extension(style_notebook, window, + page.active ? GTK_STATE_NORMAL : GTK_STATE_ACTIVE, GTK_SHADOW_OUT, + &area, widget, + const_cast("tab"), + tab_rect.x, tab_rect.y, + tab_rect.width, tab_rect.height, + GTK_POS_BOTTOM); + } + + wxCoord textX = tab_rect.x + padding + style_notebook->xthickness; + + int bitmap_offset = 0; + if (page.bitmap.IsOk()) + { + bitmap_offset = textX; + + // draw bitmap + int bitmapY = tab_rect.y +(tab_rect.height - page.bitmap.GetHeight()) / 2; + if(!page.active) + { + if (tab_pos == wxAUI_NB_TOP) + bitmapY += style_notebook->ythickness / 2; + else + bitmapY -= style_notebook->ythickness / 2; + } + dc.DrawBitmap(page.bitmap, + bitmap_offset, + bitmapY, + true); + + textX += page.bitmap.GetWidth() + padding; + } + + wxCoord textW, textH, textY; + + dc.SetFont(m_normalFont); + dc.GetTextExtent(page.caption, &textW, &textH); + textY = tab_rect.y + (tab_rect.height - textH) / 2; + if(!page.active) + { + if (tab_pos == wxAUI_NB_TOP) + textY += style_notebook->ythickness / 2; + else + textY -= style_notebook->ythickness / 2; + } + + // draw tab text + GdkColor text_colour = page.active ? style_notebook->fg[GTK_STATE_NORMAL] : style_notebook->fg[GTK_STATE_ACTIVE]; + dc.SetTextForeground(wxColor(text_colour)); + GdkRectangle focus_area; + + int padding_focus = padding - focus_width; + focus_area.x = tab_rect.x + padding_focus; + focus_area.y = textY - focus_width; + focus_area.width = tab_rect.width - 2 * padding_focus; + focus_area.height = textH + 2 * focus_width; + + if(page.active && (wnd->FindFocus() == wnd) && focus_area.x <= (area.x + area.width)) + { + // clipping seems not to work here, so we we have to recalc the focus-area manually + if((focus_area.x + focus_area.width) > (area.x + area.width)) + focus_area.width = area.x + area.width - focus_area.x + focus_width - GTK_NOTEBOOK (wxGTKPrivate::GetNotebookWidget())->tab_vborder; + gtk_paint_focus (style_notebook, window, + GTK_STATE_ACTIVE, NULL, widget, "tab", + focus_area.x, focus_area.y, focus_area.width, focus_area.height); + } + + dc.DrawText(page.caption, textX, textY); + + // draw close-button on tab (if enabled) + if (close_button_state != wxAUI_BUTTON_STATE_HIDDEN) + { + wxRect rect(tab_rect.x, tab_rect.y, tab_rect.width - style_notebook->xthickness, tab_rect.height); + if(!page.active) + { + if (tab_pos == wxAUI_NB_TOP) + rect.y += style_notebook->ythickness / 2; + else + rect.y -= style_notebook->ythickness / 2; + } + *out_button_rect = DrawCloseButton(dc, widget, close_button_state, rect, wxRIGHT, &area); + } + + tab_rect.width = std::min(tab_rect.width, clip_width); + *out_tab_rect = tab_rect; + + dc.DestroyClippingRegion(); +} + +wxRect DrawSimpleArrow(wxDC& dc, + GtkWidget *widget, + int button_state, + wxRect const &in_rect, + int orientation, + GtkArrowType arrow_type) +{ + int scroll_arrow_hlength, scroll_arrow_vlength; + gtk_widget_style_get(widget, + "scroll-arrow-hlength", &scroll_arrow_hlength, + "scroll-arrow-vlength", &scroll_arrow_vlength, + NULL); + + GtkStateType state; + GtkShadowType shadow; + ButtonStateAndShadow(button_state, state, shadow); + + wxRect out_rect; + + if (orientation == wxLEFT) + out_rect.x = in_rect.x; + else + out_rect.x = in_rect.x + in_rect.width - scroll_arrow_hlength; + out_rect.y = (in_rect.y + in_rect.height - 3 * gtk_widget_get_style(wxGTKPrivate::GetNotebookWidget())->ythickness - scroll_arrow_vlength) / 2; + out_rect.width = scroll_arrow_hlength; + out_rect.height = scroll_arrow_vlength; + + wxGTKDCImpl *impldc = (wxGTKDCImpl*) dc.GetImpl(); + GdkWindow* window = impldc->GetGDKWindow(); + gtk_paint_arrow (gtk_widget_get_style(wxGTKPrivate::GetButtonWidget()), window, state, shadow, NULL, widget, "notebook", + arrow_type, TRUE, out_rect.x, out_rect.y, out_rect.width, out_rect.height); + + return out_rect; +} + +void wxAuiGtkTabArt::DrawButton(wxDC& dc, wxWindow* wnd, + const wxRect& in_rect, + int bitmap_id, + int button_state, + int orientation, + wxRect* out_rect) +{ + GtkWidget *widget = wnd->GetHandle(); + wxRect rect = in_rect; + if (m_flags &wxAUI_NB_BOTTOM) + rect.y += 2 * gtk_widget_get_style(wxGTKPrivate::GetButtonWidget())->ythickness; + + switch (bitmap_id) + { + case wxAUI_BUTTON_CLOSE: + rect.y -= 2 * gtk_widget_get_style(wxGTKPrivate::GetButtonWidget())->ythickness; + rect = DrawCloseButton(dc, widget, button_state, rect, orientation, NULL); + break; + + case wxAUI_BUTTON_LEFT: + rect = DrawSimpleArrow(dc, widget, button_state, rect, orientation, GTK_ARROW_LEFT); + break; + + case wxAUI_BUTTON_RIGHT: + rect = DrawSimpleArrow(dc, widget, button_state, rect, orientation, GTK_ARROW_RIGHT); + break; + + case wxAUI_BUTTON_WINDOWLIST: + { + rect.height -= 4 * gtk_widget_get_style(wxGTKPrivate::GetButtonWidget())->ythickness; + rect.width = rect.height; + rect.x = in_rect.x + in_rect.width - rect.width; + + if (button_state == wxAUI_BUTTON_STATE_HOVER) + wxRendererNative::Get().DrawComboBoxDropButton(wnd, dc, rect, wxCONTROL_CURRENT); + else if (button_state == wxAUI_BUTTON_STATE_PRESSED) + wxRendererNative::Get().DrawComboBoxDropButton(wnd, dc, rect, wxCONTROL_PRESSED); + else + wxRendererNative::Get().DrawDropArrow(wnd, dc, rect); + } + break; + } + + *out_rect = rect; +} + + +int wxAuiGtkTabArt::GetBestTabCtrlSize(wxWindow* wnd, + const wxAuiNotebookPageArray& pages, + const wxSize& required_bmp_size) +{ + SetMeasuringFont(m_normalFont); + SetSelectedFont(m_normalFont); + int tab_height = 3 * gtk_widget_get_style(wxGTKPrivate::GetNotebookWidget())->ythickness + wxAuiGenericTabArt::GetBestTabCtrlSize(wnd, pages, required_bmp_size); + return tab_height; +} + +wxSize wxAuiGtkTabArt::GetTabSize(wxDC& dc, + wxWindow* wnd, + const wxString& caption, + const wxBitmap& bitmap, + bool active, + int close_button_state, + int* x_extent) +{ + wxSize s = wxAuiGenericTabArt::GetTabSize(dc, wnd, caption, bitmap, active, close_button_state, x_extent); + + int overlap = 0; + gtk_widget_style_get (wnd->GetHandle(), + "focus-line-width", &overlap, + NULL); + *x_extent -= overlap; + return s; +} +#endif // wxUSE_AUI