Custom dialog with Prism

Get your dialog parameters back into you viewModel

Custom dialog with Prism

I'm going to show you how to create a dialog with many different buttons and input and move that information (parameters) back into your ViewModel.

I'm going to base my code on the following Prism documentation on the Dialog Service.

Create the dialog

<?xml version="1.0" encoding="UTF-8" ?>
<Frame
    x:Class="ST.MathTester.Multiplication.Views.YesNoMaybeDialog"
    xmlns="http://xamarin.com/schemas/2014/forms"
    xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
    xmlns:prism="http://prismlibrary.com"
    prism:ViewModelLocator.AutowireViewModel="True"
    prism:DialogLayout.RelativeWidthRequest="{OnIdiom Default=0.75,
                                                      Desktop=0.5}"
    HasShadow="false"
    BackgroundColor="White">
    <StackLayout>
        <Label
            Text="{Binding Message}"
            HorizontalOptions="CenterAndExpand" />
        <Button
            Text="Yes"
            Command="{Binding YesCommand}"
            TextColor="White"
            HorizontalOptions="FillAndExpand"
            BackgroundColor="Green" />
        <Button
            Text="No"
            Command="{Binding NoCommand}"
            TextColor="White"
            HorizontalOptions="FillAndExpand"
            BackgroundColor="Red" />
        <Button
            Text="Maybe"
            Command="{Binding MaybeCommand}"
            TextColor="White"
            HorizontalOptions="FillAndExpand"
            BackgroundColor="Blue" />
    </StackLayout>
</Frame>

Create a ViewModel

Create a ViewModel for the dialog like this

public class YesNoMaybeDialogViewModel : BindableBase, IDialogAware, IAutoInitialize
{
    private string? _message;

    public string? Message
    {
        get => _message;
        set => SetProperty(ref _message, value);
    }

    public DelegateCommand YesCommand => new DelegateCommand(() =>
    {
        var param = new DialogParameters { { "Delete", true } };

        RequestClose?.Invoke(param);
    });

    public DelegateCommand NoCommand => new DelegateCommand(() =>
    {
        var param = new DialogParameters { { "Delete", false } };

        RequestClose?.Invoke(param);
    });

    public DelegateCommand MaybeCommand => new DelegateCommand(() =>
    {
        var param = new DialogParameters { { "Maybe", true } };

        RequestClose?.Invoke(param);
    });


    public event Action<IDialogParameters>? RequestClose;

    public bool CanCloseDialog() => true;

    public void OnDialogClosed()
    {
    }

    public void OnDialogOpened(IDialogParameters parameters)
    {
        // If not using IAutoInitialize 
        // you would need to set the Message property like this
        //Message = parameters.GetValue<string>("message");
    }
}

Call the dialog from somewhere

Based on your logic, fire up the dialog like this with a callback method in you ViewModel

 var param = new DialogParameters
    {
        { "Message", $"Are you sure you want to delete {Profile.Name}?" }
    };

 DialogService?.ShowDialog("YesNoMaybeDialog", param, CloseDialogCallbackAsync);

Note that you need to register the dialog in the App.xaml.cs file like this

containerRegistry.RegisterDialog<YesNoMaybeDialog, YesNoMaybeDialogViewModel>();

The dialog

Then you will have something like this
YesNoMaybeDialog

Get the data back to your viewModel

Now you can get back information on what was clicked by

private async void CloseDialogCallbackAsync(IDialogResult result)
{
    // Check for exception
    if (result.Exception != null)
    {
        var e = result.Exception;
        Console.WriteLine($"Dialog failed. {(e.InnerException ?? e).Message}");
        return;
    }

    // here you can then do what you want
    var yesNo = result.Parameters.GetValue<bool>("Delete");
    var maybe = result.Parameters.GetValue<bool>("Maybe");
    
    // Note that you can also add checks to check if the parameter is sent over
    // result.Parameters.ContainsKey("Delete");
    // else GetValue will always return false
}

What else?

You can customize your dialog as you like and add entries, checkboxes etc. and then just return the results back like we did here.

The world is your ouster