/**
* Recursively deliver events to the actor and its parents, until the event is consumed or the stage is reached.
*/
-Dali::Actor EmitTouchSignals( Dali::Actor actor, RenderTask& renderTask, const TouchEvent& event )
+Dali::Actor EmitTouchSignals( Dali::Actor actor, const TouchEvent& event )
{
Dali::Actor consumedActor;
(parent == oldParent) )
{
// One of the actor's parents may consumed the event and they should be set as the consumed actor.
- consumedActor = EmitTouchSignals( parent, renderTask, event );
+ consumedActor = EmitTouchSignals( parent, event );
}
}
}
primaryPoint.hitActor = actor;
primaryPoint.state = state;
- return EmitTouchSignals( Dali::Actor(actor), renderTask, touchEvent );
+ return EmitTouchSignals( Dali::Actor(actor), touchEvent );
}
/**
: mStage( stage ),
mLastPrimaryHitActor(),
mLastConsumedActor(),
+ mTouchDownConsumedActor(),
mLastRenderTask()
{
DALI_LOG_TRACE_METHOD( gLogFilter );
Dali::Actor consumingActor;
touchEvent.points.push_back(event.points[0]);
- if ( mLastRenderTask )
+ Actor* lastPrimaryHitActor( mLastPrimaryHitActor.GetActor() );
+ if ( lastPrimaryHitActor )
{
- RenderTask& lastRenderTaskImpl( GetImplementation( mLastRenderTask ) );
+ Dali::Actor lastPrimaryHitActorHandle( lastPrimaryHitActor );
+ touchEvent.points[0].hitActor = lastPrimaryHitActorHandle;
+ consumingActor = EmitTouchSignals( lastPrimaryHitActorHandle, touchEvent );
+ }
- Actor* lastPrimaryHitActor( mLastPrimaryHitActor.GetActor() );
- if ( lastPrimaryHitActor )
- {
- Dali::Actor lastPrimaryHitActorHandle( lastPrimaryHitActor );
- touchEvent.points[0].hitActor = lastPrimaryHitActorHandle;
- consumingActor = EmitTouchSignals( lastPrimaryHitActorHandle, lastRenderTaskImpl, touchEvent );
- }
+ // If the last consumed actor was different to the primary hit actor then inform it as well (if it has not already been informed).
+ Actor* lastConsumedActor( mLastConsumedActor.GetActor() );
+ if ( lastConsumedActor &&
+ lastConsumedActor != lastPrimaryHitActor &&
+ lastConsumedActor != consumingActor )
+ {
+ Dali::Actor lastConsumedActorHandle( lastConsumedActor );
+ touchEvent.points[0].hitActor = lastConsumedActorHandle;
+ EmitTouchSignals( lastConsumedActorHandle, touchEvent );
+ }
- // If the last consumed actor was different to the primary hit actor then inform it as well (if it has not already been informed).
- Actor* lastConsumedActor( mLastConsumedActor.GetActor() );
- if ( lastConsumedActor &&
- lastConsumedActor != lastPrimaryHitActor &&
- lastConsumedActor != consumingActor )
- {
- Dali::Actor lastConsumedActorHandle( lastConsumedActor );
- touchEvent.points[0].hitActor = lastConsumedActorHandle;
- EmitTouchSignals( lastConsumedActorHandle, lastRenderTaskImpl, touchEvent );
- }
+ // Tell the touch-down consuming actor as well, if required
+ Actor* touchDownConsumedActor( mTouchDownConsumedActor.GetActor() );
+ if ( touchDownConsumedActor &&
+ touchDownConsumedActor != lastPrimaryHitActor &&
+ touchDownConsumedActor != lastConsumedActor &&
+ touchDownConsumedActor != consumingActor )
+ {
+ Dali::Actor touchDownConsumedActorHandle( touchDownConsumedActor );
+ touchEvent.points[0].hitActor = touchDownConsumedActorHandle;
+ EmitTouchSignals( touchDownConsumedActorHandle, touchEvent );
}
mLastPrimaryHitActor.SetActor( NULL );
mLastConsumedActor.SetActor( NULL );
+ mTouchDownConsumedActor.SetActor( NULL );
mLastRenderTask.Reset();
touchEvent.points[0].hitActor = NULL;
Dali::Actor consumedActor;
if ( currentRenderTask )
{
- consumedActor = EmitTouchSignals( touchEvent.points[0].hitActor, GetImplementation( currentRenderTask ), touchEvent );
+ consumedActor = EmitTouchSignals( touchEvent.points[0].hitActor, touchEvent );
}
TouchPoint& primaryPoint = touchEvent.points[0];
DALI_LOG_INFO( gLogFilter, Debug::Concise, "PrimaryHitActor: (%p) %s\n", primaryPoint.hitActor ? (void*)&primaryPoint.hitActor.GetBaseObject() : NULL, primaryPoint.hitActor ? primaryPoint.hitActor.GetName().c_str() : "" );
DALI_LOG_INFO( gLogFilter, Debug::Concise, "ConsumedActor: (%p) %s\n", consumedActor ? (void*)&consumedActor.GetBaseObject() : NULL, consumedActor ? consumedActor.GetName().c_str() : "" );
+ if ( ( primaryPointState == TouchPoint::Down ) &&
+ ( touchEvent.GetPointCount() == 1 ) &&
+ ( consumedActor && consumedActor.OnStage() ) )
+ {
+ mTouchDownConsumedActor.SetActor( &GetImplementation( consumedActor ) );
+ }
+
// 4) Check if the last primary hit actor requires a leave event and if it was different to the current primary
// hit actor. Also process the last consumed actor in the same manner.
+ Actor* lastPrimaryHitActor( mLastPrimaryHitActor.GetActor() );
+ Actor* lastConsumedActor( mLastConsumedActor.GetActor() );
if( (primaryPointState == TouchPoint::Motion) || (primaryPointState == TouchPoint::Up) || (primaryPointState == TouchPoint::Stationary) )
{
if ( mLastRenderTask )
Dali::Actor leaveEventConsumer;
RenderTask& lastRenderTaskImpl( GetImplementation( mLastRenderTask ) );
- Actor* lastPrimaryHitActor( mLastPrimaryHitActor.GetActor() );
if( lastPrimaryHitActor &&
lastPrimaryHitActor != primaryHitActor &&
lastPrimaryHitActor != consumedActor )
// Check if the motion event has been consumed by another actor's listener. In this case, the previously
// consumed actor's listeners may need to be informed (through a leave event).
// Further checks here to ensure we do not signal the same actor twice for the same event.
- Actor* lastConsumedActor( mLastConsumedActor.GetActor() );
if ( lastConsumedActor &&
lastConsumedActor != consumedActor &&
lastConsumedActor != lastPrimaryHitActor &&
}
}
- // 6) Emit the stage touched event if required.
+ // 6) Emit an interrupted event to the touch-down actor if it hasn't consumed the up and
+ // emit the stage touched event if required.
+
if ( touchEvent.GetPointCount() == 1 ) // Only want the first touch and the last release
{
switch ( primaryPointState )
{
- case TouchPoint::Down:
case TouchPoint::Up:
{
+ Actor* touchDownConsumedActor( mTouchDownConsumedActor.GetActor() );
+ if ( touchDownConsumedActor &&
+ touchDownConsumedActor != consumedActor &&
+ touchDownConsumedActor != lastPrimaryHitActor &&
+ touchDownConsumedActor != lastConsumedActor )
+ {
+ Dali::Actor touchDownConsumedActorHandle( touchDownConsumedActor );
+ touchEvent.points[0].hitActor = touchDownConsumedActorHandle;
+ touchEvent.points[0].state = TouchPoint::Interrupted;
+ EmitTouchSignals( touchDownConsumedActorHandle, touchEvent );
+ }
+
+ mTouchDownConsumedActor.SetActor( NULL );
+ }
+ // No break, Fallthrough
+
+ case TouchPoint::Down:
+ {
mStage.EmitTouchedSignal( touchEvent );
break;
}