From: Agnelo Vaz Date: Fri, 26 Oct 2018 16:30:14 +0000 (+0100) Subject: Setting layout already in use X-Git-Tag: dali_1.3.48~2 X-Git-Url: http://review.tizen.org/git/?p=platform%2Fcore%2Fuifw%2Fdali-toolkit.git;a=commitdiff_plain;h=f03adf37a72ffbbd03e75cc263908aeb368f953c;hp=03915a08214a088623b6e21be5287ab15d351325 Setting layout already in use If a control is using a layout and that layout is then set to another control the original control gets a BinLayout. Change-Id: I482d00239eaec765126b3554b982c8e86ab135f6 --- diff --git a/automated-tests/src/dali-toolkit/utc-Dali-LayoutingSettingAndRemoval.cpp b/automated-tests/src/dali-toolkit/utc-Dali-LayoutingSettingAndRemoval.cpp index b55afd6..7e12c1c 100644 --- a/automated-tests/src/dali-toolkit/utc-Dali-LayoutingSettingAndRemoval.cpp +++ b/automated-tests/src/dali-toolkit/utc-Dali-LayoutingSettingAndRemoval.cpp @@ -233,4 +233,85 @@ int UtcDaliLayoutingSettingAndRemoval_RemoveLayoutFromHbox(void) DALI_TEST_EQUALS( controls[1].GetProperty( Actor::Property::SIZE ), Vector3( 60.0f, 40.0f, 0.0f ), 0.0001f, TEST_LOCATION ); END_TEST; -} \ No newline at end of file +} + +int UtcDaliLayouting_SetLayoutAlreadyInUse(void) +{ + /* + 1 ControlA (LinearLayoutA) + 2 Add 3 children + + 3 ControlB (LinearLayoutA) + 4 Add 4 children + + Test number of children in each control/layout + + LinearLayoutA should now have 4 children + + ControlB should have 4 children too + ControlA should have 3 children. + + */ + + ToolkitTestApplication application; + tet_infoline(" UtcDaliLayouting_SetLayoutAlreadyInUse - Set layout belonging to controlA to controlB"); + + Stage stage = Stage::GetCurrent(); + + auto rootControl = Control::New(); + auto absoluteLayout = AbsoluteLayout::New(); + DevelControl::SetLayout( rootControl, absoluteLayout ); + rootControl.SetName( "AbsoluteLayout" ); + stage.Add( rootControl ); + + auto controlA = Control::New(); + auto hboxLayout = LinearLayout::New(); + controlA.SetName( "controlA"); + + rootControl.Add( controlA ); + + DevelControl::SetLayout( controlA, hboxLayout ); + + // Add child controls + std::vector< Control > controls; + controls.push_back( CreateLeafControl( 100, 100 ) ); // 0 + controls.push_back( CreateLeafControl( 100, 100 ) ); // 1 + controls.push_back( CreateLeafControl( 100, 100 ) ); // 2 + + for( auto&& iter : controls ) + { + controlA.Add( iter ); + } + + // Ensure layouting happens + application.SendNotification(); + application.Render(); + + tet_infoline("SetLayout to another control"); + + auto controlB = Control::New(); + controlB.SetName( "controlB"); + + std::vector< Control > moreControls; + moreControls.push_back( CreateLeafControl( 100, 100 ) ); // 0 + moreControls.push_back( CreateLeafControl( 100, 100 ) ); // 1 + moreControls.push_back( CreateLeafControl( 100, 100 ) ); // 3 + moreControls.push_back( CreateLeafControl( 100, 100 ) ); // 4 + + for( auto&& iter : moreControls ) + { + controlB.Add( iter ); + } + + DevelControl::SetLayout( controlB, hboxLayout ); // Set hboxLayout used by ControlA to ControlB + + // Ensure layouting happens + application.SendNotification(); + application.Render(); + + tet_infoline("Get number of children in each control's layout"); + DALI_TEST_EQUALS( ( LayoutGroup::DownCast( DevelControl::GetLayout( controlA ) ) ).GetChildCount(), 3 , TEST_LOCATION ); + DALI_TEST_EQUALS( ( LayoutGroup::DownCast( DevelControl::GetLayout( controlB ) ) ).GetChildCount(), 4 , TEST_LOCATION ); + + END_TEST; +} diff --git a/dali-toolkit/devel-api/controls/control-devel.h b/dali-toolkit/devel-api/controls/control-devel.h index 52a0d4a..404a9ec 100755 --- a/dali-toolkit/devel-api/controls/control-devel.h +++ b/dali-toolkit/devel-api/controls/control-devel.h @@ -291,6 +291,9 @@ DALI_TOOLKIT_API Toolkit::LayoutItem GetLayout( Control control ); * @param[in] layout Pointer to the layout * @note Providing an empty layout will remove the current layout and * replace it with a BinLayout. + * Setting a layout that has already been set will result in the + * original control becoming a BinLayout. Two Controls can not share + * the same layout. */ DALI_TOOLKIT_API void SetLayout( Internal::Control& control, Toolkit::LayoutItem layout ); diff --git a/dali-toolkit/internal/controls/control/control-data-impl.cpp b/dali-toolkit/internal/controls/control/control-data-impl.cpp index c5af35e..a8387ee 100755 --- a/dali-toolkit/internal/controls/control/control-data-impl.cpp +++ b/dali-toolkit/internal/controls/control/control-data-impl.cpp @@ -1441,15 +1441,35 @@ Toolkit::Internal::LayoutItemPtr Control::Impl::GetLayout() const void Control::Impl::SetLayout( Toolkit::Internal::LayoutItem& layout ) { - DALI_LOG_INFO( gLogFilterLayout, Debug::Verbose, "Control::SetLayout control:%s existing layout:%s\n", + DALI_LOG_INFO( gLogFilterLayout, Debug::Verbose, "Control::SetLayout control:%s replacing existing layout:%s\n", mControlImpl.Self().GetName().c_str(), mLayout?"true":"false" ); + // Check if layout already has an owner. + auto control = Toolkit::Control::DownCast( layout.GetOwner() ); + if ( control ) + { + // If the owner is not this control then the owning control can no longer own it. + Dali::Toolkit::Control handle( mControlImpl.GetOwner() ); + if( control != handle ) + { + DALI_LOG_INFO( gLogFilterLayout, Debug::Verbose, "Control::SetLayout Layout already in use, %s will now have a BinLayout\n", + control.GetName().c_str() ); + Toolkit::BinLayout binLayout = Toolkit::BinLayout::New(); + // Previous owner of the layout gets a BinLayout instead of the layout. + DevelControl::SetLayout( control, binLayout ) ; + } + else + { + return; // layout is already set to this control. + } + } if( mLayout ) { mLayout->Unparent(); mLayout.Reset(); } + mLayout = &layout; auto controlHandle = Toolkit::Control::DownCast( mControlImpl.Self() ); // Get a handle of this control implementation without copying internals.