Thomas Carlton
Thomas Carlton

Reputation: 5968

How to create custom control in Maui with an event handler?

I'm trying to create a custom control in Maui from two buttons.

Whenever a developer wants to insert the control in a page, two buttons will show and he can add some specific actions as handlers.

public partial class BottomButtons : Grid
{
    public BottomButtons()
    {
        InitializeComponent();
    }

    public BindableProperty LeftButtonTextProperty = BindableProperty.Create(propertyName: nameof(LeftButtonText),
                                                                    returnType: typeof(String),
                                                                    defaultValue: "Cancel",
                                                                    defaultBindingMode: BindingMode.OneWay,
                                                                    declaringType: typeof(BottomButtons)
                                                                    );
    public String LeftButtonText
    {
        get => (String)GetValue(LeftButtonTextProperty);
        set { SetValue(LeftButtonTextProperty, value); }
    }


    public BindableProperty RightButtonTextProperty = BindableProperty.Create(propertyName: nameof(RightButtonText),
                                                                    returnType: typeof(String),
                                                                    defaultValue: "Save",
                                                                    defaultBindingMode: BindingMode.OneWay,
                                                                    declaringType: typeof(BottomButtons)
                                                                    );

    public String RightButtonText
    {
        get => (String)GetValue(RightButtonTextProperty);
        set { SetValue(RightButtonTextProperty, value); }
    }

    public BindableProperty ClickActionProperty = BindableProperty.Create(propertyName: nameof(ClickAction),
                                                                    returnType: typeof(EventHandler),
                                                                    defaultValue: null,
                                                                    defaultBindingMode: BindingMode.OneWay,
                                                                    declaringType: typeof(BottomButtons)
                                                                    );
    public EventHandler ClickAction
    {
        get => (EventHandler)GetValue(ClickActionProperty);
        set {SetValue(ClickActionProperty, value); }
    }

}

XAML code :

<Grid xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             x:Class="Resources.Controls.BottomButtons"
             ColumnDefinitions="*,*" Padding="10" ColumnSpacing="20"
             x:Name="this">

    <Button Text="{Binding Source={x:Reference this},Path=RightButtonText}" Grid.Column="1" HorizontalOptions="Fill"></Button>
    <Button Text="{Binding Source={x:Reference this},Path=LeftButtonText}" Grid.Column="0" HorizontalOptions="Fill"></Button>

</Grid>

Now I insert the custom control in a page as follows :

<?xml version="1.0" encoding="utf-8" ?>  
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
               xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"               
               x:Class="Pages.SeancesSelector"
               xmlns:viewmodel="clr-namespace:ViewModels" xmlns:VerticalStackLayout="clr-namespace:Resources.Controls">

        <!-- Something... -->
        <BottomButtons ClickAction="MyEventHandler"/>  <!-- Custom control inserted here -->
        
</ContentPage>

and the corresponding C# code :

public partial class SeancesSelector : ContentPage //Popup
{

    public SeancesSelector()
    {
        InitializeComponent();          
    }       

    public void MyEventHandler(Object Sender, EventArgs E)
    {

    }
}

but after doing so, I'm getting a compilation error:

No property, BindableProperty, or event found for "ClickAction", or mismatching type between value and property.

I guess the error is related to the fact that the value given to the property ClickAction is interpreted as a string instead of an EventHandler object.

How can I solve that?

Upvotes: 7

Views: 5973

Answers (1)

Isidoros Moulas
Isidoros Moulas

Reputation: 697

I had the same problem and solved by doing the following.

As the event it's not a property remove get and set and add the event keyword. Also you have to delete the BindableProperty as said by others.

Just add to your control code behind:

public event EventHandler ClickAction;

and when the users interacts with the control by pressing any of the buttons, do not forget to raise the event by adding the below invocation to your code behind of your control.

ClickAction?.Invoke(this, e);

Then your page will listen to the event MyEventHandler.

hope that helps anyone come to this page.

Upvotes: 7

Related Questions