X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/5293e4b7109139cc51052d57c0585716d6250b76..92a98ecc5369edfebf13151dc9e9d4acaf326342:/tests/events/evthandler.cpp diff --git a/tests/events/evthandler.cpp b/tests/events/evthandler.cpp index 031a0658da..1496f4c196 100644 --- a/tests/events/evthandler.cpp +++ b/tests/events/evthandler.cpp @@ -3,7 +3,6 @@ // Purpose: Test the new event types and wxEvtHandler-methods // Author: Peter Most // Created: 2009-01-24 -// RCS-ID: $Id$ // Copyright: (c) 2009 Peter Most /////////////////////////////////////////////////////////////////////////////// @@ -37,7 +36,7 @@ public: }; typedef void (wxEvtHandler::*MyEventFunction)(MyEvent&); -#if wxEVENTS_COMPATIBILITY_2_8 +#ifndef wxHAS_EVENT_BIND #define MyEventHandler(func) wxEVENT_HANDLER_CAST(MyEventFunction, func) #else #define MyEventHandler(func) &func @@ -75,7 +74,14 @@ void GlobalOnMyEvent(MyEvent&) g_called.function = true; } +void GlobalOnEvent(wxEvent&) +{ + g_called.function = true; +} + +#ifdef TEST_INVALID_BIND_GLOBAL void GlobalOnAnotherEvent(AnotherEvent&); +#endif void GlobalOnIdle(wxIdleEvent&) { @@ -130,7 +136,7 @@ BEGIN_EVENT_TABLE(MyClassWithEventTable, wxEvtHandler) EVT_IDLE(MyClassWithEventTable::OnIdle) EVT_MYEVENT(MyClassWithEventTable::OnMyEvent) -#if !wxEVENTS_COMPATIBILITY_2_8 +#ifdef wxHAS_EVENT_BIND EVT_MYEVENT(MyClassWithEventTable::OnEvent) #endif @@ -155,28 +161,34 @@ private: CPPUNIT_TEST_SUITE( EvtHandlerTestCase ); CPPUNIT_TEST( BuiltinConnect ); CPPUNIT_TEST( LegacyConnect ); -#if !wxEVENTS_COMPATIBILITY_2_8 + CPPUNIT_TEST( DisconnectWildcard ); + CPPUNIT_TEST( AutoDisconnect ); +#ifdef wxHAS_EVENT_BIND CPPUNIT_TEST( BindFunction ); CPPUNIT_TEST( BindStaticMethod ); CPPUNIT_TEST( BindFunctor ); CPPUNIT_TEST( BindMethod ); CPPUNIT_TEST( BindMethodUsingBaseEvent ); + CPPUNIT_TEST( BindFunctionUsingBaseEvent ); CPPUNIT_TEST( BindNonHandler ); CPPUNIT_TEST( InvalidBind ); -#endif // !wxEVENTS_COMPATIBILITY_2_8 +#endif // wxHAS_EVENT_BIND CPPUNIT_TEST_SUITE_END(); void BuiltinConnect(); void LegacyConnect(); -#if !wxEVENTS_COMPATIBILITY_2_8 + void DisconnectWildcard(); + void AutoDisconnect(); +#ifdef wxHAS_EVENT_BIND void BindFunction(); void BindStaticMethod(); void BindFunctor(); void BindMethod(); void BindMethodUsingBaseEvent(); + void BindFunctionUsingBaseEvent(); void BindNonHandler(); void InvalidBind(); -#endif // !wxEVENTS_COMPATIBILITY_2_8 +#endif // wxHAS_EVENT_BIND // these member variables exceptionally don't use "m_" prefix because @@ -190,7 +202,7 @@ private: // register in the unnamed registry so that these tests are run by default CPPUNIT_TEST_SUITE_REGISTRATION( EvtHandlerTestCase ); -// also include in it's own registry so that these tests can be run alone +// also include in its own registry so that these tests can be run alone CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( EvtHandlerTestCase, "EvtHandlerTestCase" ); void EvtHandlerTestCase::BuiltinConnect() @@ -206,7 +218,7 @@ void EvtHandlerTestCase::BuiltinConnect() handler.Connect(wxEVT_IDLE, (wxObjectEventFunction)(wxEventFunction)&MyHandler::OnIdle); handler.Disconnect(wxEVT_IDLE, (wxObjectEventFunction)(wxEventFunction)&MyHandler::OnIdle); -#if !wxEVENTS_COMPATIBILITY_2_8 +#ifdef wxHAS_EVENT_BIND handler.Bind(wxEVT_IDLE, GlobalOnIdle); handler.Unbind(wxEVT_IDLE, GlobalOnIdle); @@ -219,7 +231,7 @@ void EvtHandlerTestCase::BuiltinConnect() handler.Bind(wxEVT_IDLE, &MyHandler::StaticOnIdle); handler.Unbind(wxEVT_IDLE, &MyHandler::StaticOnIdle); -#endif // !wxEVENTS_COMPATIBILITY_2_8 +#endif // wxHAS_EVENT_BIND } void EvtHandlerTestCase::LegacyConnect() @@ -242,7 +254,32 @@ void EvtHandlerTestCase::LegacyConnect() handler.Disconnect( 0, 0, LegacyEventType, (wxObjectEventFunction)&MyHandler::OnEvent, NULL, &handler ); } -#if !wxEVENTS_COMPATIBILITY_2_8 +void EvtHandlerTestCase::DisconnectWildcard() +{ + // should be able to disconnect a different handler using "wildcard search" + MyHandler sink; + wxEvtHandler source; + source.Connect(wxEVT_IDLE, wxIdleEventHandler(MyHandler::OnIdle), NULL, &sink); + CPPUNIT_ASSERT(source.Disconnect(wxID_ANY, wxEVT_IDLE)); + // destruction of source and sink here should properly clean up the + // wxEventConnectionRef without crashing +} + +void EvtHandlerTestCase::AutoDisconnect() +{ + wxEvtHandler source; + { + MyHandler sink; + source.Connect(wxEVT_IDLE, wxIdleEventHandler(MyHandler::OnIdle), NULL, &sink); + // mismatched event type, so nothing should be disconnected + CPPUNIT_ASSERT(!source.Disconnect(wxEVT_THREAD, wxIdleEventHandler(MyHandler::OnIdle), NULL, &sink)); + } + // destruction of sink should have automatically disconnected it, so + // there should be nothing to disconnect anymore + CPPUNIT_ASSERT(!source.Disconnect(wxID_ANY, wxEVT_IDLE)); +} + +#ifdef wxHAS_EVENT_BIND void EvtHandlerTestCase::BindFunction() { @@ -302,6 +339,19 @@ void EvtHandlerTestCase::BindFunctor() handler.Bind( MyEventType, functor, 0, 0 ); handler.Unbind( MyEventType, functor, 0, 0 ); + + // test that a temporary functor is working as well and also test that + // unbinding a different (though equal) instance of the same functor does + // not work + MyFunctor func; + handler.Bind( MyEventType, MyFunctor() ); + CPPUNIT_ASSERT( !handler.Unbind( MyEventType, func )); + + handler.Bind( MyEventType, MyFunctor(), 0 ); + CPPUNIT_ASSERT( !handler.Unbind( MyEventType, func, 0 )); + + handler.Bind( MyEventType, MyFunctor(), 0, 0 ); + CPPUNIT_ASSERT( !handler.Unbind( MyEventType, func, 0, 0 )); } void EvtHandlerTestCase::BindMethod() @@ -345,6 +395,29 @@ void EvtHandlerTestCase::BindMethodUsingBaseEvent() } +void EvtHandlerTestCase::BindFunctionUsingBaseEvent() +{ + // test connecting a function taking just wxEvent and not MyEvent: this + // should work too if we don't need any MyEvent-specific information in the + // handler + handler.Bind( MyEventType, GlobalOnEvent ); + g_called.Reset(); + handler.ProcessEvent(e); + CPPUNIT_ASSERT( g_called.function ); + handler.Unbind( MyEventType, GlobalOnEvent ); + g_called.Reset(); + handler.ProcessEvent(e); + CPPUNIT_ASSERT( !g_called.function ); + + handler.Bind( MyEventType, GlobalOnEvent, 0 ); + handler.Unbind( MyEventType, GlobalOnEvent, 0 ); + + handler.Bind( MyEventType, GlobalOnEvent, 0, 0 ); + handler.Unbind( MyEventType, GlobalOnEvent, 0, 0 ); +} + + + void EvtHandlerTestCase::BindNonHandler() { // class method tests for class not derived from wxEvtHandler @@ -366,20 +439,40 @@ void EvtHandlerTestCase::InvalidBind() // automatically, you need to uncomment them manually and test that // compilation does indeed fail - //handler.Bind(MyEventType, GlobalOnAnotherEvent); - //IdleFunctor f; handler.Bind(MyEventType, f); - //handler.Bind(MyEventType, &MyHandler::StaticOnAnotherEvent); - //handler.Bind(MyEventType, &MyHandler::OnAnotherEvent, &handler); + // connecting a handler with incompatible signature shouldn't work +#ifdef TEST_INVALID_BIND_GLOBAL + handler.Bind(MyEventType, GlobalOnAnotherEvent); +#endif +#ifdef TEST_INVALID_BIND_STATIC + handler.Bind(MyEventType, &MyHandler::StaticOnAnotherEvent); +#endif +#ifdef TEST_INVALID_BIND_METHOD + handler.Bind(MyEventType, &MyHandler::OnAnotherEvent, &handler); +#endif +#ifdef TEST_INVALID_BIND_FUNCTOR + IdleFunctor f; + handler.Bind(MyEventType, f); +#endif - // Test that this sample (discussed on the mailing list) doesn't compile: - // >struct C1 : wxEvtHandler { }; - // >struct C2 : wxEvtHandler { void OnWhatever(wxEvent&) }; - // >C1 c1; - // >c1.Connect(&C2::OnWhatever); // BOOM + // the handler can't be omitted when calling Bind() +#ifdef TEST_INVALID_BIND_NO_HANDLER + handler.Bind(MyEventType, &MyHandler::OnMyEvent); +#endif + + // calling a derived class method with a base class pointer must not work +#ifdef TEST_INVALID_BIND_DERIVED + struct C1 : wxEvtHandler { }; + struct C2 : wxEvtHandler { void OnWhatever(wxEvent&); }; + C1 c1; + c1.Bind(&C2::OnWhatever); +#endif - //MySink mySink; - //MyHandler myHandler; - //myHandler.Bind( MyEventType, &MyHandler::OnMyEvent, &mySink ); + // using object pointer incompatible with the method must not work +#ifdef TEST_INVALID_BIND_WRONG_CLASS + MySink mySink; + MyHandler myHandler; + myHandler.Bind(MyEventType, &MyHandler::OnMyEvent, &mySink); +#endif } -#endif // !wxEVENTS_COMPATIBILITY_2_8 +#endif // wxHAS_EVENT_BIND