]> git.saurik.com Git - wxWidgets.git/commitdiff
Yet another fix to event propagation in scrolled windows.
authorVadim Zeitlin <vadim@wxwidgets.org>
Fri, 21 May 2010 12:07:45 +0000 (12:07 +0000)
committerVadim Zeitlin <vadim@wxwidgets.org>
Fri, 21 May 2010 12:07:45 +0000 (12:07 +0000)
Calling ProcessEventLocally() didn't work because the command events were not
propagated to the parent window any more, breaking a lot of things including
wxDataViewCtrl event generation in the generic version. So do restore
ProcessEvent() call but use it on the next handler (i.e. the window itself)
and not this one now. This still results in some duplicate calls but at least
the events should be passed everywhere where they are expected to arrive.

wxScrollHelperEvtHandler must die.

Closes #12078.

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@64370 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775

src/generic/scrlwing.cpp
tests/events/propagation.cpp

index bc1d5cdbde502775016d864e75fe98e52225f78b..0f1a4f57efc2034ca165399faadafe443450de21 100644 (file)
@@ -203,8 +203,18 @@ bool wxScrollHelperEvtHandler::ProcessEvent(wxEvent& event)
     // user code defined OnPaint() in the derived class)
     m_hasDrawnWindow = true;
 
     // user code defined OnPaint() in the derived class)
     m_hasDrawnWindow = true;
 
-    // pass it on to the real handler
-    bool processed = m_nextHandler->ProcessEventLocally(event);
+    // Pass it on to the real handler: notice that we must not call
+    // ProcessEvent() on this object itself as it wouldn't pass it to the next
+    // handler (i.e. the real window) if we're called from a previous handler
+    // (as indicated by "process here only" flag being set) and we do want to
+    // execute the handler defined in the window we're associated with right
+    // now, without waiting until TryAfter() is called from wxEvtHandler.
+    //
+    // Note that this means that the handler in the window will be called twice
+    // if there is a preceding event handler in the chain because we do it from
+    // here now and the base class DoTryChain() will also call it itself when
+    // we return. But this unfortunately seems unavoidable.
+    bool processed = m_nextHandler->ProcessEvent(event);
 
     // always process the size events ourselves, even if the user code handles
     // them as well, as we need to AdjustScrollbars()
 
     // always process the size events ourselves, even if the user code handles
     // them as well, as we need to AdjustScrollbars()
index f27395f1a5bac02f6ee64bef7c30bf58293c4d23..7ec1e50dd3860a0af4d32c49eb7fcd9496b2e539 100644 (file)
@@ -264,20 +264,27 @@ void EventPropagationTestCase::WindowWithHandler()
 
 void EventPropagationTestCase::ScrollWindowWithoutHandler()
 {
 
 void EventPropagationTestCase::ScrollWindowWithoutHandler()
 {
-    TestScrollWindow * const
-        win = new TestScrollWindow(wxTheApp->GetTopWindow());
-    wxON_BLOCK_EXIT_OBJ0( *win, wxWindow::Destroy );
+    TestWindow * const parent = new TestWindow(wxTheApp->GetTopWindow(), 'p');
+    wxON_BLOCK_EXIT_OBJ0( *parent, wxWindow::Destroy );
+
+    TestScrollWindow * const win = new TestScrollWindow(parent);
 
     wxPaintEvent event(win->GetId());
     win->ProcessWindowEvent(event);
     CPPUNIT_ASSERT_EQUAL( "PD", g_str );
 
     wxPaintEvent event(win->GetId());
     win->ProcessWindowEvent(event);
     CPPUNIT_ASSERT_EQUAL( "PD", g_str );
+
+    g_str.clear();
+    wxCommandEvent eventCmd(TEST_EVT);
+    win->HandleWindowEvent(eventCmd);
+    CPPUNIT_ASSERT_EQUAL( "apA", g_str );
 }
 
 void EventPropagationTestCase::ScrollWindowWithHandler()
 {
 }
 
 void EventPropagationTestCase::ScrollWindowWithHandler()
 {
-    TestScrollWindow * const
-        win = new TestScrollWindow(wxTheApp->GetTopWindow());
-    wxON_BLOCK_EXIT_OBJ0( *win, wxWindow::Destroy );
+    TestWindow * const parent = new TestWindow(wxTheApp->GetTopWindow(), 'p');
+    wxON_BLOCK_EXIT_OBJ0( *parent, wxWindow::Destroy );
+
+    TestScrollWindow * const win = new TestScrollWindow(parent);
 
     TestPaintEvtHandler h('h');
     win->PushEventHandler(&h);
 
     TestPaintEvtHandler h('h');
     win->PushEventHandler(&h);
@@ -286,5 +293,10 @@ void EventPropagationTestCase::ScrollWindowWithHandler()
     wxPaintEvent event(win->GetId());
     win->ProcessWindowEvent(event);
     CPPUNIT_ASSERT_EQUAL( "ohPD", g_str );
     wxPaintEvent event(win->GetId());
     win->ProcessWindowEvent(event);
     CPPUNIT_ASSERT_EQUAL( "ohPD", g_str );
+
+    g_str.clear();
+    wxCommandEvent eventCmd(TEST_EVT);
+    win->HandleWindowEvent(eventCmd);
+    CPPUNIT_ASSERT_EQUAL( "apA", g_str );
 }
 
 }