X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/39b44a399f090256ec313711e61567d2a05e3407..63c839616ab76e78d48018fb9fa5003653598c06:/src/gtk1/window.cpp diff --git a/src/gtk1/window.cpp b/src/gtk1/window.cpp index d468e1b8e8..13d9f19cd6 100644 --- a/src/gtk1/window.cpp +++ b/src/gtk1/window.cpp @@ -267,10 +267,6 @@ extern bool g_mainThreadLocked; // debug //----------------------------------------------------------------------------- -#ifndef __WXGTK20__ -#define DISABLE_STYLE_IF_BROKEN_THEME 0 -#endif - #ifdef __WXDEBUG__ #if wxUSE_THREADS @@ -1347,39 +1343,36 @@ static gint gtk_window_key_release_callback( GtkWidget *widget, // mouse event processing helpers // ---------------------------------------------------------------------------- -// init wxMouseEvent with the info from gdk_event -// -// NB: this has to be a macro as gdk_event type is different for different -// events we're used with -#define InitMouseEvent(/* wxWindowGTK * */ win, \ - /* wxMouseEvent& */ event, \ - /* GdkEventXXX * */ gdk_event) \ -{ \ - event.SetTimestamp( gdk_event->time ); \ - event.m_shiftDown = (gdk_event->state & GDK_SHIFT_MASK); \ - event.m_controlDown = (gdk_event->state & GDK_CONTROL_MASK); \ - event.m_altDown = (gdk_event->state & GDK_MOD1_MASK); \ - event.m_metaDown = (gdk_event->state & GDK_MOD2_MASK); \ - event.m_leftDown = (gdk_event->state & GDK_BUTTON1_MASK); \ - event.m_middleDown = (gdk_event->state & GDK_BUTTON2_MASK); \ - event.m_rightDown = (gdk_event->state & GDK_BUTTON3_MASK); \ - if (event.GetEventType()==wxEVT_MOUSEWHEEL) \ - { \ - event.m_linesPerAction = 3; \ - if (((GdkEventButton*)gdk_event)->button == 4) \ - event.m_wheelRotation = 120; \ - else if (((GdkEventButton*)gdk_event)->button == 5) \ - event.m_wheelRotation = -120; \ - } \ - \ - wxPoint pt = win->GetClientAreaOrigin(); \ - event.m_x = (wxCoord)gdk_event->x - pt.x; \ - event.m_y = (wxCoord)gdk_event->y - pt.y; \ - \ - event.SetEventObject( win ); \ - event.SetId( win->GetId() ); \ - event.SetTimestamp( gdk_event->time ); \ -} \ +// init wxMouseEvent with the info from GdkEventXXX struct +template void InitMouseEvent(wxWindowGTK *win, + wxMouseEvent& event, + T *gdk_event) +{ + event.SetTimestamp( gdk_event->time ); + event.m_shiftDown = (gdk_event->state & GDK_SHIFT_MASK); + event.m_controlDown = (gdk_event->state & GDK_CONTROL_MASK); + event.m_altDown = (gdk_event->state & GDK_MOD1_MASK); + event.m_metaDown = (gdk_event->state & GDK_MOD2_MASK); + event.m_leftDown = (gdk_event->state & GDK_BUTTON1_MASK); + event.m_middleDown = (gdk_event->state & GDK_BUTTON2_MASK); + event.m_rightDown = (gdk_event->state & GDK_BUTTON3_MASK); + if (event.GetEventType() == wxEVT_MOUSEWHEEL) + { + event.m_linesPerAction = 3; + if (((GdkEventButton*)gdk_event)->button == 4) + event.m_wheelRotation = 120; + else if (((GdkEventButton*)gdk_event)->button == 5) + event.m_wheelRotation = -120; + } + + wxPoint pt = win->GetClientAreaOrigin(); + event.m_x = (wxCoord)gdk_event->x - pt.x; + event.m_y = (wxCoord)gdk_event->y - pt.y; + + event.SetEventObject( win ); + event.SetId( win->GetId() ); + event.SetTimestamp( gdk_event->time ); +} static void AdjustEventButtonState(wxMouseEvent& event) { @@ -2569,7 +2562,6 @@ void wxWindowGTK::Init() m_oldClientHeight = 0; m_resizing = FALSE; - m_widgetStyle = (GtkStyle*) NULL; m_insertCallback = (wxInsertChildFunction) NULL; @@ -2763,16 +2755,6 @@ wxWindowGTK::~wxWindowGTK() gdk_ic_attr_destroy (m_icattr); #endif - if (m_widgetStyle) - { -#if DISABLE_STYLE_IF_BROKEN_THEME - // don't delete if it's a pixmap theme style - if (!m_widgetStyle->engine_data) - gtk_style_unref( m_widgetStyle ); -#endif - m_widgetStyle = (GtkStyle*) NULL; - } - if (m_wxwindow) { gtk_widget_destroy( m_wxwindow ); @@ -3822,11 +3804,9 @@ void wxWindowGTK::GtkSendPaintEvents() // Clip to paint region in wxClientDC m_clipPaintRegion = TRUE; -#ifndef __WXGTK20__ // widget to draw on GtkPizza *pizza = GTK_PIZZA (m_wxwindow); - // later for GTK 2.0, too. if (GetThemeEnabled()) { // find ancestor from which to steal background @@ -3847,7 +3827,7 @@ void wxWindowGTK::GtkSendPaintEvents() gtk_paint_flat_box( parent->m_widget->style, pizza->bin_window, - GTK_STATE_NORMAL, + (GtkStateType)GTK_WIDGET_STATE(m_wxwindow), GTK_SHADOW_NONE, &rect, parent->m_widget, @@ -3858,7 +3838,6 @@ void wxWindowGTK::GtkSendPaintEvents() } } else -#endif #ifdef __WXGTK20__ { @@ -4103,131 +4082,69 @@ PangoContext *wxWindowGTK::GtkGetPangoX11Context() return m_x11Context; } #endif - -GtkStyle *wxWindowGTK::GetWidgetStyle() -{ - if (m_widgetStyle) - { - GtkStyle *remake = gtk_style_copy( m_widgetStyle ); - - // FIXME: no more klass in 2.0 -#ifndef __WXGTK20__ - remake->klass = m_widgetStyle->klass; -#endif - - gtk_style_unref( m_widgetStyle ); - m_widgetStyle = remake; - } - else - { - GtkStyle *def = gtk_rc_get_style( m_widget ); - - if (!def) - def = gtk_widget_get_default_style(); - - m_widgetStyle = gtk_style_copy( def ); - - // FIXME: no more klass in 2.0 -#ifndef __WXGTK20__ - m_widgetStyle->klass = def->klass; -#endif - } - - return m_widgetStyle; -} - -void wxWindowGTK::SetWidgetStyle() + +GtkRcStyle *wxWindowGTK::CreateWidgetStyle() { -#if DISABLE_STYLE_IF_BROKEN_THEME - if (m_widget->style->engine_data) + // do we need to apply any changes at all? + if ( !m_hasFont && !m_hasFgCol && + (!m_hasBgCol || !m_backgroundColour.Ok()) ) { - static bool s_warningPrinted = FALSE; - if (!s_warningPrinted) - { - printf( "wxWidgets warning: Widget styles disabled due to buggy GTK theme.\n" ); - s_warningPrinted = TRUE; - } - m_widgetStyle = m_widget->style; - return; + return NULL; } -#endif - GtkStyle *style = GetWidgetStyle(); + GtkRcStyle *style = gtk_rc_style_new(); if ( m_hasFont ) { #ifdef __WXGTK20__ - pango_font_description_free( style->font_desc ); - style->font_desc = pango_font_description_copy( m_font.GetNativeFontInfo()->description ); + style->font_desc = + pango_font_description_copy( m_font.GetNativeFontInfo()->description ); #else - gdk_font_unref( style->font ); - style->font = gdk_font_ref( m_font.GetInternalFont( 1.0 ) ); + wxString xfontname = m_font.GetNativeFontInfo()->GetXFontName(); + style->fontset_name = g_strdup(xfontname.c_str()); #endif } if ( m_hasFgCol ) { m_foregroundColour.CalcPixel( gtk_widget_get_colormap( m_widget ) ); - if (m_foregroundColour != wxSystemSettings::GetColour(wxSYS_COLOUR_BTNTEXT)) - { - style->fg[GTK_STATE_NORMAL] = *m_foregroundColour.GetColor(); - style->fg[GTK_STATE_PRELIGHT] = *m_foregroundColour.GetColor(); - style->fg[GTK_STATE_ACTIVE] = *m_foregroundColour.GetColor(); - } - else - { - // Try to restore the gtk default style. This is still a little - // oversimplified for what is probably really needed here for controls - // other than buttons, but is better than not being able to (re)set a - // control's foreground colour to *wxBLACK -- RL - GtkStyle *def = gtk_rc_get_style( m_widget ); - - if (!def) - def = gtk_widget_get_default_style(); - - style->fg[GTK_STATE_NORMAL] = def->fg[GTK_STATE_NORMAL]; - style->fg[GTK_STATE_PRELIGHT] = def->fg[GTK_STATE_PRELIGHT]; - style->fg[GTK_STATE_ACTIVE] = def->fg[GTK_STATE_ACTIVE]; - } + + style->fg[GTK_STATE_NORMAL] = *m_foregroundColour.GetColor(); + style->color_flags[GTK_STATE_NORMAL] = GTK_RC_FG; + + style->fg[GTK_STATE_PRELIGHT] = *m_foregroundColour.GetColor(); + style->color_flags[GTK_STATE_PRELIGHT] = GTK_RC_FG; + + style->fg[GTK_STATE_ACTIVE] = *m_foregroundColour.GetColor(); + style->color_flags[GTK_STATE_ACTIVE] = GTK_RC_FG; } if ( m_hasBgCol && m_backgroundColour.Ok() ) { m_backgroundColour.CalcPixel( gtk_widget_get_colormap( m_widget ) ); - if (m_backgroundColour != wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE)) - { - style->bg[GTK_STATE_NORMAL] = *m_backgroundColour.GetColor(); - style->base[GTK_STATE_NORMAL] = *m_backgroundColour.GetColor(); - style->bg[GTK_STATE_PRELIGHT] = *m_backgroundColour.GetColor(); - style->base[GTK_STATE_PRELIGHT] = *m_backgroundColour.GetColor(); - style->bg[GTK_STATE_ACTIVE] = *m_backgroundColour.GetColor(); - style->base[GTK_STATE_ACTIVE] = *m_backgroundColour.GetColor(); - style->bg[GTK_STATE_INSENSITIVE] = *m_backgroundColour.GetColor(); - style->base[GTK_STATE_INSENSITIVE] = *m_backgroundColour.GetColor(); - } - else - { - // Try to restore the gtk default style. This is still a little - // oversimplified for what is probably really needed here for controls - // other than buttons, but is better than not being able to (re)set a - // control's background colour to default grey and means resetting a - // button to wxSYS_COLOUR_BTNFACE will restore its usual highlighting - // behavior -- RL - GtkStyle *def = gtk_rc_get_style( m_widget ); - - if (!def) - def = gtk_widget_get_default_style(); - - style->bg[GTK_STATE_NORMAL] = def->bg[GTK_STATE_NORMAL]; - style->base[GTK_STATE_NORMAL] = def->base[GTK_STATE_NORMAL]; - style->bg[GTK_STATE_PRELIGHT] = def->bg[GTK_STATE_PRELIGHT]; - style->base[GTK_STATE_PRELIGHT] = def->base[GTK_STATE_PRELIGHT]; - style->bg[GTK_STATE_ACTIVE] = def->bg[GTK_STATE_ACTIVE]; - style->base[GTK_STATE_ACTIVE] = def->base[GTK_STATE_ACTIVE]; - style->bg[GTK_STATE_INSENSITIVE] = def->bg[GTK_STATE_INSENSITIVE]; - style->base[GTK_STATE_INSENSITIVE] = def->base[GTK_STATE_INSENSITIVE]; - } + + style->bg[GTK_STATE_NORMAL] = *m_backgroundColour.GetColor(); + style->base[GTK_STATE_NORMAL] = *m_backgroundColour.GetColor(); + style->color_flags[GTK_STATE_NORMAL] = (GtkRcFlags) + (style->color_flags[GTK_STATE_NORMAL] | GTK_RC_BG | GTK_RC_BASE); + + style->bg[GTK_STATE_PRELIGHT] = *m_backgroundColour.GetColor(); + style->base[GTK_STATE_PRELIGHT] = *m_backgroundColour.GetColor(); + style->color_flags[GTK_STATE_PRELIGHT] = (GtkRcFlags) + (style->color_flags[GTK_STATE_PRELIGHT] | GTK_RC_BG | GTK_RC_BASE); + + style->bg[GTK_STATE_ACTIVE] = *m_backgroundColour.GetColor(); + style->base[GTK_STATE_ACTIVE] = *m_backgroundColour.GetColor(); + style->color_flags[GTK_STATE_ACTIVE] = (GtkRcFlags) + (style->color_flags[GTK_STATE_ACTIVE] | GTK_RC_BG | GTK_RC_BASE); + + style->bg[GTK_STATE_INSENSITIVE] = *m_backgroundColour.GetColor(); + style->base[GTK_STATE_INSENSITIVE] = *m_backgroundColour.GetColor(); + style->color_flags[GTK_STATE_INSENSITIVE] = (GtkRcFlags) + (style->color_flags[GTK_STATE_INSENSITIVE] | GTK_RC_BG | GTK_RC_BASE); } + + return style; } void wxWindowGTK::ApplyWidgetStyle() @@ -4285,30 +4202,44 @@ extern "C" void wxPopupMenuPositionCallback( GtkMenu *menu, bool wxWindowGTK::DoPopupMenu( wxMenu *menu, int x, int y ) { - wxCHECK_MSG( m_widget != NULL, FALSE, wxT("invalid window") ); + wxCHECK_MSG( m_widget != NULL, false, wxT("invalid window") ); - wxCHECK_MSG( menu != NULL, FALSE, wxT("invalid popup-menu") ); + wxCHECK_MSG( menu != NULL, false, wxT("invalid popup-menu") ); SetInvokingWindow( menu, this ); menu->UpdateUI(); - wxPoint pos(ClientToScreen(wxPoint(x, y))); - - bool is_waiting = TRUE; + bool is_waiting = true; gtk_signal_connect( GTK_OBJECT(menu->m_menu), "hide", GTK_SIGNAL_FUNC(gtk_pop_hide_callback), (gpointer)&is_waiting ); + wxPoint pos; + gpointer userdata; + GtkMenuPositionFunc posfunc; + if ( x == -1 && y == -1 ) + { + // use GTK's default positioning algorithm + userdata = NULL; + posfunc = NULL; + } + else + { + pos = ClientToScreen(wxPoint(x, y)); + userdata = &pos; + posfunc = wxPopupMenuPositionCallback; + } + gtk_menu_popup( GTK_MENU(menu->m_menu), (GtkWidget *) NULL, // parent menu shell (GtkWidget *) NULL, // parent menu item - wxPopupMenuPositionCallback, // function to position it - &pos, // client data - 0 /* FIXME! */, // button used to activate it + posfunc, // function to position it + userdata, // client data + 0, // button used to activate it #ifdef __WXGTK20__ gtk_get_current_event_time() #else @@ -4321,7 +4252,7 @@ bool wxWindowGTK::DoPopupMenu( wxMenu *menu, int x, int y ) gtk_main_iteration(); } - return TRUE; + return true; } #endif // wxUSE_MENUS_NATIVE