Remove RenderSurface from Core
[platform/core/uifw/dali-core.git] / automated-tests / src / dali / utc-Dali-SignalTemplatesFunctors.cpp
1 /*
2  * Copyright (c) 2014 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17
18 // EXTERNAL INCLUDES
19 #include <iostream>
20 #include <stdlib.h>
21
22 // INTERNAL INCLUDES
23 #include <dali/public-api/dali-core.h>
24 #include <dali-test-suite-utils.h>
25
26 using namespace Dali;
27
28 void utc_dali_signal_templates_functors_startup(void)
29 {
30   test_return_value = TET_UNDEF;
31 }
32
33 void utc_dali_signal_templates_functors_cleanup(void)
34 {
35   test_return_value = TET_PASS;
36 }
37
38 namespace
39 {
40
41 class TestSignals
42 {
43 public:
44
45   typedef Signal<void ()> VoidSignalVoid;
46   typedef Signal<void (float)> VoidSignalFloat;
47
48   typedef Signal<float ()> FloatSignalVoid;
49   typedef Signal<float (float)> FloatSignalFloat;
50
51   TestSignals()
52   {
53   }
54
55   void CheckNoConnections()
56   {
57     DALI_TEST_EQUALS( mVoidSignalVoid.GetConnectionCount(), 0u, TEST_LOCATION );
58     DALI_TEST_EQUALS( mVoidSignalFloat.GetConnectionCount(), 0u, TEST_LOCATION );
59
60     DALI_TEST_EQUALS( mFloatSignalVoid.GetConnectionCount(), 0u, TEST_LOCATION );
61     DALI_TEST_EQUALS( mFloatSignalFloat.GetConnectionCount(), 0u, TEST_LOCATION );
62   }
63
64   VoidSignalVoid mVoidSignalVoid;
65   VoidSignalFloat mVoidSignalFloat;
66
67   FloatSignalVoid mFloatSignalVoid;
68   FloatSignalFloat mFloatSignalFloat;
69 };
70
71 class TestConnectionTracker : public ConnectionTracker
72 {
73 public:
74
75   TestConnectionTracker()
76   {
77   }
78 };
79
80 struct VoidFunctorVoid
81 {
82   VoidFunctorVoid()
83   {
84     ++mTotalInstanceCount;
85     ++mCurrentInstanceCount;
86   }
87
88   VoidFunctorVoid( const VoidFunctorVoid& copyMe )
89   {
90     ++mTotalInstanceCount;
91     ++mCurrentInstanceCount;
92   }
93
94   ~VoidFunctorVoid()
95   {
96     --mCurrentInstanceCount;
97   }
98
99   void operator()()
100   {
101     ++mCallbackCount;
102   }
103
104   static int mTotalInstanceCount;
105   static int mCurrentInstanceCount;
106   static int mCallbackCount;
107 };
108
109 struct VoidFunctorFloat
110 {
111   VoidFunctorFloat( float* lastReceivedValue )
112   : mLastReceivedValue( lastReceivedValue )
113   {
114     ++mTotalInstanceCount;
115     ++mCurrentInstanceCount;
116   }
117
118   VoidFunctorFloat( const VoidFunctorFloat& copyMe )
119   : mLastReceivedValue( copyMe.mLastReceivedValue )
120   {
121     ++mTotalInstanceCount;
122     ++mCurrentInstanceCount;
123   }
124
125   ~VoidFunctorFloat()
126   {
127     --mCurrentInstanceCount;
128   }
129
130   void operator()(float value)
131   {
132     ++mCallbackCount;
133
134     if( mLastReceivedValue )
135     {
136       *mLastReceivedValue = value;
137     }
138   }
139
140   float* mLastReceivedValue;
141
142   static int mTotalInstanceCount;
143   static int mCurrentInstanceCount;
144   static int mCallbackCount;
145 };
146
147 struct FloatFunctorVoid
148 {
149   static float DEFAULT_RETURN_VALUE;
150
151   FloatFunctorVoid()
152   {
153     ++mTotalInstanceCount;
154     ++mCurrentInstanceCount;
155   }
156
157   FloatFunctorVoid( const FloatFunctorVoid& copyMe )
158   {
159     ++mTotalInstanceCount;
160     ++mCurrentInstanceCount;
161   }
162
163   ~FloatFunctorVoid()
164   {
165     --mCurrentInstanceCount;
166   }
167
168   float operator()()
169   {
170     ++mCallbackCount;
171
172     return DEFAULT_RETURN_VALUE;
173   }
174
175   static int mTotalInstanceCount;
176   static int mCurrentInstanceCount;
177   static int mCallbackCount;
178 };
179
180 float FloatFunctorVoid::DEFAULT_RETURN_VALUE = 5.0f;
181
182 struct FloatFunctorFloat
183 {
184   FloatFunctorFloat()
185   : mLastReceivedValue()
186   {
187     ++mTotalInstanceCount;
188     ++mCurrentInstanceCount;
189   }
190
191   FloatFunctorFloat( const FloatFunctorFloat& copyMe )
192   : mLastReceivedValue (copyMe.mLastReceivedValue )
193   {
194     ++mTotalInstanceCount;
195     ++mCurrentInstanceCount;
196   }
197
198   ~FloatFunctorFloat()
199   {
200     --mCurrentInstanceCount;
201   }
202
203   float operator()(float value)
204   {
205     ++mCallbackCount;
206
207     return value + 1.0f;
208   }
209
210   float* mLastReceivedValue;
211
212   static int mTotalInstanceCount;
213   static int mCurrentInstanceCount;
214   static int mCallbackCount;
215 };
216
217 static void ResetFunctorCounts()
218 {
219   VoidFunctorVoid::mTotalInstanceCount   = 0;
220   VoidFunctorVoid::mCurrentInstanceCount = 0;
221   VoidFunctorVoid::mCallbackCount        = 0;
222
223   VoidFunctorFloat::mTotalInstanceCount   = 0;
224   VoidFunctorFloat::mCurrentInstanceCount = 0;
225   VoidFunctorFloat::mCallbackCount        = 0;
226
227   FloatFunctorVoid::mTotalInstanceCount   = 0;
228   FloatFunctorVoid::mCurrentInstanceCount = 0;
229   FloatFunctorVoid::mCallbackCount        = 0;
230
231   FloatFunctorFloat::mTotalInstanceCount   = 0;
232   FloatFunctorFloat::mCurrentInstanceCount = 0;
233   FloatFunctorFloat::mCallbackCount        = 0;
234 }
235
236 int VoidFunctorVoid::mTotalInstanceCount   = 0;
237 int VoidFunctorVoid::mCurrentInstanceCount = 0;
238 int VoidFunctorVoid::mCallbackCount        = 0;
239
240 int VoidFunctorFloat::mTotalInstanceCount   = 0;
241 int VoidFunctorFloat::mCurrentInstanceCount = 0;
242 int VoidFunctorFloat::mCallbackCount        = 0;
243
244 int FloatFunctorVoid::mTotalInstanceCount   = 0;
245 int FloatFunctorVoid::mCurrentInstanceCount = 0;
246 int FloatFunctorVoid::mCallbackCount        = 0;
247
248 int FloatFunctorFloat::mTotalInstanceCount   = 0;
249 int FloatFunctorFloat::mCurrentInstanceCount = 0;
250 int FloatFunctorFloat::mCallbackCount        = 0;
251
252 } // anon namespace
253
254
255 int UtcDaliSignalFunctorsEmptyCheck(void)
256 {
257   // Test that Empty() check works before & after signal connection
258
259   ResetFunctorCounts();
260
261   {
262     TestSignals::VoidSignalVoid signal;
263     DALI_TEST_CHECK( signal.Empty() );
264     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 0, TEST_LOCATION );
265     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
266     TestConnectionTracker tracker;
267     signal.Connect( &tracker, VoidFunctorVoid() );
268     DALI_TEST_CHECK( ! signal.Empty() );
269     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
270     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 1, TEST_LOCATION );
271   }
272   // TestConnectionTracker should auto-disconnect
273   DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
274   DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
275
276   {
277     TestSignals::VoidSignalFloat signal;
278     DALI_TEST_CHECK( signal.Empty() );
279     DALI_TEST_EQUALS( VoidFunctorFloat::mTotalInstanceCount, 0, TEST_LOCATION );
280     DALI_TEST_EQUALS( VoidFunctorFloat::mCurrentInstanceCount, 0, TEST_LOCATION );
281     TestConnectionTracker tracker;
282     signal.Connect( &tracker, VoidFunctorFloat(NULL) );
283     DALI_TEST_CHECK( ! signal.Empty() );
284     DALI_TEST_EQUALS( VoidFunctorFloat::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
285     DALI_TEST_EQUALS( VoidFunctorFloat::mCurrentInstanceCount, 1, TEST_LOCATION );
286   }
287   // TestConnectionTracker should auto-disconnect
288   DALI_TEST_EQUALS( VoidFunctorFloat::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
289   DALI_TEST_EQUALS( VoidFunctorFloat::mCurrentInstanceCount, 0, TEST_LOCATION );
290   END_TEST;
291 }
292
293 int UtcDaliSignalFunctorsEmit(void)
294 {
295   // Test basic signal emission for each functor type
296
297   ResetFunctorCounts();
298
299   TestSignals signals;
300
301   {
302     TestConnectionTracker tracker;
303
304     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 0, TEST_LOCATION );
305     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
306
307     signals.mVoidSignalVoid.Connect( &tracker, VoidFunctorVoid() );
308     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
309     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 1, TEST_LOCATION );
310     DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 0, TEST_LOCATION );
311
312     signals.mVoidSignalVoid.Emit();
313     DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 1, TEST_LOCATION );
314
315     // Test double emission
316     signals.mVoidSignalVoid.Emit();
317     DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 2, TEST_LOCATION );
318   }
319   // TestConnectionTracker should auto-disconnect
320   DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
321   DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
322   DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 2, TEST_LOCATION );
323   signals.CheckNoConnections();
324
325   {
326     TestConnectionTracker tracker;
327     float lastReceivedValue( 0.0f );
328
329     DALI_TEST_EQUALS( VoidFunctorFloat::mTotalInstanceCount, 0, TEST_LOCATION );
330     DALI_TEST_EQUALS( VoidFunctorFloat::mCurrentInstanceCount, 0, TEST_LOCATION );
331
332     signals.mVoidSignalFloat.Connect( &tracker, VoidFunctorFloat(&lastReceivedValue) );
333     DALI_TEST_EQUALS( VoidFunctorFloat::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
334     DALI_TEST_EQUALS( VoidFunctorFloat::mCurrentInstanceCount, 1, TEST_LOCATION );
335     DALI_TEST_EQUALS( VoidFunctorFloat::mCallbackCount, 0, TEST_LOCATION );
336
337     signals.mVoidSignalFloat.Emit( 3.5f );
338     DALI_TEST_EQUALS( VoidFunctorFloat::mCallbackCount, 1, TEST_LOCATION );
339     DALI_TEST_EQUALS( lastReceivedValue, 3.5f, TEST_LOCATION );
340
341     // Test double emission
342     signals.mVoidSignalFloat.Emit( 7.0f );
343     DALI_TEST_EQUALS( VoidFunctorFloat::mCallbackCount, 2, TEST_LOCATION );
344     DALI_TEST_EQUALS( lastReceivedValue, 7.0f, TEST_LOCATION );
345   }
346   // TestConnectionTracker should auto-disconnect
347   DALI_TEST_EQUALS( VoidFunctorFloat::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
348   DALI_TEST_EQUALS( VoidFunctorFloat::mCurrentInstanceCount, 0, TEST_LOCATION );
349   DALI_TEST_EQUALS( VoidFunctorFloat::mCallbackCount, 2, TEST_LOCATION );
350   signals.CheckNoConnections();
351   END_TEST;
352 }
353
354 int UtcDaliSignalFunctorsEmitReturn(void)
355 {
356   // Test signals with return values
357
358   ResetFunctorCounts();
359
360   TestSignals signals;
361
362   {
363     TestConnectionTracker tracker;
364
365     DALI_TEST_EQUALS( FloatFunctorVoid::mTotalInstanceCount, 0, TEST_LOCATION );
366     DALI_TEST_EQUALS( FloatFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
367
368     signals.mFloatSignalVoid.Connect( &tracker, FloatFunctorVoid() );
369     DALI_TEST_EQUALS( FloatFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
370     DALI_TEST_EQUALS( FloatFunctorVoid::mCurrentInstanceCount, 1, TEST_LOCATION );
371     DALI_TEST_EQUALS( FloatFunctorVoid::mCallbackCount, 0, TEST_LOCATION );
372
373     float returnValue = signals.mFloatSignalVoid.Emit();
374     DALI_TEST_EQUALS( FloatFunctorVoid::mCallbackCount, 1, TEST_LOCATION );
375     DALI_TEST_EQUALS( returnValue, FloatFunctorVoid::DEFAULT_RETURN_VALUE, TEST_LOCATION );
376
377     // Test double emission
378     returnValue = signals.mFloatSignalVoid.Emit();
379     DALI_TEST_EQUALS( FloatFunctorVoid::mCallbackCount, 2, TEST_LOCATION );
380     DALI_TEST_EQUALS( returnValue, FloatFunctorVoid::DEFAULT_RETURN_VALUE, TEST_LOCATION );
381   }
382   // TestConnectionTracker should auto-disconnect
383   DALI_TEST_EQUALS( FloatFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
384   DALI_TEST_EQUALS( FloatFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
385   DALI_TEST_EQUALS( FloatFunctorVoid::mCallbackCount, 2, TEST_LOCATION );
386   signals.CheckNoConnections();
387
388   {
389     TestConnectionTracker tracker;
390
391     DALI_TEST_EQUALS( FloatFunctorFloat::mTotalInstanceCount, 0, TEST_LOCATION );
392     DALI_TEST_EQUALS( FloatFunctorFloat::mCurrentInstanceCount, 0, TEST_LOCATION );
393
394     signals.mFloatSignalFloat.Connect( &tracker, FloatFunctorFloat() );
395     DALI_TEST_EQUALS( FloatFunctorFloat::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
396     DALI_TEST_EQUALS( FloatFunctorFloat::mCurrentInstanceCount, 1, TEST_LOCATION );
397     DALI_TEST_EQUALS( FloatFunctorFloat::mCallbackCount, 0, TEST_LOCATION );
398
399     float returnValue = signals.mFloatSignalFloat.Emit( 0.1f );
400     DALI_TEST_EQUALS( FloatFunctorFloat::mCallbackCount, 1, TEST_LOCATION );
401     DALI_TEST_EQUALS( returnValue, 1.0f + 0.1f, TEST_LOCATION );
402
403     // Test double emission
404     returnValue = signals.mFloatSignalFloat.Emit( 0.2f );
405     DALI_TEST_EQUALS( FloatFunctorFloat::mCallbackCount, 2, TEST_LOCATION );
406     DALI_TEST_EQUALS( returnValue, 1.0f + 0.2f, TEST_LOCATION );
407   }
408   // TestConnectionTracker should auto-disconnect
409   DALI_TEST_EQUALS( FloatFunctorFloat::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
410   DALI_TEST_EQUALS( FloatFunctorFloat::mCurrentInstanceCount, 0, TEST_LOCATION );
411   DALI_TEST_EQUALS( FloatFunctorFloat::mCallbackCount, 2, TEST_LOCATION );
412   signals.CheckNoConnections();
413   END_TEST;
414 }
415
416 int UtcDaliSignalFunctorsDisconnectBeforeEmit(void)
417 {
418   // Test explicit disconnect using ConnectionTracker
419
420   ResetFunctorCounts();
421
422   TestSignals signals;
423
424   {
425     TestConnectionTracker tracker;
426
427     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 0, TEST_LOCATION );
428     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
429
430     signals.mVoidSignalVoid.Connect( &tracker, VoidFunctorVoid() );
431     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
432     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 1, TEST_LOCATION );
433
434     tracker.DisconnectAll();
435     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
436     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
437
438     signals.mVoidSignalVoid.Emit();
439     DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 0, TEST_LOCATION );
440
441     // Test double emission
442     signals.mVoidSignalVoid.Emit();
443     DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 0, TEST_LOCATION );
444   }
445   END_TEST;
446 }
447
448 int UtcDaliSignalFunctorsDestroySignal(void)
449 {
450   // Test destruction of signal before slot
451
452   ResetFunctorCounts();
453
454   TestConnectionTracker tracker;
455
456   {
457     TestSignals signals;
458
459     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 0, TEST_LOCATION );
460     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
461
462     signals.mVoidSignalVoid.Connect( &tracker, VoidFunctorVoid() );
463     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
464     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 1, TEST_LOCATION );
465
466     signals.mVoidSignalVoid.Emit();
467     DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount,1, TEST_LOCATION );
468
469     DALI_TEST_EQUALS( tracker.GetConnectionCount(), 1u, TEST_LOCATION );
470   }
471
472   // Functor should have been deleted with signal
473   DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
474   DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
475   DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 1, TEST_LOCATION );
476
477   DALI_TEST_EQUALS( tracker.GetConnectionCount(), 0u, TEST_LOCATION );
478   END_TEST;
479 }
480
481 int UtcDaliSignalConnectVoidFunctor(void)
482 {
483   // Test connecting a functor using the VoidFunctor wrapper
484
485   ResetFunctorCounts();
486
487   TestSignals signals;
488
489   {
490     TestConnectionTracker tracker;
491
492     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 0, TEST_LOCATION );
493     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
494
495     signals.mVoidSignalVoid.Connect( &tracker, FunctorDelegate::New( VoidFunctorVoid() ) );
496     DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
497     DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 1, TEST_LOCATION );
498     DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 0, TEST_LOCATION );
499
500     signals.mVoidSignalVoid.Emit();
501     DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 1, TEST_LOCATION );
502
503     // Test double emission
504     signals.mVoidSignalVoid.Emit();
505     DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 2, TEST_LOCATION );
506   }
507   // TestConnectionTracker should auto-disconnect
508   DALI_TEST_EQUALS( VoidFunctorVoid::mTotalInstanceCount, 2/*temporary copy + signal copy*/, TEST_LOCATION );
509   DALI_TEST_EQUALS( VoidFunctorVoid::mCurrentInstanceCount, 0, TEST_LOCATION );
510   DALI_TEST_EQUALS( VoidFunctorVoid::mCallbackCount, 2, TEST_LOCATION );
511   signals.CheckNoConnections();
512   END_TEST;
513 }