2 * Copyright (c) 2020 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.
19 #include <dali-toolkit/internal/controls/scroll-bar/scroll-bar-impl.h>
22 #include <cstring> // for strcmp
23 #include <dali/public-api/animation/constraint.h>
24 #include <dali/public-api/animation/constraints.h>
25 #include <dali/public-api/object/type-registry.h>
26 #include <dali/public-api/object/property-array.h>
27 #include <dali/public-api/object/type-registry-helper.h>
28 #include <dali/integration-api/debug.h>
29 #include <dali/devel-api/object/property-helper-devel.h>
30 #include <dali/devel-api/actors/actor-devel.h>
33 #include <dali-toolkit/devel-api/asset-manager/asset-manager.h>
34 #include <dali-toolkit/internal/controls/scrollable/item-view/item-view-impl.h>
35 #include <dali-toolkit/public-api/controls/image-view/image-view.h>
42 const char* DEFAULT_INDICATOR_IMAGE_FILE_NAME = "popup_scroll.9.png";
43 const float DEFAULT_SLIDER_DEPTH(1.0f);
44 const float DEFAULT_INDICATOR_SHOW_DURATION(0.5f);
45 const float DEFAULT_INDICATOR_HIDE_DURATION(0.5f);
46 const float DEFAULT_PAN_GESTURE_PROCESS_TIME(16.7f); // 16.7 milliseconds, i.e. one frame
47 const float DEFAULT_INDICATOR_FIXED_HEIGHT(80.0f);
48 const float DEFAULT_INDICATOR_MINIMUM_HEIGHT(0.0f);
49 const float DEFAULT_INDICATOR_START_PADDING(0.0f);
50 const float DEFAULT_INDICATOR_END_PADDING(0.0f);
51 const float DEFAULT_INDICATOR_TRANSIENT_DURATION(1.0f);
54 * Indicator size constraint
55 * Indicator size depends on both indicator's parent size and the scroll content size
57 struct IndicatorSizeConstraint
60 * @param[in] minimumHeight The minimum height for the indicator
61 * @param[in] padding The sum of the padding at the start & end of the indicator
63 IndicatorSizeConstraint( float minimumHeight, float padding )
64 : mMinimumHeight( minimumHeight ),
71 * @param[in] current The current indicator size
72 * @param[in] parentSizeProperty The parent size of scroll indicator.
73 * @return The new scroll indicator size.
75 void operator()( Vector3& current, const PropertyInputContainer& inputs )
77 const Vector3& parentSize = inputs[0]->GetVector3();
78 const float contentSize = inputs[1]->GetFloat();
80 // Take into account padding that may exist at the beginning and end of the indicator.
81 const float parentHeightMinusPadding = parentSize.height - mPadding;
83 float height = contentSize > parentHeightMinusPadding ?
84 parentHeightMinusPadding * ( parentHeightMinusPadding / contentSize ) :
85 parentHeightMinusPadding * ( ( parentHeightMinusPadding - contentSize * 0.5f ) / parentHeightMinusPadding );
87 current.y = std::max( mMinimumHeight, height );
95 * Indicator position constraint
96 * Positions the indicator to reflect the current scroll position within the scroll domain.
98 struct IndicatorPositionConstraint
101 * @param[in] startPadding The padding at the start of the indicator
102 * @param[in] endPadding The padding at the end of the indicator
104 IndicatorPositionConstraint( float startPadding, float endPadding )
105 : mStartPadding( startPadding ),
106 mEndPadding( endPadding )
111 * Constraint operator
112 * @param[in,out] current The current indicator position
113 * @param[in] inputs Contains the size of indicator, the size of indicator's parent, and the scroll position of the scrollable container (from 0.0 -> 1.0 in each axis)
114 * @return The new indicator position is returned.
116 void operator()( Vector3& current, const PropertyInputContainer& inputs )
118 const Vector3& indicatorSize = inputs[0]->GetVector3();
119 const Vector3& parentSize = inputs[1]->GetVector3();
120 const float scrollPosition = -inputs[2]->GetFloat();
121 const float minimumScrollPosition = inputs[3]->GetFloat();
122 const float maximumScrollPosition = inputs[4]->GetFloat();
124 // Take into account padding that may exist at the beginning and end of the indicator.
125 const float parentHeightMinusPadding = parentSize.height - ( mStartPadding + mEndPadding );
127 float relativePosition = std::max( 0.0f, std::min( 1.0f, ( scrollPosition - minimumScrollPosition ) / ( maximumScrollPosition - minimumScrollPosition ) ) );
128 current.y = mStartPadding + ( parentHeightMinusPadding - indicatorSize.height ) * relativePosition;
129 current.z = DEFAULT_SLIDER_DEPTH;
136 } // unnamed namespace
150 using namespace Dali;
154 return Toolkit::ScrollBar::New();
157 // Setup properties, signals and actions using the type-registry.
158 DALI_TYPE_REGISTRATION_BEGIN( Toolkit::ScrollBar, Toolkit::Control, Create );
160 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "scrollDirection", STRING, SCROLL_DIRECTION )
161 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "indicatorHeightPolicy", STRING, INDICATOR_HEIGHT_POLICY )
162 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "indicatorFixedHeight", FLOAT, INDICATOR_FIXED_HEIGHT )
163 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "indicatorShowDuration", FLOAT, INDICATOR_SHOW_DURATION )
164 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "indicatorHideDuration", FLOAT, INDICATOR_HIDE_DURATION )
165 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "scrollPositionIntervals", ARRAY, SCROLL_POSITION_INTERVALS )
166 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "indicatorMinimumHeight", FLOAT, INDICATOR_MINIMUM_HEIGHT )
167 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "indicatorStartPadding", FLOAT, INDICATOR_START_PADDING )
168 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "indicatorEndPadding", FLOAT, INDICATOR_END_PADDING )
169 DALI_PROPERTY_REGISTRATION( Toolkit, ScrollBar, "indicatorTransientDuration", FLOAT, INDICATOR_TRANSIENT_DURATION )
171 DALI_SIGNAL_REGISTRATION( Toolkit, ScrollBar, "panFinished", PAN_FINISHED_SIGNAL )
172 DALI_SIGNAL_REGISTRATION( Toolkit, ScrollBar, "scrollPositionIntervalReached", SCROLL_POSITION_INTERVAL_REACHED_SIGNAL )
174 DALI_ACTION_REGISTRATION( Toolkit, ScrollBar, "ShowIndicator", ACTION_SHOW_INDICATOR )
175 DALI_ACTION_REGISTRATION( Toolkit, ScrollBar, "HideIndicator", ACTION_HIDE_INDICATOR )
176 DALI_ACTION_REGISTRATION( Toolkit, ScrollBar, "ShowTransientIndicator", ACTION_SHOW_TRANSIENT_INDICATOR )
178 DALI_TYPE_REGISTRATION_END()
180 const char* SCROLL_DIRECTION_NAME[] = {"VERTICAL", "HORIZONTAL"};
181 const char* INDICATOR_HEIGHT_POLICY_NAME[] = {"VARIABLE", "FIXED"};
185 ScrollBar::ScrollBar(Toolkit::ScrollBar::Direction direction)
186 : Control( ControlBehaviour( CONTROL_BEHAVIOUR_DEFAULT ) ),
187 mIndicatorShowAlpha(1.0f),
188 mDirection(direction),
189 mScrollableObject(WeakHandle<Handle>()),
190 mPropertyScrollPosition(Property::INVALID_INDEX),
191 mPropertyMinScrollPosition(Property::INVALID_INDEX),
192 mPropertyMaxScrollPosition(Property::INVALID_INDEX),
193 mPropertyScrollContentSize(Property::INVALID_INDEX),
194 mIndicatorShowDuration(DEFAULT_INDICATOR_SHOW_DURATION),
195 mIndicatorHideDuration(DEFAULT_INDICATOR_HIDE_DURATION),
196 mTransientIndicatorDuration(DEFAULT_INDICATOR_TRANSIENT_DURATION),
198 mGestureDisplacement( Vector2::ZERO ),
199 mCurrentScrollPosition(0.0f),
200 mIndicatorHeightPolicy(Toolkit::ScrollBar::VARIABLE),
201 mIndicatorFixedHeight(DEFAULT_INDICATOR_FIXED_HEIGHT),
202 mIndicatorMinimumHeight(DEFAULT_INDICATOR_MINIMUM_HEIGHT),
203 mIndicatorStartPadding(DEFAULT_INDICATOR_START_PADDING),
204 mIndicatorEndPadding(DEFAULT_INDICATOR_END_PADDING),
206 mIndicatorFirstShow(true)
210 ScrollBar::~ScrollBar()
214 void ScrollBar::OnInitialize()
216 CreateDefaultIndicatorActor();
217 Self().SetProperty( Actor::Property::DRAW_MODE,DrawMode::OVERLAY_2D);
219 DevelControl::SetAccessibilityConstructor( Self(), []( Dali::Actor actor ) {
220 return std::unique_ptr< Dali::Accessibility::Accessible >(
221 new AccessibleImpl( actor, Dali::Accessibility::Role::SCROLL_BAR ) );
225 void ScrollBar::SetScrollPropertySource( Handle handle, Property::Index propertyScrollPosition, Property::Index propertyMinScrollPosition, Property::Index propertyMaxScrollPosition, Property::Index propertyScrollContentSize )
228 && propertyScrollPosition != Property::INVALID_INDEX
229 && propertyMinScrollPosition != Property::INVALID_INDEX
230 && propertyMaxScrollPosition != Property::INVALID_INDEX
231 && propertyScrollContentSize != Property::INVALID_INDEX )
233 mScrollableObject = WeakHandle<Handle>(handle);
234 mPropertyScrollPosition = propertyScrollPosition;
235 mPropertyMinScrollPosition = propertyMinScrollPosition;
236 mPropertyMaxScrollPosition = propertyMaxScrollPosition;
237 mPropertyScrollContentSize = propertyScrollContentSize;
243 DALI_LOG_ERROR("Can not set empty handle of source object or invalid source property index\n");
247 void ScrollBar::CreateDefaultIndicatorActor()
249 const std::string imageDirPath = AssetManager::GetDaliImagePath();
250 Toolkit::ImageView indicator = Toolkit::ImageView::New( imageDirPath + DEFAULT_INDICATOR_IMAGE_FILE_NAME );
251 indicator.SetProperty( Actor::Property::PARENT_ORIGIN, ParentOrigin::TOP_LEFT );
252 indicator.SetProperty( Actor::Property::ANCHOR_POINT, AnchorPoint::TOP_LEFT );
253 indicator.SetStyleName( "ScrollBarIndicator" );
254 indicator.SetProperty( Actor::Property::COLOR_MODE, USE_OWN_MULTIPLY_PARENT_COLOR );
255 SetScrollIndicator(indicator);
258 void ScrollBar::SetScrollIndicator( Actor indicator )
260 // Don't allow empty handle
263 // Remove current Indicator
266 Self().Remove( mIndicator );
268 mIndicator = indicator;
270 mIndicatorFirstShow = true;
271 Self().Add( mIndicator );
273 EnableGestureDetection( GestureType::Value( GestureType::PAN ) );
275 PanGestureDetector detector( GetPanGestureDetector() );
276 detector.DetachAll();
277 detector.Attach( mIndicator );
279 unsigned int childCount = mIndicator.GetChildCount();
280 for ( unsigned int index = 0; index < childCount; index++ )
282 Actor child = mIndicator.GetChildAt( index );
285 detector.Attach( child );
291 DALI_LOG_ERROR("Empty handle of scroll indicator\n");
295 Actor ScrollBar::GetScrollIndicator()
300 void ScrollBar::ApplyConstraints()
302 Handle scrollableHandle = mScrollableObject.GetHandle();
304 if( scrollableHandle )
306 if(mIndicatorSizeConstraint)
308 mIndicatorSizeConstraint.Remove();
311 // Set indicator height according to the indicator's height policy
312 if(mIndicatorHeightPolicy == Toolkit::ScrollBar::FIXED)
314 mIndicator.SetProperty( Actor::Property::SIZE, Vector2( Self().GetCurrentProperty< Vector3 >( Actor::Property::SIZE ).width, mIndicatorFixedHeight) );
318 mIndicatorSizeConstraint = Constraint::New<Vector3>( mIndicator, Actor::Property::SIZE,
319 IndicatorSizeConstraint( mIndicatorMinimumHeight, mIndicatorStartPadding + mIndicatorEndPadding ) );
320 mIndicatorSizeConstraint.AddSource( ParentSource( Actor::Property::SIZE ) );
321 mIndicatorSizeConstraint.AddSource( Source( scrollableHandle, mPropertyScrollContentSize ) );
322 mIndicatorSizeConstraint.Apply();
325 if(mIndicatorPositionConstraint)
327 mIndicatorPositionConstraint.Remove();
330 mIndicatorPositionConstraint = Constraint::New<Vector3>( mIndicator, Actor::Property::POSITION,
331 IndicatorPositionConstraint( mIndicatorStartPadding, mIndicatorEndPadding ) );
332 mIndicatorPositionConstraint.AddSource( LocalSource( Actor::Property::SIZE ) );
333 mIndicatorPositionConstraint.AddSource( ParentSource( Actor::Property::SIZE ) );
334 mIndicatorPositionConstraint.AddSource( Source( scrollableHandle, mPropertyScrollPosition ) );
335 mIndicatorPositionConstraint.AddSource( Source( scrollableHandle, mPropertyMinScrollPosition ) );
336 mIndicatorPositionConstraint.AddSource( Source( scrollableHandle, mPropertyMaxScrollPosition ) );
337 mIndicatorPositionConstraint.Apply();
341 void ScrollBar::SetScrollPositionIntervals( const Dali::Vector<float>& positions )
343 mScrollPositionIntervals = positions;
345 Handle scrollableHandle = mScrollableObject.GetHandle();
347 if( scrollableHandle )
349 if( mPositionNotification )
351 scrollableHandle.RemovePropertyNotification(mPositionNotification);
354 mPositionNotification = scrollableHandle.AddPropertyNotification( mPropertyScrollPosition, VariableStepCondition(mScrollPositionIntervals) );
355 mPositionNotification.NotifySignal().Connect( this, &ScrollBar::OnScrollPositionIntervalReached );
359 Dali::Vector<float> ScrollBar::GetScrollPositionIntervals() const
361 return mScrollPositionIntervals;
364 void ScrollBar::OnScrollPositionIntervalReached(PropertyNotification& source)
366 // Emit the signal to notify the scroll position crossing
367 Handle scrollableHandle = mScrollableObject.GetHandle();
370 mScrollPositionIntervalReachedSignal.Emit( scrollableHandle.GetCurrentProperty< float >( mPropertyScrollPosition ) );
371 if (Self() == Dali::Accessibility::Accessible::GetCurrentlyHighlightedActor())
373 Control::Impl::GetAccessibilityObject(Self())->Emit(Dali::Accessibility::ObjectPropertyChangeEvent::VALUE);
378 void ScrollBar::ShowIndicator()
380 // Cancel any animation
387 if( mIndicatorFirstShow )
389 // Preserve the alpha value from the stylesheet
390 mIndicatorShowAlpha = Self().GetCurrentProperty< Vector4 >( Actor::Property::COLOR ).a;
391 mIndicatorFirstShow = false;
394 if(mIndicatorShowDuration > 0.0f)
396 mAnimation = Animation::New( mIndicatorShowDuration );
397 mAnimation.AnimateTo( Property( mIndicator, Actor::Property::COLOR_ALPHA ), mIndicatorShowAlpha, AlphaFunction::EASE_IN );
402 mIndicator.SetProperty( Actor::Property::OPACITY,mIndicatorShowAlpha);
406 void ScrollBar::HideIndicator()
408 // Cancel any animation
415 if(mIndicatorHideDuration > 0.0f)
417 mAnimation = Animation::New( mIndicatorHideDuration );
418 mAnimation.AnimateTo( Property( mIndicator, Actor::Property::COLOR_ALPHA ), 0.0f, AlphaFunction::EASE_IN );
423 mIndicator.SetProperty( Actor::Property::OPACITY,0.0f);
427 void ScrollBar::ShowTransientIndicator()
429 // Cancel any animation
436 mAnimation = Animation::New( mIndicatorShowDuration + mTransientIndicatorDuration + mIndicatorHideDuration );
437 if(mIndicatorShowDuration > 0.0f)
439 mAnimation.AnimateTo( Property( mIndicator, Actor::Property::COLOR_ALPHA ),
440 mIndicatorShowAlpha, AlphaFunction::EASE_IN, TimePeriod(0, mIndicatorShowDuration) );
444 mIndicator.SetProperty( Actor::Property::OPACITY,mIndicatorShowAlpha);
446 mAnimation.AnimateTo( Property( mIndicator, Actor::Property::COLOR_ALPHA ),
447 0.0f, AlphaFunction::EASE_IN, TimePeriod((mIndicatorShowDuration + mTransientIndicatorDuration), mIndicatorHideDuration) );
451 bool ScrollBar::OnPanGestureProcessTick()
453 // Update the scroll position property.
454 Handle scrollableHandle = mScrollableObject.GetHandle();
455 if( scrollableHandle )
457 scrollableHandle.SetProperty(mPropertyScrollPosition, mCurrentScrollPosition);
463 void ScrollBar::OnPan( const PanGesture& gesture )
465 Handle scrollableHandle = mScrollableObject.GetHandle();
469 Dali::Toolkit::ItemView itemView = Dali::Toolkit::ItemView::DownCast(scrollableHandle);
471 switch(gesture.GetState())
473 case Dali::GestureState::STARTED:
475 if( !mPanProcessTimer )
477 // Make sure the pan gesture is only being processed once per frame.
478 mPanProcessTimer = Timer::New( DEFAULT_PAN_GESTURE_PROCESS_TIME );
479 mPanProcessTimer.TickSignal().Connect( this, &ScrollBar::OnPanGestureProcessTick );
480 mPanProcessTimer.Start();
484 mScrollStart = scrollableHandle.GetCurrentProperty< float >( mPropertyScrollPosition );
485 mGestureDisplacement = Vector2::ZERO;
490 case Dali::GestureState::CONTINUING:
492 mGestureDisplacement += gesture.GetDisplacement();
494 float minScrollPosition = scrollableHandle.GetCurrentProperty<float>( mPropertyMinScrollPosition );
495 float maxScrollPosition = scrollableHandle.GetCurrentProperty<float>( mPropertyMaxScrollPosition );
497 // The domain size is the internal range
498 float domainSize = maxScrollPosition - minScrollPosition;
499 float logicalSize = Self().GetCurrentProperty< Vector3 >( Actor::Property::SIZE ).y - ( mIndicator.GetCurrentProperty< Vector3 >( Actor::Property::SIZE ).y + mIndicatorStartPadding + mIndicatorEndPadding );
501 mCurrentScrollPosition = mScrollStart - ( ( mGestureDisplacement.y * domainSize ) / logicalSize );
502 mCurrentScrollPosition = -std::min( maxScrollPosition, std::max( -mCurrentScrollPosition, minScrollPosition ) );
510 if( mPanProcessTimer )
512 // Destroy the timer when pan gesture is finished.
513 mPanProcessTimer.Stop();
514 mPanProcessTimer.TickSignal().Disconnect( this, &ScrollBar::OnPanGestureProcessTick );
515 mPanProcessTimer.Reset();
520 // Refresh the ItemView cache with extra items
521 GetImpl(itemView).DoRefresh(mCurrentScrollPosition, true);
524 mPanFinishedSignal.Emit();
532 // Disable automatic refresh in ItemView during fast scrolling
533 GetImpl(itemView).SetRefreshEnabled(!mIsPanning);
538 void ScrollBar::OnSizeSet( const Vector3& size )
540 if(mIndicatorHeightPolicy == Toolkit::ScrollBar::FIXED)
542 mIndicator.SetProperty( Actor::Property::SIZE, Vector2( size.width, mIndicatorFixedHeight ) );
545 Control::OnSizeSet( size );
548 void ScrollBar::SetScrollDirection( Toolkit::ScrollBar::Direction direction )
550 mDirection = direction;
553 Toolkit::ScrollBar::Direction ScrollBar::GetScrollDirection() const
558 void ScrollBar::SetIndicatorHeightPolicy( Toolkit::ScrollBar::IndicatorHeightPolicy policy )
560 if( policy != mIndicatorHeightPolicy )
562 mIndicatorHeightPolicy = policy;
567 Toolkit::ScrollBar::IndicatorHeightPolicy ScrollBar::GetIndicatorHeightPolicy() const
569 return mIndicatorHeightPolicy;
572 void ScrollBar::SetIndicatorFixedHeight( float height )
574 mIndicatorFixedHeight = height;
576 if(mIndicatorHeightPolicy == Toolkit::ScrollBar::FIXED)
578 mIndicator.SetProperty( Actor::Property::SIZE, Vector2( Self().GetCurrentProperty< Vector3 >( Actor::Property::SIZE ).width, mIndicatorFixedHeight) );
582 float ScrollBar::GetIndicatorFixedHeight() const
584 return mIndicatorFixedHeight;
587 void ScrollBar::SetIndicatorShowDuration( float durationSeconds )
589 mIndicatorShowDuration = durationSeconds;
592 float ScrollBar::GetIndicatorShowDuration() const
594 return mIndicatorShowDuration;
597 void ScrollBar::SetIndicatorHideDuration( float durationSeconds )
599 mIndicatorHideDuration = durationSeconds;
602 float ScrollBar::GetIndicatorHideDuration() const
604 return mIndicatorHideDuration;
607 void ScrollBar::OnScrollDirectionPropertySet( Property::Value propertyValue )
609 std::string directionName( propertyValue.Get<std::string>() );
610 if(directionName == "VERTICAL")
612 SetScrollDirection(Toolkit::ScrollBar::VERTICAL);
614 else if(directionName == "HORIZONTAL")
616 SetScrollDirection(Toolkit::ScrollBar::HORIZONTAL);
620 DALI_ASSERT_ALWAYS( !"ScrollBar::OnScrollDirectionPropertySet(). Invalid Property value." );
624 void ScrollBar::OnIndicatorHeightPolicyPropertySet( Property::Value propertyValue )
626 std::string policyName( propertyValue.Get<std::string>() );
627 if(policyName == "VARIABLE")
629 SetIndicatorHeightPolicy(Toolkit::ScrollBar::VARIABLE);
631 else if(policyName == "FIXED")
633 SetIndicatorHeightPolicy(Toolkit::ScrollBar::FIXED);
637 DALI_ASSERT_ALWAYS( !"ScrollBar::OnIndicatorHeightPolicyPropertySet(). Invalid Property value." );
641 bool ScrollBar::DoConnectSignal( BaseObject* object, ConnectionTrackerInterface* tracker, const std::string& signalName, FunctorDelegate* functor )
643 Dali::BaseHandle handle( object );
645 bool connected( true );
646 Toolkit::ScrollBar scrollBar = Toolkit::ScrollBar::DownCast( handle );
648 if( 0 == strcmp( signalName.c_str(), PAN_FINISHED_SIGNAL ) )
650 scrollBar.PanFinishedSignal().Connect( tracker, functor );
652 else if( 0 == strcmp( signalName.c_str(), SCROLL_POSITION_INTERVAL_REACHED_SIGNAL ) )
654 scrollBar.ScrollPositionIntervalReachedSignal().Connect( tracker, functor );
658 // signalName does not match any signal
665 void ScrollBar::SetProperty( BaseObject* object, Property::Index index, const Property::Value& value )
667 Toolkit::ScrollBar scrollBar = Toolkit::ScrollBar::DownCast( Dali::BaseHandle( object ) );
671 ScrollBar& scrollBarImpl( GetImpl( scrollBar ) );
674 case Toolkit::ScrollBar::Property::SCROLL_DIRECTION:
676 scrollBarImpl.OnScrollDirectionPropertySet( value );
679 case Toolkit::ScrollBar::Property::INDICATOR_HEIGHT_POLICY:
681 scrollBarImpl.OnIndicatorHeightPolicyPropertySet( value );
684 case Toolkit::ScrollBar::Property::INDICATOR_FIXED_HEIGHT:
686 scrollBarImpl.SetIndicatorFixedHeight(value.Get<float>());
689 case Toolkit::ScrollBar::Property::INDICATOR_SHOW_DURATION:
691 scrollBarImpl.SetIndicatorShowDuration(value.Get<float>());
694 case Toolkit::ScrollBar::Property::INDICATOR_HIDE_DURATION:
696 scrollBarImpl.SetIndicatorHideDuration(value.Get<float>());
699 case Toolkit::ScrollBar::Property::SCROLL_POSITION_INTERVALS:
701 const Property::Array* array = value.GetArray();
704 Dali::Vector<float> positions;
705 size_t positionCount = array->Count();
706 positions.Resize( positionCount );
707 for( size_t i = 0; i != positionCount; ++i )
709 array->GetElementAt( i ).Get( positions[i] );
712 scrollBarImpl.SetScrollPositionIntervals(positions);
716 case Toolkit::ScrollBar::Property::INDICATOR_MINIMUM_HEIGHT:
718 scrollBarImpl.mIndicatorMinimumHeight = value.Get<float>();
719 scrollBarImpl.ApplyConstraints();
722 case Toolkit::ScrollBar::Property::INDICATOR_START_PADDING:
724 scrollBarImpl.mIndicatorStartPadding = value.Get<float>();
725 scrollBarImpl.ApplyConstraints();
728 case Toolkit::ScrollBar::Property::INDICATOR_END_PADDING:
730 scrollBarImpl.mIndicatorEndPadding = value.Get<float>();
731 scrollBarImpl.ApplyConstraints();
734 case Toolkit::ScrollBar::Property::INDICATOR_TRANSIENT_DURATION:
736 scrollBarImpl.mTransientIndicatorDuration = value.Get<float>();
743 Property::Value ScrollBar::GetProperty( BaseObject* object, Property::Index index )
745 Property::Value value;
747 Toolkit::ScrollBar scrollBar = Toolkit::ScrollBar::DownCast( Dali::BaseHandle( object ) );
751 ScrollBar& scrollBarImpl( GetImpl( scrollBar ) );
754 case Toolkit::ScrollBar::Property::SCROLL_DIRECTION:
756 value = SCROLL_DIRECTION_NAME[ scrollBarImpl.GetScrollDirection() ];
759 case Toolkit::ScrollBar::Property::INDICATOR_HEIGHT_POLICY:
761 value = INDICATOR_HEIGHT_POLICY_NAME[ scrollBarImpl.GetIndicatorHeightPolicy() ];
764 case Toolkit::ScrollBar::Property::INDICATOR_FIXED_HEIGHT:
766 value = scrollBarImpl.GetIndicatorFixedHeight();
769 case Toolkit::ScrollBar::Property::INDICATOR_SHOW_DURATION:
771 value = scrollBarImpl.GetIndicatorShowDuration();
774 case Toolkit::ScrollBar::Property::INDICATOR_HIDE_DURATION:
776 value = scrollBarImpl.GetIndicatorHideDuration();
779 case Toolkit::ScrollBar::Property::SCROLL_POSITION_INTERVALS:
781 Property::Value tempValue( Property::ARRAY );
782 Property::Array* array = tempValue.GetArray();
786 Dali::Vector<float> positions = scrollBarImpl.GetScrollPositionIntervals();
787 size_t positionCount( positions.Count() );
789 for( size_t i( 0 ); i != positionCount; ++i )
791 array->PushBack( positions[i] );
798 case Toolkit::ScrollBar::Property::INDICATOR_MINIMUM_HEIGHT:
800 value = scrollBarImpl.mIndicatorMinimumHeight;
803 case Toolkit::ScrollBar::Property::INDICATOR_START_PADDING:
805 value = scrollBarImpl.mIndicatorStartPadding;
808 case Toolkit::ScrollBar::Property::INDICATOR_END_PADDING:
810 value = scrollBarImpl.mIndicatorEndPadding;
813 case Toolkit::ScrollBar::Property::INDICATOR_TRANSIENT_DURATION:
815 value = scrollBarImpl.mTransientIndicatorDuration;
823 bool ScrollBar::DoAction( BaseObject* object, const std::string& actionName, const Property::Map& attributes )
827 Dali::BaseHandle handle( object );
829 Toolkit::ScrollBar scrollBar = Toolkit::ScrollBar::DownCast( handle );
831 DALI_ASSERT_DEBUG( scrollBar );
835 if( 0 == strcmp( actionName.c_str(), ACTION_SHOW_INDICATOR ) )
837 GetImpl( scrollBar ).ShowIndicator();
840 else if( 0 == strcmp( actionName.c_str(), ACTION_HIDE_INDICATOR ) )
842 GetImpl( scrollBar ).HideIndicator();
845 else if( 0 == strcmp( actionName.c_str(), ACTION_SHOW_TRANSIENT_INDICATOR ) )
847 GetImpl( scrollBar ).ShowTransientIndicator();
855 Toolkit::ScrollBar ScrollBar::New(Toolkit::ScrollBar::Direction direction)
857 // Create the implementation, temporarily owned by this handle on stack
858 IntrusivePtr< ScrollBar > impl = new ScrollBar(direction);
860 // Pass ownership to CustomActor handle
861 Toolkit::ScrollBar handle( *impl );
863 // Second-phase init of the implementation
864 // This can only be done after the CustomActor connection has been made...
870 double ScrollBar::AccessibleImpl::GetMinimum()
872 auto p = Toolkit::ScrollBar::DownCast( self );
873 Handle scrollableHandle = GetImpl( p ).mScrollableObject.GetHandle();
874 return scrollableHandle ? scrollableHandle.GetCurrentProperty< float >( GetImpl( p ).mPropertyMinScrollPosition ) : 0.0f;
877 double ScrollBar::AccessibleImpl::GetCurrent()
879 auto p = Toolkit::ScrollBar::DownCast( self );
880 Handle scrollableHandle = GetImpl( p ).mScrollableObject.GetHandle();
881 return scrollableHandle ? scrollableHandle.GetCurrentProperty< float >( GetImpl( p ).mPropertyScrollPosition ) : 0.0f;
884 double ScrollBar::AccessibleImpl::GetMaximum()
886 auto p = Toolkit::ScrollBar::DownCast( self );
887 Handle scrollableHandle = GetImpl( p ).mScrollableObject.GetHandle();
888 return scrollableHandle ? scrollableHandle.GetCurrentProperty< float >( GetImpl( p ).mPropertyMaxScrollPosition ) : 1.0f;
891 bool ScrollBar::AccessibleImpl::SetCurrent( double current )
893 if( current < GetMinimum() || current > GetMaximum() )
896 auto value_before = GetCurrent();
898 auto p = Toolkit::ScrollBar::DownCast( self );
899 Handle scrollableHandle = GetImpl( p ).mScrollableObject.GetHandle();
900 if( !scrollableHandle )
902 scrollableHandle.SetProperty( GetImpl( p ).mPropertyScrollPosition, static_cast< float >( current ) );
904 auto value_after = GetCurrent();
906 if( ( current != value_before ) && ( value_before == value_after ) )
912 double ScrollBar::AccessibleImpl::GetMinimumIncrement() { return 1.0; }
914 } // namespace Internal
916 } // namespace Toolkit