This guide explores advanced navigation patterns and techniques within .NET MAUI, empowering you to build sophisticated and user-friendly mobile applications.
.NET MAUI uses a NavigationPage
to manage a stack of pages. Pushing a new page onto the stack displays it, while popping a page removes it, returning the user to the previous page. This provides a familiar hierarchical navigation experience.
The most basic form of navigation involves pushing a new page onto the navigation stack or popping the current page off.
// Navigating to a new page
await Navigation.PushAsync(new MyNextPage());
// Navigating back
await Navigation.PopAsync();
For operations that require user interaction without disrupting the main navigation flow, modal pages are ideal. They are presented on top of the current page.
// Presenting a modal page
await Navigation.PushModalAsync(new MyModalPage());
// Dismissing a modal page
await Navigation.PopModalAsync();
Often, you need to pass data between pages. This can be achieved by passing parameters to the constructor of the destination page.
When navigating, create an instance of the target page and pass the required data through its constructor.
// On the source page
var userId = 123;
await Navigation.PushAsync(new UserProfilePage(userId));
// On the destination page (UserProfilePage.xaml.cs)
public partial class UserProfilePage : ContentPage
{
private int _userId;
public UserProfilePage(int userId)
{
InitializeComponent();
_userId = userId;
LoadUserData(_userId);
}
private void LoadUserData(int id)
{
// Fetch and display user data based on id
}
}
Deep linking allows users to navigate directly to a specific page or content within your application from external sources like web links or push notifications.
You can configure your application to handle specific URI schemes.
In your MauiProgram.cs
:
public static MauiApp CreateMauiApp()
{
var builder = MauiApp.CreateBuilder();
builder
.UseMauiApp<App>()
.ConfigureFonts(fonts =>
{
fonts.AddFont("OpenSans-Regular.ttf", "OpenSansRegular");
fonts.AddFont("OpenSans-Semibold.ttf", "OpenSansSemibold");
})
.ConfigureMauiHandlers(handlers =>
{
// Example: Registering a custom handler if needed for specific routing
});
// Configure URI scheme for deep linking
Microsoft.Maui.Hosting.MauiApp.SetGlobalConfigurationValue("UriScheme", "myapp");
return builder.Build();
}
Override the OnAppLinkRequestReceived
method in your App.xaml.cs
.
public partial class App : Application
{
public App()
{
InitializeComponent();
MainPage = new AppShell(); // Or your initial page
}
protected override async void OnAppLinkRequestReceived(Uri uri)
{
base.OnAppLinkRequestReceived(uri);
if (uri.Scheme == "myapp")
{
var host = uri.Host;
var path = uri.AbsolutePath;
if (host == "userprofile" && path.StartsWith("/"))
{
var userIdString = path.Substring(1); // Remove leading slash
if (int.TryParse(userIdString, out int userId))
{
// Navigate to the user profile page
// Note: Ensure your MainPage is a NavigationPage or has a Navigation property
if (MainPage is NavigationPage navigationPage)
{
await navigationPage.PushAsync(new UserProfilePage(userId));
}
else
{
// Handle cases where MainPage is not a NavigationPage or is Shell
// You might need to access Shell navigation or set a new NavigationPage
await Navigation.PushAsync(new UserProfilePage(userId)); // This might need adjustment based on your AppShell setup
}
}
}
}
}
}
MainPage
is wrapped in a NavigationPage
if you intend to use Navigation.PushAsync
directly within OnAppLinkRequestReceived
. Alternatively, integrate with AppShell
navigation.
.NET MAUI's Shell provides a streamlined way to build cross-platform applications with a consistent navigation structure. It simplifies common navigation patterns.
Shell supports flyouts (drawers) and bottom tabs for primary navigation. Define your navigation hierarchy in your AppShell.xaml
.
<!-- AppShell.xaml -->
<Shell xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:local="clr-namespace:YourAppName"
x:Class="YourAppName.AppShell"
Shell.FlyoutBehavior="Disabled">
<ShellContent Title="Home"
ContentTemplate="{DataTemplate local:HomePage}"
Route="HomePage" />
<ShellContent Title="About"
ContentTemplate="{DataTemplate local:AboutPage}"
Route="AboutPage" />
<ShellContent Title="User Profile"
ContentTemplate="{DataTemplate local:UserProfilePage}"
Route="userprofile" />
<!-- Example of adding tabs -->
<TabBar>
<ShellContent Title="Tab 1" Icon="tab1_icon.png" ContentTemplate="{DataTemplate local:TabOnePage}" />
<ShellContent Title="Tab 2" Icon="tab2_icon.png" ContentTemplate="{DataTemplate local:TabTwoPage}" />
</TabBar>
</Shell>
You can navigate between Shell items using their routes.
// Navigating to a page defined by a route
await Shell.Current.GoToAsync("userprofile?id=456"); // With query parameters
// Navigating back in Shell
await Shell.Current.GoToAsync("..");
Pass data as query parameters in Shell navigation for cleaner URIs.
// Navigating with query parameters
await Shell.Current.GoToAsync($"userprofile?id=789");
// On the destination page (UserProfilePage.xaml.cs)
[QueryProperty(nameof(UserId), "id")]
public partial class UserProfilePage : ContentPage
{
public string UserId { get; set; }
protected override void OnAppearing()
{
base.OnAppearing();
if (int.TryParse(UserId, out int id))
{
LoadUserData(id);
}
}
private void LoadUserData(int id)
{
// Fetch and display user data
}
}
Enhance user experience by customizing page transitions.
// Custom transition for PushAsync
await Navigation.PushAsync(new MyCustomTransitionPage(), animate: true); // Default animation
// You can also define custom animations using AnimationExtensions or third-party libraries.
// .NET MAUI currently offers basic animation control. For more advanced, consider custom renderers or platform-specific code.
Explore the official .NET MAUI documentation for more in-depth details and advanced scenarios.
Back to Top