dcae5dc12dd38862a36a235076694926f4940ece
[platform/core/uifw/dali-core.git] / automated-tests / src / dali / utc-Dali-ShaderEffect.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 #include <iostream>
19
20 #include <stdlib.h>
21 #include <dali/public-api/dali-core.h>
22 #include <dali-test-suite-utils.h>
23
24 using namespace Dali;
25
26 void utc_dali_shader_effect_startup(void)
27 {
28   test_return_value = TET_UNDEF;
29 }
30
31 void utc_dali_shader_effect_cleanup(void)
32 {
33   test_return_value = TET_PASS;
34 }
35
36 namespace
37 {
38
39 static const char* VertexSource =
40 "This is a custom vertex shader\n"
41 "made on purpose to look nothing like a normal vertex shader inside dali\n";
42
43 static const char* FragmentSource =
44 "This is a custom fragment shader\n"
45 "made on purpose to look nothing like a normal fragment shader inside dali\n";
46
47 static const char* FragmentSourceUsingExtensions =
48 "This is a custom fragment shader using extensions\n"
49 "made on purpose to look nothing like a normal fragment shader inside dali\n";
50
51 const int GETSOURCE_BUFFER_SIZE = 0x10000;
52
53
54 struct TestConstraintToVector3
55 {
56   TestConstraintToVector3(Vector3 target)
57   : mTarget(target)
58   {
59   }
60
61   Vector3 operator()(const Vector3& current)
62   {
63     return mTarget;
64   }
65
66   Vector3 mTarget;
67 };
68
69 struct TestConstraintFromPositionToVector3
70 {
71   TestConstraintFromPositionToVector3()
72   {
73   }
74
75   Vector3 operator()(const Vector3& current, const PropertyInput& position)
76   {
77
78     return position.GetVector3();
79   }
80 };
81
82 struct TestConstraintToVector3Double
83 {
84   TestConstraintToVector3Double(Vector3 target)
85   : mTarget(target)
86   {
87   }
88
89   Vector3 operator()(const Vector3& current)
90   {
91     return mTarget * 2.0f;
92   }
93
94   Vector3 mTarget;
95 };
96
97 class ShaderEffectExtension : public ShaderEffect::Extension {};
98
99
100 class TestExtension : public ShaderEffect::Extension
101 {
102 public:
103   TestExtension( bool& deleted )
104   : mDeleted(deleted)
105   {
106     mDeleted = false;
107   }
108   ~TestExtension()
109   {
110     mDeleted = true;
111   }
112   bool IsAlive() const
113   {
114     return !mDeleted;
115   }
116 private:
117   bool& mDeleted;
118 };
119
120 static const char* TestImageFilename = "icon_wrt.png";
121
122 Integration::Bitmap* CreateBitmap( unsigned int imageHeight, unsigned int imageWidth, unsigned int initialColor )
123 {
124   Integration::Bitmap* bitmap = Integration::Bitmap::New( Integration::Bitmap::BITMAP_2D_PACKED_PIXELS, ResourcePolicy::RETAIN );
125   Integration::PixelBuffer* pixbuffer = bitmap->GetPackedPixelsProfile()->ReserveBuffer( Pixel::RGBA8888,  imageWidth,imageHeight,imageWidth,imageHeight );
126   unsigned int bytesPerPixel = GetBytesPerPixel(  Pixel::RGBA8888 );
127
128   memset( pixbuffer,  initialColor , imageHeight*imageWidth*bytesPerPixel);
129
130   return bitmap;
131 }
132
133 } // anon namespace
134
135
136 int UtcDaliShaderEffectMethodNew01(void)
137 {
138   TestApplication application;
139
140   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
141   DALI_TEST_CHECK(effect);
142   END_TEST;
143 }
144
145 int UtcDaliShaderEffectMethodNew02(void)
146 {
147   TestApplication application;
148
149   ShaderEffect effect;
150
151   try
152   {
153     // New must be called to create a ShaderEffect or it wont be valid.
154     effect.SetUniform( "uUniform", 0 );
155     DALI_TEST_CHECK( false );
156   }
157   catch (Dali::DaliException& e)
158   {
159     // Tests that a negative test of an assertion succeeds
160     DALI_TEST_PRINT_ASSERT( e );
161     DALI_TEST_CHECK( !effect );
162   }
163   END_TEST;
164 }
165
166 int UtcDaliShaderEffectMethodNew04(void)
167 {
168   TestApplication application;
169   tet_infoline("Testing prefixed version of Dali::ShaderEffect::New()");
170
171   std::string fragmentShaderPrefix = "#define TEST_FS 1\n#extension GL_OES_standard_derivatives : enable";
172   std::string vertexShaderPrefix = "#define TEST_VS 1";
173
174   try
175   {
176     // Call render to compile default shaders.
177     application.SendNotification();
178     application.Render();
179     application.Render();
180     application.Render();
181
182     GLuint lastShaderCompiledBefore = application.GetGlAbstraction().GetLastShaderCompiled();
183     ShaderEffect effect = ShaderEffect::NewWithPrefix( vertexShaderPrefix, VertexSource,
184                                                        fragmentShaderPrefix, FragmentSourceUsingExtensions,
185                                                        GEOMETRY_TYPE_IMAGE, ShaderEffect::HINT_NONE );
186
187     BufferImage image = CreateBufferImage();
188     ImageActor actor = ImageActor::New( image );
189     actor.SetSize( 100.0f, 100.0f );
190     actor.SetName("TestImageFilenameActor");
191     actor.SetShaderEffect(effect);
192     Stage::GetCurrent().Add(actor);
193
194     application.SendNotification();
195     application.Render();
196     GLuint lastShaderCompiledAfter = application.GetGlAbstraction().GetLastShaderCompiled();
197     bool testResult = false;
198
199     // we should have compiled 2 shaders.
200     DALI_TEST_EQUALS( lastShaderCompiledAfter, lastShaderCompiledBefore + 2, TEST_LOCATION );
201
202     char testVertexSourceResult[GETSOURCE_BUFFER_SIZE];
203     char testFragmentSourceResult[GETSOURCE_BUFFER_SIZE];
204
205      // we are interested in the first two.
206     GLuint vertexShaderId = lastShaderCompiledBefore + 1;
207     GLuint fragmentShaderId = lastShaderCompiledBefore + 2;
208
209     GLsizei lengthVertexResult;
210     GLsizei lengthFragmentResult;
211
212     application.GetGlAbstraction().GetShaderSource(vertexShaderId, GETSOURCE_BUFFER_SIZE, &lengthVertexResult, testVertexSourceResult);
213     application.GetGlAbstraction().GetShaderSource(fragmentShaderId, GETSOURCE_BUFFER_SIZE, &lengthFragmentResult, testFragmentSourceResult);
214
215     int vertexShaderHasPrefix = strncmp(testVertexSourceResult, "#define ", strlen("#define "));
216     int fragmentShaderHasPrefix = strncmp(testFragmentSourceResult, "#define ", strlen("#define "));
217     testResult = (vertexShaderHasPrefix == 0) && (fragmentShaderHasPrefix == 0);
218
219     DALI_TEST_CHECK(testResult);
220   }
221   catch(Dali::DaliException& e)
222   {
223     DALI_TEST_PRINT_ASSERT( e );
224     tet_result( TET_FAIL );
225   }
226   END_TEST;
227 }
228
229 int UtcDaliShaderEffectMethodNew05(void)
230 {
231   TestApplication application;
232
233   // heap constructor / destructor
234   DefaultFunctionCoverage<ShaderEffect> shaderEffect;
235   DefaultFunctionCoverage<ShaderEffectExtension> shaderEffectExtension;
236
237   END_TEST;
238 }
239
240 int UtcDaliShaderEffectMethodDownCast(void)
241 {
242   TestApplication application;
243   tet_infoline("Testing Dali::ShaderEffect::DownCast()");
244
245   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
246
247   BaseHandle object(effect);
248
249   ShaderEffect effect2 = ShaderEffect::DownCast(object);
250   DALI_TEST_CHECK(effect2);
251
252   ShaderEffect effect3 = DownCast< ShaderEffect >(object);
253   DALI_TEST_CHECK(effect3);
254
255   BaseHandle unInitializedObject;
256   ShaderEffect effect4 = ShaderEffect::DownCast(unInitializedObject);
257   DALI_TEST_CHECK(!effect4);
258
259   ShaderEffect effect5 = DownCast< ShaderEffect >(unInitializedObject);
260   DALI_TEST_CHECK(!effect5);
261   END_TEST;
262 }
263
264 int UtcDaliShaderEffectMethodDelete01(void)
265 {
266    TestApplication application;
267
268    // get the default shaders built, this is not required but makes it
269    // easier to debug the TET case and isolate the custom shader compilation.
270    application.SendNotification();
271    application.Render();
272
273    GLuint beforeShaderCompiled = application.GetGlAbstraction().GetLastShaderCompiled();
274
275    // create a new shader effect
276    // the vertex and fragment shader will be cached in the ShaderFactory
277    ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
278
279    // destroy the shader effect
280    effect.Reset();
281
282    // Create the same shader effect again, this should now use the cached version
283    // held in the shader factory
284    effect= ShaderEffect::New( VertexSource, FragmentSource );
285
286    // Compile the shader effect
287    application.SendNotification();
288    application.Render();
289
290    GLuint lastShaderCompiled = application.GetGlAbstraction().GetLastShaderCompiled();
291    // no shaders were compiled as they are now compiled on demand and this shader was not used
292    DALI_TEST_EQUALS( beforeShaderCompiled, lastShaderCompiled, TEST_LOCATION );
293
294    END_TEST;
295 }
296
297 int UtcDaliShaderEffectMethodSetUniformFloat(void)
298 {
299   TestApplication application;
300
301   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
302   DALI_TEST_CHECK( effect );
303
304   BufferImage image = CreateBufferImage();
305
306   effect.SetUniform( "uFloat", 1.0f );
307
308   ImageActor actor = ImageActor::New( image );
309   actor.SetSize( 100.0f, 100.0f );
310   actor.SetName("TestImageFilenameActor");
311   actor.SetShaderEffect(effect);
312   Stage::GetCurrent().Add(actor);
313
314   application.SendNotification();
315   application.Render();
316
317   DALI_TEST_CHECK(
318       application.GetGlAbstraction().CheckUniformValue(
319           "uFloat", 1.0f ) );
320   END_TEST;
321 }
322
323 int UtcDaliShaderEffectMethodSetUniformVector2(void)
324 {
325   TestApplication application;
326
327   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
328   DALI_TEST_CHECK( effect );
329
330   BufferImage image = CreateBufferImage();
331
332   effect.SetUniform( "uVec2", Vector2( 2.0f, 3.0f ) );
333
334   ImageActor actor = ImageActor::New( image );
335   actor.SetSize( 100.0f, 100.0f );
336   actor.SetName("TestImageFilenameActor");
337   actor.SetShaderEffect(effect);
338   Stage::GetCurrent().Add(actor);
339
340   application.SendNotification();
341   application.Render();
342
343   DALI_TEST_CHECK(
344       application.GetGlAbstraction().CheckUniformValue(
345           "uVec2", Vector2( 2.0f, 3.0f ) ) );
346   END_TEST;
347 }
348
349 int UtcDaliShaderEffectMethodSetUniformVector3(void)
350 {
351   TestApplication application;
352
353   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
354   DALI_TEST_CHECK( effect );
355
356   BufferImage image = CreateBufferImage();
357
358   effect.SetUniform( "uVec3", Vector3( 4.0f, 5.0f, 6.0f ) );
359
360   ImageActor actor = ImageActor::New( image );
361   actor.SetSize( 100.0f, 100.0f );
362   actor.SetName("TestImageFilenameActor");
363   actor.SetShaderEffect(effect);
364   Stage::GetCurrent().Add(actor);
365
366   application.SendNotification();
367   application.Render();
368
369   DALI_TEST_CHECK(
370       application.GetGlAbstraction().CheckUniformValue(
371           "uVec3", Vector3( 4.0f, 5.0f, 6.0f ) ) );
372   END_TEST;
373 }
374
375 int UtcDaliShaderEffectMethodSetUniformVector4(void)
376 {
377   TestApplication application;
378
379   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
380   DALI_TEST_CHECK( effect );
381
382   BufferImage image = CreateBufferImage();
383
384   effect.SetUniform( "uVec4", Vector4( 7.0f, 8.0f, 9.0f, 10.0f ) );
385
386   ImageActor actor = ImageActor::New( image );
387   actor.SetSize( 100.0f, 100.0f );
388   actor.SetName("TestImageFilenameActor");
389   actor.SetShaderEffect(effect);
390   Stage::GetCurrent().Add(actor);
391
392   application.SendNotification();
393   application.Render();
394
395   DALI_TEST_CHECK(
396       application.GetGlAbstraction().CheckUniformValue(
397           "uVec4", Vector4( 7.0f, 8.0f, 9.0f, 10.0f ) ) );
398   END_TEST;
399 }
400
401 int UtcDaliShaderEffectMethodSetUniformMatrix(void)
402 {
403   TestApplication application;
404
405   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
406   DALI_TEST_CHECK( effect );
407
408   BufferImage image = CreateBufferImage();
409
410   effect.SetUniform( "uModelView", Matrix::IDENTITY );
411
412   ImageActor actor = ImageActor::New( image );
413   actor.SetSize( 100.0f, 100.0f );
414   actor.SetName("TestImageFilenameActor");
415   actor.SetShaderEffect(effect);
416   Stage::GetCurrent().Add(actor);
417
418   application.SendNotification();
419   application.Render();
420
421   DALI_TEST_CHECK(
422       application.GetGlAbstraction().CheckUniformValue(
423           "uModelView", Matrix::IDENTITY ) );
424   END_TEST;
425 }
426
427 int UtcDaliShaderEffectMethodSetUniformMatrix3(void)
428 {
429   TestApplication application;
430
431   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
432   DALI_TEST_CHECK( effect );
433
434   BufferImage image = CreateBufferImage();
435
436   Matrix3 matIdentity(1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f);
437   effect.SetUniform( "uMatrix3", matIdentity );
438
439   ImageActor actor = ImageActor::New( image );
440   actor.SetSize( 100.0f, 100.0f );
441   actor.SetName("TestImageFilenameActor");
442   actor.SetShaderEffect(effect);
443   Stage::GetCurrent().Add(actor);
444
445   application.SendNotification();
446   application.Render();
447
448   DALI_TEST_CHECK( application.GetGlAbstraction().CheckUniformValue("uMatrix3", matIdentity) );
449   END_TEST;
450 }
451
452 int UtcDaliShaderEffectMethodSetUniformViewport(void)
453 {
454   TestApplication application;
455
456   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
457   DALI_TEST_CHECK( effect );
458
459   BufferImage image = CreateBufferImage();
460
461   ImageActor actor = ImageActor::New( image );
462   actor.SetSize( 100.0f, 100.0f );
463   actor.SetName("TestImageFilenameActor");
464   actor.SetShaderEffect(effect);
465   Stage::GetCurrent().Add(actor);
466
467   effect.SetUniform( "uVec2", Vector2( 0.0f, 0.0f ), ShaderEffect::COORDINATE_TYPE_VIEWPORT_POSITION );
468   effect.SetUniform( "uVec2Dir", Vector2( 1.0f, 2.0f ), ShaderEffect::COORDINATE_TYPE_VIEWPORT_DIRECTION );
469
470   application.SendNotification();
471   application.Render();
472
473   const Vector2& stageSize(Stage::GetCurrent().GetSize());
474
475   DALI_TEST_CHECK( application.GetGlAbstraction().CheckUniformValue( "uVec2", Vector2( stageSize.x/2, -stageSize.y/2 ) ) );
476
477   DALI_TEST_CHECK( application.GetGlAbstraction().CheckUniformValue( "uVec2Dir", Vector2( -1.0f, 2.0f ) ) );
478
479   // change coordinate types
480   effect.SetUniform( "uVec2", Vector2( 0.1f, 0.2f ), ShaderEffect::COORDINATE_TYPE_DEFAULT );
481   effect.SetUniform( "uVec2Dir", Vector2( 1.0f, 2.0f ), ShaderEffect::COORDINATE_TYPE_VIEWPORT_POSITION );
482   actor.SetPixelArea( ImageActor::PixelArea( 0, 0, 10, 10 ) );
483
484   application.SendNotification();
485   application.Render();
486
487   Vector2 outValue;
488   application.GetGlAbstraction().GetUniformValue( "uVec2", outValue );
489   DALI_TEST_EQUALS( outValue, Vector2( 0.1f, 0.2f ), TEST_LOCATION );
490
491   application.GetGlAbstraction().GetUniformValue( "uVec2Dir", outValue );
492   DALI_TEST_EQUALS( outValue, Vector2( stageSize.x *.5f - 1.f, -stageSize.y * .5f + 2.f), TEST_LOCATION );
493
494   END_TEST;
495 }
496
497 int UtcDaliShaderEffectMethodSetEffectImage(void)
498 {
499   TestApplication application;
500
501   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
502   DALI_TEST_CHECK( effect );
503
504   BufferImage image = CreateBufferImage();
505
506   effect.SetEffectImage(image);
507
508   ImageActor actor = ImageActor::New( image );
509   actor.SetSize( 100.0f, 100.0f );
510   actor.SetName("TestImageFilenameActor");
511   actor.SetShaderEffect(effect);
512   Stage::GetCurrent().Add(actor);
513
514   application.SendNotification();
515   application.Render(16);
516   application.SendNotification();
517   application.Render(16);
518   application.SendNotification();
519
520   GLuint programId, uniformId;
521   bool uniformWasSet = application.GetGlAbstraction().GetUniformIds( "sEffect", programId, uniformId );
522   // we dont care about the value of the sampler uniform as thats internal to DALi core and subject to change
523   DALI_TEST_CHECK( uniformWasSet );
524   END_TEST;
525 }
526
527 int UtcDaliShaderEffectMethodSetEffectImageAndDelete(void)
528 {
529   TestApplication application;
530
531   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
532
533   BufferImage effectImage = CreateBufferImage();
534   effect.SetEffectImage(effectImage);
535
536   ImageActor actor = ImageActor::New();
537
538   actor.SetShaderEffect(effect);
539   effect.Reset();
540
541   Stage::GetCurrent().Add(actor);
542
543   // do an update / render cycle
544   application.SendNotification();
545   application.Render(16);
546   application.SendNotification();
547   application.Render(16);
548   application.SendNotification();
549   application.Render(16);
550
551   printf("removing image actor from stage and Reseting handle\n");
552   Stage::GetCurrent().Remove(actor);
553   actor.Reset();
554
555   tet_printf("### Update & Render  \n");
556
557   application.SendNotification();
558   application.Render(16);
559
560   tet_printf("#### Update Only  \n");
561
562   tet_printf("effectImage.Reset \n");
563
564   // this releases the effect texture resource,
565   // Update will send a DispatchDiscardTexture message to render
566   effectImage.Reset();
567   application.SendNotification();
568   application.UpdateOnly(16);
569
570   tet_printf("#### Update Only \n");
571
572   // at this point shader is deleted, during clear discard queue
573   // and it sends a Shader:: DispatchRemoveObserver message to render thread
574   application.UpdateOnly(16);
575
576   tet_printf("#### Render Only  \n");
577   // This is where it used to crash, there is a message in the queue to perform DispatchDiscardTexture
578   // which tries to call observer->TextureDiscarded, where observer == shader that was deleted
579   // in previous update.
580   application.RenderOnly();
581
582
583   // process the discard texture message
584   application.RenderOnly();
585   application.SendNotification();
586   application.Render(16);
587
588   tet_result(TET_PASS);
589
590   END_TEST;
591 }
592
593 int UtcDaliShaderEffectMethodApplyConstraint(void)
594 {
595   // Test whether Shader's uniform can be constrained to a stationary constraint.
596   TestApplication application;
597
598   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
599   DALI_TEST_CHECK( effect );
600
601   BufferImage image = CreateBufferImage();
602
603   effect.SetUniform( "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) );
604
605   ImageActor actor = ImageActor::New( image );
606   actor.SetSize( 100.0f, 100.0f );
607   actor.SetName("TestImageFilenameActor");
608   actor.SetShaderEffect(effect);
609   Stage::GetCurrent().Add(actor);
610
611   Property::Index uVecProperty = effect.GetPropertyIndex("uVec3");
612
613   application.SendNotification();
614   application.Render();
615
616   // Test effects of SetUniform...
617   DALI_TEST_CHECK(
618       application.GetGlAbstraction().CheckUniformValue(
619           "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) ) );
620
621   Constraint constraint = Constraint::New<Vector3>( uVecProperty,
622                                                     TestConstraintToVector3(Vector3(4.0f, 9.0f, 16.0f)) );
623
624   effect.ApplyConstraint(constraint);
625
626   application.SendNotification();
627   application.Render();
628
629   // Test effects of Constraint.
630   DALI_TEST_CHECK(
631       application.GetGlAbstraction().CheckUniformValue(
632           "uVec3", Vector3( 4.0f, 9.0f, 16.0f ) ) );
633   END_TEST;
634 }
635
636
637 int UtcDaliShaderEffectMethodApplyConstraintFromActor(void)
638 {
639   // Test whether Shader's uniform can be constrained to Actor's position.
640   TestApplication application;
641
642   const Vector3 targetPosition = Vector3( 100.0f, 70.0f, 20.0f);
643
644   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
645   DALI_TEST_CHECK( effect );
646
647   BufferImage image = CreateBufferImage();
648
649   effect.SetUniform( "uVec3", Vector3( 50.0f, 25.0f, 0.0f ) );
650
651   ImageActor actor = ImageActor::New( image );
652   actor.SetPosition(targetPosition);
653   actor.SetSize( 100.0f, 100.0f );
654   actor.SetName("TestImageFilenameActor");
655   actor.SetShaderEffect(effect);
656   Stage::GetCurrent().Add(actor);
657
658   Property::Index uVecProperty = effect.GetPropertyIndex("uVec3");
659
660   Constraint constraint = Constraint::New<Vector3>( uVecProperty,
661                                                     Source(actor, Actor::Property::Position),
662                                                     TestConstraintFromPositionToVector3() );
663
664   effect.ApplyConstraint(constraint);
665
666   application.SendNotification();
667   application.Render();
668
669   // Test effects of Constraint.
670   DALI_TEST_CHECK(
671       application.GetGlAbstraction().CheckUniformValue(
672           "uVec3", targetPosition ) );
673   END_TEST;
674 }
675
676 int UtcDaliShaderEffectMethodApplyConstraintFromActor2(void)
677 {
678   // Test whether Shader's uniform can be constrained to Actor's position.
679   // While Actor's position is constrained to another point * 2.0f
680   TestApplication application;
681
682   const Vector3 targetPosition = Vector3( 25.0f, 36.0f, 49.0f );
683
684   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
685   DALI_TEST_CHECK( effect );
686
687   BufferImage image = CreateBufferImage();
688
689   effect.SetUniform( "uVec3", Vector3( 50.0f, 25.0f, 0.0f ) );
690
691   ImageActor actor = ImageActor::New( image );
692   actor.SetPosition(Vector3( 100.0f, 70.0f, 20.0f));
693   actor.SetSize( 100.0f, 100.0f );
694   actor.SetName("TestImageFilenameActor");
695   actor.SetShaderEffect(effect);
696   Stage::GetCurrent().Add(actor);
697
698   Property::Index uVecProperty = effect.GetPropertyIndex("uVec3");
699
700   Constraint shaderConstraint = Constraint::New<Vector3>( uVecProperty,
701                                                     Source(actor, Actor::Property::Position),
702                                                     TestConstraintFromPositionToVector3() );
703
704   effect.ApplyConstraint(shaderConstraint);
705
706   Constraint actorConstraint = Constraint::New<Vector3>( Actor::Property::Position,
707                                                          TestConstraintToVector3Double(targetPosition) );
708
709   actor.ApplyConstraint(actorConstraint);
710
711   application.SendNotification();
712   application.Render();
713
714   // Test effects of Constraint.
715   DALI_TEST_CHECK(
716       application.GetGlAbstraction().CheckUniformValue(
717           "uVec3", targetPosition * 2.0f ) );
718   END_TEST;
719 }
720
721 int UtcDaliShaderEffectMethodApplyConstraintCallback(void)
722 {
723   // Test whether Shader's uniform can be constrained to a stationary constraint.
724   TestApplication application;
725
726   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
727   DALI_TEST_CHECK( effect );
728
729   BufferImage image = CreateBufferImage();
730
731   effect.SetUniform( "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) );
732
733   ImageActor actor = ImageActor::New( image );
734   actor.SetSize( 100.0f, 100.0f );
735   actor.SetName("TestImageFilenameActor");
736   actor.SetShaderEffect(effect);
737   Stage::GetCurrent().Add(actor);
738
739   Property::Index uVecProperty = effect.GetPropertyIndex("uVec3");
740
741   application.SendNotification();
742   application.Render();
743
744   // Test effects of SetUniform...
745   DALI_TEST_CHECK(
746       application.GetGlAbstraction().CheckUniformValue(
747           "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) ) );
748
749   Constraint constraint = Constraint::New<Vector3>( uVecProperty,
750                                                     TestConstraintToVector3(Vector3(4.0f, 9.0f, 16.0f)) );
751
752   constraint.SetApplyTime( 10.0f );
753
754   bool constraintCheck( false );
755   ConstraintAppliedCheck appliedCheck( constraintCheck );
756
757   // We should receive the "Applied" signal after 10 seconds
758   ActiveConstraint active = effect.ApplyConstraint(constraint);
759   active.AppliedSignal().Connect( &application, appliedCheck );
760
761   application.SendNotification();
762   application.Render(static_cast<unsigned int>(1000.0f)); // 1 elapsed second
763
764   // Check signal has not fired
765   application.SendNotification();
766   appliedCheck.CheckSignalNotReceived();
767
768   application.Render(static_cast<unsigned int>(4000.0f)); // 5 elapsed seconds
769
770   // Check signal has not fired
771   application.SendNotification();
772   appliedCheck.CheckSignalNotReceived();
773
774   application.Render(static_cast<unsigned int>(5000.0f - 1.0f)); // <10 elapsed seconds
775
776   // Check signal has not fired
777   application.SendNotification();
778   appliedCheck.CheckSignalNotReceived();
779
780   application.Render(static_cast<unsigned int>(2.0f)); // >10 elapsed seconds
781
782   // Signal should have fired
783   application.SendNotification();
784   appliedCheck.CheckSignalReceived();
785
786   // Test effects of Constraint.
787   DALI_TEST_CHECK(
788       application.GetGlAbstraction().CheckUniformValue(
789           "uVec3", Vector3( 4.0f, 9.0f, 16.0f ) ) );
790   END_TEST;
791 }
792
793 int UtcDaliShaderEffectMethodRemoveConstraints(void)
794 {
795   // Test if constrains can be removed before they are ever applyed.
796   TestApplication application;
797
798   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
799   DALI_TEST_CHECK( effect );
800
801   BufferImage image = CreateBufferImage();
802
803   effect.SetUniform( "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) );
804
805   ImageActor actor = ImageActor::New( image );
806   actor.SetSize( 100.0f, 100.0f );
807   actor.SetName("TestImageFilenameActor");
808   actor.SetShaderEffect(effect);
809   Stage::GetCurrent().Add(actor);
810
811   Property::Index uVecProperty = effect.GetPropertyIndex("uVec3");
812
813   application.SendNotification();
814   application.Render();
815
816   // Test effects of SetUniform...
817   DALI_TEST_CHECK(
818       application.GetGlAbstraction().CheckUniformValue(
819           "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) ) );
820
821   Constraint constraint = Constraint::New<Vector3>( uVecProperty,
822                                                     TestConstraintToVector3(Vector3(4.0f, 9.0f, 16.0f)) );
823
824   effect.ApplyConstraint(constraint);
825
826   // Remove the constraints
827   effect.RemoveConstraints();
828
829   application.SendNotification();
830   application.Render();
831
832   // Test effects of Constraint.
833   DALI_TEST_CHECK(
834       application.GetGlAbstraction().CheckUniformValue(
835           "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) ) );
836   END_TEST;
837 }
838
839 int UtcDaliShaderEffectMethodRemoveConstraints2(void)
840 {
841   // Test whether Shader's uniform constrains can be removed after they are applyed.
842   TestApplication application;
843
844   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
845   DALI_TEST_CHECK( effect );
846
847   BufferImage image = CreateBufferImage();
848
849   effect.SetUniform( "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) );
850
851   ImageActor actor = ImageActor::New( image );
852   actor.SetSize( 100.0f, 100.0f );
853   actor.SetName("TestImageFilenameActor");
854   actor.SetShaderEffect(effect);
855   Stage::GetCurrent().Add(actor);
856
857   Property::Index uVecProperty = effect.GetPropertyIndex("uVec3");
858
859   application.SendNotification();
860   application.Render();
861
862   // Test effects of SetUniform...
863   DALI_TEST_CHECK(
864       application.GetGlAbstraction().CheckUniformValue(
865           "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) ) );
866
867   Constraint constraint = Constraint::New<Vector3>( uVecProperty,
868                                                     TestConstraintToVector3(Vector3(4.0f, 9.0f, 16.0f)) );
869
870   effect.ApplyConstraint(constraint);
871
872   application.SendNotification();
873   application.Render();
874
875   // Reset the value and remove the constraints
876   effect.SetUniform( "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) );
877   effect.RemoveConstraints();
878
879   application.SendNotification();
880   application.Render();
881
882   // Test effects of Constraint.
883   DALI_TEST_CHECK(
884       application.GetGlAbstraction().CheckUniformValue(
885           "uVec3", Vector3( 1.0f, 2.0f, 3.0f ) ) );
886   END_TEST;
887 }
888
889 int UtcDaliShaderEffectMethodCreateExtension(void)
890 {
891   // Test creation of a shader extension
892   TestApplication aplication;
893
894   bool deleted;
895   {
896     ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
897     DALI_TEST_CHECK( effect );
898
899     TestExtension* extension = new TestExtension ( deleted );
900
901     effect.AttachExtension( extension );
902
903     DALI_TEST_CHECK( static_cast<TestExtension&>(effect.GetExtension()).IsAlive() );
904   }
905
906   DALI_TEST_CHECK( deleted );
907   END_TEST;
908 }
909
910 int UtcDaliShaderEffectMethodCreateExtension2(void)
911 {
912   // Test creation of a shader extension
913   bool deleted;
914   {
915     TestApplication application;
916
917     ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
918     DALI_TEST_CHECK( effect );
919
920     BufferImage image = CreateBufferImage();
921
922     effect.SetUniform( "uFloat", 1.0f );
923
924     ImageActor actor = ImageActor::New( image );
925     actor.SetSize( 100.0f, 100.0f );
926     actor.SetName("TestImageFilenameActor");
927     actor.SetShaderEffect(effect);
928     Stage::GetCurrent().Add(actor);
929
930     application.SendNotification();
931     application.Render();
932
933     TestExtension* extension = new TestExtension ( deleted );
934
935     effect.AttachExtension( extension );
936
937     const ShaderEffect& constEffect(effect);
938     const TestExtension& ext( static_cast<const TestExtension&>(constEffect.GetExtension()) );
939
940     DALI_TEST_CHECK( ext.IsAlive() );
941   }
942
943   DALI_TEST_CHECK( deleted );
944   END_TEST;
945 }
946
947 int UtcDaliShaderEffectMethodNoExtension(void)
948 {
949   TestApplication application;
950
951   ShaderEffect effect;
952
953   try
954   {
955     ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
956     DALI_TEST_CHECK( effect );
957
958     // Don't attach extension
959     ShaderEffect::Extension& extension = effect.GetExtension();
960     (void) extension;
961
962     DALI_TEST_CHECK( false );
963   }
964   catch (Dali::DaliException& e)
965   {
966     // Tests that a negative test of an assertion succeeds
967     DALI_TEST_PRINT_ASSERT( e );
968     DALI_TEST_CHECK( !effect );
969   }
970   END_TEST;
971 }
972
973
974 int UtcDaliShaderEffectPropertyIndices(void)
975 {
976   TestApplication application;
977   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
978
979   Property::IndexContainer indices;
980   effect.GetPropertyIndices( indices );
981   DALI_TEST_CHECK( ! indices.empty() );
982   DALI_TEST_EQUALS( indices.size(), effect.GetPropertyCount(), TEST_LOCATION );
983   END_TEST;
984 }
985
986 int UtcDaliShaderBinaries(void)
987 {
988   TestApplication application;
989   // these will not affect the "first round" of dali render as core is already initialized and it has queried the defaults
990   application.GetGlAbstraction().SetBinaryFormats( 1 );
991   application.GetGlAbstraction().SetNumBinaryFormats( 1 );
992   application.GetGlAbstraction().SetProgramBinaryLength( 1 );
993
994   GLuint lastShaderCompiledBefore = application.GetGlAbstraction().GetLastShaderCompiled();
995
996   ShaderEffect effect = ShaderEffect::New( VertexSource, FragmentSource );
997   DALI_TEST_CHECK( effect );
998
999   BufferImage image = CreateBufferImage();
1000   ImageActor actor = ImageActor::New( image );
1001   actor.SetSize( 100.0f, 100.0f );
1002   actor.SetName("TestImageFilenameActor");
1003   actor.SetShaderEffect(effect);
1004   Stage::GetCurrent().Add(actor);
1005
1006   application.SendNotification();
1007   application.Render(16);
1008   // binary was not requested by DALi
1009   DALI_TEST_CHECK( !(application.GetGlAbstraction().GetProgramBinaryCalled()) );
1010
1011   GLuint lastShaderCompiledAfter = application.GetGlAbstraction().GetLastShaderCompiled();
1012
1013   // check that the shader was compiled
1014   DALI_TEST_EQUALS( lastShaderCompiledAfter, lastShaderCompiledBefore + 2, TEST_LOCATION );
1015
1016   // simulate context loss to get core to re-initialize its GL
1017   application.GetCore().ContextDestroyed();
1018   application.GetCore().ContextCreated();
1019
1020   application.SendNotification();
1021   application.Render(16);
1022
1023   // shader is recompiled
1024   GLuint finalShaderCompiled = application.GetGlAbstraction().GetLastShaderCompiled();
1025   // check that the shader was compiled
1026   DALI_TEST_EQUALS( lastShaderCompiledAfter + 2, finalShaderCompiled, TEST_LOCATION );
1027
1028   // binary was requested by DALi
1029   DALI_TEST_CHECK( application.GetGlAbstraction().GetProgramBinaryCalled() );
1030
1031   END_TEST;
1032 }
1033
1034 int UtcDaliShaderEffectFromProperties01(void)
1035 {
1036   TestApplication application;
1037   tet_infoline("UtcDaliShaderEffectFromProperties01()");
1038
1039   std::string fragmentShaderPrefix = "#define TEST_FS 1\n#extension GL_OES_standard_derivatives : enable";
1040   std::string vertexShaderPrefix = "#define TEST_VS 1";
1041   std::string vertexShader(VertexSource);
1042   std::string fragmentShader(FragmentSource);
1043
1044   // Call render to compile default shaders.
1045   application.SendNotification();
1046   application.Render();
1047
1048   GLuint lastShaderCompiledBefore = application.GetGlAbstraction().GetLastShaderCompiled();
1049
1050   // create from type registry
1051
1052   TypeInfo typeInfo = TypeRegistry::Get().GetTypeInfo( "ShaderEffect" );
1053   DALI_TEST_CHECK( typeInfo );
1054   ShaderEffect effect = ShaderEffect::DownCast( typeInfo.CreateInstance() );
1055   DALI_TEST_CHECK( effect );
1056
1057   Property::Value programMap = Property::Value(Property::MAP);
1058
1059   programMap.SetValue("vertex", vertexShader);
1060   programMap.SetValue("fragment", fragmentShader);
1061
1062   programMap.SetValue("vertex-prefix", vertexShaderPrefix);
1063   programMap.SetValue("fragment-prefix", fragmentShaderPrefix);
1064
1065   programMap.SetValue("geometry-type", "GEOMETRY_TYPE_IMAGE");
1066
1067   effect.SetProperty(effect.GetPropertyIndex("program"), programMap);
1068
1069   Property::Value imageMap = Property::Value(Property::MAP);
1070   imageMap.SetValue("filename", Property::Value(TestImageFilename));
1071   effect.SetProperty(effect.GetPropertyIndex("image"), imageMap);
1072
1073   // do a update & render to get the image request
1074   application.SendNotification();
1075   application.Render();
1076
1077   Integration::ResourceRequest* request = application.GetPlatform().GetRequest();
1078   // create the image
1079   Integration::Bitmap* bitmap = CreateBitmap( 10, 10, 0xFF );
1080   Integration::ResourcePointer resourcePtr(bitmap);
1081   TestPlatformAbstraction& platform = application.GetPlatform();
1082   platform.SetResourceLoaded(request->GetId(), request->GetType()->id, resourcePtr);
1083
1084   BufferImage image(CreateBufferImage());
1085   ImageActor actor = ImageActor::New( image );
1086   actor.SetSize( 100.0f, 100.0f );
1087   actor.SetName("TestImageFilenameActor");
1088   actor.SetShaderEffect(effect);
1089   Stage::GetCurrent().Add(actor);
1090
1091   application.SendNotification();
1092   application.Render();
1093   GLuint lastShaderCompiledAfter = application.GetGlAbstraction().GetLastShaderCompiled();
1094
1095   // we should have compiled 2 shaders.
1096   DALI_TEST_EQUALS(lastShaderCompiledAfter, lastShaderCompiledBefore + 2, TEST_LOCATION );
1097
1098   std::string actualVertexShader = application.GetGlAbstraction().GetShaderSource( lastShaderCompiledBefore + 1 );
1099   DALI_TEST_EQUALS( vertexShaderPrefix, actualVertexShader.substr( 0, vertexShaderPrefix.length() ), TEST_LOCATION );
1100   DALI_TEST_EQUALS( vertexShader, actualVertexShader.substr( actualVertexShader.length() - vertexShader.length() ), TEST_LOCATION );
1101
1102   std::string actualFragmentShader = application.GetGlAbstraction().GetShaderSource( lastShaderCompiledBefore + 2 );
1103   DALI_TEST_EQUALS( fragmentShaderPrefix, actualFragmentShader.substr( 0, fragmentShaderPrefix.length() ), TEST_LOCATION );
1104   DALI_TEST_EQUALS( fragmentShader, actualFragmentShader.substr( actualFragmentShader.length() - fragmentShader.length() ), TEST_LOCATION );
1105
1106   END_TEST;
1107 }
1108
1109 int UtcDaliShaderEffectFromProperties02(void)
1110 {
1111   try
1112   {
1113     TestApplication application;
1114     tet_infoline("UtcDaliShaderEffectFromProperties02()");
1115
1116     // Call render to compile default shaders.
1117     application.SendNotification();
1118     application.Render();
1119     application.Render();
1120     application.Render();
1121
1122     // create from type registry (currently only way to get ShaderEffect with no shader setup in constructor
1123     TypeInfo typeInfo = TypeRegistry::Get().GetTypeInfo( "ShaderEffect" );
1124     DALI_TEST_CHECK( typeInfo );
1125     ShaderEffect effect = ShaderEffect::DownCast( typeInfo.CreateInstance() );
1126     DALI_TEST_CHECK( effect );
1127
1128     Property::Value programMap = Property::Value(Property::MAP);
1129
1130     programMap.SetValue("vertex",   std::string(VertexSource));
1131     programMap.SetValue("fragment", std::string(FragmentSource));
1132
1133     // programMap.SetValue("geometry-type", "GEOMETRY_TYPE_IMAGE");
1134     // dont set by value
1135     programMap.SetValue("geometry-type", GeometryType( GEOMETRY_TYPE_IMAGE ));
1136
1137     effect.SetProperty(effect.GetPropertyIndex("program"), programMap);
1138
1139     tet_result( TET_FAIL );
1140   }
1141   catch(Dali::DaliException& e)
1142   {
1143     DALI_TEST_PRINT_ASSERT( e );
1144   }
1145   END_TEST;
1146 }
1147
1148 int UtcDaliShaderEffectFromProperties03(void)
1149 {
1150   try
1151   {
1152     TestApplication application;
1153     tet_infoline("UtcDaliShaderEffectFromProperties03()");
1154
1155     // Call render to compile default shaders.
1156     application.SendNotification();
1157     application.Render();
1158     application.Render();
1159     application.Render();
1160
1161     // create from type registry (currently only way to get ShaderEffect with no shader setup in constructor
1162     TypeInfo typeInfo = TypeRegistry::Get().GetTypeInfo( "ShaderEffect" );
1163     DALI_TEST_CHECK( typeInfo );
1164     ShaderEffect effect = ShaderEffect::DownCast( typeInfo.CreateInstance() );
1165     DALI_TEST_CHECK( effect );
1166
1167     // dont set unknown
1168     effect.SetProperty( effect.GetPropertyIndex("geometry-hints"), "HINT_2" );
1169
1170     tet_result( TET_FAIL );
1171   }
1172   catch(Dali::DaliException& e)
1173   {
1174     DALI_TEST_PRINT_ASSERT( e );
1175   }
1176   END_TEST;
1177 }