From 118f87dfe57967bfed8ccdf9143a078eaef1b119 Mon Sep 17 00:00:00 2001 From: Anton Obzhirov Date: Wed, 31 Oct 2018 14:26:59 +0000 Subject: [PATCH] Add size animation in layout measure phase. Change-Id: If7b9c8478d0c6d84a12b4e4e15f146ec2bec93e5 --- .../dali-toolkit/utc-Dali-LayoutingAnimation.cpp | 338 +++++++++++++++++++-- .../devel-api/layouting/layout-item-impl.cpp | 62 ++-- .../devel-api/layouting/layout-transition-data.h | 34 ++- .../internal/layouting/layout-controller-impl.cpp | 190 +++++++++--- .../internal/layouting/layout-controller-impl.h | 21 ++ .../layouting/layout-transition-data-impl.cpp | 300 ++++++++++++++---- .../layouting/layout-transition-data-impl.h | 80 +++-- 7 files changed, 843 insertions(+), 182 deletions(-) diff --git a/automated-tests/src/dali-toolkit/utc-Dali-LayoutingAnimation.cpp b/automated-tests/src/dali-toolkit/utc-Dali-LayoutingAnimation.cpp index c7e2e4f..2bf827a 100644 --- a/automated-tests/src/dali-toolkit/utc-Dali-LayoutingAnimation.cpp +++ b/automated-tests/src/dali-toolkit/utc-Dali-LayoutingAnimation.cpp @@ -199,7 +199,7 @@ int UtcDaliLayouting_LayoutTransitionDataSetGetTransition(void) int UtcDaliLayouting_SetLayoutTransition01(void) { ToolkitTestApplication application; - tet_infoline(" UtcDaliLayouting_SetLayoutTransition01"); + tet_infoline(" UtcDaliLayouting_SetLayoutTransition01" ); Stage stage = Stage::GetCurrent(); auto container = Control::New(); @@ -382,7 +382,7 @@ int UtcDaliLayouting_SetLayoutTransition01(void) int UtcDaliLayouting_AddChildLayoutTransition01(void) { ToolkitTestApplication application; - tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition01"); + tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition01" ); Stage stage = Stage::GetCurrent(); auto container = Control::New(); @@ -479,7 +479,7 @@ int UtcDaliLayouting_AddChildLayoutTransition01(void) int UtcDaliLayouting_RemoveChildLayoutTransition01(void) { ToolkitTestApplication application; - tet_infoline(" UtcDaliLayouting_RemoveChildLayoutTransition01"); + tet_infoline(" UtcDaliLayouting_RemoveChildLayoutTransition01" ); Stage stage = Stage::GetCurrent(); auto container = Control::New(); @@ -679,7 +679,7 @@ int UtcDaliLayouting_RemoveChildLayoutTransition01(void) int UtcDaliLayouting_FocusChildLayoutTransition01(void) { ToolkitTestApplication application; - tet_infoline(" UtcDaliLayouting_FocusChildLayoutTransition01"); + tet_infoline(" UtcDaliLayouting_FocusChildLayoutTransition01" ); Stage stage = Stage::GetCurrent(); auto container = Control::New(); @@ -734,7 +734,7 @@ int UtcDaliLayouting_FocusChildLayoutTransition01(void) map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::POSITION; map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = Property::Value(); // capture from layout update map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() - .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, "LINEAR") + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, "LINEAR" ) .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f ) .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.0f ) ); @@ -743,11 +743,12 @@ int UtcDaliLayouting_FocusChildLayoutTransition01(void) { // Shrink the lost focus child Property::Map map; + map[ "affectsSiblings" ] = false; map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::SIZE; map[ LayoutTransitionData::AnimatorKey::CONDITION ] = LayoutTransitionData::Condition::ON_FOCUS_LOST; map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = Vector3( 80.0f, 80.0f, 0 ); map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() - .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, "LINEAR") + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, "LINEAR" ) .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f) .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.5f)); @@ -756,6 +757,7 @@ int UtcDaliLayouting_FocusChildLayoutTransition01(void) { // Grow the gained focus child Property::Map map; + map[ "affectsSiblings" ] = false; map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::SIZE; map[ LayoutTransitionData::AnimatorKey::CONDITION ] = LayoutTransitionData::Condition::ON_FOCUS_GAINED; map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = Vector3( 120.0f, 120.0f, 0 ); @@ -816,10 +818,310 @@ int UtcDaliLayouting_FocusChildLayoutTransition01(void) END_TEST; } +int UtcDaliLayouting_FocusChildLayoutTransition02(void) +{ + ToolkitTestApplication application; + tet_infoline(" UtcDaliLayouting_FocusChildLayoutTransition02" ); + + Stage stage = Stage::GetCurrent(); + auto container = Control::New(); + auto horizontalLayout = LinearLayout::New(); + horizontalLayout.SetAnimateLayout( false ); + horizontalLayout.SetOrientation( LinearLayout::Orientation::HORIZONTAL ); + + DevelControl::SetLayout( container, horizontalLayout ); + container.SetName( "Container" ); + + std::vector< Control > controls; + controls.push_back( CreateLeafControl( 100, 100 ) ); + controls.push_back( CreateLeafControl( 100, 100 ) ); + + stage.Add( container ); + container.Add( controls[0] ); + container.Add( controls[1] ); + + KeyInputFocusManager manager = KeyInputFocusManager::Get(); + manager.SetFocus( controls[0] ); + + // Initial rendering done + application.SendNotification(); + application.Render(); + + DALI_TEST_EQUALS( container.GetProperty( Actor::Property::POSITION ), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::POSITION ), Vector3( 0.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::POSITION ), Vector3( 100.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + DALI_TEST_EQUALS( container.GetProperty( Actor::Property::SIZE ), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + horizontalLayout.SetAnimateLayout( true ); + + auto layoutTransitionData = LayoutTransitionData::New(); + { + // Shrink the lost focus child width + Property::Map map; + map[ LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS ] = false; + map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::POSITION; + map[ LayoutTransitionData::AnimatorKey::TYPE ] = LayoutTransitionData::Animator::ANIMATE_TO; + map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, AlphaFunction::LINEAR ) + .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() + .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f) + .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.5f)); + layoutTransitionData.AddPropertyAnimator( Actor(), map ); // move all children + } + { + // Shrink the lost focus child width + Property::Map map; + map[ LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS ] = true; + map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::SIZE_WIDTH; + map[ LayoutTransitionData::AnimatorKey::CONDITION ] = LayoutTransitionData::Condition::ON_FOCUS_LOST; + map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = 80.0f; + map[ LayoutTransitionData::AnimatorKey::TYPE ] = LayoutTransitionData::Animator::ANIMATE_TO; + map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, AlphaFunction::LINEAR ) + .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() + .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f) + .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.5f)); + layoutTransitionData.AddPropertyAnimator( Actor(), map ); // apply to on focus lost child + } + { + // Shrink the lost focus child height + Property::Map map; + map[ LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS ] = true; + map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::SIZE_HEIGHT; + map[ LayoutTransitionData::AnimatorKey::CONDITION ] = LayoutTransitionData::Condition::ON_FOCUS_LOST; + map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = 80.0f; + map[ LayoutTransitionData::AnimatorKey::TYPE ] = LayoutTransitionData::Animator::ANIMATE_TO; + map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, AlphaFunction::LINEAR ) + .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() + .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f) + .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.5f)); + layoutTransitionData.AddPropertyAnimator( Actor(), map ); // apply to on focus lost child + } + { + // Grow the gained focus child + Property::Map map; + map[ LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS ] = true; + map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::SIZE; + map[ LayoutTransitionData::AnimatorKey::CONDITION ] = LayoutTransitionData::Condition::ON_FOCUS_GAINED; + map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = Vector3( 120.0f, 120.0f, 0 ); + map[ LayoutTransitionData::AnimatorKey::TYPE ] = LayoutTransitionData::Animator::ANIMATE_TO; + map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, AlphaFunction::LINEAR ) + .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() + .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f) + .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.5f)); + layoutTransitionData.AddPropertyAnimator( Actor(), map ); // apply to on focus gained child + } + + horizontalLayout.SetTransitionData( LayoutTransitionData::ON_CHILD_FOCUS, layoutTransitionData ); + + bool signalReceived(false); + LayoutTransitionFinishCheck finishCheck(signalReceived); + layoutTransitionData.FinishedSignal().Connect(&application, finishCheck); + manager.SetFocus( controls[1] ); + + application.SendNotification(); + application.Render( 1u /*just very beginning of the animation*/ ); + + finishCheck.CheckSignalNotReceived(); + // Animation just started + DALI_TEST_EQUALS( container.GetCurrentPosition(), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentPosition(), Vector3( 0.0f, 350.0f, 0.0f ), 1.0f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentPosition(), Vector3( 100.0f, 350.0f, 0.0f ), 1.0f, TEST_LOCATION ); + + DALI_TEST_EQUALS( container.GetCurrentSize(), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 1.0f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 1.0f, TEST_LOCATION ); + + application.SendNotification(); + application.Render(static_cast( 0.5f * 1000.0f ) + 1u /*just after the end of the animation*/ ); + + // Animation just finished + DALI_TEST_EQUALS( container.GetCurrentPosition(), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentPosition(), Vector3( 0.0f, 360.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentPosition(), Vector3( 80.0f, 340.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + DALI_TEST_EQUALS( container.GetCurrentSize(), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentSize(), Vector3( 80.0f, 80.0f, 0.0f ), 1.0f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentSize(), Vector3( 120.0f, 120.0f, 0.0f ), 1.0f, TEST_LOCATION ); + + application.SendNotification(); + application.Render( 10u /* wait a bit more for a signal */ ); + + // Now sizes and positions are finally set + DALI_TEST_EQUALS( container.GetProperty( Actor::Property::POSITION ), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::POSITION ), Vector3( 0.0f, 360.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::POSITION ), Vector3( 80.0f, 340.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + DALI_TEST_EQUALS( container.GetProperty( Actor::Property::SIZE ), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::SIZE ), Vector3( 80.0f, 80.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::SIZE ), Vector3( 120.0f, 120.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + finishCheck.CheckSignalReceived(); + + END_TEST; +} + +int UtcDaliLayouting_FocusChildLayoutTransition03(void) +{ + ToolkitTestApplication application; + tet_infoline(" UtcDaliLayouting_FocusChildLayoutTransition03" ); + + Stage stage = Stage::GetCurrent(); + auto container = Control::New(); + auto horizontalLayout = LinearLayout::New(); + horizontalLayout.SetAnimateLayout( false ); + horizontalLayout.SetOrientation( LinearLayout::Orientation::HORIZONTAL ); + + DevelControl::SetLayout( container, horizontalLayout ); + container.SetName( "Container" ); + + std::vector< Control > controls; + controls.push_back( CreateLeafControl( 100, 100 ) ); + controls.push_back( CreateLeafControl( 100, 100 ) ); + + stage.Add( container ); + container.Add( controls[0] ); + container.Add( controls[1] ); + + KeyInputFocusManager manager = KeyInputFocusManager::Get(); + manager.SetFocus( controls[0] ); + + // Initial rendering done + application.SendNotification(); + application.Render(); + + DALI_TEST_EQUALS( container.GetProperty( Actor::Property::POSITION ), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::POSITION ), Vector3( 0.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::POSITION ), Vector3( 100.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + DALI_TEST_EQUALS( container.GetProperty( Actor::Property::SIZE ), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + horizontalLayout.SetAnimateLayout( true ); + + auto layoutTransitionData = LayoutTransitionData::New(); + { + // Shrink the lost focus child width + Property::Map map; + map[ LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS ] = false; + map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::POSITION; + map[ LayoutTransitionData::AnimatorKey::TYPE ] = LayoutTransitionData::Animator::ANIMATE_TO; + map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, AlphaFunction::LINEAR ) + .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() + .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f) + .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.5f)); + layoutTransitionData.AddPropertyAnimator( Actor(), map ); // move all children + } + { + // Shrink the lost focus child width + Property::Map map; + map[ LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS ] = true; + map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::SCALE_X; + map[ LayoutTransitionData::AnimatorKey::CONDITION ] = LayoutTransitionData::Condition::ON_FOCUS_LOST; + map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = 0.8f; + map[ LayoutTransitionData::AnimatorKey::TYPE ] = LayoutTransitionData::Animator::ANIMATE_TO; + map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, AlphaFunction::LINEAR ) + .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() + .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f) + .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.5f)); + layoutTransitionData.AddPropertyAnimator( Actor(), map ); // apply to on focus lost child + } + { + // Shrink the lost focus child height + Property::Map map; + map[ LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS ] = true; + map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::SCALE_Y; + map[ LayoutTransitionData::AnimatorKey::CONDITION ] = LayoutTransitionData::Condition::ON_FOCUS_LOST; + map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = 0.8f; + map[ LayoutTransitionData::AnimatorKey::TYPE ] = LayoutTransitionData::Animator::ANIMATE_TO; + map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, AlphaFunction::LINEAR ) + .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() + .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f) + .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.5f)); + layoutTransitionData.AddPropertyAnimator( Actor(), map ); // apply to on focus lost child + } + { + // Grow the gained focus child + Property::Map map; + map[ LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS ] = true; + map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::SCALE; + map[ LayoutTransitionData::AnimatorKey::CONDITION ] = LayoutTransitionData::Condition::ON_FOCUS_GAINED; + map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = Vector3( 1.2f, 1.2f, 1.0f ); + map[ LayoutTransitionData::AnimatorKey::TYPE ] = LayoutTransitionData::Animator::ANIMATE_TO; + map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() + .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, AlphaFunction::LINEAR ) + .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() + .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f) + .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.5f)); + layoutTransitionData.AddPropertyAnimator( Actor(), map ); // apply to on focus gained child + } + + horizontalLayout.SetTransitionData( LayoutTransitionData::ON_CHILD_FOCUS, layoutTransitionData ); + + bool signalReceived(false); + LayoutTransitionFinishCheck finishCheck(signalReceived); + layoutTransitionData.FinishedSignal().Connect(&application, finishCheck); + manager.SetFocus( controls[1] ); + + application.SendNotification(); + application.Render( 1u /*just very beginning of the animation*/ ); + + finishCheck.CheckSignalNotReceived(); + // Animation just started + DALI_TEST_EQUALS( container.GetCurrentPosition(), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentPosition(), Vector3( 0.0f, 350.0f, 0.0f ), 1.0f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentPosition(), Vector3( 100.0f, 350.0f, 0.0f ), 1.0f, TEST_LOCATION ); + + DALI_TEST_EQUALS( container.GetCurrentSize(), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 1.0f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 1.0f, TEST_LOCATION ); + + application.SendNotification(); + application.Render(static_cast( 0.5f * 1000.0f ) + 1u /*just after the end of the animation*/ ); + + // Animation just finished + DALI_TEST_EQUALS( container.GetCurrentPosition(), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentPosition(), Vector3( -10.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentPosition(), Vector3( 90.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + DALI_TEST_EQUALS( container.GetCurrentSize(), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentSize() * controls[0].GetCurrentScale(), Vector3( 80.0f, 80.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentSize() * controls[1].GetCurrentScale(), Vector3( 120.0f, 120.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + application.SendNotification(); + application.Render( 10u /* wait a bit more for a signal */ ); + + // Now sizes and positions are finally set + DALI_TEST_EQUALS( container.GetProperty( Actor::Property::POSITION ), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::POSITION ), Vector3( -10.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::POSITION ), Vector3( 90.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + DALI_TEST_EQUALS( container.GetProperty( Actor::Property::SIZE ), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::SIZE ) * controls[0].GetProperty( Actor::Property::SCALE ), Vector3( 80.0f, 80.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::SIZE ) * controls[1].GetProperty( Actor::Property::SCALE ), Vector3( 120.0f, 120.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + + finishCheck.CheckSignalReceived(); + + END_TEST; +} + int UtcDaliLayouting_AddChildLayoutTransition02_KeyFrames(void) { ToolkitTestApplication application; - tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition02_KeyFrames"); + tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition02_KeyFrames" ); Stage stage = Stage::GetCurrent(); auto container = Control::New(); @@ -919,7 +1221,7 @@ int UtcDaliLayouting_AddChildLayoutTransition02_KeyFrames(void) int UtcDaliLayouting_AddChildLayoutTransition03_Path(void) { ToolkitTestApplication application; - tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition03_Path"); + tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition03_Path" ); Stage stage = Stage::GetCurrent(); auto container = Control::New(); @@ -1047,7 +1349,7 @@ int UtcDaliLayouting_AddChildLayoutTransition03_Path(void) int UtcDaliLayouting_AddChildLayoutTransition04_AnimateBy(void) { ToolkitTestApplication application; - tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition04_AnimateBy"); + tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition04_AnimateBy" ); Stage stage = Stage::GetCurrent(); auto container = Control::New(); @@ -1089,7 +1391,7 @@ int UtcDaliLayouting_AddChildLayoutTransition04_AnimateBy(void) { Property::Map map; map[ LayoutTransitionData::AnimatorKey::PROPERTY ] = Actor::Property::SIZE; - map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = Vector3( 0.0f, 350.0f, 0 ); + map[ LayoutTransitionData::AnimatorKey::TARGET_VALUE ] = Vector3( 10.0f, 10.0f, 0 ); map[ LayoutTransitionData::AnimatorKey::ANIMATOR ] = Property::Map() .Add( LayoutTransitionData::AnimatorKey::TYPE, "ANIMATE_BY") .Add( LayoutTransitionData::AnimatorKey::ALPHA_FUNCTION, "LINEAR") @@ -1122,7 +1424,7 @@ int UtcDaliLayouting_AddChildLayoutTransition04_AnimateBy(void) DALI_TEST_EQUALS( controls[0].GetCurrentPosition(), Vector3( 0.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); DALI_TEST_EQUALS( container.GetCurrentSize(), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); - DALI_TEST_EQUALS( controls[0].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetCurrentSize(), Vector3( 110.0f, 110.0f, 0.0f ), 0.0001f, TEST_LOCATION ); application.SendNotification(); application.Render( 10u /* wait a bit more for a signal */ ); @@ -1132,7 +1434,7 @@ int UtcDaliLayouting_AddChildLayoutTransition04_AnimateBy(void) DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::POSITION ), Vector3( 0.0f, 350.0f, 0.0f ), 0.0001f, TEST_LOCATION ); DALI_TEST_EQUALS( container.GetProperty( Actor::Property::SIZE ), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); - DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[0].GetProperty( Actor::Property::SIZE ), Vector3( 110.0f, 110.0f, 0.0f ), 0.0001f, TEST_LOCATION ); finishCheck.CheckSignalReceived(); @@ -1142,7 +1444,7 @@ int UtcDaliLayouting_AddChildLayoutTransition04_AnimateBy(void) int UtcDaliLayouting_AddChildLayoutTransition05(void) { ToolkitTestApplication application; - tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition05"); + tet_infoline(" UtcDaliLayouting_AddChildLayoutTransition05" ); Stage stage = Stage::GetCurrent(); auto container = Control::New(); @@ -1382,7 +1684,7 @@ int UtcDaliLayouting_AddChildLayoutTransition05(void) int UtcDaliLayouting_DefaultTransition01(void) { ToolkitTestApplication application; - tet_infoline(" UtcDaliLayouting_DefaultTransition01"); + tet_infoline(" UtcDaliLayouting_DefaultTransition01" ); Stage stage = Stage::GetCurrent(); auto container = Control::New(); @@ -1440,7 +1742,7 @@ int UtcDaliLayouting_DefaultTransition01(void) .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.0f ) ); layoutTransitionData0.AddPropertyAnimator( controls[0], map ); } - DevelControl::GetLayout( controls[0] ).SetTransitionData(LayoutTransitionData::Type::ON_LAYOUT_CHANGE, layoutTransitionData0 ); + DevelControl::GetLayout( controls[0] ).SetTransitionData( LayoutTransitionData::Type::ON_LAYOUT_CHANGE, layoutTransitionData0 ); auto layoutTransitionData1 = LayoutTransitionData::New(); { @@ -1465,9 +1767,9 @@ int UtcDaliLayouting_DefaultTransition01(void) .Add( LayoutTransitionData::AnimatorKey::TIME_PERIOD, Property::Map() .Add( LayoutTransitionData::AnimatorKey::DELAY, 0.0f ) .Add( LayoutTransitionData::AnimatorKey::DURATION, 0.0f ) ); - layoutTransitionData0.AddPropertyAnimator( controls[1], map ); + layoutTransitionData1.AddPropertyAnimator( controls[1], map ); } - DevelControl::GetLayout( controls[1] ).SetTransitionData(LayoutTransitionData::Type::ON_LAYOUT_CHANGE, layoutTransitionData1 ); + DevelControl::GetLayout( controls[1] ).SetTransitionData( LayoutTransitionData::Type::ON_LAYOUT_CHANGE, layoutTransitionData1 ); horizontalLayout.SetOrientation( LinearLayout::Orientation::VERTICAL ); @@ -1481,7 +1783,7 @@ int UtcDaliLayouting_DefaultTransition01(void) DALI_TEST_EQUALS( container.GetCurrentSize(), Vector3( 480.0f, 800.0f, 0.0f ), 0.0001f, TEST_LOCATION ); DALI_TEST_EQUALS( controls[0].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 1.0f, TEST_LOCATION ); - DALI_TEST_EQUALS( controls[0].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 1.0f, TEST_LOCATION ); + DALI_TEST_EQUALS( controls[1].GetCurrentSize(), Vector3( 100.0f, 100.0f, 0.0f ), 1.0f, TEST_LOCATION ); // Now sizes and positions are set DALI_TEST_EQUALS( container.GetProperty( Actor::Property::POSITION ), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION ); diff --git a/dali-toolkit/devel-api/layouting/layout-item-impl.cpp b/dali-toolkit/devel-api/layouting/layout-item-impl.cpp index 0b638de..fe26362 100644 --- a/dali-toolkit/devel-api/layouting/layout-item-impl.cpp +++ b/dali-toolkit/devel-api/layouting/layout-item-impl.cpp @@ -273,7 +273,7 @@ void LayoutItem::Layout( LayoutLength l, LayoutLength t, LayoutLength r, LayoutL } LayoutData& layoutData = *mImpl->sLayoutData; - size_t size = layoutData.childrenPropertyAnimators.size(); + size_t size = layoutData.childrenLayoutDataArray.size(); bool changed = SetFrame( l, t, r, b ); @@ -284,9 +284,9 @@ void LayoutItem::Layout( LayoutLength l, LayoutLength t, LayoutLength r, LayoutL mImpl->ClearPrivateFlag( Impl::PRIVATE_FLAG_LAYOUT_REQUIRED ); } - if ( size != layoutData.childrenPropertyAnimators.size() ) + if ( size != layoutData.childrenLayoutDataArray.size() ) { - layoutData.childrenPropertyAnimators.resize( size ); + layoutData.childrenLayoutDataArray.resize( size ); } mImpl->ClearPrivateFlag( Impl::PRIVATE_FLAG_FORCE_LAYOUT ); @@ -496,7 +496,7 @@ void LayoutItem::SetMeasuredDimensions( MeasuredSize measuredWidth, MeasuredSize LayoutLength LayoutItem::GetMeasuredWidth() const { // Get the size portion of the measured width - return mImpl->mMeasuredWidth.GetSize(); + return mImpl->mMeasuredWidth.GetSize(); } LayoutLength LayoutItem::GetMeasuredHeight() const @@ -599,52 +599,50 @@ bool LayoutItem::SetFrame( LayoutLength left, LayoutLength top, LayoutLength rig auto owner = GetOwner(); auto actor = Actor::DownCast( owner ); LayoutData& layoutData = *mImpl->sLayoutData; + if( actor ) { - if( mImpl->mAnimated && !layoutData.speculativeLayout ) + if( changed || mImpl->mAnimated ) { - LayoutItem* transitionOwner = layoutData.layoutTransition.layoutItem.Get(); - LayoutTransitionDataPtr layoutTransitionDataPtr = GetTransitionData( layoutData.layoutTransition.layoutTransitionType ); + layoutData.layoutPositionDataArray.push_back( + LayoutPositionData( actor, left.AsDecimal(), top.AsDecimal(), right.AsDecimal(), bottom.AsDecimal(), mImpl->mAnimated ) ); + } - // Found transition owner - if( transitionOwner == this && layoutTransitionDataPtr.Get() ) + if( mImpl->mAnimated && !layoutData.speculativeLayout ) + { + if( layoutData.layoutTransition.layoutTransitionType != -1 ) { - DALI_LOG_INFO( gLayoutFilter, Debug::Verbose, "LayoutItem::SetFrame apply transition to (%s), transition type (%d)\n", actor.GetName().c_str(), layoutData.layoutTransition.layoutTransitionType ); - layoutData.layoutPositionDataArray.push_back( LayoutPositionData( actor, left.AsDecimal(), top.AsDecimal(), right.AsDecimal(), bottom.AsDecimal(), true ) ); - layoutTransitionDataPtr->ConvertToLayoutDataElements( actor, layoutData ); - changed = true; + LayoutItem* transitionOwner = layoutData.layoutTransition.layoutItem.Get(); + LayoutTransitionDataPtr layoutTransitionDataPtr = GetTransitionData( layoutData.layoutTransition.layoutTransitionType ); + + // Found transition owner + if( transitionOwner == this && layoutTransitionDataPtr.Get() ) + { + DALI_LOG_INFO( gLayoutFilter, Debug::Verbose, "LayoutItem::SetFrame apply transition to (%s), transition type (%d)\n", actor.GetName().c_str(), layoutData.layoutTransition.layoutTransitionType ); + layoutTransitionDataPtr->CollectLayoutDataElements( actor, layoutData ); + changed = true; + } + else + { + LayoutTransitionData::CollectChildrenLayoutDataElements( actor, layoutData ); + } } else { if( changed ) { - layoutTransitionDataPtr = GetTransitionData( Dali::Toolkit::LayoutTransitionData::ON_LAYOUT_CHANGE ); - if ( layoutTransitionDataPtr ) + LayoutTransitionDataPtr layoutTransitionDataPtr = GetTransitionData( Dali::Toolkit::LayoutTransitionData::ON_LAYOUT_CHANGE ); + if( layoutTransitionDataPtr ) // has custom default animation and normal update { DALI_LOG_INFO( gLayoutFilter, Debug::Verbose, "LayoutItem::SetFrame apply custom default transition to (%s), transition type (%d)\n", actor.GetName().c_str(), Dali::Toolkit::LayoutTransitionData::ON_LAYOUT_CHANGE ); - layoutData.layoutPositionDataArray.push_back( LayoutPositionData( actor, left.AsDecimal(), top.AsDecimal(), right.AsDecimal(), bottom.AsDecimal(), true ) ); - layoutTransitionDataPtr->ConvertToLayoutDataElements( actor, layoutData ); + layoutTransitionDataPtr->CollectLayoutDataElements( actor, layoutData ); } else { DALI_LOG_INFO( gLayoutFilter, Debug::Verbose, "LayoutItem::SetFrame apply default transition to (%s), transition type (%d)\n", actor.GetName().c_str(), layoutData.layoutTransition.layoutTransitionType ); - layoutData.layoutPositionDataArray.push_back( LayoutPositionData( actor, left.AsDecimal(), top.AsDecimal(), right.AsDecimal(), bottom.AsDecimal(), true ) ); - GetDefaultTransition()->ConvertToLayoutDataElements( actor, layoutData ); + GetDefaultTransition()->CollectLayoutDataElements( actor, layoutData ); } } - else - { - DALI_LOG_INFO( gLayoutFilter, Debug::Verbose, "LayoutItem::SetFrame apply children animators to (%s), transition type (%d)\n", actor.GetName().c_str(), layoutData.layoutTransition.layoutTransitionType ); - layoutData.layoutPositionDataArray.push_back( LayoutPositionData( actor, left.AsDecimal(), top.AsDecimal(), right.AsDecimal(), bottom.AsDecimal(), true ) ); - LayoutTransitionData::ConvertChildrenAnimatorsToLayoutDataElements( actor, layoutData ); - } - } - } - else - { - if( changed ) - { - layoutData.layoutPositionDataArray.push_back( LayoutPositionData( actor, left.AsDecimal(), top.AsDecimal(), right.AsDecimal(), bottom.AsDecimal(), false ) ); } } } diff --git a/dali-toolkit/devel-api/layouting/layout-transition-data.h b/dali-toolkit/devel-api/layouting/layout-transition-data.h index d51d28a..6b56301 100644 --- a/dali-toolkit/devel-api/layouting/layout-transition-data.h +++ b/dali-toolkit/devel-api/layouting/layout-transition-data.h @@ -50,17 +50,29 @@ public: { enum Type { - CONDITION, ///< A condition triggering the transition animation (the actor is added/removed/focus gained/focus lost) - PROPERTY, ///< A property to animate - INITIAL_VALUE, ///< Initial value of an animated property - TARGET_VALUE, ///< Target value of an animated property - ANIMATOR, ///< Animator for an animated property - TYPE, ///< Type of an animator - NAME, ///< Name of an animator - TIME_PERIOD, ///< Time period of an property animation - DURATION, ///< Duration of an property animation - DELAY, ///< Delay of an property animation - ALPHA_FUNCTION, ///< Alpha function of a property animation + CONDITION, ///< A condition triggering the transition animation (the actor is added/removed/focus gained/focus lost) + PROPERTY, ///< A property to animate + INITIAL_VALUE, ///< Initial value of an animated property + TARGET_VALUE, ///< Target value of an animated property + ANIMATOR, ///< Animator for an animated property + TYPE, ///< Type of an animator + NAME, ///< Name of an animator + TIME_PERIOD, ///< Time period of an property animation + DURATION, ///< Duration of an property animation + DELAY, ///< Delay of an property animation + ALPHA_FUNCTION, ///< Alpha function of a property animation + AFFECTS_SIBLINGS, ///< Might change the actor siblings positions etc by updating the actor measured size if the actor size is changed due to the animation. False by default. + }; + }; + + struct Animator + { + enum Type + { + ANIMATE_TO, ///< Animate to property target value + ANIMATE_BY, ///< Animate by property target value + ANIMATE_BETWEEN, ///< Animate between property initial and target values + ANIMATE_PATH ///< Animate using the animation path }; }; diff --git a/dali-toolkit/internal/layouting/layout-controller-impl.cpp b/dali-toolkit/internal/layouting/layout-controller-impl.cpp index d2e0119..746e8e5 100644 --- a/dali-toolkit/internal/layouting/layout-controller-impl.cpp +++ b/dali-toolkit/internal/layouting/layout-controller-impl.cpp @@ -127,17 +127,11 @@ void LayoutController::Process() MeasureSpec widthSpec( stageWidth, MeasureSpec::Mode::EXACTLY ); MeasureSpec heightSpec( stageHeight, MeasureSpec::Mode::EXACTLY ); - // Test how to perform a measure on each control. - MeasureHierarchy( stage.GetRootLayer(), widthSpec, heightSpec ); - - LAYOUT_DEBUG_MEASURE_STATES( stage.GetRootLayer() ); - LayoutTransition layoutTransition; LayoutPositionDataArray layoutPositionDataArray; - LayoutDataArray layoutDataArray; LayoutAnimatorArray layoutAnimatorArray; - layoutAnimatorArray.push_back( LayoutDataAnimator() ); - PropertyAnimatorArray childrenPropertiesAnimators; + LayoutDataArray layoutDataArray; + LayoutDataArray childrenLayoutDataArray; if ( mLayoutTransitions.size() ) { @@ -150,8 +144,28 @@ void LayoutController::Process() mLayoutRequested = false; } - LayoutData layoutData( layoutTransition, layoutPositionDataArray, layoutDataArray, layoutAnimatorArray, childrenPropertiesAnimators ); + LayoutData layoutData( layoutTransition, layoutPositionDataArray, layoutAnimatorArray, layoutDataArray, childrenLayoutDataArray ); LayoutItem::Impl::sLayoutData = &layoutData; + + if( layoutTransition.layoutTransitionType != -1 ) + { + UpdateMeasureHierarchyForAnimation( layoutData ); + } + + // Test how to perform a measure on each control. + MeasureHierarchy( stage.GetRootLayer(), widthSpec, heightSpec ); + + LAYOUT_DEBUG_MEASURE_STATES( stage.GetRootLayer() ); + + if( layoutTransition.layoutTransitionType != -1 ) + { + RestoreActorsSpecs(); + } + + layoutAnimatorArray.clear(); + layoutDataArray.clear(); + childrenLayoutDataArray.clear(); + PerformLayout( stage.GetRootLayer(), 0, 0, stageWidth, stageHeight ); PerformLayoutPositioning( layoutPositionDataArray, false ); @@ -199,6 +213,93 @@ void LayoutController::MeasureHierarchy( Actor root, MeasureSpec widthSpec, Meas } } +void LayoutController::UpdateMeasureHierarchyForAnimation( LayoutData& layoutData ) +{ + LayoutTransition& layoutTransition = layoutData.layoutTransition; + Actor transitionOwner = Actor::DownCast( layoutTransition.layoutItem.Get()->GetOwner() ); + LayoutTransitionDataPtr layoutTransitionDataPtr = layoutTransition.layoutItem->GetTransitionData( layoutTransition.layoutTransitionType ); + + if( !layoutTransitionDataPtr->HasUpdateMeasuredSize() ) + { + return; + } + + layoutData.updateMeasuredSize = true; + layoutTransitionDataPtr->CollectLayoutDataElements( transitionOwner, layoutData ); + + UpdateMeasureHierarchyForAnimation( transitionOwner, layoutData ); + + for( auto layoutDataElement : layoutData.layoutDataArray ) + { + if( !layoutDataElement.updateMeasuredSize ) + { + continue; + } + + Actor actor = Actor::DownCast( layoutDataElement.handle ); + LayoutDataAnimator animator = layoutData.layoutAnimatorArray[ layoutDataElement.animatorIndex ]; + float width = actor.GetProperty( Toolkit::LayoutItem::ChildProperty::WIDTH_SPECIFICATION ); + float height = actor.GetProperty( Toolkit::LayoutItem::ChildProperty::HEIGHT_SPECIFICATION ); + + if( layoutDataElement.AdjustMeasuredSize( width, height, animator.animatorType ) ) + { + mActorSizeSpecs.push_back( ActorSizeSpec( actor ) ); + actor.SetProperty( Toolkit::LayoutItem::ChildProperty::WIDTH_SPECIFICATION, static_cast( width ) ); + actor.SetProperty( Toolkit::LayoutItem::ChildProperty::HEIGHT_SPECIFICATION, static_cast( height ) ); + } + } + + layoutData.updateMeasuredSize = false; +} + +void LayoutController::UpdateMeasureHierarchyForAnimation( Actor root, LayoutData& layoutData ) +{ + Toolkit::Control control = Toolkit::Control::DownCast( root ); + if( control ) + { + DALI_LOG_INFO( gLogFilter, Debug::Verbose, "LayoutController::UpdateMeasureHierarchyForAnimation control:%s\n", control.GetName().c_str() ); + Internal::Control& controlImpl = GetImplementation( control ); + Internal::Control::Impl& controlDataImpl = Internal::Control::Impl::Get( controlImpl ); + LayoutItemPtr layout = controlDataImpl.GetLayout(); + + if( layout ) + { + auto layoutGroup = Toolkit::LayoutGroup::DownCast( layout.Get() ); + if( layoutGroup ) + { + unsigned int childCount = layoutGroup.GetChildCount(); + for( unsigned int i=0; i= 0 ) + if( layoutDataElement.animatorIndex >= 0 ) { Actor actor = Actor::DownCast( layoutDataElement.handle ); if ( actor ) { LayoutDataAnimator animator = layoutAnimatorArray[ layoutDataElement.animatorIndex ]; TimePeriod timePeriod = TimePeriod( 0, animation.GetDuration() ); - if (animator.timePeriod.durationSeconds >= 0) + if( animator.timePeriod.durationSeconds >= 0 ) { timePeriod = animator.timePeriod; } @@ -275,7 +380,7 @@ void LayoutController::PerformLayoutAnimation( LayoutTransition& layoutTransitio // Other values are set to current actor ones. if( value.GetType() == Property::NONE ) { - if ( layoutDataElement.positionDataIndex < 0) + if( layoutDataElement.positionDataIndex < 0) { auto result = std::find_if( layoutPositionDataArray.begin(), layoutPositionDataArray.end(), [&actor](const LayoutPositionData& iter) { return iter.handle == actor; } ); @@ -283,10 +388,23 @@ void LayoutController::PerformLayoutAnimation( LayoutTransition& layoutTransitio { continue; } - layoutDataElement.positionDataIndex = std::distance(layoutPositionDataArray.begin(), result); + layoutDataElement.positionDataIndex = std::distance( layoutPositionDataArray.begin(), result ); } LayoutPositionData& positionData = layoutPositionDataArray[ layoutDataElement.positionDataIndex ]; + // with updated measured size scale animation the measured size includes scale, so we need to fit in the centre of the measured rectangle + // the real size child so that the all scale related animations placed correctly + if( positionData.updateWithCurrentSize ) + { + Vector3 size = actor.GetCurrentSize(); + float dX = ( ( positionData.right - positionData.left ) - size.width ) / 2; + float dY = ( ( positionData.bottom - positionData.top ) - size.height ) / 2; + positionData.left += dX; + positionData.top += dY; + positionData.right -= dX; + positionData.bottom -= dY; + positionData.updateWithCurrentSize = false; + } switch ( layoutDataElement.propertyIndex ) { @@ -313,7 +431,7 @@ void LayoutController::PerformLayoutAnimation( LayoutTransition& layoutTransitio } } - // Failed to get target value, just move the next one + // Failed to get target value, just move to the next one if( value.GetType() == Property::NONE ) { continue; @@ -327,29 +445,31 @@ void LayoutController::PerformLayoutAnimation( LayoutTransition& layoutTransitio } // Create an animator for the property - switch (animator.animatorType) - { - case LayoutDataAnimator::AnimatorType::ANIMATE_TO: + switch( animator.animatorType ) { - animation.AnimateTo( Property( actor, layoutDataElement.propertyIndex ), value, animator.alphaFunction, timePeriod ); - break; - } - case LayoutDataAnimator::AnimatorType::ANIMATE_BY: - { - animation.AnimateBy( Property( actor, layoutDataElement.propertyIndex ), value, animator.alphaFunction, timePeriod ); - break; - } - case LayoutDataAnimator::AnimatorType::ANIMATE_BETWEEN: - { - animation.AnimateBetween( Property( actor, layoutDataElement.propertyIndex ), animator.keyFrames, animator.alphaFunction, animator.interpolation ); - break; - } - case LayoutDataAnimator::AnimatorType::ANIMATE_PATH: - animation.Animate( actor, animator.path, animator.forward, animator.alphaFunction, timePeriod ); - break; + case Toolkit::LayoutTransitionData::Animator::ANIMATE_TO: + { + animation.AnimateTo( Property( actor, layoutDataElement.propertyIndex ), value, animator.alphaFunction, timePeriod ); + break; + } + case Toolkit::LayoutTransitionData::Animator::ANIMATE_BY: + { + animation.AnimateBy( Property( actor, layoutDataElement.propertyIndex ), value, animator.alphaFunction, timePeriod ); + break; + } + case Toolkit::LayoutTransitionData::Animator::ANIMATE_BETWEEN: + { + animation.AnimateBetween( Property( actor, layoutDataElement.propertyIndex ), animator.keyFrames, animator.alphaFunction, animator.interpolation ); + break; + } + case Toolkit::LayoutTransitionData::Animator::ANIMATE_PATH: + { + animation.Animate( actor, animator.path, animator.forward, animator.alphaFunction, timePeriod ); + break; + } } + isAnimatorAdded = true; } - isAnimatorAdded = true; } } diff --git a/dali-toolkit/internal/layouting/layout-controller-impl.h b/dali-toolkit/internal/layouting/layout-controller-impl.h index 71c947c..7443776 100644 --- a/dali-toolkit/internal/layouting/layout-controller-impl.h +++ b/dali-toolkit/internal/layouting/layout-controller-impl.h @@ -92,6 +92,27 @@ protected: // Implementation of Processor virtual void Process(); private: + struct ActorSizeSpec + { + ActorSizeSpec(Actor actor) + : actor( actor ) + , widthSpec( actor.GetProperty( Toolkit::LayoutItem::ChildProperty::WIDTH_SPECIFICATION ) ) + , heightSpec( actor.GetProperty( Toolkit::LayoutItem::ChildProperty::HEIGHT_SPECIFICATION ) ) + { + } + + Actor actor; + int widthSpec; + int heightSpec; + }; + std::vector mActorSizeSpecs; + + void UpdateMeasureHierarchyForAnimation( LayoutData& layoutData ); + + void UpdateMeasureHierarchyForAnimation( Actor root, LayoutData& layoutData ); + + void RestoreActorsSpecs(); + std::list< LayoutTransition > mLayoutTransitions; struct AnimationFinishedFunctor { diff --git a/dali-toolkit/internal/layouting/layout-transition-data-impl.cpp b/dali-toolkit/internal/layouting/layout-transition-data-impl.cpp index f65f874..fa24192 100644 --- a/dali-toolkit/internal/layouting/layout-transition-data-impl.cpp +++ b/dali-toolkit/internal/layouting/layout-transition-data-impl.cpp @@ -36,6 +36,7 @@ Debug::Filter* gLayoutFilter = Debug::Filter::New( Debug::NoLogging, false, "LOG // Key tokens const char* TOKEN_CONDITION("condition"); +const char* TOKEN_AFFECTS_SIBLINGS("affectsSiblings"); const char* TOKEN_PROPERTY("property"); const char* TOKEN_INITIAL_VALUE("initialValue"); const char* TOKEN_TARGET_VALUE("targetValue"); @@ -47,6 +48,13 @@ const char* TOKEN_DURATION("duration"); const char* TOKEN_DELAY("delay"); const char* TOKEN_ALPHA_FUNCTION("alphaFunction"); +DALI_ENUM_TO_STRING_TABLE_BEGIN( ANIMATOR_TYPE ) +DALI_ENUM_TO_STRING_WITH_SCOPE( Dali::Toolkit::LayoutTransitionData::Animator::Type, ANIMATE_TO ) +DALI_ENUM_TO_STRING_WITH_SCOPE( Dali::Toolkit::LayoutTransitionData::Animator::Type, ANIMATE_BY ) +DALI_ENUM_TO_STRING_WITH_SCOPE( Dali::Toolkit::LayoutTransitionData::Animator::Type, ANIMATE_BETWEEN ) +DALI_ENUM_TO_STRING_WITH_SCOPE( Dali::Toolkit::LayoutTransitionData::Animator::Type, ANIMATE_PATH ) +DALI_ENUM_TO_STRING_TABLE_END( ANIMATOR_TYPE ) + DALI_ENUM_TO_STRING_TABLE_BEGIN( ALPHA_FUNCTION_BUILTIN ) DALI_ENUM_TO_STRING_WITH_SCOPE(Dali::AlphaFunction, LINEAR) DALI_ENUM_TO_STRING_WITH_SCOPE(Dali::AlphaFunction, REVERSE) @@ -72,7 +80,135 @@ namespace Toolkit namespace Internal { -LayoutTransitionData::LayoutTransitionData() +bool LayoutDataElement::AdjustMeasuredSize( float& width, float& height, Toolkit::LayoutTransitionData::Animator::Type animatorType ) +{ + bool adjusted = true; + if( targetValue.GetType() == Property::NONE ) + { + return false; + } + + Actor actor = Actor::DownCast( handle ); + float animateByMultiplier = ( animatorType == Toolkit::LayoutTransitionData::Animator::Type::ANIMATE_BY ) ? 1.0f : 0.0f; + Vector3 size = actor.GetCurrentSize(); + + switch ( targetValue.GetType() ) + { + case Property::Type::VECTOR3: + { + Vector3 value = targetValue.Get(); + switch( propertyIndex ) + { + case Actor::Property::SCALE: + { + width = size.x * ( animateByMultiplier + value.x ); + height = size.y * ( animateByMultiplier + value.y ); + break; + } + case Actor::Property::SIZE: + { + width = value.x + ( animateByMultiplier * size.x ); + height = value.y + ( animateByMultiplier * size.y ); + break; + } + default: + { + adjusted = false; + break; + } + } + break; + } + case Property::Type::FLOAT: + { + float value = targetValue.Get(); + switch( propertyIndex ) + { + case Actor::Property::SCALE_X: + { + width = size.x * ( animateByMultiplier + value ); + break; + } + case Actor::Property::SCALE_Y: + { + height = size.y * ( animateByMultiplier + value ); + break; + } + case Actor::Property::SIZE_WIDTH: + { + width = value + ( animateByMultiplier * size.x ); + break; + } + case Actor::Property::SIZE_HEIGHT: + { + height = value + ( animateByMultiplier * size.y ); + break; + } + default: + { + adjusted = true; + break; + } + } + break; + } + default: + { + adjusted = false; + break; + } + } + + return adjusted; +} + +void LayoutDataElement::UpdatePropertyIndex() +{ + if( propertyIndex == -1 && handle && !propertyName.empty() ) + { + Actor actor = Actor::DownCast( handle ); + propertyIndex = DevelHandle::GetPropertyIndex( actor, Property::Key( propertyName ) ); + } +} + +void LayoutDataElement::UpdateAnimatorIndex( const LayoutAnimatorArray& animators ) +{ + if( animatorIndex == -1 ) + { + if( animatorName.empty() ) + { + animatorIndex = 0; + return; + } + + std::string animatorName = this->animatorName; + auto animator = std::find_if( animators.begin(), animators.end(), [ &animatorName ](const LayoutDataAnimator& iter) { + return ( iter.name == animatorName ); } ); + if( animator != animators.end() ) + { + animatorIndex = std::distance( animators.begin(), animator ); + } + } +} + +void LayoutDataElement::UpdatePositionDataIndex( LayoutData& layoutData ) +{ + positionDataIndex = layoutData.layoutPositionDataArray.size() - 1; + switch( propertyIndex ) + { + case Actor::Property::SCALE: + case Actor::Property::SCALE_X: + case Actor::Property::SCALE_Y: + if( positionDataIndex != -1 && updateMeasuredSize ) + { + layoutData.layoutPositionDataArray[ positionDataIndex ].updateWithCurrentSize = true; + } + break; + } +} + +LayoutTransitionData::LayoutTransitionData() : + mUpdateMeasuredSize( false ) { } @@ -119,17 +255,35 @@ LayoutTransitionData::PropertyAnimator::PropertyAnimator( Actor actor, Property: void LayoutTransitionData::AddPropertyAnimator( Actor actor, Property::Map map ) { - mPropertyAnimators.push_back( PropertyAnimator( actor, map ) ); + LayoutDataElement layoutDataElement; + if( ConvertToLayoutDataElement( PropertyAnimator( actor, map ), layoutDataElement ) ) + { + mLayoutDataElements.push_back( layoutDataElement ); + } + + UpdateAnimatorsIndices(); } void LayoutTransitionData::AddPropertyAnimator( Actor actor, Property::Map map, KeyFrames keyFrames, Animation::Interpolation interpolation ) { - mPropertyAnimators.push_back( PropertyAnimator( actor, map, keyFrames, interpolation ) ); + LayoutDataElement layoutDataElement; + if( ConvertToLayoutDataElement( PropertyAnimator( actor, map, keyFrames, interpolation ), layoutDataElement ) ) + { + mLayoutDataElements.push_back( layoutDataElement ); + } + + UpdateAnimatorsIndices(); } void LayoutTransitionData::AddPropertyAnimator( Actor actor, Property::Map map, Path path, Vector3 forward ) { - mPropertyAnimators.push_back( PropertyAnimator( actor, map, path, forward ) ); + LayoutDataElement layoutDataElement; + if( ConvertToLayoutDataElement( PropertyAnimator( actor, map, path, forward ), layoutDataElement ) ) + { + mLayoutDataElements.push_back( layoutDataElement ); + } + + UpdateAnimatorsIndices(); } bool LayoutTransitionData::ConvertToLayoutAnimator( const Property::Map& animatorMap, const PropertyAnimator& propertyAnimator, LayoutDataAnimator& layoutDataAnimator ) @@ -305,26 +459,30 @@ bool LayoutTransitionData::ConvertToLayoutAnimator( const Property::Map& animato if( value.GetType() == Property::STRING ) { std::string animatorType = value.Get(); - if( animatorType == "ANIMATE_TO" ) + if( animatorType == ANIMATOR_TYPE_TABLE[ Toolkit::LayoutTransitionData::Animator::Type::ANIMATE_TO ].string ) { - layoutDataAnimator.animatorType = LayoutDataAnimator::AnimatorType::ANIMATE_TO; + layoutDataAnimator.animatorType = Toolkit::LayoutTransitionData::Animator::Type::ANIMATE_TO; } - else if( animatorType == "ANIMATE_BY" ) + else if( animatorType == ANIMATOR_TYPE_TABLE[ Toolkit::LayoutTransitionData::Animator::Type::ANIMATE_BY ].string ) { - layoutDataAnimator.animatorType = LayoutDataAnimator::AnimatorType::ANIMATE_BY; + layoutDataAnimator.animatorType = Toolkit::LayoutTransitionData::Animator::Type::ANIMATE_BY; } - else if( animatorType == "ANIMATE_BETWEEN" ) + else if( animatorType == ANIMATOR_TYPE_TABLE[ Toolkit::LayoutTransitionData::Animator::Type::ANIMATE_BETWEEN ].string ) { - layoutDataAnimator.animatorType = LayoutDataAnimator::AnimatorType::ANIMATE_BETWEEN; + layoutDataAnimator.animatorType = Toolkit::LayoutTransitionData::Animator::Type::ANIMATE_BETWEEN; layoutDataAnimator.keyFrames = propertyAnimator.keyFrames; } - else if( animatorType == "ANIMATE_PATH" ) + else if( animatorType == ANIMATOR_TYPE_TABLE[ Toolkit::LayoutTransitionData::Animator::Type::ANIMATE_PATH ].string ) { - layoutDataAnimator.animatorType = LayoutDataAnimator::AnimatorType::ANIMATE_PATH; + layoutDataAnimator.animatorType = Toolkit::LayoutTransitionData::Animator::Type::ANIMATE_PATH; layoutDataAnimator.path = propertyAnimator.path; layoutDataAnimator.forward = propertyAnimator.forward; } } + else if ( value.GetType() == Property::INTEGER ) + { + layoutDataAnimator.animatorType = static_cast( pair.second.Get() ); + } } else if ( indexKey == Dali::Toolkit::LayoutTransitionData::AnimatorKey::TIME_PERIOD ) { @@ -366,11 +524,19 @@ bool LayoutTransitionData::ConvertToLayoutAnimator( const Property::Map& animato return valid; } -bool LayoutTransitionData::ConvertToLayoutDataElement( const PropertyAnimator& propertyAnimator, LayoutDataElement& layoutDataElement, LayoutData& layoutData ) +bool LayoutTransitionData::ConvertToLayoutDataElement( + const PropertyAnimator& propertyAnimator, LayoutDataElement& layoutDataElement ) { const Property::Map& map = propertyAnimator.map; bool propertyFound = false; + if( mLayoutAnimators.size() == 0 ) + { + mLayoutAnimators.push_back( LayoutDataAnimator() ); + } + + layoutDataElement.handle = propertyAnimator.handle; + for( unsigned int mapIdx = 0; mapIdx < map.Count(); ++mapIdx ) { const KeyValuePair pair( map.GetKeyValue( mapIdx ) ); @@ -400,6 +566,10 @@ bool LayoutTransitionData::ConvertToLayoutDataElement( const PropertyAnimator& p { indexKey = Dali::Toolkit::LayoutTransitionData::AnimatorKey::ANIMATOR; } + else if( key == TOKEN_AFFECTS_SIBLINGS ) + { + indexKey = Dali::Toolkit::LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS; + } } else { @@ -410,12 +580,20 @@ bool LayoutTransitionData::ConvertToLayoutDataElement( const PropertyAnimator& p { layoutDataElement.condition = value.Get(); } + else if ( indexKey == Dali::Toolkit::LayoutTransitionData::AnimatorKey::AFFECTS_SIBLINGS ) + { + layoutDataElement.updateMeasuredSize = value.Get(); + if( layoutDataElement.updateMeasuredSize ) + { + mUpdateMeasuredSize = true; + } + } else if( indexKey == Dali::Toolkit::LayoutTransitionData::AnimatorKey::PROPERTY ) { if( value.GetType() == Property::STRING ) { - Actor actor = Actor::DownCast( layoutDataElement.handle ); - layoutDataElement.propertyIndex = DevelHandle::GetPropertyIndex( actor, Property::Key( value.Get() ) ); + layoutDataElement.propertyName = value.Get(); + layoutDataElement.UpdatePropertyIndex(); } else { @@ -435,20 +613,8 @@ bool LayoutTransitionData::ConvertToLayoutDataElement( const PropertyAnimator& p { if( value.GetType() == Property::STRING ) { - std::string animatorName = value.Get(); - if ( animatorName.empty() ) - { - layoutDataElement.animatorIndex = 0; - } - else - { - auto animator = std::find_if( layoutData.layoutAnimatorArray.begin(), layoutData.layoutAnimatorArray.end(), [&animatorName](const LayoutDataAnimator& iter) { - return (iter.name == animatorName); } ); - if( animator != layoutData.layoutAnimatorArray.end() ) - { - layoutDataElement.animatorIndex = std::distance( layoutData.layoutAnimatorArray.begin(), animator ); - } - } + layoutDataElement.animatorName = value.Get(); + layoutDataElement.UpdateAnimatorIndex( mLayoutAnimators ); } else if ( value.GetType() == Property::MAP ) { @@ -456,8 +622,8 @@ bool LayoutTransitionData::ConvertToLayoutDataElement( const PropertyAnimator& p LayoutDataAnimator layoutDataAnimator; if( ConvertToLayoutAnimator( animatorMap, propertyAnimator, layoutDataAnimator ) ) { - layoutData.layoutAnimatorArray.push_back( layoutDataAnimator ); - layoutDataElement.animatorIndex = layoutData.layoutAnimatorArray.size()-1; + mLayoutAnimators.push_back( layoutDataAnimator ); + layoutDataElement.animatorIndex = mLayoutAnimators.size() - 1; } } } @@ -466,20 +632,20 @@ bool LayoutTransitionData::ConvertToLayoutDataElement( const PropertyAnimator& p return propertyFound; } -void LayoutTransitionData::ConvertChildrenAnimatorsToLayoutDataElements( Actor child, LayoutData& layoutData ) +void LayoutTransitionData::CollectChildrenLayoutDataElements( Actor child, LayoutData& layoutData ) { LayoutDataArray& layoutDataArray = layoutData.layoutDataArray; // Add the children animators - for( const PropertyAnimator& iter : layoutData.childrenPropertyAnimators ) + for( const LayoutDataElement& iter : layoutData.childrenLayoutDataArray ) { - LayoutDataElement layoutDataElement; - layoutDataElement.handle = child; - layoutDataElement.positionDataIndex = layoutData.layoutPositionDataArray.size() - 1; + if( iter.handle != nullptr && iter.handle != child ) + { + continue; + } - if( ConvertToLayoutDataElement( iter, layoutDataElement, layoutData ) ) + LayoutDataElement layoutDataElement = iter; + switch ( layoutDataElement.condition ) { - switch ( layoutDataElement.condition ) - { case Dali::Toolkit::LayoutTransitionData::Condition::ON_ADD: if ( layoutData.layoutTransition.layoutTransitionType != Dali::Toolkit::LayoutTransitionData::ON_CHILD_ADD || layoutData.layoutTransition.gainedChild != child ) @@ -510,35 +676,58 @@ void LayoutTransitionData::ConvertChildrenAnimatorsToLayoutDataElements( Actor c break; default: break; - } + } - layoutDataArray.push_back( layoutDataElement ); + if( layoutData.updateMeasuredSize && !layoutDataElement.updateMeasuredSize ) + { + continue; } + + layoutDataElement.handle = child; + layoutDataElement.UpdatePropertyIndex(); + layoutDataElement.UpdatePositionDataIndex( layoutData ); + layoutDataArray.push_back( layoutDataElement ); } } -void LayoutTransitionData::ConvertToLayoutDataElements( Actor owner, LayoutData& layoutData ) +void LayoutTransitionData::UpdateAnimatorsIndices() { - LayoutDataArray& layoutDataArray = layoutData.layoutDataArray; + for( LayoutDataElement& iter: mLayoutDataElements ) + { + iter.UpdateAnimatorIndex( mLayoutAnimators ); + } +} - // Add the children animators - ConvertChildrenAnimatorsToLayoutDataElements( owner, layoutData ); +void LayoutTransitionData::CollectLayoutDataElements( Actor owner, LayoutData& layoutData ) +{ + LayoutAnimatorArray& layoutAnimatorArray = layoutData.layoutAnimatorArray; + LayoutAnimatorArray::iterator it = mLayoutAnimators.begin(); + if (layoutAnimatorArray.size() != 0) + { + // skip default animator + ++it; + } + std::copy( it, mLayoutAnimators.end(), std::back_inserter( layoutAnimatorArray ) ); - // Add the transition animators - for( const PropertyAnimator& iter : mPropertyAnimators ) + LayoutDataArray& layoutDataArray = layoutData.layoutDataArray; + // Collect the transition animators + for( const LayoutDataElement& iter : mLayoutDataElements ) { - if( iter.handle == nullptr ) + if( iter.handle == nullptr || iter.handle != owner ) { - layoutData.childrenPropertyAnimators.push_back( iter ); + layoutData.childrenLayoutDataArray.push_back( iter ); continue; } - LayoutDataElement layoutDataElement; - layoutDataElement.handle = iter.handle; - if( ConvertToLayoutDataElement( iter, layoutDataElement, layoutData ) ) + LayoutDataElement layoutDataElement = iter; + if( layoutData.updateMeasuredSize && !layoutDataElement.updateMeasuredSize ) { - layoutDataArray.push_back( layoutDataElement ); + continue; } + + layoutDataElement.UpdatePropertyIndex(); + layoutDataElement.UpdatePositionDataIndex( layoutData ); + layoutDataArray.push_back( layoutDataElement ); } } @@ -556,6 +745,11 @@ void LayoutTransitionData::EmitSignalFinish( int layoutTransitionType ) } } +bool LayoutTransitionData::HasUpdateMeasuredSize() +{ + return mUpdateMeasuredSize; +} + } // namespace Internal } // namespace Toolkit } // namespace Dali diff --git a/dali-toolkit/internal/layouting/layout-transition-data-impl.h b/dali-toolkit/internal/layouting/layout-transition-data-impl.h index dec0b76..348f2d9 100644 --- a/dali-toolkit/internal/layouting/layout-transition-data-impl.h +++ b/dali-toolkit/internal/layouting/layout-transition-data-impl.h @@ -68,16 +68,8 @@ const float DEFAULT_TRANSITION_DURATION( 0.5f ); struct LayoutDataAnimator { - enum class AnimatorType - { - ANIMATE_TO, - ANIMATE_BY, - ANIMATE_BETWEEN, - ANIMATE_PATH - }; - LayoutDataAnimator() - : animatorType( AnimatorType::ANIMATE_TO ), + : animatorType( Toolkit::LayoutTransitionData::Animator::ANIMATE_TO ), alphaFunction( AlphaFunction::LINEAR ), timePeriod( 0.0f, DEFAULT_TRANSITION_DURATION ), interpolation( Animation::Linear ) @@ -85,7 +77,7 @@ struct LayoutDataAnimator } std::string name; - AnimatorType animatorType; + Toolkit::LayoutTransitionData::Animator::Type animatorType; AlphaFunction alphaFunction; TimePeriod timePeriod; @@ -101,7 +93,7 @@ using LayoutAnimatorArray = std::vector< LayoutDataAnimator >; struct LayoutPositionData { LayoutPositionData( Handle handle, float left, float top, float right, float bottom, bool animated ) : - handle( handle ), left( left ), top( top ), right( right ), bottom( bottom ), animated( animated ) + handle( handle ), left( left ), top( top ), right( right ), bottom( bottom ), animated( animated ), updateWithCurrentSize(false) { }; @@ -111,6 +103,7 @@ struct LayoutPositionData float right; float bottom; bool animated; + bool updateWithCurrentSize; }; using LayoutPositionDataArray = std::vector< LayoutPositionData >; @@ -121,19 +114,30 @@ struct LayoutDataElement : propertyIndex( Property::INVALID_KEY ), animatorIndex( -1 ), positionDataIndex(-1 ), - condition( Dali::Toolkit::LayoutTransitionData::Condition::NONE ) + condition( Dali::Toolkit::LayoutTransitionData::Condition::NONE ), + updateMeasuredSize( false ) { }; + bool AdjustMeasuredSize( float& width, float& height, Toolkit::LayoutTransitionData::Animator::Type animatorType ); + void UpdatePropertyIndex(); + void UpdateAnimatorIndex( const LayoutAnimatorArray& animators ); + void UpdatePositionDataIndex( LayoutData& layoutData ); + BaseHandle handle; + std::string propertyName; Property::Index propertyIndex; Property::Value initialValue; Property::Value targetValue; + std::string animatorName; int animatorIndex; int positionDataIndex; int condition; + bool updateMeasuredSize; }; +using LayoutDataArray = std::vector< LayoutDataElement >; + class LayoutTransitionData; using LayoutTransitionDataPtr = IntrusivePtr; @@ -160,7 +164,6 @@ public: Path path; Vector3 forward; }; - using PropertyAnimatorArray = std::vector< PropertyAnimator >; static LayoutTransitionDataPtr New(); @@ -173,7 +176,7 @@ public: * @param[in] actor The actor * @param[in] map The map containing the transition animator keys * - * This will add the property animator to the list of animators related to this transition + * This will parse the property animator map and add the layout data element to the array of layout data elements related to this transition */ void AddPropertyAnimator( Actor actor, Property::Map map ); @@ -184,7 +187,7 @@ public: * @param[in] keyFrames The key frames used by the property animator * @param[in] interpolation The interpolation used by the property animator * - * This will add the property animator to the list of animators related to this transition + * This will parse the property animator map and add the layout data element to the array of layout data elements related to this transition */ void AddPropertyAnimator( Actor actor, Property::Map map, KeyFrames keyFrames, Animation::Interpolation interpolation ); @@ -195,27 +198,27 @@ public: * @param[in] path The path for the property animator * @param[in] forward The forward vector for the property animator * - * This will add the property animator to the list of animators related to this transition + * This will parse the property animator map and add the layout data element to the array of layout data elements related to this transition */ void AddPropertyAnimator( Actor actor, Property::Map map, Path path, Vector3 forward ); /** - * @brief Convert the transition property animators to the layout data elements + * @brief Collect the transition layout data elements * @param[in] actor The actor the transition property animators are applied to * @param[in] layoutData The layout data containing layout data elements array for the layout update * - * This will parse the property animators and add the layout data elements to the layout data elements array + * This will copy the transition layout data elements to the layout data elements array */ - void ConvertToLayoutDataElements( Actor, LayoutData& layoutData ); + void CollectLayoutDataElements( Actor, LayoutData& layoutData ); /** - * @brief Convert the transition children property animators to the layout data elements + * @brief Collect the transition children layout data elements * @param[in] actor The actor the transition property animators are applied to * @param[in] layoutData The layout data containing layout data elements array for the layout update * - * This will parse the children property animators and add the layout data elements to the layout data elements array + * This will copy the children transition layout data elements to the layout data elements array */ - static void ConvertChildrenAnimatorsToLayoutDataElements( Actor, LayoutData& layoutData ); + static void CollectChildrenLayoutDataElements( Actor, LayoutData& layoutData ); /** * @copydoc Dali::Toolkit::LayoutTransitionData::FinishedSignal() @@ -228,6 +231,11 @@ public: */ void EmitSignalFinish( int layoutTransitionType ); + /** + * @brief Check if one of the layout data elements has updateMeasuredSize flag set + */ + bool HasUpdateMeasuredSize(); + private: /** * @brief Convert the property animator data to the layout data animator @@ -235,9 +243,9 @@ private: * @param[in] propertyAnimator The property animator * @param[in] layoutAnimator The layout animator * - * This will parse the property animator data and add the layout data element animator + * This will parse the property animator map and add the layout data element animator to the layout animators array */ - static bool ConvertToLayoutAnimator( const Property::Map& animatorData, const PropertyAnimator& propertyAnimator, LayoutDataAnimator& layoutAnimator ); + bool ConvertToLayoutAnimator( const Property::Map& animatorData, const PropertyAnimator& propertyAnimator, LayoutDataAnimator& layoutAnimator ); /** * @brief Convert the property animator to the layout data element @@ -245,11 +253,15 @@ private: * @param[in] layoutDataElement The layout data element * @param[in] layoutDataElement The layout data * - * This will parse the children property animators and add the layout data elements to the layout data elements array + * This will parse the property animator map and add the layout data element to the layout data elements array */ - static bool ConvertToLayoutDataElement( const PropertyAnimator& propertyAnimator, LayoutDataElement& layoutDataElement, LayoutData& layoutData ); + bool ConvertToLayoutDataElement( const PropertyAnimator& propertyAnimator, LayoutDataElement& layoutDataElement ); - PropertyAnimatorArray mPropertyAnimators; + void UpdateAnimatorsIndices(); + + bool mUpdateMeasuredSize; + LayoutAnimatorArray mLayoutAnimators; + LayoutDataArray mLayoutDataElements; /** * Ref counted object - Only allow construction via New(). @@ -271,23 +283,25 @@ using LayoutDataArray = std::vector< LayoutDataElement >; struct LayoutData { - LayoutData( LayoutTransition& layoutTransition, LayoutPositionDataArray& layoutPositionDataArray, LayoutDataArray& layoutDataArray, - LayoutAnimatorArray& layoutAnimatorArray, PropertyAnimatorArray& childrenPropertyAnimators ) + LayoutData( LayoutTransition& layoutTransition, LayoutPositionDataArray& layoutPositionDataArray, LayoutAnimatorArray& layoutAnimatorArray, + LayoutDataArray& layoutDataArray, LayoutDataArray& childrenLayoutDataArray ) : speculativeLayout( false ), + updateMeasuredSize( false ), layoutTransition( layoutTransition ), layoutPositionDataArray( layoutPositionDataArray ), - layoutDataArray( layoutDataArray), layoutAnimatorArray( layoutAnimatorArray ), - childrenPropertyAnimators( childrenPropertyAnimators ) + layoutDataArray( layoutDataArray), + childrenLayoutDataArray( childrenLayoutDataArray ) { }; bool speculativeLayout; + bool updateMeasuredSize; LayoutTransition& layoutTransition; LayoutPositionDataArray& layoutPositionDataArray; - LayoutDataArray& layoutDataArray; LayoutAnimatorArray& layoutAnimatorArray; - PropertyAnimatorArray& childrenPropertyAnimators; + LayoutDataArray& layoutDataArray; + LayoutDataArray& childrenLayoutDataArray; }; } //namespace Internal -- 2.7.4