8 changed files with 258 additions and 38 deletions
@ -0,0 +1,59 @@ |
|||
// Copyright (c) The Perspex Project. All rights reserved.
|
|||
// Licensed under the MIT license. See licence.md file in the project root for full license information.
|
|||
|
|||
using System; |
|||
using Perspex.Interactivity; |
|||
|
|||
namespace Perspex.Input |
|||
{ |
|||
public static class Gestures |
|||
{ |
|||
public static readonly RoutedEvent<RoutedEventArgs> TappedEvent = RoutedEvent.Register<RoutedEventArgs>( |
|||
"Tapped", |
|||
RoutingStrategies.Bubble, |
|||
typeof(Gestures)); |
|||
|
|||
public static readonly RoutedEvent<RoutedEventArgs> DoubleTappedEvent = RoutedEvent.Register<RoutedEventArgs>( |
|||
"DoubleTapped", |
|||
RoutingStrategies.Bubble, |
|||
typeof(Gestures)); |
|||
|
|||
private static IInteractive s_lastPress; |
|||
|
|||
static Gestures() |
|||
{ |
|||
InputElement.PointerPressedEvent.RouteFinished.Subscribe(PointerPressed); |
|||
InputElement.PointerReleasedEvent.RouteFinished.Subscribe(PointerReleased); |
|||
} |
|||
|
|||
private static void PointerPressed(RoutedEventArgs ev) |
|||
{ |
|||
if (ev.Route == RoutingStrategies.Bubble) |
|||
{ |
|||
var e = (PointerPressedEventArgs)ev; |
|||
|
|||
if (e.ClickCount <= 1) |
|||
{ |
|||
s_lastPress = e.Source; |
|||
} |
|||
else if (e.ClickCount == 2 && s_lastPress == e.Source) |
|||
{ |
|||
e.Source.RaiseEvent(new RoutedEventArgs(DoubleTappedEvent)); |
|||
} |
|||
} |
|||
} |
|||
|
|||
private static void PointerReleased(RoutedEventArgs ev) |
|||
{ |
|||
if (ev.Route == RoutingStrategies.Bubble) |
|||
{ |
|||
var e = (PointerReleasedEventArgs)ev; |
|||
|
|||
if (s_lastPress == e.Source) |
|||
{ |
|||
s_lastPress.RaiseEvent(new RoutedEventArgs(TappedEvent)); |
|||
} |
|||
} |
|||
} |
|||
} |
|||
} |
|||
@ -0,0 +1,82 @@ |
|||
// Copyright (c) The Perspex Project. All rights reserved.
|
|||
// Licensed under the MIT license. See licence.md file in the project root for full license information.
|
|||
|
|||
using System.Collections.Generic; |
|||
using Perspex.Controls; |
|||
using Perspex.Input; |
|||
using Xunit; |
|||
|
|||
namespace Perspex.Interactivity.UnitTests |
|||
{ |
|||
public class GestureTests |
|||
{ |
|||
[Fact] |
|||
public void Tapped_Should_Follow_Pointer_Pressed_Released() |
|||
{ |
|||
Border border; |
|||
var decorator = new Decorator |
|||
{ |
|||
Child = border = new Border() |
|||
}; |
|||
var result = new List<string>(); |
|||
|
|||
decorator.AddHandler(Border.PointerPressedEvent, (s, e) => result.Add("dp")); |
|||
decorator.AddHandler(Border.PointerReleasedEvent, (s, e) => result.Add("dr")); |
|||
decorator.AddHandler(Gestures.TappedEvent, (s, e) => result.Add("dt")); |
|||
border.AddHandler(Border.PointerPressedEvent, (s, e) => result.Add("bp")); |
|||
border.AddHandler(Border.PointerReleasedEvent, (s, e) => result.Add("br")); |
|||
border.AddHandler(Gestures.TappedEvent, (s, e) => result.Add("bt")); |
|||
|
|||
border.RaiseEvent(new PointerPressedEventArgs()); |
|||
border.RaiseEvent(new PointerReleasedEventArgs()); |
|||
|
|||
Assert.Equal(new[] { "bp", "dp", "br", "dr", "bt", "dt" }, result); |
|||
} |
|||
|
|||
[Fact] |
|||
public void Tapped_Should_Be_Raised_Even_When_PointerPressed_Handled() |
|||
{ |
|||
Border border; |
|||
var decorator = new Decorator |
|||
{ |
|||
Child = border = new Border() |
|||
}; |
|||
var result = new List<string>(); |
|||
|
|||
border.AddHandler(Border.PointerPressedEvent, (s, e) => e.Handled = true); |
|||
decorator.AddHandler(Gestures.TappedEvent, (s, e) => result.Add("dt")); |
|||
border.AddHandler(Gestures.TappedEvent, (s, e) => result.Add("bt")); |
|||
|
|||
border.RaiseEvent(new PointerPressedEventArgs()); |
|||
border.RaiseEvent(new PointerReleasedEventArgs()); |
|||
|
|||
Assert.Equal(new[] { "bt", "dt" }, result); |
|||
} |
|||
|
|||
[Fact] |
|||
public void DoubleTapped_Should_Follow_Pointer_Pressed_Released_Pressed() |
|||
{ |
|||
Border border; |
|||
var decorator = new Decorator |
|||
{ |
|||
Child = border = new Border() |
|||
}; |
|||
var result = new List<string>(); |
|||
|
|||
decorator.AddHandler(Border.PointerPressedEvent, (s, e) => result.Add("dp")); |
|||
decorator.AddHandler(Border.PointerReleasedEvent, (s, e) => result.Add("dr")); |
|||
decorator.AddHandler(Gestures.TappedEvent, (s, e) => result.Add("dt")); |
|||
decorator.AddHandler(Gestures.DoubleTappedEvent, (s, e) => result.Add("ddt")); |
|||
border.AddHandler(Border.PointerPressedEvent, (s, e) => result.Add("bp")); |
|||
border.AddHandler(Border.PointerReleasedEvent, (s, e) => result.Add("br")); |
|||
border.AddHandler(Gestures.TappedEvent, (s, e) => result.Add("bt")); |
|||
border.AddHandler(Gestures.DoubleTappedEvent, (s, e) => result.Add("bdt")); |
|||
|
|||
border.RaiseEvent(new PointerPressedEventArgs()); |
|||
border.RaiseEvent(new PointerReleasedEventArgs()); |
|||
border.RaiseEvent(new PointerPressedEventArgs { ClickCount = 2 }); |
|||
|
|||
Assert.Equal(new[] { "bp", "dp", "br", "dr", "bt", "dt", "bp", "dp", "bdt", "ddt" }, result); |
|||
} |
|||
} |
|||
} |
|||
Loading…
Reference in new issue