Search code examples
xamlmauiattached-propertiesbindableproperty

.Net Maui Couldn't get value by binding to Attached Property


In .net Maui 7, I have been trying to bind custom bindable property to an attached property value. I have tried various ways to bind the attached property value to custom bindable property value. In xaml code below you will see the custom view inherited from Border and new bindable property created.

<views:CustomView
                    Margin="0,0,0,20" 
                    attached:AttachedProperty.Animate="False" 
                    ShouldAnimateOut="{Binding (attached:AttachedProperty.Animate), Source=                                     {RelativeSource Mode=Self}}"
                    StrokeThickness="0" 
                    x:Name="myCustomView" 
                    Padding="10,10" 
                    VerticalOptions="End" 
                    Background="#345173" 
                    HeightRequest="200">



                <views:CustomView.GestureRecognizers>
                    <TapGestureRecognizer Tapped="TapGestureRecognizer_Tapped"/>
                </views:CustomView.GestureRecognizers>


 </views:CustomView>`

Code Behind for the UserCredentialsView:

 public class UserCredentialsView : Border
{
        public static readonly BindableProperty ShouldAnimateOutProperty =
                               BindableProperty.Create(nameof(ShouldAnimateOut), typeof(bool),  typeof(UserCredentialsView), false, BindingMode.TwoWay, propertyChanged: ShouldAnimateOutPropertyChanged);

        private static void ShouldAnimateOutPropertyChanged(BindableObject bindable, object oldValue, object newValue)
        {
            AttachedProperty.SetAnimate(bindable, false);
        }

        public bool ShouldAnimateOut
        {
            get => (bool)GetValue(ShouldAnimateOutProperty);
            set => SetValue(ShouldAnimateOutProperty, value);
        }
}

Code Behind for the main page:

public partial class MainPage : ContentPage
{

    public MainPage (SomeViewModel viewModel)
    {
        InitializeComponent();

        BindingContext = viewModel;

    }

    private void TapGestureRecognizer_Tapped(object sender, TappedEventArgs e)
    {
        var mControl = sender as Border;
        
        AttachedProperty.SetAnimate(mControl, !AttachedProperty.GetAnimate(mControl));
    }
}

Attached Property definition:

 public static readonly BindableProperty AnimateProperty = 
        BindableProperty.CreateAttached("Animate", typeof(bool), typeof(AttachedProperty), false, 
            BindingMode.TwoWay, propertyChanged: HandleChanged);


    private static void HandleChanged(BindableObject bindable, object oldValue, object newValue)
    {
        var mObject = bindable as UserCredentialsView;

        if (mObject is null)
            return;

        if ((bool)oldValue == (bool)newValue)
            return;

        if ((bool)newValue)
            DoSomething();

        else
            DoSomethingElse();
    }

    public static bool GetAnimate(BindableObject view) =>  (bool)view.GetValue(AnimateProperty);

    public static void SetAnimate(BindableObject view, bool value) => view.SetValue(AnimateProperty, value);

So far I have tried different "Binding" ways.

Such as; 1)

ShouldAnimateOut="{Binding Path=(attached:AttachedProperty.Animate),Source= {RelativeSource Mode=Self}}"
ShouldAnimateOut="{Binding Path=(attached:AttachedProperty.Animate),Source= {x:Reference myCustomView}}"

Well, Bindable property (ShouldAnimateOut) bind to attached property (Animate) value. Any changes on the Animate attached property reflects to ShouldAnimateOut property and when changes on the property happeens should fire Bindable Property's poperty changed event. But nothing happens.

I've tried bind ShouldAnimateOut to IsEnabled property.

ShouldAnimateOut="{Binding Path=IsEnabled, Source= {RelativeSource Mode=Self}}"
IsEnabled = "False"

If I change IsEnabled property ShouldAnimateOut properties property changed event fires. That's what I want to happened. But I couldn't get the value from attached property.

Also, I have looked Microsot .net maui documentation for further detail but no luck. Very basic information they have in their documentation.

Further check: I also looked github for possible bug for the attached properties bindings but I coulnd't find any.

Any help much preciated. Thanks in advance...


Solution

  • So far, we couldn't bind to an Attached Properties as there is no property backing up the Attached Properties in the custom control. Here is the similar question on StackOverflow: Binding to Attached Properties in Xamarin Forms.

    Also I found the issue on Github Support binding to attached BP and you could follow it.