]> git.saurik.com Git - wxWidgets.git/blobdiff - src/motif/window.cpp
Added script to help make wxMotif via configure; nativdlg sample works again;
[wxWidgets.git] / src / motif / window.cpp
index 9fc441729c430a27160c2d71744321c949851a75..9be496a55ae1bfe622f7ccc05b7ffa2d189a1158 100644 (file)
@@ -52,7 +52,7 @@ void wxCanvasRepaintProc (Widget, XtPointer, XmDrawingAreaCallbackStruct * cbs);
 void wxCanvasInputEvent (Widget drawingArea, XtPointer data, XmDrawingAreaCallbackStruct * cbs);
 void wxCanvasMotionEvent (Widget, XButtonEvent * event);
 void wxCanvasEnterLeave (Widget drawingArea, XtPointer clientData, XCrossingEvent * event);
-void wxScrollBarCallback(Widget widget, XtPointer clientData,
+static void wxScrollBarCallback(Widget widget, XtPointer clientData,
                         XmScaleCallbackStruct *cbs);
 void wxPanelItemEventHandler (Widget    wid,
                               XtPointer client_data,
@@ -135,7 +135,6 @@ wxWindow::wxWindow()
     m_canAddEventHandler = FALSE;
     m_scrollPosX = 0;
     m_scrollPosY = 0;
-    m_paintRegion = (WXRegion) 0;
 }
 
 // Destructor
@@ -143,10 +142,6 @@ wxWindow::~wxWindow()
 {
     //// Motif-specific
 
-    if (m_paintRegion)
-        XDestroyRegion ((Region) m_paintRegion);
-    m_paintRegion = (WXRegion) 0;
-
     if (GetMainWidget())
         DetachWidget(GetMainWidget()); // Removes event handlers
 
@@ -243,6 +238,8 @@ wxWindow::~wxWindow()
 
     if ( m_windowValidator ) delete m_windowValidator;
     if (m_clientObject) delete m_clientObject;
+
+    ClearUpdateRects();
 }
 
 // Destroy the window (delayed, if a managed window)
@@ -309,7 +306,6 @@ bool wxWindow::Create(wxWindow *parent, wxWindowID id,
     m_pixmapOffsetY = 0;
     m_scrollPosX = 0;
     m_scrollPosY = 0;
-    m_paintRegion = (WXRegion) 0;
 
     if (!parent)
         return FALSE;
@@ -482,6 +478,7 @@ bool wxWindow::Create(wxWindow *parent, wxWindowID id,
   // Without this, the cursor may not be restored properly
   // (e.g. in splitter sample).
   SetCursor(*wxSTANDARD_CURSOR);
+  SetFont(wxSystemSettings::GetSystemFont(wxSYS_DEFAULT_GUI_FONT));
   SetSize(pos.x, pos.y, size.x, size.y);
 
   return TRUE;
@@ -665,6 +662,27 @@ void wxWindow::GetClientSize(int *x, int *y) const
 
 void wxWindow::SetSize(int x, int y, int width, int height, int sizeFlags)
 {
+  // A bit of optimization to help sort out the flickers.
+  int oldX, oldY, oldW, oldH;
+  GetSize(& oldW, & oldH);
+  GetPosition(& oldX, & oldY);
+
+  bool useOldPos = FALSE;
+  bool useOldSize = FALSE;
+
+  if ((x == -1) && (x == -1) && ((sizeFlags & wxSIZE_ALLOW_MINUS_ONE) == 0))
+    useOldPos = TRUE;
+  else if (x == oldX && y == oldY)
+    useOldPos = TRUE;
+
+  if ((width == -1) && (height == -1))
+    useOldSize = TRUE;
+  else if (width == oldW && height == oldH)
+    useOldSize = TRUE;
+
+  if (useOldPos && useOldSize)
+    return;
+
   if (m_drawingArea)
   {
     CanvasSetSize(x, y, width, height, sizeFlags);
@@ -681,22 +699,32 @@ void wxWindow::SetSize(int x, int y, int width, int height, int sizeFlags)
   int xx = x; int yy = y;
   AdjustForParentClientOrigin(xx, yy, sizeFlags);
 
-  if (x > -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
-    XtVaSetValues(widget, XmNx, xx, NULL);
-  if (y > -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
-    XtVaSetValues(widget, XmNy, yy, NULL);
-  if (width > -1)
-    XtVaSetValues(widget, XmNwidth, width, NULL);
-  if (height > -1)
-    XtVaSetValues(widget, XmNheight, height, NULL);
+  if (!useOldPos)
+  {
+    if (x > -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
+      XtVaSetValues(widget, XmNx, xx, NULL);
+    if (y > -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
+      XtVaSetValues(widget, XmNy, yy, NULL);
+  }
+  if (!useOldSize)
+  {
+    if (width > -1)
+      XtVaSetValues(widget, XmNwidth, width, NULL);
+    if (height > -1)
+      XtVaSetValues(widget, XmNheight, height, NULL);
+  }
 
   if (managed)
     XtManageChild(widget);
 
+  // How about this bit. Maybe we don't need to generate size events
+  // all the time -- they'll be generated when the window is sized anyway.
+  /*
   wxSizeEvent sizeEvent(wxSize(width, height), GetId());
   sizeEvent.SetEventObject(this);
   
   GetEventHandler()->ProcessEvent(sizeEvent);
+  */
 }
 
 void wxWindow::SetClientSize(int width, int height)
@@ -750,7 +778,11 @@ bool wxWindow::Show(bool show)
        }
        else
        {
-           XtMapWidget((Widget) GetTopWidget());
+           WXWidget topWidget = GetTopWidget();
+           if (GetTopWidget())
+             XtMapWidget((Widget) GetTopWidget());
+           else if (GetMainWidget())
+             XtMapWidget((Widget) GetMainWidget());
        }
     }
     else
@@ -763,7 +795,10 @@ bool wxWindow::Show(bool show)
        }
        else
        {
-           XtUnmapWidget((Widget) GetTopWidget());
+           if (GetTopWidget())
+             XtUnmapWidget((Widget) GetTopWidget());
+           else if (GetMainWidget())
+             XtUnmapWidget((Widget) GetMainWidget());
        }
     }
 
@@ -861,7 +896,7 @@ void wxWindow::GetTextExtent(const wxString& string, int *x, int *y,
     *externalLeading = 0;
 }
 
-void wxWindow::Refresh(bool eraseBack, const wxRectangle *rect)
+void wxWindow::Refresh(bool eraseBack, const wxRect *rect)
 {
     Display *display = XtDisplay((Widget) GetMainWidget());
     Window thisWindow = XtWindow((Widget) GetMainWidget());
@@ -895,7 +930,10 @@ void wxWindow::Refresh(bool eraseBack, const wxRectangle *rect)
         wxClientDC dc(this);
         wxBrush backgroundBrush(GetBackgroundColour(), wxSOLID);
         dc.SetBackground(backgroundBrush);
-        dc.Clear();
+        if (rect)
+          dc.Clear(*rect);
+        else
+          dc.Clear();
     }
 
     XSendEvent(display, thisWindow, False, ExposureMask, (XEvent *)&dummyEvent);
@@ -904,7 +942,7 @@ void wxWindow::Refresh(bool eraseBack, const wxRectangle *rect)
 // Responds to colour changes: passes event on to children.
 void wxWindow::OnSysColourChanged(wxSysColourChangedEvent& event)
 {
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while ( node )
     {
         // Only propagate to non-top-level windows
@@ -1138,7 +1176,7 @@ void wxWindow::SetScrollbar(int orient, int pos, int thumbVisible,
 }
 
 // Does a physical scroll
-void wxWindow::ScrollWindow(int dx, int dy, const wxRectangle *rect)
+void wxWindow::ScrollWindow(int dx, int dy, const wxRect *rect)
 {
 //  cerr << "Scrolling. delta = " << dx << ", " << dy << endl;
   int x, y, w, h;
@@ -1286,6 +1324,16 @@ void wxWindow::ScrollWindow(int dx, int dy, const wxRectangle *rect)
     node = node->Next();
 
   }
+
+  // Delete the update rects
+  node = updateRects.First();
+  while (node)
+  {
+    wxRect* rect = (wxRect*) node->Data();
+    delete rect;
+    node = node->Next();
+  }
+
 }
 
 void wxWindow::OnChar(wxKeyEvent& event)
@@ -1323,7 +1371,7 @@ bool wxWindow::IsEnabled() const
 // it's an application error (pops up a dialog)
 bool wxWindow::TransferDataToWindow()
 {
-       wxNode *node = GetChildren()->First();
+       wxNode *node = GetChildren().First();
        while ( node )
        {
                wxWindow *child = (wxWindow *)node->Data();
@@ -1343,7 +1391,7 @@ bool wxWindow::TransferDataToWindow()
 // validation failed: don't quit
 bool wxWindow::TransferDataFromWindow()
 {
-       wxNode *node = GetChildren()->First();
+       wxNode *node = GetChildren().First();
        while ( node )
        {
                wxWindow *child = (wxWindow *)node->Data();
@@ -1359,7 +1407,7 @@ bool wxWindow::TransferDataFromWindow()
 
 bool wxWindow::Validate()
 {
-       wxNode *node = GetChildren()->First();
+       wxNode *node = GetChildren().First();
        while ( node )
        {
                wxWindow *child = (wxWindow *)node->Data();
@@ -1382,22 +1430,26 @@ wxWindow *wxWindow::FindFocus()
 
 void wxWindow::AddChild(wxWindow *child)
 {
-    GetChildren()->Append(child);
+    GetChildren().Append(child);
     child->m_windowParent = this;
 }
 
 void wxWindow::RemoveChild(wxWindow *child)
 {
-    if (GetChildren())
-        GetChildren()->DeleteObject(child);
+    GetChildren().DeleteObject(child);
     child->m_windowParent = NULL;
 }
 
+// Reparents this window to have the new parent.
+bool wxWindow::Reparent(wxWindow* WXUNUSED(parent))
+{
+    // For now, we indicate that this isn't implemented.
+    return FALSE;
+}
+
 void wxWindow::DestroyChildren()
 {
-  if (GetChildren())
-  {
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while (node)
     {
       wxNode* next = node->Next();
@@ -1405,19 +1457,18 @@ void wxWindow::DestroyChildren()
       delete child;
       node = next;
     }
-    GetChildren()->Clear();
+    GetChildren().Clear();
 #if 0
     wxNode *node;
-    while ((node = GetChildren()->First()) != (wxNode *)NULL) {
+    while ((node = GetChildren().First()) != (wxNode *)NULL) {
       wxWindow *child;
       if ((child = (wxWindow *)node->Data()) != (wxWindow *)NULL) {
         delete child;
-               if ( GetChildren()->Member(child) )
+               if ( GetChildren().Member(child) )
                        delete node;
       }
     } /* while */
 #endif
-  }
 }
 
 void wxWindow::MakeModal(bool modal)
@@ -1632,7 +1683,7 @@ bool wxWindow::DoPhase(int phase)
   {
     noChanges = 0;
     noFailures = 0;
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while (node)
     {
       wxWindow *child = (wxWindow *)node->Data();
@@ -1677,7 +1728,7 @@ void wxWindow::ResetConstraints()
     constr->centreX.SetDone(FALSE);
     constr->centreY.SetDone(FALSE);
   }
-  wxNode *node = GetChildren()->First();
+  wxNode *node = GetChildren().First();
   while (node)
   {
     wxWindow *win = (wxWindow *)node->Data();
@@ -1736,7 +1787,7 @@ void wxWindow::SetConstraintSizes(bool recurse)
 
   if (recurse)
   {
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while (node)
     {
       wxWindow *win = (wxWindow *)node->Data();
@@ -1873,9 +1924,7 @@ bool wxWindow::Close(bool force)
 wxObject* wxWindow::GetChild(int number) const
 {
   // Return a pointer to the Nth object in the window
-  if (!GetChildren())
-    return(NULL) ;
-  wxNode *node = GetChildren()->First();
+  wxNode *node = GetChildren().First();
   int n = number;
   while (node && n--)
     node = node->Next() ;
@@ -1906,7 +1955,7 @@ void wxWindow::Fit()
 {
        int maxX = 0;
        int maxY = 0;
-       wxNode *node = GetChildren()->First();
+       wxNode *node = GetChildren().First();
        while ( node )
        {
                wxWindow *win = (wxWindow *)node->Data();
@@ -1960,7 +2009,7 @@ wxWindow *wxWindow::FindWindow(long id)
        if ( GetId() == id)
                return this;
 
-       wxNode *node = GetChildren()->First();
+       wxNode *node = GetChildren().First();
        while ( node )
        {
                wxWindow *child = (wxWindow *)node->Data();
@@ -1977,7 +2026,7 @@ wxWindow *wxWindow::FindWindow(const wxString& name)
        if ( GetName() == name)
                return this;
 
-       wxNode *node = GetChildren()->First();
+       wxNode *node = GetChildren().First();
        while ( node )
        {
                wxWindow *child = (wxWindow *)node->Data();
@@ -2016,9 +2065,9 @@ bool wxWindow::AcceptsFocus() const
 }
 
 // Update region access
-wxRegion wxWindow::GetUpdateRegion() const
+wxRegion& wxWindow::GetUpdateRegion() const
 {
-    return m_updateRegion;
+    return (wxRegion&) m_updateRegion;
 }
 
 bool wxWindow::IsExposed(int x, int y, int w, int h) const
@@ -2135,75 +2184,41 @@ void wxCanvasRepaintProc (Widget drawingArea, XtPointer clientData,
  XmDrawingAreaCallbackStruct * cbs)
 {
     if (!wxWidgetHashTable->Get ((long) (Widget) drawingArea))
-       return;
+           return;
 
     XEvent * event = cbs->event;
-    wxWindow * canvas = (wxWindow *) clientData;
-    Display * display = (Display *) canvas->GetXDisplay();
-    //    GC gc = (GC) canvas->GetDC()->gc;
+    wxWindow * win = (wxWindow *) clientData;
+    Display * display = (Display *) win->GetXDisplay();
 
     switch (event->type)
     {
-      case Expose:
-      {
-       /* TODO
-        wxCanvasDC* canvasDC = canvas->GetDC();
-        if (canvasDC)
-       {
-          if (canvasDC->onpaint_reg)
-            XDestroyRegion(canvasDC->onpaint_reg);
-          canvasDC->onpaint_reg = XCreateRegion();
-          
-       }
-       */
-
-       int n = canvas->m_updateRects.Number();
-        XRectangle* xrects = new XRectangle[n];
-        int i;
-       for (i = 0; i < canvas->m_updateRects.Number(); i++)
-       {
-         wxRect* rect = (wxRect*) canvas->m_updateRects.Nth(i)->Data();
-         xrects[i].x = rect->x;
-          xrects[i].y = rect->y;
-          xrects[i].width = rect->width;
-          xrects[i].height = rect->height;
-         /* TODO (?) Actually ignore it I think.
-          if (canvasDC)
-            XUnionRectWithRegion(&(xrects[i]), canvasDC->onpaint_reg,
-              canvasDC->onpaint_reg);
-      */
-       }
-       /* TODO must clip the area being repainted. So we need a gc.
-         * Alternatively, wxPaintDC must do the clipping
-         * when it's created.
-        XSetClipRectangles(display, gc, 0, 0, xrects, n, Unsorted);
-       */
-
-        canvas->DoPaint() ; // xrects, n);
-        delete[] xrects;
+        case Expose:
+        {
+            wxRect* rect = new wxRect(event->xexpose.x, event->xexpose.y,
+                                       event->xexpose.width, event->xexpose.height);
+           /*
+            cout << "Expose proc. wxRect: " << rect->x << ", " << rect->y << ", ";
+            cout << rect->width << ", " << rect->height << "\n\n";
+           */
 
-        canvas->m_updateRects.Clear();
+            win->m_updateRects.Append((wxObject*) rect);
 
-       /*
-        if (canvasDC)
-       {
-          XDestroyRegion(canvasDC->onpaint_reg);
-          canvasDC->onpaint_reg = NULL;
-       }
-
-       XGCValues gc_val;
-       gc_val.clip_mask = None;
-       XChangeGC(display, gc, GCClipMask, &gc_val);
-       */
+            if (event -> xexpose.count == 0)
+            {
+                wxPaintEvent event(win->GetId());
+                event.SetEventObject(win);
+                win->GetEventHandler()->ProcessEvent(event);
 
-       break;
-    }
-    default:
-    {
-       cout << "\n\nNew Event ! is = " << event -> type << "\n";
-       break;
+                win->ClearUpdateRects();
+            }
+            break;
+        }
+        default:
+        {
+               cout << "\n\nNew Event ! is = " << event -> type << "\n";
+               break;
+        }
     }
-  }
 }
 
 // Unable to deal with Enter/Leave without a separate EventHandler (Motif 1.1.4)
@@ -2255,6 +2270,30 @@ void wxCanvasInputEvent (Widget drawingArea, XtPointer data, XmDrawingAreaCallba
 
   local_event = *(cbs->event); // We must keep a copy!
 
+  /*
+  switch (local_event.xany.type)
+    {
+    case EnterNotify:
+      cout << "EnterNotify\n";
+      break;
+    case LeaveNotify:
+      cout << "LeaveNotify\n";
+      break;
+    case ButtonPress:
+      cout << "ButtonPress\n";
+      break;
+    case ButtonRelease:
+      cout << "ButtonRelease\n";
+      break;
+    case MotionNotify:
+      cout << "MotionNotify\n";
+      break;
+    default:
+      cout << "Something else\n";
+      break;
+  }
+  */
+
   switch (local_event.xany.type)
     {
     case EnterNotify:
@@ -2511,6 +2550,27 @@ void wxWindow::DoPaint()
 // SetSize, but as per old wxCanvas (with drawing widget etc.)
 void wxWindow::CanvasSetSize (int x, int y, int w, int h, int sizeFlags)
 {
+  // A bit of optimization to help sort out the flickers.
+  int oldX, oldY, oldW, oldH;
+  GetSize(& oldW, & oldH);
+  GetPosition(& oldX, & oldY);
+
+  bool useOldPos = FALSE;
+  bool useOldSize = FALSE;
+
+  if ((x == -1) && (x == -1) && ((sizeFlags & wxSIZE_ALLOW_MINUS_ONE) == 0))
+    useOldPos = TRUE;
+  else if (x == oldX && y == oldY)
+    useOldPos = TRUE;
+
+  if ((w == -1) && (h == -1))
+    useOldSize = TRUE;
+  else if (w == oldW && h == oldH)
+    useOldSize = TRUE;
+
+  if (useOldPos && useOldSize)
+    return;
+
   Widget drawingArea = (Widget) m_drawingArea;
   bool managed = XtIsManaged(m_borderWidget ? (Widget) m_borderWidget : (Widget) m_scrolledWindow);
 
@@ -2521,19 +2581,25 @@ void wxWindow::CanvasSetSize (int x, int y, int w, int h, int sizeFlags)
   int xx = x; int yy = y;
   AdjustForParentClientOrigin(xx, yy, sizeFlags);
 
-  if (x > -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
+  if (!useOldPos)
+  {
+    if (x > -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
     {
       XtVaSetValues (m_borderWidget ? (Widget) m_borderWidget : (Widget) m_scrolledWindow,
                     XmNx, xx, NULL);
     }
 
-  if (y > -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
+    if (y > -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
     {
       XtVaSetValues (m_borderWidget ? (Widget) m_borderWidget : (Widget) m_scrolledWindow,
                     XmNy, yy, NULL);
     }
+  }
 
-  if (w > -1)
+  if (!useOldSize)
+  {
+
+    if (w > -1)
     {
       if (m_borderWidget)
        {
@@ -2595,16 +2661,21 @@ void wxWindow::CanvasSetSize (int x, int y, int w, int h, int sizeFlags)
 
       XtVaSetValues ((Widget) m_drawingArea, XmNheight, h, NULL);
     }
+  }
+
   if (managed)
     XtManageChild (m_borderWidget ? (Widget) m_borderWidget : (Widget) m_scrolledWindow);
   XtVaSetValues((Widget) m_drawingArea, XmNresizePolicy, XmRESIZE_NONE, NULL);
 
+  /*
   int ww, hh;
   GetClientSize (&ww, &hh);
   wxSizeEvent sizeEvent(wxSize(ww, hh), GetId());
   sizeEvent.SetEventObject(this);
   
   GetEventHandler()->ProcessEvent(sizeEvent);
+  */
+
 }
 
 void wxWindow::CanvasSetClientSize (int w, int h)
@@ -2637,10 +2708,12 @@ void wxWindow::CanvasSetClientSize (int w, int h)
   DoRefresh ();
   */
 
+  /*
   wxSizeEvent sizeEvent(wxSize(w, h), GetId());
   sizeEvent.SetEventObject(this);
   
   GetEventHandler()->ProcessEvent(sizeEvent);
+  */
 }
 
 void wxWindow::CanvasGetClientSize (int *w, int *h) const
@@ -2773,7 +2846,7 @@ void wxPanelItemEventHandler (Widget    wid,
   *continueToDispatch = True;
 }
 
-void wxScrollBarCallback(Widget scrollbar, XtPointer clientData,
+static void wxScrollBarCallback(Widget scrollbar, XtPointer clientData,
                         XmScaleCallbackStruct *cbs)
 {
     Widget scrolledWindow = XtParent (scrollbar);
@@ -3120,9 +3193,12 @@ void wxWindow::ChangeFont(bool keepOriginalSize)
         int width, height, width1, height1;
         GetSize(& width, & height);
 
+// lesstif 0.87 hangs here
+#ifndef LESSTIF_VERSION        
         XtVaSetValues (w,
                   XmNfontList, (XmFontList) m_windowFont.GetFontList(1.0, XtDisplay(w)),
                   NULL);
+#endif
 
         GetSize(& width1, & height1);
         if (keepOriginalSize && (width != width1 || height != height1))
@@ -3138,4 +3214,83 @@ void wxWindow::SetFont(const wxFont& font)
     ChangeFont();
 }
 
+void wxWindow::ClearUpdateRects()
+{
+    wxNode* node = m_updateRects.First();
+    while (node)
+    {
+        wxRect* rect = (wxRect*) node->Data();
+        delete rect;
+        node = node->Next();
+    }
+    m_updateRects.Clear();
+}
+
+bool wxWindow::ProcessAccelerator(wxKeyEvent& event)
+{
+    if (!m_acceleratorTable.Ok())
+        return FALSE;
+
+    int count = m_acceleratorTable.GetCount();
+    wxAcceleratorEntry* entries = m_acceleratorTable.GetEntries();
+    int i;
+    for (i = 0; i < count; i++)
+    {
+        wxAcceleratorEntry* entry = & (entries[i]);
+        if (entry->MatchesEvent(event))
+        {
+            // Bingo, we have a match. Now find a control
+            // that matches the entry command id.
+
+            // Need to go up to the top of the window hierarchy,
+            // since it might be e.g. a menu item
+            wxWindow* parent = this;
+            while (parent && !parent->IsKindOf(CLASSINFO(wxFrame)) && !parent->IsKindOf(CLASSINFO(wxDialog)))
+                parent = parent->GetParent();
+
+            if (!parent)
+                return FALSE;
+
+            if (parent->IsKindOf(CLASSINFO(wxFrame)))
+            {
+                // Try for a menu command
+                wxFrame* frame = (wxFrame*) parent;
+                if (frame->GetMenuBar())
+                {
+                    wxMenuItem* item = frame->GetMenuBar()->FindItemForId(entry->GetCommand());
+                    if (item)
+                    {
+                        wxCommandEvent commandEvent(wxEVT_COMMAND_MENU_SELECTED, entry->GetCommand());
+                        commandEvent.SetEventObject(frame);
+
+                        // If ProcessEvent returns TRUE (it was handled), then
+                        // the calling code will skip the event handling.
+                        return frame->GetEventHandler()->ProcessEvent(commandEvent);
+                    }
+                }
+            }
+
+            // Find a child matching the command id
+            wxWindow* child = parent->FindWindow(entry->GetCommand());
+
+            // No such child
+            if (!child)
+                return FALSE;
+
+            // Now we process those kinds of windows that we can.
+            // For now, only buttons.
+            if (child->IsKindOf(CLASSINFO(wxButton)))
+            {
+                wxCommandEvent commandEvent (wxEVT_COMMAND_BUTTON_CLICKED, child->GetId());
+                commandEvent.SetEventObject(child);
+                return child->GetEventHandler()->ProcessEvent(commandEvent);
+            }
+
+            return FALSE;
+        } // matches event
+    }// for
+
+    // We didn't match the key event against an accelerator.
+    return FALSE;
+}