Mimicking a modal in Xamarin.Forms

Control Templates are a versatile element in Xamarin Forms. A good description can be found in the Microsoft documentation. Recently I wanted to try and save some screen space on an app where I have some help text that, especially on smaller phones, takes up more room than I would like. Using a Control Template to add functionality that replicates a modal window on a website was a nice way to ensure that the help text was still available, but only if the user wanted/needed to see it.

Here’s how we can do this.

We start by creating a new ContentView that will be our modal. Ideally, we want this to be reusable, so convert the <ContentView.Content> to <ContentView.ControlTemplate>. Doing this allows us to define a control that will display dynamic data.

Set up the layout for our Modal. In my example, I have a close button to hide the modal, a Header Label that is set when the control is used on a screen and a ContentPresenter. It is the ContentPresenter that will take the dynamic content we want to pass through.

Style="{StaticResource ModalStyle}"
<ColumnDefinition Width="8*" />
<ColumnDefinition Width="2*" />
Style="{StaticResource HeaderLabel}"
Text="{Binding Source={x:Reference ModalControl}, Path=ModalHeader}"
VerticalOptions="Start" />
Text="X" />
<ContentPresenter />
view raw Modal.xaml hosted with ❤ by GitHub

In the code behind, we need to specify the bindable properties. At the very least, we will need a property to track if the modal is visible or not. For my example, I also have a bindable property defined for the header I have set up.

namespace XamarinModalExample.Controls
public partial class Modal : ContentView
public static readonly BindableProperty ShowModalProperty
= BindableProperty.Create(nameof(ShowModal), typeof(bool), typeof(Modal), defaultValue: false, defaultBindingMode: BindingMode.TwoWay, propertyChanged: ShowModalPropertyChanged);
public static readonly BindableProperty ModalHeaderProperty
= BindableProperty.Create(nameof(ModalHeader), typeof(string), typeof(Modal), defaultValue: string.Empty, defaultBindingMode: BindingMode.TwoWay);
public string ModalHeader
get => GetValue(ModalHeaderProperty).ToString();
set => SetValue(ModalHeaderProperty, value);
public bool ShowModal
get => (bool)GetValue(ShowModalProperty);
set => SetValue(ShowModalProperty, value);
public Modal()
IsVisible = false;
private static void ShowModalPropertyChanged(BindableObject bindable, object oldvalue, object newvalue)
((Modal)bindable).IsVisible = (bool)newvalue;
private void CloseModalBtn_OnClicked(object sender, EventArgs e)
ShowModal = false;
view raw Modal.xaml.cs hosted with ❤ by GitHub

Now, to use the control, we declare a new XML namespace to allow us to reference it within our ContentPage.

<?xml version="1.0" encoding="utf-8" ?>
view raw MainView.xaml hosted with ❤ by GitHub

In order to allow us to display the modal over our actual screen content, we set our ContentPage root element to be a Grid. Our main content for the page is set to appear in Grid.Row=”0″. And then we set our modal control to also display in Grid.Row=”0″.

<ScrollView Grid.Row="0">
<!– main content here –>
ModalHeader="Help Text"
ShowModal="{Binding ShowHelpModal}"
<!– modal content here –>
view raw MainView.xaml hosted with ❤ by GitHub

The modal visibility is controlled by a binding to ShowHelpModal, a boolean property in our ViewModel, so on the first rendering of the page, it is hidden. Because I have set up a header property for my example, I have also set the ModalHeader value.

In the main layout of the page, we add a button that will display the modal for us. And that’s it!

The full code for this example can be found here.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s