#include <dali-toolkit/internal/controls/scrollable/scrollable-impl.h>
#include <dali-toolkit/public-api/controls/scrollable/scroll-view/scroll-view.h>
+#include <dali-toolkit/public-api/controls/default-controls/solid-color-actor.h>
using namespace Dali;
namespace Internal
{
-const char* OVERSHOOT_OVERLAY_IMAGE_PATH = DALI_IMAGE_DIR "scroll_overshoot.png";
-const char* OVERSHOOT_OVERLAY_RIPPLE_IMAGE_PATH = DALI_IMAGE_DIR "overshoot_ripple.png";
const float DEFAULT_MAX_OVERSHOOT_HEIGHT = 36.0f; // 36 pixels
const Rect<int> OVERSHOOT_RIPPLE_IMAGE_1_PIXEL_AREA( 0, 0, 720, 58 );
const float DEFAULT_OVERSHOOT_ANIMATION_DURATION = 0.35f; // time in seconds
}
-ScrollOvershootEffectGradient::ScrollOvershootEffectGradient(bool vertical) :
- ScrollOvershootEffect(vertical),
- mMaxOvershootImageSize(DEFAULT_MAX_OVERSHOOT_HEIGHT)
-{
- Image overshootImage = Image::New( OVERSHOOT_OVERLAY_IMAGE_PATH );
- mOvershootImage = ImageActor::New( overshootImage );
- mOvershootImage.SetParentOrigin(ParentOrigin::TOP_LEFT);
- mOvershootImage.SetAnchorPoint(AnchorPoint::TOP_LEFT);
- mOvershootImage.SetDrawMode(DrawMode::OVERLAY);
-}
-
-void ScrollOvershootEffectGradient::Apply(Scrollable& scrollable)
-{
- Actor scrollableActor = scrollable.Self();
- int overshootXPropertyIndex = scrollableActor.GetPropertyIndex(Toolkit::ScrollView::SCROLL_OVERSHOOT_X_PROPERTY_NAME);
- int overshootYPropertyIndex = scrollableActor.GetPropertyIndex(Toolkit::ScrollView::SCROLL_OVERSHOOT_Y_PROPERTY_NAME);
-
- Constraint constraint = Constraint::New<Vector3>( Actor::SIZE,
- Source( scrollableActor, overshootXPropertyIndex ),
- Source( scrollableActor, overshootYPropertyIndex ),
- Source( scrollableActor, Actor::SIZE ),
- boost::bind( &ScrollOvershootEffectGradient::SizeConstraint, this, _1, _2, _3, _4) );
- mSizeConstraint = mOvershootImage.ApplyConstraint(constraint);
-
- constraint = Constraint::New<Quaternion>( Actor::ROTATION,
- Source( scrollableActor, overshootXPropertyIndex ),
- Source( scrollableActor, overshootYPropertyIndex ),
- boost::bind( &ScrollOvershootEffectGradient::RotationConstraint, this, _1, _2, _3) );
- mRotationConstraint = mOvershootImage.ApplyConstraint(constraint);
-
- constraint = Constraint::New<Vector3>( Actor::POSITION,
- Source( scrollableActor, Actor::SIZE ),
- Source( scrollableActor, overshootXPropertyIndex ),
- Source( scrollableActor, overshootYPropertyIndex ),
- boost::bind( &ScrollOvershootEffectGradient::PositionConstraint, this, _1, _2, _3, _4) );
- mPositionConstraint = mOvershootImage.ApplyConstraint(constraint);
-
- constraint = Constraint::New<bool>( Actor::VISIBLE,
- Source( scrollableActor, IsVertical() ? scrollableActor.GetPropertyIndex(Scrollable::SCROLLABLE_CAN_SCROLL_VERTICAL) : scrollableActor.GetPropertyIndex(Scrollable::SCROLLABLE_CAN_SCROLL_HORIZONTAL)),
- boost::bind( &ScrollOvershootEffectGradient::VisibilityConstraint, this, _1, _2) );
- mVisibilityConstraint = mOvershootImage.ApplyConstraint(constraint);
- scrollable.AddOverlay(mOvershootImage);
- SetPropertyNotifications(scrollableActor);
-}
-
-void ScrollOvershootEffectGradient::Remove(Scrollable& scrollable)
-{
- if(mOvershootImage)
- {
- if(mSizeConstraint)
- {
- mOvershootImage.RemoveConstraint(mSizeConstraint);
- mSizeConstraint = NULL;
- }
- if(mRotationConstraint)
- {
- mOvershootImage.RemoveConstraint(mRotationConstraint);
- mRotationConstraint = NULL;
- }
- if(mPositionConstraint)
- {
- mOvershootImage.RemoveConstraint(mPositionConstraint);
- mPositionConstraint = NULL;
- }
- if(mVisibilityConstraint)
- {
- mOvershootImage.RemoveConstraint(mVisibilityConstraint);
- mVisibilityConstraint = NULL;
- }
- scrollable.RemoveOverlay(mOvershootImage);
- }
-}
-
-Vector3 ScrollOvershootEffectGradient::SizeConstraint(const Vector3& current,
- const PropertyInput& overshootPropertyX, const PropertyInput& overshootPropertyY,
- const PropertyInput& parentSizeProperty)
-{
- float overshootx = overshootPropertyX.GetFloat();
- float overshooty = overshootPropertyY.GetFloat();
- const Vector3 parentSize = parentSizeProperty.GetVector3();
-
- float overlayWidth = IsVertical() ? parentSize.x : parentSize.y;
- float overlayHeight = mMaxOvershootImageSize * fabsf(IsVertical() ? overshooty : overshootx);
-
- return Vector3(overlayWidth, overlayHeight, current.z);
-}
-
-Quaternion ScrollOvershootEffectGradient::RotationConstraint(const Quaternion& current,
- const PropertyInput& overshootPropertyX, const PropertyInput& overshootPropertyY)
-{
- float overshootx = overshootPropertyX.GetFloat();
- float overshooty = overshootPropertyY.GetFloat();
-
- Quaternion rotation;
-
- if(IsVertical())
- {
- if(overshooty < -Math::MACHINE_EPSILON_0)
- {
- rotation = Quaternion(Math::PI, Vector3::ZAXIS);
- }
- else if(overshooty > Math::MACHINE_EPSILON_0)
- {
- rotation = Quaternion(0.0f, Vector3::ZAXIS);
- }
- }
- else
- {
- if(overshootx < -Math::MACHINE_EPSILON_0)
- {
- rotation = Quaternion(0.5f * Math::PI, Vector3::ZAXIS);
- }
- else if(overshootx > Math::MACHINE_EPSILON_0)
- {
- rotation = Quaternion(1.5f * Math::PI, Vector3::ZAXIS);
- }
- }
-
- return rotation;
-}
-
-Vector3 ScrollOvershootEffectGradient::PositionConstraint(const Vector3& current,
- const PropertyInput& parentSizeProperty,
- const PropertyInput& overshootPropertyX, const PropertyInput& overshootPropertyY)
-{
- float overshootx = overshootPropertyX.GetFloat();
- float overshooty = overshootPropertyY.GetFloat();
- const Vector3 parentSize = parentSizeProperty.GetVector3();
-
- Vector3 relativeOffset = Vector3::ZERO;
-
- if(IsVertical())
- {
- if(overshooty > Math::MACHINE_EPSILON_0)
- {
- relativeOffset = Vector3(0.0f, 0.0f, 0.0f);
- }
- else if (overshooty < -Math::MACHINE_EPSILON_0)
- {
- relativeOffset = Vector3(1.0f, 1.0f, 0.0f);
- }
- }
- else
- {
- if(overshootx > Math::MACHINE_EPSILON_0)
- {
- relativeOffset = Vector3(0.0f, 1.0f, 0.0f);
- }
- else if (overshootx < -Math::MACHINE_EPSILON_0)
- {
- relativeOffset = Vector3(1.0f, 0.0f, 0.0f);
- }
- }
-
- return relativeOffset * parentSize;
-}
-
-bool ScrollOvershootEffectGradient::VisibilityConstraint(const bool& current,
- const PropertyInput& canScrollProperty)
-{
- return canScrollProperty.GetBoolean();
-}
-
-ScrollOvershootEffectGradientPtr ScrollOvershootEffectGradient::New(bool vertical)
-{
- return new ScrollOvershootEffectGradient(vertical);
-}
-
-namespace
-{
-
-const std::string OVERSHOOT_PROPERTY_NAME( "uOvershoot" );
-const std::string OVERSHOOT_IMAGE_COUNT_PROPERTY_NAME( "uOvershootImageCount" );
-
-} // namespace
-
-OvershootRippleEffect::OvershootRippleEffect()
-{
-}
-
-//Call the Parent copy constructor to add reference to the implementation for this object
-OvershootRippleEffect::OvershootRippleEffect(ShaderEffect handle)
-:ShaderEffect(handle)
-{
-}
-
-OvershootRippleEffect::~OvershootRippleEffect()
-{
-}
-
-OvershootRippleEffect OvershootRippleEffect::New()
-{
- std::string vertextShader(
- "precision mediump float; \n"
- "uniform float uOvershoot; \n"
- "uniform float uOvershootImageCount; \n"
- "void main() \n"
- "{ \n"
- " gl_Position = uProjection * uModelView * vec4(aPosition, 1.0); \n"
- " vTexCoord = aTexCoord; \n"
- " vTexCoord.y += (1.0 / uOvershootImageCount) * min(floor((abs(uOvershoot) * (uOvershootImageCount - 1.0)) + 0.5), (uOvershootImageCount - 1.0)); \n"
- "} \n" );
-
- std::string fragmentShader(
- "void main() \n"
- "{ \n"
- " gl_FragColor = texture2D(sTexture, vTexCoord); \n"
- "} \n" );
-
- // Create the implementation, temporarily owned on stack,
- Dali::ShaderEffect shaderEffectCustom = Dali::ShaderEffect::New(
- vertextShader,
- fragmentShader);
-
- /* Pass ownership to OvershootRippleEffect through overloaded constructor, So that it now has access to the
- Dali::ShaderEffect implementation */
- OvershootRippleEffect handle( shaderEffectCustom );
- handle.SetUniform(OVERSHOOT_PROPERTY_NAME, 0.0f);
- handle.SetUniform(OVERSHOOT_IMAGE_COUNT_PROPERTY_NAME, 10.0f);
- return handle;
-}
-
-void OvershootRippleEffect::SetOvershoot( float overshoot )
-{
- SetUniform( OVERSHOOT_PROPERTY_NAME, overshoot );
-}
-
-void OvershootRippleEffect::SetOvershootImageCount( float imageCount )
-{
- SetUniform( OVERSHOOT_IMAGE_COUNT_PROPERTY_NAME, imageCount );
-}
-
-const std::string& OvershootRippleEffect::GetOvershootPropertyName() const
-{
- return OVERSHOOT_PROPERTY_NAME;
-}
-
-const std::string& OvershootRippleEffect::GetOvershootImageCountPropertyName() const
-{
- return OVERSHOOT_IMAGE_COUNT_PROPERTY_NAME;
-}
-
ScrollOvershootEffectRipple::ScrollOvershootEffectRipple(bool vertical) :
ScrollOvershootEffect(vertical),
mMaxOvershootImageSize(DEFAULT_MAX_OVERSHOOT_HEIGHT)
{
- mRippleEffect = OvershootRippleEffect::New();
- Image overshootImage = Image::New( OVERSHOOT_OVERLAY_RIPPLE_IMAGE_PATH );
- mOvershootImage = ImageActor::New( overshootImage );
+ mRippleEffect = BouncingEffect::New(Scrollable::DEFAULT_OVERSHOOT_COLOUR);
+ mOvershootImage = CreateSolidColorActor(Vector4::ONE);
mOvershootImage.SetParentOrigin(ParentOrigin::TOP_LEFT);
mOvershootImage.SetAnchorPoint(AnchorPoint::TOP_LEFT);
mOvershootImage.SetDrawMode(DrawMode::OVERLAY);
mOvershootImage.SetShaderEffect(mRippleEffect);
- mOvershootImage.SetPixelArea(OVERSHOOT_RIPPLE_IMAGE_1_PIXEL_AREA);
mOvershootImage.SetVisible(false);
mAnimatingOvershootOn = false;
mAnimateOvershootOff = false;
mAnimatingOvershootOn = false;
mAnimateOvershootOff = false;
mOvershootImage.SetVisible(false);
- mRippleEffect.SetUniform(mRippleEffect.GetOvershootPropertyName(), 0.0f);
+ mRippleEffect.SetProgressRate(0.0f);
if(mScrollOvershootAnimation)
{
mScrollOvershootAnimation.Clear();
void ScrollOvershootEffectRipple::UpdateConstraints(Actor& scrollable)
{
- int overshootPropertyIndex = mRippleEffect.GetPropertyIndex(mRippleEffect.GetOvershootPropertyName());
+ int overshootPropertyIndex = mRippleEffect.GetPropertyIndex(mRippleEffect.GetProgressRatePropertyName());
Constraint constraint;
if(!mSizeConstraint)
{
// make sure we animate back if needed
mAnimateOvershootOff = (!animatingOn && mAnimatingOvershootOn);
- int overShootProperty = mRippleEffect.GetPropertyIndex(mRippleEffect.GetOvershootPropertyName());
+ int overShootProperty = mRippleEffect.GetPropertyIndex(mRippleEffect.GetProgressRatePropertyName());
float currentOvershoot = mRippleEffect.GetProperty<float>(overShootProperty);
if(((currentOvershoot < 0.0f && overshootAmount > 0.0f)
|| (currentOvershoot > 0.0f && overshootAmount < 0.0f)))
//
#include <dali/dali.h>
+#include <dali-toolkit/public-api/shader-effects/bouncing-effect.h>
namespace Dali
{
};
/**
- * OvershootRippleEffect is a custom shader effect for the overshoot indicator
- */
-class OvershootRippleEffect : public ShaderEffect
-{
-public:
-
- /**
- * Create an uninitialized OvershootRippleEffect; this can be initialized with OvershootRippleEffect::New()
- * Calling member functions with an uninitialized Dali::Object is not allowed.
- */
- OvershootRippleEffect();
-
- /**
- * Virtual destructor.
- */
- virtual ~OvershootRippleEffect();
-
- /**
- * Create an initialized OvershootRippleEffect.
- *
- * @return A handle to a newly allocated Dali resource.
- */
- static OvershootRippleEffect New();
-
- /**
- * Set the current overshoot value
- *
- * @param[in] overshoot current overshoot value in the range [0.0f,1.0f]
- */
- void SetOvershoot(float overshoot);
-
- /**
- * Set the number of sub images in the overshoot bounce image
- *
- * @param[in] imageCount number of sub images in main ripple effect image
- */
- void SetOvershootImageCount(float imageCount);
-
- /**
- * Get the name for the overshoot property
- * which can be used in Animation API's
- *
- * @return A std::string containing the property name
- */
- const std::string& GetOvershootPropertyName() const;
-
- /**
- * Get the name for the sub image count property
- * which can be used in Animation API's
- *
- * @return A std::string containing the property name
- */
- const std::string& GetOvershootImageCountPropertyName() const;
-
-private: // Not intended for application developers
- OvershootRippleEffect(ShaderEffect handle);
-};
-
-/**
- * ScrollOvershootEffectGradient creates a gradiented effect at the end of the scrollable area if the user
- * attempts to scroll past it
- */
-struct ScrollOvershootEffectGradient : public ScrollOvershootEffect
-{
-public:
- /**
- * Create a new gradient overshoot effect, passing in whether it is vertical or horizontal
- *
- * @param[in] vertical whether this effect is a vertical or horizontal one
- */
- ScrollOvershootEffectGradient(bool vertical);
-
- /**
- * @copydoc ScrollOvershootEffect::Apply
- */
- virtual void Apply(Scrollable& scrollable);
-
- /**
- * @copydoc ScrollOvershootEffect::Remove
- */
- virtual void Remove(Scrollable& scrollable);
-
- /**
- * @copydoc ScrollOvershootEffect::Reset
- */
- virtual void Reset() {}
-
- /**
- * Constrains the size of the gradient image
- * @param[in] current current size of the image actor
- * @param[in] overshootPropertyX current overshoot x amount
- * @param[in] overshootPropertyY current overshoot y amount
- * @param[in] parentSizeProperty size of the scrollable area so we can make sure the image stretches across it
- * @return the new size of the image depending on the overshoot amount
- */
- Vector3 SizeConstraint(const Vector3& current, const PropertyInput& overshootPropertyX, const PropertyInput& overshootPropertyY, const PropertyInput& parentSizeProperty);
-
- /**
- * Constrains the size of the gradient image
- * @param[in] current current rotation of the image actor
- * @param[in] overshootPropertyX current overshoot x amount
- * @param[in] overshootPropertyY current overshoot y amount
- * @return new rotation os the gradient image actor
- */
- Quaternion RotationConstraint(const Quaternion& current, const PropertyInput& overshootPropertyX, const PropertyInput& overshootPropertyY);
-
- /**
- * Constrains the size of the gradient image
- * @param[in] current current position of the image actor
- * @param[in] parentSizeProperty size of the scrollable area so we can position image on the edge of it
- * @param[in] overshootPropertyX current overshoot x amount
- * @param[in] overshootPropertyY current overshoot y amount
- * @return new position of the gradient image actor
- */
- Vector3 PositionConstraint(const Vector3& current, const PropertyInput& parentSizeProperty, const PropertyInput& overshootPropertyX, const PropertyInput& overshootPropertyY);
-
- /**
- * Constrains the size of the gradient image
- * @param[in] current current visibility of the image actor
- * @param[in] overshootPropertyX current overshoot x amount
- * @param[in] overshootPropertyY current overshoot y amount
- * @return new visibility property depending on overshoot values
- */
- bool VisibilityConstraint(const bool& current, const PropertyInput& canScrollProperty);
-
- /**
- * Creates a new ScrollOvershootEffectGradient objects and returns a pointer to it
- * @param[in] vertical whether to create a vertical(true) or horizontal effect
- * @return a pointer to the new effect
- */
- static ScrollOvershootEffectGradientPtr New( bool vertical );
-
-private:
- float mMaxOvershootImageSize; ///< maximum size of the image when overshoot value is 1.0f
- ImageActor mOvershootImage; ///< the overshoot image...
- ActiveConstraint mSizeConstraint; ///< active constraint handle used to store the image width constraint
- ActiveConstraint mRotationConstraint; ///< active constraint handle used to store the image rotation constraint
- ActiveConstraint mPositionConstraint; ///< active constraint handle used to store the image position constraint
- ActiveConstraint mVisibilityConstraint; ///< active constraint handle used to store the image visibility constraint
-};
-
-/**
* ScrollOvershootEffectRipple creates an animated bounce effect at the end of the scrollable area if the user
* attempts to scroll past it
*/
bool mAnimatingOvershootOn; ///< whether we are currently animating overshoot to 1.0f/-1.0f (on) or to 0.0f (off)
bool mAnimateOvershootOff; ///< whether we are currently animating overshoot to 1.0f/-1.0f (on) or to 0.0f (off)
int mCanScrollPropertyIndex; ///< property index to a property that informs indicator if it is needed
- OvershootRippleEffect mRippleEffect; // the ripple vertex/fragment shader effect
+ BouncingEffect mRippleEffect; // the ripple vertex/fragment shader effect
PropertyNotification mOvershootPositiveNotification; // stores the property notification used for positive overshoot values
PropertyNotification mOvershootNegativeNotification; // stores the property notification used for negative overshoot values
ActiveConstraint mSizeConstraint; // active constraint handle used to store the image width constraint