]> git.saurik.com Git - wxWidgets.git/blobdiff - src/gtk/menu.cpp
compilation fix for yet another broken version of mingw (ENSESSION_LOGOFF not defined)
[wxWidgets.git] / src / gtk / menu.cpp
index 88eb8cf728ff54b81fdd36b7fc54a5c16fe82885..dea54b9e727bbbea0e9c66aca0501ee1f6aa67a5 100644 (file)
@@ -701,6 +701,28 @@ static void gtk_menu_clicked_callback( GtkWidget *widget, wxMenu *menu )
     if (!menu->IsEnabled(id))
         return;
 
+    wxMenuItem* item = menu->FindChildItem( id );
+    wxCHECK_RET( item, wxT("error in menu item callback") );
+
+    if (item->IsCheckable())
+    {
+        bool isReallyChecked = item->IsChecked(),
+            isInternallyChecked = item->wxMenuItemBase::IsChecked();
+
+        // ensure that the internal state is always consistent with what is
+        // shown on the screen
+        item->wxMenuItemBase::Check(isReallyChecked);
+
+        // we must not report the events for the radio button going up nor the
+        // events resulting from the calls to wxMenuItem::Check()
+        if ( (item->GetKind() == wxITEM_RADIO && !isReallyChecked) ||
+             (isInternallyChecked == isReallyChecked) )
+        {
+            return;
+        }
+    }
+
+
     // Is this menu on a menubar?  (possibly nested)
     wxFrame* frame = NULL;
     wxMenu*  pm = menu;
@@ -708,41 +730,24 @@ static void gtk_menu_clicked_callback( GtkWidget *widget, wxMenu *menu )
     {
         if ( pm->IsAttached() )
             frame = pm->GetMenuBar()->GetFrame();
-        else
-            pm = pm->GetParent();
+        pm = pm->GetParent();
     }
 
-    // If it is then let the frame send the event
     if (frame)
     {
-        frame->ProcessCommand(id);
+        // If it is attached then let the frame send the event.
+        // Don't call frame->ProcessCommand(id) because it toggles
+        // checkable items and we've already done that above.
+        wxCommandEvent commandEvent(wxEVT_COMMAND_MENU_SELECTED, id);
+        commandEvent.SetEventObject(frame);
+        if (item->IsCheckable())
+            commandEvent.SetInt(item->IsChecked());
+
+        frame->GetEventHandler()->ProcessEvent(commandEvent);
     }
-    // otherwise let the menu have it
     else
     {
-        wxMenuItem* item = menu->FindChildItem( id );
-        wxCHECK_RET( item, wxT("error in menu item callback") );
-
-        if (item->IsCheckable())
-        {
-            bool isReallyChecked = item->IsChecked(),
-                isInternallyChecked = item->wxMenuItemBase::IsChecked();
-
-            // ensure that the internal state is always consistent with what is
-            // shown on the screen
-            item->wxMenuItemBase::Check(isReallyChecked);
-
-            // we must not report the events for the radio button going up nor the
-            // events resulting from the calls to wxMenuItem::Check()
-            if ( (item->GetKind() == wxITEM_RADIO && !isReallyChecked) ||
-                 (isInternallyChecked == isReallyChecked) )
-            {
-                return;
-            }
-
-            // the user pressed on the menu item: report the event below
-        }
-
+        // otherwise let the menu have it
         menu->SendEvent(id, item->IsCheckable() ? item->IsChecked() : -1);
     }
 }
@@ -1119,7 +1124,8 @@ wxMenu::~wxMenu()
 {
    m_items.Clear();
 
-   gtk_widget_destroy( m_menu );
+   if ( GTK_IS_WIDGET( m_menu ))
+       gtk_widget_destroy( m_menu );
 
    gtk_object_unref( GTK_OBJECT(m_factory) );
 }
@@ -1192,16 +1198,36 @@ bool wxMenu::GtkAppend(wxMenuItem *mitem)
         GtkWidget *label = gtk_accel_label_new ( wxGTK_CONV( text ) );
         gtk_misc_set_alignment (GTK_MISC (label), 0.0, 0.5);
         gtk_container_add (GTK_CONTAINER (menuItem), label);
-        guint accel_key = gtk_label_parse_uline (GTK_LABEL(label), wxGTK_CONV( text ) );
         gtk_accel_label_set_accel_widget (GTK_ACCEL_LABEL (label), menuItem);
+        guint accel_key;
+        GdkModifierType accel_mods;
+
+        // accelerator for the item, as specified by its label
+        // (ex. Ctrl+O for open)
+        gtk_accelerator_parse(GetHotKey(*mitem).c_str(),
+                              &accel_key, &accel_mods);
         if (accel_key != GDK_VoidSymbol)
         {
             gtk_widget_add_accelerator (menuItem,
                                         "activate_item",
-                                        gtk_menu_ensure_uline_accel_group (GTK_MENU (m_menu)),
+                                        gtk_menu_get_accel_group(
+                                            GTK_MENU(m_menu)),
+                                        accel_key, accel_mods,
+                                        GTK_ACCEL_VISIBLE);
+        }
+
+        // accelerator for the underlined char (ex ALT+F for the File menu)
+        accel_key = gtk_label_parse_uline (GTK_LABEL(label), wxGTK_CONV( text ) );
+        if (accel_key != GDK_VoidSymbol)
+        {
+            gtk_widget_add_accelerator (menuItem,
+                                        "activate_item",
+                                        gtk_menu_ensure_uline_accel_group (
+                                            GTK_MENU (m_menu)),
                                         accel_key, 0,
                                         GTK_ACCEL_LOCKED);
         }
+
         gtk_widget_show (label);
 
         mitem->SetLabelWidget(label);
@@ -1215,6 +1241,7 @@ bool wxMenu::GtkAppend(wxMenuItem *mitem)
                             (gpointer)this );
 
         gtk_menu_append( GTK_MENU(m_menu), menuItem );
+
         gtk_widget_show( menuItem );
 
         appended = TRUE; // We've done this, don't do it again