add wx/window.h for MSVC compilation
[wxWidgets.git] / tests / events / propagation.cpp
1 ///////////////////////////////////////////////////////////////////////////////
2 // Name: tests/events/propagation.cpp
3 // Purpose: Test events propagation
4 // Author: Vadim Zeitlin
5 // Created: 2009-01-16
6 // RCS-ID: $Id$
7 // Copyright: (c) 2009 Vadim Zeitlin <vadim@wxwidgets.org>
8 ///////////////////////////////////////////////////////////////////////////////
9
10 // ----------------------------------------------------------------------------
11 // headers
12 // ----------------------------------------------------------------------------
13
14 #include "testprec.h"
15
16 #ifdef __BORLANDC__
17 #pragma hdrstop
18 #endif
19
20 #ifndef WX_PRECOMP
21 #endif // WX_PRECOMP
22
23 #include "wx/event.h"
24 #include "wx/window.h"
25 #include "wx/scopeguard.h"
26
27 namespace
28 {
29
30 // this string will record the execution of all handlers
31 wxString g_str;
32
33 // a custom event
34 wxDEFINE_EVENT(TEST_EVT, wxCommandEvent);
35
36 // a custom event handler
37 class TestEvtHandler : public wxEvtHandler
38 {
39 public:
40 TestEvtHandler(char tag)
41 : m_tag(tag)
42 {
43 Connect(TEST_EVT, wxCommandEventHandler(TestEvtHandler::OnTest));
44 }
45
46 // override ProcessEvent() to confirm that it is called for all event
47 // handlers in the chain
48 virtual bool ProcessEvent(wxEvent& event)
49 {
50 if ( event.GetEventType() == TEST_EVT )
51 g_str += 'o'; // "o" == "overridden"
52
53 return wxEvtHandler::ProcessEvent(event);
54 }
55
56 private:
57 void OnTest(wxCommandEvent& event)
58 {
59 g_str += m_tag;
60
61 event.Skip();
62 }
63
64 const char m_tag;
65
66 DECLARE_NO_COPY_CLASS(TestEvtHandler)
67 };
68
69 // a window handling the test event
70 class TestWindow : public wxWindow
71 {
72 public:
73 TestWindow(wxWindow *parent, char tag)
74 : wxWindow(parent, wxID_ANY),
75 m_tag(tag)
76 {
77 Connect(TEST_EVT, wxCommandEventHandler(TestWindow::OnTest));
78 }
79
80 private:
81 void OnTest(wxCommandEvent& event)
82 {
83 g_str += m_tag;
84
85 event.Skip();
86 }
87
88 const char m_tag;
89
90 DECLARE_NO_COPY_CLASS(TestWindow)
91 };
92
93 int DoFilterEvent(wxEvent& event)
94 {
95 if ( event.GetEventType() == TEST_EVT )
96 g_str += 'a';
97
98 return -1;
99 }
100
101 bool DoProcessEvent(wxEvent& event)
102 {
103 if ( event.GetEventType() == TEST_EVT )
104 g_str += 'A';
105
106 return false;
107 }
108
109 } // anonymous namespace
110
111 // --------------------------------------------------------------------------
112 // test class
113 // --------------------------------------------------------------------------
114
115 class EventPropagationTestCase : public CppUnit::TestCase
116 {
117 public:
118 EventPropagationTestCase() {}
119
120 virtual void setUp();
121 virtual void tearDown();
122
123 private:
124 CPPUNIT_TEST_SUITE( EventPropagationTestCase );
125 CPPUNIT_TEST( OneHandler );
126 CPPUNIT_TEST( TwoHandlers );
127 CPPUNIT_TEST( WindowWithoutHandler );
128 CPPUNIT_TEST( WindowWithHandler );
129 CPPUNIT_TEST_SUITE_END();
130
131 void OneHandler();
132 void TwoHandlers();
133 void WindowWithoutHandler();
134 void WindowWithHandler();
135
136 DECLARE_NO_COPY_CLASS(EventPropagationTestCase)
137 };
138
139 // register in the unnamed registry so that these tests are run by default
140 CPPUNIT_TEST_SUITE_REGISTRATION( EventPropagationTestCase );
141
142 // also include in it's own registry so that these tests can be run alone
143 CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( EventPropagationTestCase, "EventPropagationTestCase" );
144
145 void EventPropagationTestCase::setUp()
146 {
147 SetFilterEventFunc(DoFilterEvent);
148 SetProcessEventFunc(DoProcessEvent);
149
150 g_str.clear();
151 }
152
153 void EventPropagationTestCase::tearDown()
154 {
155 SetFilterEventFunc(NULL);
156 SetProcessEventFunc(NULL);
157 }
158
159 void EventPropagationTestCase::OneHandler()
160 {
161 wxCommandEvent event(TEST_EVT);
162 TestEvtHandler h1('1');
163 h1.ProcessEvent(event);
164 CPPUNIT_ASSERT_EQUAL( "oa1A", g_str );
165 }
166
167 void EventPropagationTestCase::TwoHandlers()
168 {
169 wxCommandEvent event(TEST_EVT);
170 TestEvtHandler h1('1');
171 TestEvtHandler h2('2');
172 h1.SetNextHandler(&h2);
173 h2.SetPreviousHandler(&h1);
174 h1.ProcessEvent(event);
175 CPPUNIT_ASSERT_EQUAL( "oa1o2A", g_str );
176 }
177
178 void EventPropagationTestCase::WindowWithoutHandler()
179 {
180 wxCommandEvent event(TEST_EVT);
181 TestWindow * const parent = new TestWindow(wxTheApp->GetTopWindow(), 'p');
182 wxON_BLOCK_EXIT_OBJ0( *parent, wxWindow::Destroy );
183
184 TestWindow * const child = new TestWindow(parent, 'c');
185
186 child->ProcessEvent(event);
187 CPPUNIT_ASSERT_EQUAL( "acpA", g_str );
188 }
189
190 void EventPropagationTestCase::WindowWithHandler()
191 {
192 wxCommandEvent event(TEST_EVT);
193 TestWindow * const parent = new TestWindow(wxTheApp->GetTopWindow(), 'p');
194 wxON_BLOCK_EXIT_OBJ0( *parent, wxWindow::Destroy );
195
196 TestWindow * const child = new TestWindow(parent, 'c');
197
198 TestEvtHandler h1('1');
199 child->PushEventHandler(&h1);
200 wxON_BLOCK_EXIT_OBJ0( *child, wxWindow::PopEventHandler );
201 TestEvtHandler h2('2');
202 child->PushEventHandler(&h2);
203 wxON_BLOCK_EXIT_OBJ0( *child, wxWindow::PopEventHandler );
204
205 child->HandleWindowEvent(event);
206 CPPUNIT_ASSERT_EQUAL( "oa2o1cpA", g_str );
207 }
208