Skip to content

Instantly share code, notes, and snippets.

@hamid-shaikh
Last active July 2, 2019 06:07
Show Gist options
  • Save hamid-shaikh/fba678321385608ac3b0b5164f9ae935 to your computer and use it in GitHub Desktop.
Save hamid-shaikh/fba678321385608ac3b0b5164f9ae935 to your computer and use it in GitHub Desktop.
Xamarin.Forms Attach Properties (TapCommand, TapCommandParameter, AnimateView, AnimateOnTap) - Easily attach any of these properties to Xamarin.Forms controls
using System.Threading.Tasks;
using System.Windows.Input;
using Xamarin.Forms;
//TapCommandProperty
public static class AppAttachProperties
{
public static readonly BindableProperty TapCommandProperty =
BindableProperty.CreateAttached(
"TapCommand",
typeof(ICommand),
typeof(AppAttachProperties),
default(ICommand),
propertyChanged: OnTapCommandChanged);
public static ICommand GetTapCommand(BindableObject bindable)
{
return (ICommand)bindable.GetValue(TapCommandProperty);
}
public static void SetTapCommand(BindableObject bindable, ICommand value)
{
bindable.SetValue(TapCommandProperty, value);
}
public static void OnTapCommandChanged(BindableObject bindable, object oldValue, object newValue)
{
if (bindable is View control)
{
if (control is Button button)
{
button.Command = GetAnimatedCommand(control);
}
else if (control is ImageButton imageButton)
{
imageButton.Command = GetAnimatedCommand(control);
}
else
{
control.GestureRecognizers.Clear();
control.GestureRecognizers.Add(
new TapGestureRecognizer
{
Command = GetAnimatedCommand(control)
}
);
}
}
}
//TapCommandParameter
public static readonly BindableProperty TapCommandParameterProperty =
BindableProperty.CreateAttached(
"TapCommandParameter",
typeof(object),
typeof(AppAttachProperties),
default(object),
propertyChanged: OnTapCommandParameterChanged);
public static void OnTapCommandParameterChanged(BindableObject bindable, object oldValue, object newValue)
{
if (bindable is View control)
{
SetTapCommandParameter(control, newValue);
control.GestureRecognizers.Clear();
control.GestureRecognizers.Add(
new TapGestureRecognizer
{
Command = GetAnimatedCommand(control)
}
);
}
}
public static object GetTapCommandParameter(BindableObject bindableObject)
{
return bindableObject.GetValue(TapCommandParameterProperty);
}
public static void SetTapCommandParameter(BindableObject bindableObject, object value)
{
bindableObject.SetValue(TapCommandParameterProperty, value);
}
//AnimateView - This property allows to animate a different view on attached control click
public static readonly BindableProperty AnimateViewProperty =
BindableProperty.CreateAttached(
"AnimateView",
typeof(View),
typeof(AppAttachProperties),
default(View),
propertyChanged: OnAnimateViewChanged);
public static void OnAnimateViewChanged(BindableObject bindable, object oldValue, object newValue)
{
if (bindable is View control && newValue is View animateView)
{
SetAnimateView(control, animateView);
}
}
public static View GetAnimateView(BindableObject bindable)
{
return (View)bindable.GetValue(AnimateViewProperty);
}
public static void SetAnimateView(BindableObject bindable, object value)
{
bindable.SetValue(AnimateViewProperty, value);
}
//AnimateOnTap - Default is true (set to false if dont want any animation to happen
public static readonly BindableProperty AnimateOnTapProperty =
BindableProperty.CreateAttached(
"AnimateOnTap",
typeof(bool),
typeof(AppAttachProperties),
true,
propertyChanged: OnAnimateOnTapPropertyChanged);
public static void OnAnimateOnTapPropertyChanged(BindableObject bindable, object oldValue, object newValue)
{
SetAnimateOnTap(bindable, newValue);
}
public static bool GetAnimateOnTap(BindableObject bindable)
{
return (bool)bindable.GetValue(AnimateOnTapProperty);
}
public static void SetAnimateOnTap(BindableObject bindable, object value)
{
bindable.SetValue(AnimateOnTapProperty, value);
}
public static Command GetAnimatedCommand(BindableObject bindable)
{
return new Command(async () =>
{
var bindableView = bindable as View;
var animateView = GetAnimateView(bindableView);
var parameterValue = GetTapCommandParameter(bindableView);
View view = animateView ?? bindableView;
if (GetAnimateOnTap(bindableView))
{
view.AnchorX = view.AnchorY = 0.48;
await view.ScaleTo(0.8, 50, Easing.Linear);
await Task.Delay(100);
await view.ScaleTo(1, 50, Easing.Linear);
}
var command = GetTapCommand(bindableView);
if (command != null)
{
command.Execute(parameterValue);
}
});
}
}
@hamid-shaikh
Copy link
Author

hamid-shaikh commented Jun 18, 2019

Please find the below gist for usage example for your reference.

https://gist.github.com/hamid-shaikh/ada51d3605ab744aadd12f5991bbd822

Feel free to provide your comment, query and feedback.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment