41e8236328ccdbc03beaa170f144b3fe31183b0b
[platform/core/uifw/dali-toolkit.git] / automated-tests / src / dali-toolkit / utc-Dali-BubbleEmitter.cpp
1 /*
2  * Copyright (c) 2023 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 #include <stdlib.h>
19 #include <iostream>
20
21 // Need to override adaptor classes for toolkit test harness, so include
22 // test harness headers before dali headers.
23 #include <dali-toolkit-test-suite-utils.h>
24
25 #include <dali-toolkit/dali-toolkit.h>
26 #include <dali-toolkit/devel-api/controls/bubble-effect/bubble-emitter.h>
27 #include <dali.h>
28 #include <dali/public-api/rendering/renderer.h>
29
30 using namespace Dali;
31 using namespace Dali::Toolkit;
32
33 void utc_dali_toolkit_bubble_emitter_startup(void)
34 {
35   test_return_value = TET_UNDEF;
36 }
37
38 void utc_dali_toolkit_bubble_emitter_cleanup(void)
39 {
40   test_return_value = TET_PASS;
41 }
42
43 namespace
44 {
45 const int RENDER_FRAME_INTERVAL = 16;
46
47 static bool gObjectCreatedCallBackCalled;
48 static void TestCallback(BaseHandle handle)
49 {
50   gObjectCreatedCallBackCalled = true;
51 }
52
53 /*
54  * Simulate time passed by.
55  *
56  * @note this will always process at least 1 frame (1/60 sec)
57  *
58  * @param application Test application instance
59  * @param duration Time to pass in milliseconds.
60  * @return The actual time passed in milliseconds
61  */
62 static int Wait(ToolkitTestApplication& application, int duration = 0)
63 {
64   int time = 0;
65
66   for(int i = 0; i <= (duration / RENDER_FRAME_INTERVAL); i++)
67   {
68     application.SendNotification();
69     application.Render(RENDER_FRAME_INTERVAL);
70     time += RENDER_FRAME_INTERVAL;
71   }
72
73   return time;
74 }
75
76 static Texture CreateSolidColorTexture(ToolkitTestApplication& application, const Vector4& color, unsigned int width, unsigned int height)
77 {
78   Texture texture = Texture::New(TextureType::TEXTURE_2D, Pixel::RGBA8888, width, height);
79
80   int      bufferSize = width * height * GetBytesPerPixel(Pixel::RGBA8888);
81   uint8_t* buffer     = reinterpret_cast<uint8_t*>(malloc(bufferSize));
82
83   for(uint32_t i = 0; i < width * height; ++i)
84   {
85     buffer[i * 4 + 0] = static_cast<uint8_t>(color.r * 255.0f);
86     buffer[i * 4 + 1] = static_cast<uint8_t>(color.g * 255.0f);
87     buffer[i * 4 + 2] = static_cast<uint8_t>(color.b * 255.0f);
88     buffer[i * 4 + 3] = static_cast<uint8_t>(color.a * 255.0f);
89   }
90
91   PixelData pixelData = PixelData::New(buffer, bufferSize, width, height, Pixel::RGBA8888, PixelData::FREE);
92   texture.Upload(pixelData, 0u, 0u, 0u, 0u, width, height);
93
94   return texture;
95 }
96 } //namespace
97
98 int UtcDaliBubbleEmitterNew(void)
99 {
100   ToolkitTestApplication application;
101
102   tet_infoline(" UtcDaliBubbleEmitterNew ");
103
104   // Test default constructor
105   BubbleEmitter emitter;
106   DALI_TEST_CHECK(!emitter);
107
108   // Test object creation
109   Texture shapeImage = CreateSolidColorTexture(application, Color::GREEN, 5, 5);
110   emitter            = BubbleEmitter::New(Vector2(50.f, 50.f), shapeImage, 200, Vector2(5.f, 10.f));
111   DALI_TEST_CHECK(emitter);
112
113   // Additional check to ensure object is created by checking if it's registered
114   ObjectRegistry registry = application.GetCore().GetObjectRegistry();
115   DALI_TEST_CHECK(registry);
116   gObjectCreatedCallBackCalled = false;
117   registry.ObjectCreatedSignal().Connect(&TestCallback);
118   {
119     BubbleEmitter emitter = BubbleEmitter::New(Vector2(50.f, 50.f), shapeImage, 200, Vector2(5.f, 10.f));
120   }
121   DALI_TEST_CHECK(gObjectCreatedCallBackCalled);
122
123   // Test copy constructor
124   BubbleEmitter emitterCopy(emitter);
125   DALI_TEST_CHECK(emitterCopy);
126
127   // Test down cast
128   Handle handleEmitter;
129   handleEmitter                 = emitter;
130   BubbleEmitter downCastEmitter = BubbleEmitter::DownCast(handleEmitter);
131   DALI_TEST_CHECK(downCastEmitter);
132   END_TEST;
133 }
134
135 int UtcDaliBubbleEmitterDownCast01(void)
136 {
137   ToolkitTestApplication application;
138
139   tet_infoline(" UtcDaliBubbleEmitterDownCast01 ");
140
141   Texture       shapeImage = CreateSolidColorTexture(application, Color::GREEN, 5, 5);
142   BubbleEmitter emitter    = BubbleEmitter::New(Vector2(50.f, 50.f), shapeImage, 200, Vector2(5.f, 10.f));
143
144   BaseHandle    handle(emitter);
145   BubbleEmitter emitter2 = BubbleEmitter::DownCast(handle);
146   DALI_TEST_EQUALS((bool)emitter2, true, TEST_LOCATION);
147   END_TEST;
148 }
149
150 int UtcDaliBubbleEmitterDownCast02(void)
151 {
152   ToolkitTestApplication application;
153
154   tet_infoline(" UtcDaliBubbleEmitterDownCast02 ");
155
156   Handle        handle  = Handle::New(); // Create a custom object
157   BubbleEmitter emitter = BubbleEmitter::DownCast(handle);
158   DALI_TEST_EQUALS((bool)emitter, false, TEST_LOCATION);
159   END_TEST;
160 }
161
162 int UtcDaliBubbleEmitterGetRootActor(void)
163 {
164   ToolkitTestApplication application;
165   tet_infoline(" UtcDaliBubbleEmitterGetRootActor ");
166
167   Texture       shapeImage = CreateSolidColorTexture(application, Color::GREEN, 5, 5);
168   BubbleEmitter emitter    = BubbleEmitter::New(Vector2(50.f, 50.f), shapeImage, 270, Vector2(5.f, 10.f));
169
170   Actor root = emitter.GetRootActor();
171   DALI_TEST_CHECK(root);
172   DALI_TEST_CHECK(root.GetChildCount() == 0);
173   END_TEST;
174 }
175
176 int UtcDaliBubbleEmitterSetBackground(void)
177 {
178   ToolkitTestApplication application;
179   tet_infoline(" UtcDaliBubbleEmitterSetBackground ");
180
181   Texture       shapeImage = CreateSolidColorTexture(application, Color::GREEN, 5, 5);
182   BubbleEmitter emitter    = BubbleEmitter::New(Vector2(50.f, 50.f), shapeImage, 200, Vector2(5.f, 10.f));
183
184   RenderTaskList taskList  = application.GetScene().GetRenderTaskList();
185   unsigned int   taskCount = taskList.GetTaskCount();
186
187   Texture bgImage = CreateSolidColorTexture(application, Color::RED, 50, 50);
188   emitter.SetBackground(bgImage, Vector3(0.f, 0.f, 0.5f));
189
190   DALI_TEST_CHECK(taskList.GetTaskCount() == taskCount + 1);
191
192   Wait(application, 500);
193   DALI_TEST_CHECK(taskList.GetTaskCount() == taskCount);
194   END_TEST;
195 }
196
197 //TODO: test case for BubbleEmitter::SetShapeImage(Image)
198 // To test that the bubble-shape image is successfully switched in the sampler
199 /*int UtcDaliBubbleEmitterSetShapeImage(void)
200 {
201 }*/
202
203 int UtcDaliBubbleEmitterSetBubbleScale(void)
204 {
205   ToolkitTestApplication application;
206   tet_infoline(" UtcDaliBubbleEmitterSetBubbleScale ");
207
208   static std::vector<UniformData> customUniforms =
209     {
210       UniformData("uDynamicScale", Property::Type::FLOAT),
211     };
212
213   TestGraphicsController& graphics = application.GetGraphicsController();
214   graphics.AddCustomUniforms(customUniforms);
215
216   Texture       shapeImage = CreateSolidColorTexture(application, Color::GREEN, 5, 5);
217   BubbleEmitter emitter    = BubbleEmitter::New(Vector2(50.f, 50.f), shapeImage, 150, Vector2(5.f, 10.f));
218   DALI_TEST_CHECK(emitter);
219   Actor root = emitter.GetRootActor();
220   application.GetScene().Add(root);
221   root.SetProperty(Actor::Property::POSITION, Vector3::ZERO);
222   root.SetProperty(Actor::Property::PARENT_ORIGIN, ParentOrigin::CENTER);
223   root.SetProperty(Actor::Property::ANCHOR_POINT, AnchorPoint::CENTER);
224
225   TestGlAbstraction& gl = application.GetGlAbstraction();
226
227   Wait(application);
228
229   float scaleValue;
230   DALI_TEST_CHECK(gl.GetUniformValue<float>("uDynamicScale", scaleValue));
231   DALI_TEST_EQUALS(scaleValue, 1.f, TEST_LOCATION);
232
233   emitter.SetBubbleScale(2.f);
234   Wait(application);
235   DALI_TEST_CHECK(gl.GetUniformValue<float>("uDynamicScale", scaleValue));
236   DALI_TEST_EQUALS(scaleValue, 2.f, TEST_LOCATION);
237
238   emitter.SetBubbleScale(0.5f);
239   Wait(application);
240   DALI_TEST_CHECK(gl.GetUniformValue<float>("uDynamicScale", scaleValue));
241   DALI_TEST_EQUALS(scaleValue, 0.5f, TEST_LOCATION);
242
243   END_TEST;
244 }
245
246 int UtcDaliBubbleEmitterSetBubbleDensity01(void)
247 {
248   ToolkitTestApplication application;
249   tet_infoline(" UtcDaliBubbleEmitterSetBubbleDensity ");
250
251   Texture       shapeImage = CreateSolidColorTexture(application, Color::GREEN, 5, 5);
252   BubbleEmitter emitter    = BubbleEmitter::New(Vector2(50.f, 50.f), shapeImage, 200, Vector2(5.f, 10.f));
253
254   try
255   {
256     emitter.SetBubbleDensity(3.f);
257     DALI_TEST_CHECK(true);
258   }
259   catch(Dali::DaliException& e)
260   {
261     DALI_TEST_PRINT_ASSERT(e);
262     DALI_TEST_ASSERT(e, "density>0 && density<=9", TEST_LOCATION);
263   }
264   END_TEST;
265 }
266
267 int UtcDaliBubbleEmitterSetBubbleDensity02(void)
268 {
269   ToolkitTestApplication application;
270   tet_infoline(" UtcDaliBubbleEmitterSetBubbleDensity ");
271
272   Texture       shapeImage = CreateSolidColorTexture(application, Color::GREEN, 5, 5);
273   BubbleEmitter emitter    = BubbleEmitter::New(Vector2(50.f, 50.f), shapeImage, 200, Vector2(5.f, 10.f));
274
275   try
276   {
277     emitter.SetBubbleDensity(10.f);
278   }
279   catch(Dali::DaliException& e)
280   {
281     DALI_TEST_PRINT_ASSERT(e);
282     DALI_TEST_ASSERT(e, "density > 0 && density <= 9", TEST_LOCATION);
283   }
284   END_TEST;
285 }
286
287 int UtcDaliBubbleEmitterEmitBubble(void)
288 {
289   ToolkitTestApplication application;
290   tet_infoline(" UtcDaliBubbleEmitterEmitBubble ");
291
292   Texture       shapeImage1 = CreateSolidColorTexture(application, Color::GREEN, 5, 5);
293   BubbleEmitter emitter     = BubbleEmitter::New(Vector2(50.f, 50.f), shapeImage1, 200, Vector2(5.f, 10.f));
294
295   Actor    root           = emitter.GetRootActor();
296   Renderer bubbleRenderer = root.GetRendererAt(0);
297   application.GetScene().Add(root);
298   DALI_TEST_CHECK(bubbleRenderer);
299
300   Property::Index propertyIndex0 = bubbleRenderer.GetPropertyIndex("uPercentage[0]");
301   Property::Index propertyIndex1 = bubbleRenderer.GetPropertyIndex("uPercentage[1]");
302   float           value0, value1;
303
304   Animation animation = Animation::New(0.5f);
305   emitter.EmitBubble(animation, Vector2(40.f, 40.f), Vector2(-5.f, -5.f), Vector2(30.f, 30.f));
306   emitter.EmitBubble(animation, Vector2(10.f, 10.f), Vector2(5.f, 5.f), Vector2(30.f, 30.f));
307   (bubbleRenderer.GetProperty(propertyIndex0)).Get(value0);
308   (bubbleRenderer.GetProperty(propertyIndex1)).Get(value1);
309   DALI_TEST_EQUALS(value0, 0.f, TEST_LOCATION);
310   DALI_TEST_EQUALS(value1, 0.f, TEST_LOCATION);
311   (bubbleRenderer.GetCurrentProperty(propertyIndex0)).Get(value0);
312   (bubbleRenderer.GetCurrentProperty(propertyIndex0)).Get(value1);
313   DALI_TEST_EQUALS(value0, 0.f, TEST_LOCATION);
314   DALI_TEST_EQUALS(value1, 0.f, TEST_LOCATION);
315
316   animation.Play();
317
318   Wait(application, 300);
319   propertyIndex0 = bubbleRenderer.GetPropertyIndex("uPercentage[0]");
320   propertyIndex1 = bubbleRenderer.GetPropertyIndex("uPercentage[1]");
321   (bubbleRenderer.GetCurrentProperty(propertyIndex0)).Get(value0);
322   (bubbleRenderer.GetCurrentProperty(propertyIndex0)).Get(value1);
323   DALI_TEST_CHECK(value0 >= 0.6f);
324   DALI_TEST_CHECK(value1 >= 0.6f);
325
326   Wait(application, 500);
327   (bubbleRenderer.GetCurrentProperty(propertyIndex0)).Get(value0);
328   (bubbleRenderer.GetCurrentProperty(propertyIndex0)).Get(value1);
329   DALI_TEST_EQUALS(value0, 1.f, TEST_LOCATION);
330   DALI_TEST_EQUALS(value1, 1.f, TEST_LOCATION);
331   END_TEST;
332 }
333
334 int UtcDaliBubbleEmitterRestore(void)
335 {
336   ToolkitTestApplication application;
337   tet_infoline(" UtcDaliBubbleEmitterRestore ");
338
339   static std::vector<UniformData> customUniforms =
340     {
341       UniformData("uPercentage[90]", Property::Type::FLOAT),
342       UniformData("uStartEndPosition[90]", Property::Type::VECTOR4),
343     };
344
345   TestGraphicsController& graphics = application.GetGraphicsController();
346   graphics.AddCustomUniforms(customUniforms);
347
348   Vector2       movementArea(50.f, 50.f);
349   Texture       shapeImage = CreateSolidColorTexture(application, Color::GREEN, 5, 5);
350   BubbleEmitter emitter    = BubbleEmitter::New(movementArea, shapeImage, 90, Vector2(5.f, 10.f));
351   Actor         root       = emitter.GetRootActor();
352   application.GetScene().Add(root);
353   root.SetProperty(Actor::Property::POSITION, Vector3::ZERO);
354   root.SetProperty(Actor::Property::PARENT_ORIGIN, ParentOrigin::CENTER);
355   root.SetProperty(Actor::Property::ANCHOR_POINT, AnchorPoint::CENTER);
356
357   Renderer renderer = root.GetRendererAt(0);
358   DALI_TEST_CHECK(renderer);
359
360   TestGlAbstraction& gl = application.GetGlAbstraction();
361
362   float   percentageValue;
363   Vector4 startEndPosValue;
364
365   Animation animation = Animation::New(0.5f);
366   emitter.EmitBubble(animation, Vector2(40.f, 40.f), Vector2(-5.f, -5.f), Vector2(30.f, 30.f));
367
368   Wait(application);
369
370   DALI_TEST_CHECK(gl.GetUniformValue<float>("uPercentage[0]", percentageValue));
371   DALI_TEST_EQUALS(percentageValue, 0.f, TEST_LOCATION);
372
373   DALI_TEST_CHECK(gl.GetUniformValue<Vector4>("uStartEndPosition[0]", startEndPosValue));
374   DALI_TEST_EQUALS(startEndPosValue.x, 40.f - movementArea.x * 0.5f, TEST_LOCATION);
375   DALI_TEST_EQUALS(startEndPosValue.y, 40.f - movementArea.x * 0.5f, TEST_LOCATION);
376
377   animation.Play();
378   Wait(application, 200);
379   animation.Clear();
380
381   DALI_TEST_CHECK(gl.GetUniformValue<float>("uPercentage[0]", percentageValue));
382   DALI_TEST_CHECK(percentageValue < 0.5f && percentageValue >= 0.4);
383
384   DALI_TEST_CHECK(gl.GetUniformValue<Vector4>("uStartEndPosition[0]", startEndPosValue));
385   DALI_TEST_EQUALS(startEndPosValue.x, 40.f - movementArea.x * 0.5f, TEST_LOCATION);
386   DALI_TEST_EQUALS(startEndPosValue.y, 40.f - movementArea.x * 0.5f, TEST_LOCATION);
387
388   emitter.Restore();
389   application.SendNotification();
390   application.Render();
391
392   DALI_TEST_CHECK(gl.GetUniformValue<float>("uPercentage[0]", percentageValue));
393   DALI_TEST_EQUALS(percentageValue, 0.f, TEST_LOCATION);
394
395   DALI_TEST_CHECK(gl.GetUniformValue<Vector4>("uStartEndPosition[0]", startEndPosValue));
396   DALI_TEST_EQUALS(startEndPosValue, Vector4::ZERO, TEST_LOCATION);
397
398   END_TEST;
399 }