2 * Copyright (c) 2022 Samsung Electronics Co., Ltd.
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
8 * http://www.apache.org/licenses/LICENSE-2.0
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.
18 #include <dali-test-suite-utils.h>
19 #include <dali/public-api/dali-core.h>
26 ///////////////////////////////////////////////////////////////////////////////
27 void utc_dali_constraint_startup(void)
29 test_return_value = TET_UNDEF;
32 void utc_dali_constraint_cleanup(void)
34 test_return_value = TET_PASS;
36 ///////////////////////////////////////////////////////////////////////////////
38 ///////////////////////////////////////////////////////////////////////////////
42 * A function to use for a constraint, no data collected.
45 void BasicFunction(T& /* current */, const PropertyInputContainer& /* inputs */)
50 * A functor which sets a given boolean when the functor is called.
53 struct BasicCalledFunctor
55 BasicCalledFunctor(bool& functorCalled)
56 : mCalled(functorCalled)
60 void operator()(T& /* current */, const PropertyInputContainer& /* inputs */)
69 * A functor which increments a given integer when the functor is called.
72 struct CalledCountFunctor
74 CalledCountFunctor(int& callCount)
75 : mCallCount(callCount)
79 void operator()(T& /* current */, const PropertyInputContainer& /* inputs */)
88 * A functor which sets the given value as the value required when the functor is called.
91 struct SetValueFunctor
93 SetValueFunctor(const T& value)
98 void operator()(T& current, const PropertyInputContainer& /* inputs */)
106 } // unnamed namespace
107 ///////////////////////////////////////////////////////////////////////////////
109 ///////////////////////////////////////////////////////////////////////////////
113 // void( *function )( T&, const PropertyInputContainer& ) )
114 ///////////////////////////////////////////////////////////////////////////////
115 namespace UtcDaliConstraintNewFunction
117 bool gConstraintFunctionCalled = false;
118 void ConstraintFunction(Vector3& /* current */, const PropertyInputContainer& /* inputs */)
120 gConstraintFunctionCalled = true;
122 } // namespace UtcDaliConstraintNewFunction
124 int UtcDaliConstraintNewFunctionP(void)
126 // Ensure that we can create a constraint using a C function and that it is called.
128 TestApplication application;
129 UtcDaliConstraintNewFunction::gConstraintFunctionCalled = false;
131 Actor actor = Actor::New();
132 application.GetScene().Add(actor);
134 application.SendNotification();
135 application.Render();
137 DALI_TEST_EQUALS(UtcDaliConstraintNewFunction::gConstraintFunctionCalled, false, TEST_LOCATION);
140 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &UtcDaliConstraintNewFunction::ConstraintFunction);
141 DALI_TEST_CHECK(constraint);
144 application.SendNotification();
145 application.Render();
147 DALI_TEST_EQUALS(UtcDaliConstraintNewFunction::gConstraintFunctionCalled, true, TEST_LOCATION);
152 int UtcDaliConstraintNewFunctionN(void)
154 // Create a constraint with an uninitialised handle
156 TestApplication application;
158 // Add a constraint with an uninitialised handle
161 Constraint constraint = Constraint::New<Vector3>(Actor(), Actor::Property::POSITION, &UtcDaliConstraintNewFunction::ConstraintFunction);
162 DALI_TEST_CHECK(false); // Should not reach here
166 DALI_TEST_CHECK(true); // Should assert!
172 // helper for next test
173 void StringConstraintFunction(std::string& /* current */, const PropertyInputContainer& /* inputs */)
177 int UtcDaliConstraintNewFunctionNonConstrainableTypeN(void)
179 // Ensure that we can create a constraint using a C function and that it is called.
181 TestApplication application;
182 UtcDaliConstraintNewFunction::gConstraintFunctionCalled = false;
184 Actor actor = Actor::New();
185 application.GetScene().Add(actor);
187 application.SendNotification();
188 application.Render();
193 Constraint constraint = Constraint::New<std::string>(actor, Actor::Property::COLOR_MODE, &StringConstraintFunction);
194 DALI_TEST_CHECK(constraint);
196 tet_result(TET_FAIL);
198 catch(Dali::DaliException& e)
200 DALI_TEST_ASSERT(e, "Property not constrainable", TEST_LOCATION);
206 ///////////////////////////////////////////////////////////////////////////////
208 ///////////////////////////////////////////////////////////////////////////////
213 ///////////////////////////////////////////////////////////////////////////////
214 int UtcDaliConstraintNewFunctorP(void)
216 // Ensure that we can create a constraint using a functor and that it is called.
218 TestApplication application;
219 bool functorCalled = false;
221 Actor actor = Actor::New();
222 application.GetScene().Add(actor);
224 application.SendNotification();
225 application.Render();
227 DALI_TEST_EQUALS(functorCalled, false, TEST_LOCATION);
230 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, BasicCalledFunctor<Vector3>(functorCalled));
231 DALI_TEST_CHECK(constraint);
234 application.SendNotification();
235 application.Render();
237 DALI_TEST_EQUALS(functorCalled, true, TEST_LOCATION);
242 int UtcDaliConstraintNewFunctorN(void)
244 // Create a constraint with an uninitialised handle
246 TestApplication application;
247 bool functorCalled = false;
249 // Add a constraint with an uninitialised handle
252 Constraint constraint = Constraint::New<Vector3>(Actor(), Actor::Property::POSITION, BasicCalledFunctor<Vector3>(functorCalled));
253 DALI_TEST_CHECK(false); // Should not reach here
257 DALI_TEST_CHECK(true); // Should assert!
263 ///////////////////////////////////////////////////////////////////////////////
265 ///////////////////////////////////////////////////////////////////////////////
270 // void ( T::*memberFunction ) ( P&, const PropertyInputContainer& ) )
271 ///////////////////////////////////////////////////////////////////////////////
272 namespace UtcDaliConstraintNewFunctorMember
276 Functor(bool& positionCalled, bool& scaleCalled)
277 : mPositionCalled(positionCalled),
278 mScaleCalled(scaleCalled)
282 void Position(Vector3& /* current */, const PropertyInputContainer& /* inputs */)
284 mPositionCalled = true;
287 void Scale(Vector3& /* current */, const PropertyInputContainer& /* inputs */)
292 bool& mPositionCalled;
295 } // namespace UtcDaliConstraintNewFunctorMember
297 int UtcDaliConstraintNewFunctorMemberP(void)
299 // Ensure that we can create a constraint using a functor and that it is called.
301 TestApplication application;
302 bool positionFunctorCalled = false;
303 bool sizeFunctorCalled = false;
305 Actor actor = Actor::New();
306 application.GetScene().Add(actor);
308 application.SendNotification();
309 application.Render();
311 DALI_TEST_EQUALS(positionFunctorCalled, false, TEST_LOCATION);
312 DALI_TEST_EQUALS(sizeFunctorCalled, false, TEST_LOCATION);
314 // Add a constraint that calls Functor::Position
315 Constraint constraint = Constraint::New<Vector3>(
317 Actor::Property::POSITION,
318 UtcDaliConstraintNewFunctorMember::Functor(positionFunctorCalled, sizeFunctorCalled),
319 &UtcDaliConstraintNewFunctorMember::Functor::Position);
320 DALI_TEST_CHECK(constraint);
323 application.SendNotification();
324 application.Render();
326 DALI_TEST_EQUALS(positionFunctorCalled, true, TEST_LOCATION);
327 DALI_TEST_EQUALS(sizeFunctorCalled, false, TEST_LOCATION);
329 // Add another constraint that calls Functor::Size
330 Constraint constraint2 = Constraint::New<Vector3>(
332 Actor::Property::SCALE,
333 UtcDaliConstraintNewFunctorMember::Functor(positionFunctorCalled, sizeFunctorCalled),
334 &UtcDaliConstraintNewFunctorMember::Functor::Scale);
335 DALI_TEST_CHECK(constraint2);
338 application.SendNotification();
339 application.Render();
341 DALI_TEST_EQUALS(positionFunctorCalled, true, TEST_LOCATION);
342 DALI_TEST_EQUALS(sizeFunctorCalled, true, TEST_LOCATION);
347 int UtcDaliConstraintNewFunctorMemberN(void)
349 // Create a constraint with an uninitialised handle
351 TestApplication application;
352 bool positionFunctorCalled = false;
353 bool sizeFunctorCalled = false;
355 // Add a constraint with an uninitialised handle
358 Constraint constraint = Constraint::New<Vector3>(
360 Actor::Property::POSITION,
361 UtcDaliConstraintNewFunctorMember::Functor(positionFunctorCalled, sizeFunctorCalled),
362 &UtcDaliConstraintNewFunctorMember::Functor::Position);
363 DALI_TEST_CHECK(false); // Should not reach here
365 catch(Dali::DaliException& e)
367 DALI_TEST_CHECK(true); // Should assert!
372 ///////////////////////////////////////////////////////////////////////////////
374 ///////////////////////////////////////////////////////////////////////////////
376 ///////////////////////////////////////////////////////////////////////////////
377 int UtcDaliConstraintCloneP(void)
379 // Ensure we can clone for another actor and it's called appropriately
381 TestApplication application;
384 Actor actor = Actor::New();
385 Actor clone = Actor::New();
387 Integration::Scene stage = application.GetScene();
391 application.SendNotification();
392 application.Render();
394 DALI_TEST_EQUALS(calledCount, 0, TEST_LOCATION);
396 // Add a constraint to actor
397 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, CalledCountFunctor<Vector3>(calledCount));
398 DALI_TEST_CHECK(constraint);
401 // Create a clone but don't apply
402 Constraint constraintClone = constraint.Clone(clone);
404 application.SendNotification();
405 application.Render();
407 DALI_TEST_EQUALS(calledCount, 1, TEST_LOCATION);
412 application.SendNotification();
413 application.Render();
415 DALI_TEST_EQUALS(calledCount, 1, TEST_LOCATION);
417 // Apply the clone constraint
418 constraintClone.Apply();
420 application.SendNotification();
421 application.Render();
423 // Should be called once for the new constraint clone and once for the original constraint
424 DALI_TEST_EQUALS(calledCount, 3, TEST_LOCATION);
429 // Change the position of both actors
430 actor.SetProperty(Actor::Property::POSITION, Vector2(100.0f, 100.0f));
431 clone.SetProperty(Actor::Property::POSITION, Vector2(100.0f, 100.0f));
433 application.SendNotification();
434 application.Render();
436 // Functor should have been called twice
437 DALI_TEST_EQUALS(calledCount, 2, TEST_LOCATION);
442 int UtcDaliConstraintCloneN(void)
444 // Attempt to clone an uninitialised constraint should cause an assert
446 TestApplication application;
448 Constraint constraint;
452 Actor actor = Actor::New();
453 Constraint clone = constraint.Clone(actor);
454 DALI_TEST_CHECK(false);
458 DALI_TEST_CHECK(true);
464 namespace UtcDaliConstraintClone
466 void Function(Vector3& /* current */, const PropertyInputContainer& inputs)
468 DALI_TEST_EQUALS(inputs[0]->GetType(), Property::VECTOR3, TEST_LOCATION);
469 DALI_TEST_EQUALS(inputs[1]->GetType(), Property::ROTATION, TEST_LOCATION);
470 DALI_TEST_EQUALS(inputs[2]->GetType(), Property::VECTOR4, TEST_LOCATION);
471 DALI_TEST_EQUALS(inputs[3]->GetType(), Property::BOOLEAN, TEST_LOCATION);
473 } // namespace UtcDaliConstraintClone
475 int UtcDaliConstraintCloneCheckSourcesAndSetters(void)
477 // Ensure all sources, the tag and remove-action are cloned appropriately
479 TestApplication application;
481 Actor actor = Actor::New();
482 Actor clone = Actor::New();
484 Integration::Scene stage = application.GetScene();
488 application.SendNotification();
489 application.Render();
491 // Create a constraint, DON'T Apply it though
492 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &UtcDaliConstraintClone::Function);
493 constraint.AddSource(LocalSource(Actor::Property::SIZE));
494 constraint.AddSource(LocalSource(Actor::Property::ORIENTATION));
495 constraint.AddSource(LocalSource(Actor::Property::COLOR));
496 constraint.AddSource(LocalSource(Actor::Property::VISIBLE));
497 constraint.SetRemoveAction(Constraint::DISCARD);
498 constraint.SetTag(123);
500 // Clone the constraint & apply the clone
501 Constraint constraintClone = constraint.Clone(clone);
502 constraintClone.Apply();
504 application.SendNotification();
505 application.Render();
507 DALI_TEST_EQUALS(constraint.GetRemoveAction(), constraintClone.GetRemoveAction(), TEST_LOCATION);
508 DALI_TEST_EQUALS(constraint.GetTag(), constraintClone.GetTag(), TEST_LOCATION);
512 ///////////////////////////////////////////////////////////////////////////////
514 ///////////////////////////////////////////////////////////////////////////////
515 // Constraint::Constraint( const Constraint& )
516 // Constraint::operator=
517 ///////////////////////////////////////////////////////////////////////////////
518 int UtcDaliConstraintCopyAndAssignment(void)
520 // Ensure copy constructor & assignment operators work
522 TestApplication application;
524 Actor actor = Actor::New();
525 application.GetScene().Add(actor);
527 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &BasicFunction<Vector3>);
528 Constraint copied(constraint);
530 DALI_TEST_CHECK(constraint == copied);
531 DALI_TEST_CHECK(copied != assigned);
533 assigned = constraint;
534 DALI_TEST_CHECK(constraint == assigned);
538 ///////////////////////////////////////////////////////////////////////////////
540 int UtcDaliConstraintMoveConstructor(void)
542 // Ensure copy constructor & assignment operators work
544 TestApplication application;
546 Actor actor = Actor::New();
547 application.GetScene().Add(actor);
549 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &BasicFunction<Vector3>);
550 DALI_TEST_CHECK(constraint);
551 DALI_TEST_EQUALS(1, constraint.GetBaseObject().ReferenceCount(), TEST_LOCATION);
552 DALI_TEST_CHECK(constraint.GetTargetObject() == actor);
554 Constraint moved = std::move(constraint);
555 DALI_TEST_CHECK(moved);
556 DALI_TEST_EQUALS(1, moved.GetBaseObject().ReferenceCount(), TEST_LOCATION);
557 DALI_TEST_CHECK(moved.GetTargetObject() == actor);
558 DALI_TEST_CHECK(!constraint);
563 int UtcDaliConstraintMoveAssignment(void)
565 // Ensure copy constructor & assignment operators work
567 TestApplication application;
569 Actor actor = Actor::New();
570 application.GetScene().Add(actor);
572 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &BasicFunction<Vector3>);
573 DALI_TEST_CHECK(constraint);
574 DALI_TEST_EQUALS(1, constraint.GetBaseObject().ReferenceCount(), TEST_LOCATION);
575 DALI_TEST_CHECK(constraint.GetTargetObject() == actor);
578 moved = std::move(constraint);
579 DALI_TEST_CHECK(moved);
580 DALI_TEST_EQUALS(1, moved.GetBaseObject().ReferenceCount(), TEST_LOCATION);
581 DALI_TEST_CHECK(moved.GetTargetObject() == actor);
582 DALI_TEST_CHECK(!constraint);
587 ///////////////////////////////////////////////////////////////////////////////
588 // Constraint::DownCast
589 ///////////////////////////////////////////////////////////////////////////////
590 int UtcDaliConstraintDownCast(void)
592 // Ensure DownCast works as expected
594 TestApplication application;
596 Actor actor = Actor::New();
597 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &BasicFunction<Vector3>);
599 // Another BaseHandle type
600 Constraint downCast = Constraint::DownCast(actor);
601 DALI_TEST_CHECK(!downCast);
604 downCast = Constraint::DownCast(constraint);
605 DALI_TEST_CHECK(downCast);
607 // An empty constraint
608 downCast = Constraint::DownCast(Constraint());
609 DALI_TEST_CHECK(!downCast);
613 ///////////////////////////////////////////////////////////////////////////////
615 ///////////////////////////////////////////////////////////////////////////////
616 // Constraint::GetTargetObject
617 ///////////////////////////////////////////////////////////////////////////////
618 int UtcDaliConstraintGetTargetObjectP(void)
620 TestApplication application;
622 Actor actor = Actor::New();
623 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &BasicFunction<Vector3>);
624 DALI_TEST_CHECK(constraint.GetTargetObject() == actor);
626 Actor actor2 = Actor::New();
627 DALI_TEST_CHECK(constraint.GetTargetObject() != actor2);
632 int UtcDaliConstraintGetTargetObjectN(void)
634 // Attempt to retrieve from uninitialised constraint
636 TestApplication application;
638 Constraint constraint;
641 Handle handle = constraint.GetTargetObject();
642 DALI_TEST_CHECK(false); // Should not reach here!
646 DALI_TEST_CHECK(true);
651 ///////////////////////////////////////////////////////////////////////////////
653 ///////////////////////////////////////////////////////////////////////////////
654 // Constraint::GetTargetProperty
655 ///////////////////////////////////////////////////////////////////////////////
656 int UtcDaliConstraintGetTargetPropertyP(void)
658 TestApplication application;
660 Actor actor = Actor::New();
661 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &BasicFunction<Vector3>);
662 DALI_TEST_EQUALS(constraint.GetTargetProperty(), (Property::Index)Actor::Property::POSITION, TEST_LOCATION);
667 int UtcDaliConstraintGetTargetPropertyN(void)
669 // Attempt to retrieve from uninitialised constraint
671 TestApplication application;
673 Constraint constraint;
676 Property::Index propertyIndex = constraint.GetTargetProperty();
678 DALI_TEST_CHECK(false); // Should not reach here!
682 DALI_TEST_CHECK(true);
687 ///////////////////////////////////////////////////////////////////////////////
689 ///////////////////////////////////////////////////////////////////////////////
690 // Constraint::SetTag
691 // Constraint::GetTag
692 ///////////////////////////////////////////////////////////////////////////////
693 int UtcDaliConstraintTagP(void)
695 TestApplication application;
697 Actor actor = Actor::New();
698 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &BasicFunction<Vector3>);
699 DALI_TEST_EQUALS(constraint.GetTag(), 0u, TEST_LOCATION);
701 const unsigned int tag = 123;
702 constraint.SetTag(tag);
703 DALI_TEST_EQUALS(constraint.GetTag(), tag, TEST_LOCATION);
708 int UtcDaliConstraintSetTagN(void)
710 // Attempt to set from uninitialised constraint
712 TestApplication application;
714 Constraint constraint;
717 constraint.SetTag(123);
718 DALI_TEST_CHECK(false); // Should not reach here!
722 DALI_TEST_CHECK(true);
728 int UtcDaliConstraintGetTagN(void)
730 // Attempt to retrieve from uninitialised constraint
732 TestApplication application;
734 Constraint constraint;
737 int tag = constraint.GetTag();
739 DALI_TEST_CHECK(false); // Should not reach here!
743 DALI_TEST_CHECK(true);
749 ///////////////////////////////////////////////////////////////////////////////
751 ///////////////////////////////////////////////////////////////////////////////
752 // Constraint::SetRemoveAction
753 // Constraint::GetRemoveAction
754 ///////////////////////////////////////////////////////////////////////////////
755 int UtcDaliConstraintRemoveActionP(void)
757 TestApplication application;
759 Actor actor = Actor::New();
760 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &BasicFunction<Vector3>);
761 DALI_TEST_EQUALS(constraint.GetRemoveAction(), Constraint::DEFAULT_REMOVE_ACTION, TEST_LOCATION);
763 constraint.SetRemoveAction(Constraint::DISCARD);
764 DALI_TEST_EQUALS(constraint.GetRemoveAction(), Constraint::DISCARD, TEST_LOCATION);
766 constraint.SetRemoveAction(Constraint::BAKE);
767 DALI_TEST_EQUALS(constraint.GetRemoveAction(), Constraint::BAKE, TEST_LOCATION);
772 int UtcDaliConstraintSetRemoveActionN(void)
774 // Attempt to set from uninitialised constraint
776 TestApplication application;
778 Constraint constraint;
781 constraint.SetRemoveAction(Constraint::DISCARD);
782 DALI_TEST_CHECK(false); // Should not reach here!
786 DALI_TEST_CHECK(true);
792 int UtcDaliConstraintGetRemoveActionN(void)
794 // Attempt to retrieve from uninitialised constraint
796 TestApplication application;
798 Constraint constraint;
801 Constraint::RemoveAction removeAction = constraint.GetRemoveAction();
803 DALI_TEST_CHECK(false); // Should not reach here!
807 DALI_TEST_CHECK(true);
813 int UtcDaliConstraintBakeRemoveAction(void)
815 // Ensure value is baked when constraint is removed
817 TestApplication application;
819 Actor actor = Actor::New();
820 application.GetScene().Add(actor);
822 application.SendNotification();
823 application.Render();
825 // Should not equal position by default
826 Vector3 position(10.0f, 20.0f, 30.0f);
827 DALI_TEST_CHECK(actor.GetCurrentProperty<Vector3>(Actor::Property::POSITION) != position);
829 // Create a constraint that constrains to position
830 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, SetValueFunctor<Vector3>(position));
831 constraint.SetRemoveAction(Constraint::BAKE);
834 application.SendNotification();
835 application.Render();
837 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector3>(Actor::Property::POSITION), position, TEST_LOCATION);
839 // Remove the constraint, it should still be at position
842 application.SendNotification();
843 application.Render();
845 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector3>(Actor::Property::POSITION), position, TEST_LOCATION);
850 int UtcDaliConstraintDiscardRemoveAction(void)
852 // Ensure value is baked when constraint is removed
854 TestApplication application;
856 Actor actor = Actor::New();
857 application.GetScene().Add(actor);
859 application.SendNotification();
860 application.Render();
862 // Get and store current position
863 Vector3 originalPosition = actor.GetCurrentProperty<Vector3>(Actor::Property::POSITION);
865 // Should not equal position by default
866 Vector3 position(10.0f, 20.0f, 30.0f);
867 DALI_TEST_CHECK(actor.GetCurrentProperty<Vector3>(Actor::Property::POSITION) != position);
869 // Create a constraint that constrains to position
870 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, SetValueFunctor<Vector3>(position));
871 constraint.SetRemoveAction(Constraint::DISCARD);
874 application.SendNotification();
875 application.Render();
877 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector3>(Actor::Property::POSITION), position, TEST_LOCATION);
879 // Remove the constraint, it should still be at position
882 application.SendNotification();
883 application.Render();
885 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector3>(Actor::Property::POSITION), originalPosition, TEST_LOCATION);
886 DALI_TEST_CHECK(actor.GetCurrentProperty<Vector3>(Actor::Property::POSITION) != position);
891 ///////////////////////////////////////////////////////////////////////////////
893 ///////////////////////////////////////////////////////////////////////////////
895 // Constraint::Remove
896 ///////////////////////////////////////////////////////////////////////////////
897 int UtcDaliConstraintApplyRemove(void)
899 // Ensure constraint functors are called appropriately
901 TestApplication application;
902 bool functorCalled = false;
904 Actor actor = Actor::New();
905 application.GetScene().Add(actor);
907 application.SendNotification();
908 application.Render();
910 DALI_TEST_EQUALS(functorCalled, false, TEST_LOCATION);
912 // Create a constraint and apply, functor should be called
913 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, BasicCalledFunctor<Vector3>(functorCalled));
916 application.SendNotification();
917 application.Render();
919 DALI_TEST_EQUALS(functorCalled, true, TEST_LOCATION);
922 functorCalled = false;
924 // Remove the constraint, functor should not be called
927 application.SendNotification();
928 application.Render();
930 DALI_TEST_EQUALS(functorCalled, false, TEST_LOCATION);
932 // Re-apply the constraint, functor should be called again
935 application.SendNotification();
936 application.Render();
938 DALI_TEST_EQUALS(functorCalled, true, TEST_LOCATION);
943 int UtcDaliConstraintApplyBeforeAddedToStage(void)
945 // Constraint gets applied to an off-stage actor.
946 // Constraint should be automatically applied when the actor is added to the stage and not before
948 TestApplication application;
949 bool functorCalled = false;
951 // Create an actor and a constraint and apply, DON'T add to stage just yet
952 Actor actor = Actor::New();
953 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, BasicCalledFunctor<Vector3>(functorCalled));
956 application.SendNotification();
957 application.Render();
959 // Should NOT be called
960 DALI_TEST_EQUALS(functorCalled, false, TEST_LOCATION);
962 // Add actor to stage
963 application.GetScene().Add(actor);
965 application.SendNotification();
966 application.Render();
968 // Should now be called
969 DALI_TEST_EQUALS(functorCalled, true, TEST_LOCATION);
974 int UtcDaliConstraintApplyAndRemoveBeforeAddedToStage(void)
976 // Constraint gets applied to an off-stage actor, then gets removed before it's added to the stage
977 // Constraint should NOT be called at all
979 TestApplication application;
980 bool functorCalled = false;
982 // Create an actor and a constraint and apply, DON'T add to stage just yet
983 Actor actor = Actor::New();
984 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, BasicCalledFunctor<Vector3>(functorCalled));
987 application.SendNotification();
988 application.Render();
990 // Should NOT be called
991 DALI_TEST_EQUALS(functorCalled, false, TEST_LOCATION);
993 // Remove the constraint
996 // Add actor to stage
997 application.GetScene().Add(actor);
999 application.SendNotification();
1000 application.Render();
1002 // Still should NOT be called
1003 DALI_TEST_EQUALS(functorCalled, false, TEST_LOCATION);
1008 int UtcDaliConstraintApplyActorStagedUnstaged(void)
1010 // Apply a constraint to an actor which is staged and unstaged.
1011 // Functor should only be called while the actor is staged.
1013 TestApplication application;
1014 bool functorCalled = false;
1016 // Create an actor and add to stage
1017 Actor actor = Actor::New();
1018 Integration::Scene stage = application.GetScene();
1021 // Create a constraint and apply
1022 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, BasicCalledFunctor<Vector3>(functorCalled));
1025 application.SendNotification();
1026 application.Render();
1028 // Constraint should be called
1029 DALI_TEST_EQUALS(functorCalled, true, TEST_LOCATION);
1032 functorCalled = false;
1034 // Remove actor from stage
1035 stage.Remove(actor);
1037 application.SendNotification();
1038 application.Render();
1040 // Constraint should NOT be called
1041 DALI_TEST_EQUALS(functorCalled, false, TEST_LOCATION);
1046 application.SendNotification();
1047 application.Render();
1049 // Constraint should be called
1050 DALI_TEST_EQUALS(functorCalled, true, TEST_LOCATION);
1055 int UtcDaliConstraintApplySeveralTimes(void)
1057 // Apply the same constraint several times.
1058 // Should not cause any problems (subsequent attempts should be no-ops)
1060 TestApplication application;
1063 // Create an actor and add to stage
1064 Actor actor = Actor::New();
1065 Integration::Scene stage = application.GetScene();
1068 // Create a constraint and apply
1069 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, CalledCountFunctor<Vector3>(count));
1073 constraint.Apply(); // no-op
1075 application.SendNotification();
1076 application.Render();
1078 // Should only have been called once
1079 DALI_TEST_EQUALS(count, 1, TEST_LOCATION);
1085 constraint.Apply(); // no-op
1087 application.SendNotification();
1088 application.Render();
1090 DALI_TEST_EQUALS(count, 1, TEST_LOCATION);
1095 // Change the position property, apply again
1096 actor.SetProperty(Actor::Property::POSITION, Vector2(10.0f, 10.0f));
1099 application.SendNotification();
1100 application.Render();
1102 // Constraint should have been called once
1103 DALI_TEST_EQUALS(count, 1, TEST_LOCATION);
1108 ///////////////////////////////////////////////////////////////////////////////
1110 ///////////////////////////////////////////////////////////////////////////////
1111 // Constraint::AddSource
1112 ///////////////////////////////////////////////////////////////////////////////
1113 namespace UtcDaliConstraintAddSource
1115 void Function(Vector3& /* current */, const PropertyInputContainer& inputs)
1117 DALI_TEST_EQUALS(inputs.Size(), 4u, TEST_LOCATION);
1118 DALI_TEST_EQUALS(inputs[0]->GetType(), Property::VECTOR3, TEST_LOCATION);
1119 DALI_TEST_EQUALS(inputs[1]->GetType(), Property::ROTATION, TEST_LOCATION);
1120 DALI_TEST_EQUALS(inputs[2]->GetType(), Property::VECTOR4, TEST_LOCATION);
1121 DALI_TEST_EQUALS(inputs[3]->GetType(), Property::BOOLEAN, TEST_LOCATION);
1123 } // namespace UtcDaliConstraintAddSource
1125 int UtcDaliConstraintAddSourceP(void)
1127 // Ensure all sources are in the correct order in the functor
1129 TestApplication application;
1131 Actor actor = Actor::New();
1132 application.GetScene().Add(actor);
1134 // Create a constraint, add sources
1135 Constraint constraint = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &UtcDaliConstraintAddSource::Function);
1136 constraint.AddSource(LocalSource(Actor::Property::SIZE));
1137 constraint.AddSource(LocalSource(Actor::Property::ORIENTATION));
1138 constraint.AddSource(LocalSource(Actor::Property::COLOR));
1139 constraint.AddSource(LocalSource(Actor::Property::VISIBLE));
1142 application.SendNotification();
1143 application.Render();
1148 int UtcDaliConstraintAddSourceN(void)
1150 // Attempt to set from uninitialised constraint
1152 TestApplication application;
1154 Constraint constraint;
1157 constraint.AddSource(LocalSource(Actor::Property::POSITION));
1158 DALI_TEST_CHECK(false); // Should not reach here!
1162 DALI_TEST_CHECK(true);
1167 ///////////////////////////////////////////////////////////////////////////////
1169 ///////////////////////////////////////////////////////////////////////////////
1170 namespace TestChaining
1172 const Vector3 gFunction1Output(Vector3::ONE);
1173 void Function1(Vector3& current, const PropertyInputContainer& /* inputs */)
1175 // current is original position
1176 DALI_TEST_EQUALS(current, Vector3::ZERO, TEST_LOCATION);
1177 current = gFunction1Output;
1180 const Vector3 gFunction2Output(10.0f, 20.0f, 30.0f);
1181 void Function2(Vector3& current, const PropertyInputContainer& /* inputs */)
1183 // current is output from Function1
1184 DALI_TEST_EQUALS(current, gFunction1Output, TEST_LOCATION);
1186 current = gFunction2Output;
1189 const Vector3 gFunction3Output(10.0f, 20.0f, 30.0f);
1190 void Function3(Vector3& current, const PropertyInputContainer& /* inputs */)
1192 // current is output from Function2
1193 DALI_TEST_EQUALS(current, gFunction2Output, TEST_LOCATION);
1195 current = gFunction3Output;
1198 const Vector3 gFunction4Output(10.0f, 20.0f, 30.0f);
1199 void Function4(Vector3& current, const PropertyInputContainer& /* inputs */)
1201 // current is output from Function3
1202 DALI_TEST_EQUALS(current, gFunction3Output, TEST_LOCATION);
1204 current = gFunction4Output;
1207 void Function5(Vector3& current, const PropertyInputContainer& /* inputs */)
1209 // current is output from Function4
1210 DALI_TEST_EQUALS(current, gFunction4Output, TEST_LOCATION);
1212 current = Vector3::ZERO;
1215 } // namespace TestChaining
1217 int UtcDaliConstraintChaining(void)
1219 // Apply several constraints to the same property and ensure the functors are called in the correct order.
1221 TestApplication application;
1223 Actor actor = Actor::New();
1224 application.GetScene().Add(actor);
1226 Constraint constraint1 = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &TestChaining::Function1);
1227 Constraint constraint2 = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &TestChaining::Function2);
1228 Constraint constraint3 = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &TestChaining::Function3);
1229 Constraint constraint4 = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &TestChaining::Function4);
1230 Constraint constraint5 = Constraint::New<Vector3>(actor, Actor::Property::POSITION, &TestChaining::Function5);
1232 constraint1.Apply();
1233 constraint2.Apply();
1234 constraint3.Apply();
1235 constraint4.Apply();
1236 constraint5.Apply();
1238 application.SendNotification();
1239 application.Render();
1243 ///////////////////////////////////////////////////////////////////////////////
1245 ///////////////////////////////////////////////////////////////////////////////
1246 namespace TestPropertyTypes
1248 template<typename T>
1249 void Execute(T value)
1251 TestApplication application;
1252 bool functorCalled = false;
1254 Actor actor = Actor::New();
1255 Property::Index index = actor.RegisterProperty("TEMP_PROPERTY_NAME", value);
1257 application.GetScene().Add(actor);
1259 application.SendNotification();
1260 application.Render();
1262 DALI_TEST_EQUALS(functorCalled, false, TEST_LOCATION);
1265 Constraint constraint = Constraint::New<T>(actor, index, BasicCalledFunctor<T>(functorCalled));
1266 DALI_TEST_CHECK(constraint);
1269 application.SendNotification();
1270 application.Render();
1272 DALI_TEST_EQUALS(functorCalled, true, TEST_LOCATION);
1274 } // namespace TestPropertyTypes
1276 int UtcDaliConstraintTestPropertyTypesP(void)
1278 // Ensure we can use a constraint functor with all supported property types
1280 TestPropertyTypes::Execute<bool>(false);
1281 TestPropertyTypes::Execute<int>(0);
1282 TestPropertyTypes::Execute<float>(0.0f);
1283 TestPropertyTypes::Execute<Vector2>(Vector2::ZERO);
1284 TestPropertyTypes::Execute<Vector3>(Vector3::ZERO);
1285 TestPropertyTypes::Execute<Vector4>(Vector4::ZERO);
1286 TestPropertyTypes::Execute<Quaternion>(Quaternion::IDENTITY);
1287 TestPropertyTypes::Execute<Matrix>(Matrix::IDENTITY);
1288 TestPropertyTypes::Execute<Matrix3>(Matrix3::IDENTITY);
1293 ///////////////////////////////////////////////////////////////////////////////
1295 ///////////////////////////////////////////////////////////////////////////////
1298 void SetHalfOpacity(Vector4& current, const PropertyInputContainer& inputs)
1302 } // unnamed namespace
1304 int UtcDaliConstraintEnsureResetterAppliedOnSceneRemoval(void)
1306 // Ensure BOTH double-buffered values of our color property is reset when a constraint is applied to it.
1308 TestApplication application;
1310 Actor actor = Actor::New();
1311 application.GetScene().Add(actor);
1313 // Check initial value is fully opaque
1314 application.SendNotification();
1315 application.Render();
1316 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 1.0f, TEST_LOCATION);
1318 // Create a constraint whose value is discarded when it is removed
1319 Constraint constraint = Constraint::New<Vector4>(actor, Actor::Property::COLOR, SetHalfOpacity);
1320 constraint.SetRemoveAction(Constraint::RemoveAction::DISCARD);
1323 // Check value after one render, it should be constrained
1324 application.SendNotification();
1325 application.Render();
1326 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 0.5f, TEST_LOCATION);
1328 // Render another frame, ensure the other value has also been updated
1329 application.SendNotification();
1330 application.Render();
1331 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 0.5f, TEST_LOCATION);
1333 // Remove the actor from the stage and delete the constraint
1335 constraint.Remove();
1338 // Check value while off-stage, it should be fully opaque
1339 application.SendNotification();
1340 application.Render();
1341 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 1.0f, TEST_LOCATION);
1343 // Add the actor back to the stage and check the value, it should be fully opaque again
1344 application.GetScene().Add(actor);
1346 // Check value when back on-stage, it should be fully opaque as the constraint is no longer applied to it.
1347 application.SendNotification();
1348 application.Render();
1349 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 1.0f, TEST_LOCATION);
1351 // Render for another frame to ensure both buffers have the correct value
1352 application.SendNotification();
1353 application.Render();
1354 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 1.0f, TEST_LOCATION);
1359 int UtcDaliConstraintOnActorAddedAndRemoved(void)
1361 // Ensure adding and removing an actor from stage with a constraint still has it applied when it is re-added back to the stage
1363 TestApplication application;
1365 Actor actor = Actor::New();
1366 application.GetScene().Add(actor);
1368 // Check initial value is fully opaque
1369 application.SendNotification();
1370 application.Render();
1371 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 1.0f, TEST_LOCATION);
1373 // Create a constraint whose value is discarded when it is removed
1374 Constraint constraint = Constraint::New<Vector4>(actor, Actor::Property::COLOR, SetHalfOpacity);
1375 constraint.SetRemoveAction(Constraint::RemoveAction::DISCARD);
1378 // Check value after one render, it should be constrained
1379 application.SendNotification();
1380 application.Render();
1381 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 0.5f, TEST_LOCATION);
1383 // Render another frame, ensure the other value has also been updated
1384 application.SendNotification();
1385 application.Render();
1386 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 0.5f, TEST_LOCATION);
1388 // Remove the actor from the stage
1391 // Check value while off-stage, the constraint is no longer being applied as it's off-stage
1392 application.SendNotification();
1393 application.Render();
1394 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 1.0f, TEST_LOCATION);
1396 // Check the other buffer, the constraint should not be applied to this either.
1397 application.SendNotification();
1398 application.Render();
1399 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 1.0f, TEST_LOCATION);
1401 // Add the actor back to the stage and check the value, the constraint should have been re-applied
1402 application.GetScene().Add(actor);
1403 application.SendNotification();
1404 application.Render();
1405 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 0.5f, TEST_LOCATION);
1407 // Render for another frame to ensure both buffers have the correct value
1408 application.SendNotification();
1409 application.Render();
1410 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR).a, 0.5f, TEST_LOCATION);
1415 ///////////////////////////////////////////////////////////////////////////////
1417 int UtcDaliConstraintGetTargetObjectNegative(void)
1419 TestApplication application;
1420 Dali::Constraint instance;
1423 instance.GetTargetObject();
1424 DALI_TEST_CHECK(false); // Should not get here
1428 DALI_TEST_CHECK(true); // We expect an assert
1433 int UtcDaliConstraintSetRemoveActionNegative(void)
1435 TestApplication application;
1436 Dali::Constraint instance;
1439 Dali::Constraint::RemoveAction arg1(Constraint::BAKE);
1440 instance.SetRemoveAction(arg1);
1441 DALI_TEST_CHECK(false); // Should not get here
1445 DALI_TEST_CHECK(true); // We expect an assert
1450 int UtcDaliConstraintGetTargetPropertyNegative(void)
1452 TestApplication application;
1453 Dali::Constraint instance;
1456 instance.GetTargetProperty();
1457 DALI_TEST_CHECK(false); // Should not get here
1461 DALI_TEST_CHECK(true); // We expect an assert
1466 int UtcDaliConstraintApplyNegative(void)
1468 TestApplication application;
1469 Dali::Constraint instance;
1473 DALI_TEST_CHECK(false); // Should not get here
1477 DALI_TEST_CHECK(true); // We expect an assert
1482 int UtcDaliConstraintCloneNegative(void)
1484 TestApplication application;
1485 Dali::Constraint instance;
1489 instance.Clone(arg1);
1490 DALI_TEST_CHECK(false); // Should not get here
1494 DALI_TEST_CHECK(true); // We expect an assert
1499 int UtcDaliConstraintRemoveNegative(void)
1501 TestApplication application;
1502 Dali::Constraint instance;
1506 DALI_TEST_CHECK(false); // Should not get here
1510 DALI_TEST_CHECK(true); // We expect an assert
1515 int UtcDaliConstraintSetTagNegative(void)
1517 TestApplication application;
1518 Dali::Constraint instance;
1521 unsigned int arg1(0u);
1522 instance.SetTag(arg1);
1523 DALI_TEST_CHECK(false); // Should not get here
1527 DALI_TEST_CHECK(true); // We expect an assert
1532 int UtcDaliConstraintGetRemoveActionNegative(void)
1534 TestApplication application;
1535 Dali::Constraint instance;
1538 instance.GetRemoveAction();
1539 DALI_TEST_CHECK(false); // Should not get here
1543 DALI_TEST_CHECK(true); // We expect an assert
1548 int UtcDaliConstraintGetTagNegative(void)
1550 TestApplication application;
1551 Dali::Constraint instance;
1555 DALI_TEST_CHECK(false); // Should not get here
1559 DALI_TEST_CHECK(true); // We expect an assert
1564 namespace ComponentTest
1566 void CheckComponentProperty(TestApplication& application, Actor& actor, Property::Index property)
1568 float value = actor.GetCurrentProperty<float>(property);
1570 // Add a component 0 constraint
1571 RelativeToConstraintFloat relativeConstraint(2.0f);
1572 Constraint constraint = Constraint::New<float>(actor, property, relativeConstraint);
1573 constraint.AddSource(Source{actor, property});
1574 DALI_TEST_CHECK(constraint);
1575 constraint.SetRemoveAction(Constraint::RemoveAction::DISCARD);
1578 application.SendNotification();
1579 application.Render();
1581 DALI_TEST_EQUALS(actor.GetCurrentProperty<float>(property), value * 2.0f, TEST_LOCATION);
1583 constraint.Remove();
1585 application.SendNotification();
1586 application.Render();
1588 DALI_TEST_EQUALS(actor.GetCurrentProperty<float>(property), value, TEST_LOCATION);
1590 } // namespace ComponentTest
1592 int UtcDaliConstraintComponentTransformPropertyConstraintP(void)
1594 TestApplication application;
1596 Actor actor = Actor::New();
1597 actor.SetProperty(Actor::Property::POSITION, Vector3(100.0f, 100.0f, 100.0f));
1598 application.GetScene().Add(actor);
1600 application.SendNotification();
1601 application.Render();
1603 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector3>(Actor::Property::POSITION), Vector3(100.0f, 100.0f, 100.0f), TEST_LOCATION);
1605 ComponentTest::CheckComponentProperty(application, actor, Actor::Property::POSITION_X); // Component 0
1606 ComponentTest::CheckComponentProperty(application, actor, Actor::Property::POSITION_Y); // Component 1
1607 ComponentTest::CheckComponentProperty(application, actor, Actor::Property::POSITION_Z); // Component 2
1612 int UtcDaliConstraintComponentNonTransformPropertyConstraintP(void)
1614 TestApplication application;
1616 Actor actor = Actor::New();
1617 actor.SetProperty(Actor::Property::COLOR, Vector4(0.25f, 0.25f, 0.25f, 0.25f));
1618 application.GetScene().Add(actor);
1620 application.SendNotification();
1621 application.Render();
1623 DALI_TEST_EQUALS(actor.GetCurrentProperty<Vector4>(Actor::Property::COLOR), Vector4(0.25f, 0.25f, 0.25f, 0.25f), TEST_LOCATION);
1625 ComponentTest::CheckComponentProperty(application, actor, Actor::Property::COLOR_RED); // Component 0
1626 ComponentTest::CheckComponentProperty(application, actor, Actor::Property::COLOR_GREEN); // Component 1
1627 ComponentTest::CheckComponentProperty(application, actor, Actor::Property::COLOR_BLUE); // Component 2
1628 ComponentTest::CheckComponentProperty(application, actor, Actor::Property::COLOR_ALPHA); // Component 3