Skip to content
This repository was archived by the owner on May 15, 2025. It is now read-only.

Commit 01016fa

Browse files
Touch and press effect is improved
1 parent 532512c commit 01016fa

9 files changed

Lines changed: 128 additions & 64 deletions

File tree

MaterialDesignControls.nuspec

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
<package xmlns="http://schemas.microsoft.com/packaging/2010/07/nuspec.xsd">
33
<metadata minClientVersion="2.8.1">
44
<id>Plugin.MaterialDesignControls</id>
5-
<version>1.4.0</version>
5+
<version>1.4.1</version>
66
<title>MaterialDesignControls Plugin for Xamarin Forms</title>
77
<authors>Horus</authors>
88
<owners>AgustinBonillaHorus</owners>

README.md

Lines changed: 1 addition & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -165,24 +165,7 @@ public class MyControl : ContentView, ITouchAndPressEffectConsumer
165165
{
166166
public void ConsumeEvent(EventType gestureType)
167167
{
168-
switch (gestureType)
169-
{
170-
case EventType.Pressing:
171-
Task.Run(async () =>
172-
{
173-
await this.ScaleTo(0.90, 100);
174-
});
175-
break;
176-
case EventType.Cancelled:
177-
case EventType.Released:
178-
Task.Run(async () =>
179-
{
180-
await this.ScaleTo(1, 100);
181-
});
182-
break;
183-
default:
184-
throw new ArgumentOutOfRangeException(nameof(gestureType), gestureType, null);
185-
}
168+
TouchAndPressAnimation.Animate(this, gestureType);
186169
}
187170
}
188171
```

example/ExampleMaterialDesignControls/Pages/MaterialButtonPage.xaml

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,12 @@
1515
<material:MaterialOutlineButton IsEnabled="false" Text="Cancel" Command="{Binding TapCommand}" CornerRadius="20" CommandParameter="Canceled" />
1616
<material:MaterialFlatButton IsEnabled="false" Text="Delete" Icon="delete.png" DisabledIcon="delete.png" Command="{Binding TapCommand}" CommandParameter="Deleted" />
1717

18-
<Label Text="Animations" HorizontalTextAlignment="Center" />
18+
<Label Text="Animations" HorizontalTextAlignment="Center" Margin="0,40,0,0" />
1919
<material:MaterialButton Animation="None" Text="None" ToUpper="True" />
2020
<material:MaterialButton Animation="Fade" AnimationParameter="0.6" Text="Fade" ToUpper="True" />
21+
<material:MaterialButton Animation="Fade" AnimationParameter="0.2" Text="Fade" ToUpper="True" />
2122
<material:MaterialButton Animation="Scale" AnimationParameter="0.98" Text="Scale" ToUpper="True" />
23+
<material:MaterialButton Animation="Scale" AnimationParameter="0.7" Text="Scale" ToUpper="True" />
2224
</StackLayout>
2325
</ScrollView>
2426
</ContentPage.Content>

src/MaterialDesignControls.Android/Effects/TouchAndPressEffect.cs

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,10 @@ protected override void OnDetached()
3535
}
3636
}
3737

38+
private float? firstX;
39+
private float? firstY;
40+
private bool ignored;
41+
3842
private void OnViewOnTouch(object sender, View.TouchEventArgs e)
3943
{
4044
switch (e.Event.ActionMasked)
@@ -60,6 +64,28 @@ private void OnViewOnTouch(object sender, View.TouchEventArgs e)
6064
case MotionEventActions.Mask:
6165
break;
6266
case MotionEventActions.Move:
67+
var motionEvent = e.Event as MotionEvent;
68+
69+
if (motionEvent != null)
70+
{
71+
var x = motionEvent.GetX();
72+
var y = motionEvent.GetY();
73+
74+
if (!this.firstX.HasValue || !this.firstY.HasValue)
75+
{
76+
this.firstX = x;
77+
this.firstY = y;
78+
}
79+
80+
var maxDelta = 10;
81+
var deltaX = Math.Abs(x - this.firstX.Value);
82+
var deltaY = Math.Abs(y - this.firstY.Value);
83+
if (!this.ignored && (deltaX > maxDelta || deltaY > maxDelta))
84+
{
85+
this.ignored = true;
86+
_touchAndPressEffectConsumer?.ConsumeEvent(EventType.Ignored);
87+
}
88+
}
6389
break;
6490
case MotionEventActions.Outside:
6591
break;
@@ -87,6 +113,13 @@ private void OnViewOnTouch(object sender, View.TouchEventArgs e)
87113
default:
88114
throw new ArgumentOutOfRangeException();
89115
}
116+
117+
if (e.Event.ActionMasked != MotionEventActions.Move)
118+
{
119+
this.ignored = false;
120+
this.firstX = null;
121+
this.firstY = null;
122+
}
90123
}
91124
}
92125
}

src/MaterialDesignControls.iOS/Effects/TouchAndPressEffect.cs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,12 @@ public override void TouchesCancelled(NSSet touches, UIEvent evt)
8181
base.TouchesCancelled(touches, evt);
8282
_touchAndPressEffectConsumer.ConsumeEvent(EventType.Cancelled);
8383
}
84+
85+
public override void IgnoreTouch(UITouch touch, UIEvent forEvent)
86+
{
87+
base.IgnoreTouch(touch, forEvent);
88+
_touchAndPressEffectConsumer.ConsumeEvent(EventType.Ignored);
89+
}
8490
}
8591
}
8692
}
Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
using System;
2+
using System.Threading.Tasks;
3+
using Xamarin.Forms;
4+
5+
namespace Plugin.MaterialDesignControls.Animations
6+
{
7+
public static class TouchAndPressAnimation
8+
{
9+
public static void Animate(View view, EventType gestureType)
10+
{
11+
var touchAndPressEffectConsumer = view as ITouchAndPressEffectConsumer;
12+
13+
switch (gestureType)
14+
{
15+
case EventType.Pressing:
16+
SetAnimation(view, touchAndPressEffectConsumer);
17+
break;
18+
case EventType.Cancelled:
19+
case EventType.Released:
20+
if (view.IsEnabled && touchAndPressEffectConsumer.Command != null && touchAndPressEffectConsumer.Command.CanExecute(touchAndPressEffectConsumer.CommandParameter))
21+
{
22+
touchAndPressEffectConsumer.Command.Execute(touchAndPressEffectConsumer.CommandParameter);
23+
}
24+
25+
RestoreAnimation(view, touchAndPressEffectConsumer);
26+
break;
27+
case EventType.Ignored:
28+
RestoreAnimation(view, touchAndPressEffectConsumer);
29+
break;
30+
default:
31+
throw new ArgumentOutOfRangeException(nameof(gestureType), gestureType, null);
32+
}
33+
}
34+
35+
private static void SetAnimation(View view, ITouchAndPressEffectConsumer touchAndPressEffectConsumer)
36+
{
37+
if (touchAndPressEffectConsumer.Animation != AnimationTypes.None && view.IsEnabled && (touchAndPressEffectConsumer.Command == null || touchAndPressEffectConsumer.Command.CanExecute(touchAndPressEffectConsumer.CommandParameter)))
38+
{
39+
Task.Run(async () =>
40+
{
41+
if (touchAndPressEffectConsumer.Animation == AnimationTypes.Fade)
42+
{
43+
await view.FadeTo(touchAndPressEffectConsumer.AnimationParameter.HasValue ? touchAndPressEffectConsumer.AnimationParameter.Value : 0.6, 100);
44+
}
45+
else
46+
{
47+
await view.ScaleTo(touchAndPressEffectConsumer.AnimationParameter.HasValue ? touchAndPressEffectConsumer.AnimationParameter.Value : 0.95, 100);
48+
}
49+
});
50+
}
51+
}
52+
53+
private static void RestoreAnimation(View view, ITouchAndPressEffectConsumer touchAndPressEffectConsumer)
54+
{
55+
if (touchAndPressEffectConsumer.Animation != AnimationTypes.None)
56+
{
57+
Task.Run(async () =>
58+
{
59+
if (touchAndPressEffectConsumer.Animation == AnimationTypes.Fade)
60+
{
61+
await view.FadeTo(1, 100);
62+
}
63+
else
64+
{
65+
await view.ScaleTo(1, 100);
66+
}
67+
});
68+
}
69+
}
70+
}
71+
}
72+

src/MaterialDesignControls/Controls/MaterialButton.cs

Lines changed: 2 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
using System.Runtime.CompilerServices;
33
using System.Threading.Tasks;
44
using System.Windows.Input;
5+
using Plugin.MaterialDesignControls.Animations;
56
using Xamarin.Forms;
67

78
namespace Plugin.MaterialDesignControls
@@ -346,49 +347,7 @@ protected override void OnPropertyChanged([CallerMemberName] string propertyName
346347

347348
public void ConsumeEvent(EventType gestureType)
348349
{
349-
switch (gestureType)
350-
{
351-
case EventType.Pressing:
352-
if (this.Animation != AnimationTypes.None && this.IsEnabled && (this.Command == null || this.Command.CanExecute(this.CommandParameter)))
353-
{
354-
Task.Run(async () =>
355-
{
356-
if (this.Animation == AnimationTypes.Fade)
357-
{
358-
await this.FadeTo(this.AnimationParameter.HasValue ? this.AnimationParameter.Value : 0.6, 100);
359-
}
360-
else
361-
{
362-
await this.ScaleTo(this.AnimationParameter.HasValue ? this.AnimationParameter.Value : 0.95, 100);
363-
}
364-
});
365-
}
366-
break;
367-
case EventType.Cancelled:
368-
case EventType.Released:
369-
if (this.IsEnabled && this.Command != null && this.Command.CanExecute(this.CommandParameter))
370-
{
371-
this.Command.Execute(this.CommandParameter);
372-
}
373-
374-
if (this.Animation != AnimationTypes.None)
375-
{
376-
Task.Run(async () =>
377-
{
378-
if (this.Animation == AnimationTypes.Fade)
379-
{
380-
await this.FadeTo(1, 100);
381-
}
382-
else
383-
{
384-
await this.ScaleTo(1, 100);
385-
}
386-
});
387-
}
388-
break;
389-
default:
390-
throw new ArgumentOutOfRangeException(nameof(gestureType), gestureType, null);
391-
}
350+
TouchAndPressAnimation.Animate(this, gestureType);
392351
}
393352

394353
#endregion Methods

src/MaterialDesignControls/Effects/TouchAndPressEffect.cs

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,26 @@
11
using System;
2+
using System.Threading.Tasks;
3+
using System.Windows.Input;
24
using Xamarin.Forms;
35

46
namespace Plugin.MaterialDesignControls
57
{
68
public interface ITouchAndPressEffectConsumer
79
{
810
void ConsumeEvent(EventType gestureType);
11+
ICommand Command { get; set; }
12+
object CommandParameter { get; set; }
13+
bool IsEnabled { get; set; }
14+
AnimationTypes Animation { get; set; }
15+
double? AnimationParameter { get; set; }
916
}
1017

1118
public enum EventType
1219
{
1320
Pressing,
1421
Released,
15-
Cancelled
22+
Cancelled,
23+
Ignored
1624
}
1725

1826
public class TouchAndPressEffect : RoutingEffect

src/MaterialDesignControls/MaterialDesignControls.csproj

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -98,6 +98,7 @@
9898
<Compile Include="Animations\ShakeAnimation.cs" />
9999
<Compile Include="Effects\TouchAndPressEffect.cs" />
100100
<Compile Include="AnimationTypes.cs" />
101+
<Compile Include="Animations\TouchAndPressAnimation.cs" />
101102
</ItemGroup>
102103

103104
<ItemGroup Condition=" $(TargetFramework.StartsWith('netstandard')) ">

0 commit comments

Comments
 (0)