#endif // !USE_SHARED_LIBRARY
+#if wxUSE_THREADS
+/* To put pending event handlers */
+extern wxList *wxPendingEvents;
+extern wxCriticalSection *wxPendingEventsLocker;
+#endif
+
/*
* General wxWindows events, covering
* all interesting things that might happen (button clicking, resizing,
case 3:
return RightDClick();
default:
- wxFAIL_MSG("invalid parameter in wxMouseEvent::ButtonDClick");
+ wxFAIL_MSG(_T("invalid parameter in wxMouseEvent::ButtonDClick"));
}
return FALSE;
case 3:
return RightDown();
default:
- wxFAIL_MSG("invalid parameter in wxMouseEvent::ButtonDown");
+ wxFAIL_MSG(_T("invalid parameter in wxMouseEvent::ButtonDown"));
}
return FALSE;
case 3:
return RightUp();
default:
- wxFAIL_MSG("invalid parameter in wxMouseEvent::ButtonUp");
+ wxFAIL_MSG(_T("invalid parameter in wxMouseEvent::ButtonUp"));
}
return FALSE;
case 3:
return (RightDown() || RightUp() || RightDClick());
default:
- wxFAIL_MSG("invalid parameter in wxMouseEvent::Button");
+ wxFAIL_MSG(_T("invalid parameter in wxMouseEvent::Button"));
}
return FALSE;
case 3:
return RightIsDown();
default:
- wxFAIL_MSG("invalid parameter in wxMouseEvent::ButtonIsDown");
+ wxFAIL_MSG(_T("invalid parameter in wxMouseEvent::ButtonIsDown"));
}
return FALSE;
m_enabled = TRUE;
m_dynamicEvents = (wxList *) NULL;
m_isWindow = FALSE;
+#if wxUSE_THREADS
+ m_eventsLocker = new wxCriticalSection();
+#endif
+ m_pendingEvents = (wxList *) NULL;
}
wxEvtHandler::~wxEvtHandler()
}
delete m_dynamicEvents;
};
+
+ if (m_pendingEvents)
+ delete m_pendingEvents;
+
+#if wxUSE_THREADS
+ delete m_eventsLocker;
+#endif
+}
+
+#if wxUSE_THREADS
+bool wxEvtHandler::ProcessThreadEvent(wxEvent& event)
+{
+ wxEvent *event_main;
+ wxCriticalSectionLocker locker(*m_eventsLocker);
+
+ // check that we are really in a child thread
+ wxASSERT( !wxThread::IsMain() );
+
+ if (m_pendingEvents == NULL)
+ m_pendingEvents = new wxList();
+
+ event_main = (wxEvent *)event.GetClassInfo()->CreateObject();
+ *event_main = event;
+
+ m_pendingEvents->Append(event_main);
+
+ wxPendingEventsLocker->Enter();
+ wxPendingEvents->Append(this);
+ wxPendingEventsLocker->Leave();
+
+ return TRUE;
}
+void wxEvtHandler::ProcessPendingEvents()
+{
+ wxCriticalSectionLocker locker(*m_eventsLocker);
+ wxNode *node = m_pendingEvents->First();
+ wxEvent *event;
+
+ while (node != NULL) {
+ event = (wxEvent *)node->Data();
+ ProcessEvent(*event);
+ delete node;
+ node = m_pendingEvents->First();
+ }
+}
+#endif
+
/*
* Event table stuff
*/
// An event handler can be enabled or disabled
if ( GetEvtHandlerEnabled() )
{
+#if wxUSE_THREADS
+ // Check whether we are in a child thread.
+ if (!wxThread::IsMain())
+ return ProcessThreadEvent(event);
+#endif
// Handle per-instance dynamic event tables first
if ( m_dynamicEvents && SearchDynamicEventTable(event) )
bool wxEvtHandler::SearchDynamicEventTable( wxEvent& event )
{
wxCHECK_MSG( m_dynamicEvents, FALSE,
- "caller should check that we have dynamic events" );
+ _T("caller should check that we have dynamic events") );
int commandId = event.GetId();
}
#endif // WXWIN_COMPATIBILITY
+// Find a window with the focus, that is also a descendant of the given window.
+// This is used to determine the window to initially send commands to.
+wxWindow* wxFindFocusDescendant(wxWindow* ancestor)
+{
+ // Process events starting with the window with the focus, if any.
+ wxWindow* focusWin = wxWindow::FindFocus();
+ wxWindow* win = focusWin;
+
+ // Check if this is a descendant of this frame.
+ // If not, win will be set to NULL.
+ while (win)
+ {
+ if (win == ancestor)
+ break;
+ else
+ win = win->GetParent();
+ }
+ if (win == (wxWindow*) NULL)
+ focusWin = (wxWindow*) NULL;
+
+ return focusWin;
+}
+