Partager via


Navigation de l’interpréteur de commandes .NET MAUI

Parcourez l’exemple. Parcourir l'exemple

L’interpréteur de commandes .NET MAUI (.NET Multi-platform App UI) Shell inclut une expérience de navigation basée sur l’URI qui utilise des routes pour accéder à n’importe quelle page de l’application, sans avoir à suivre une hiérarchie de navigation définie. De plus, l’utilisateur peut revenir en arrière sans avoir à visiter toutes les pages de la pile de navigation.

La classe Shell définit les propriétés de navigation suivantes :

  • BackButtonBehavior, de type BackButtonBehavior : une propriété qui définit le comportement du bouton Précédent.
  • CurrentItem, de type ShellItem : l’élément actuellement sélectionné.
  • CurrentPage, de type Page : la page actuellement présentée.
  • CurrentState, de type ShellNavigationState : l’état actuel de la navigation de l’élément Shell.
  • Current, de type Shell, qui fournit l’accès à l’interpréteur de commandes actuel.

Les propriétés BackButtonBehavior, CurrentItem et CurrentState sont soutenus par des objets BindableProperty, ce qui signifie que ces propriétés peuvent être des cibles de liaisons de données.

La navigation est effectuée en appelant la méthode GoToAsync à partir de la classe Shell. Lorsque la navigation est sur le point d’être effectuée, l’événement Navigating est déclenché. Une fois la navigation terminée, l’événement Navigated est déclenché.

Remarque

La navigation peut toujours être effectuée entre les pages d’une application Shell à l’aide de la propriété Navigation. Pour plus d’informations, consultez Effectuer une navigation sans mode.

Itinéraires

La navigation est effectuée dans une application Shell en spécifiant un URI auquel accéder. Les URI de navigation peuvent avoir trois composants :

  • Un itinéraire, qui définit le chemin d’accès au contenu existant dans le cadre de la hiérarchie visuelle Shell.
  • Une page. Les pages qui n’existent pas dans la hiérarchie visuelle Shell peuvent être envoyées (par push) sur la pile de navigation à partir de n’importe où dans une application Shell. Par exemple, une page de détails n’est pas définie dans la hiérarchie visuelle Shell, mais peut être envoyée (par push) sur la pile de navigation, si nécessaire.
  • Un ou plusieurs paramètres de requête. Les paramètres de requête sont des paramètres qui peuvent être transmis à la page de destination lors de la navigation.

Lorsqu’un URI de navigation comprend les trois composants, la structure est : //route/page?queryParameters

Inscrire des itinéraires

Vous pouvez définir des itinéraires sur des objets FlyoutItem, TabBar, Tab et ShellContent via leurs propriétés Route :

<Shell ...>
    <FlyoutItem ...
                Route="animals">
        <Tab ...
             Route="domestic">
            <ShellContent ...
                          Route="cats" />
            <ShellContent ...
                          Route="dogs" />
        </Tab>
        <ShellContent ...
                      Route="monkeys" />
        <ShellContent ...
                      Route="elephants" />  
        <ShellContent ...
                      Route="bears" />
    </FlyoutItem>
    <ShellContent ...
                  Route="about" />                  
    ...
</Shell>

Remarque

Tous les éléments dans la hiérarchie Shell sont associés à un itinéraire. Si vous ne définissez pas d’itinéraire, un itinéraire est généré au moment de l’exécution. Cependant, la cohérence des itinéraires générés entre les différentes sessions d’application n’est pas garantie.

L’exemple ci-dessus crée la hiérarchie d’itinéraires suivante qui peut être utilisée dans la navigation programmatique :

animals
  domestic
    cats
    dogs
  monkeys
  elephants
  bears
about

Afin d’accéder à l’objet ShellContent pour l’itinéraire dogs, l’URI de l’itinéraire absolu est //animals/domestic/dogs. De même, afin d’accéder à l’objet ShellContent pour l’itinéraire about, l’URI de l’itinéraire absolu est //about.

Avertissement

Une ArgumentException est levée au démarrage de l’application si un itinéraire en double est détecté. Cette exception est également levée si au moins deux routes au même niveau dans la hiérarchie partagent un nom de route.

Inscrire les itinéraires des pages de détails

Dans le constructeur de sous-classe Shell ou tout autre emplacement qui s’exécute avant l’appel d’une route, des routes supplémentaires peuvent être inscrites explicitement pour toutes les pages de détails qui ne sont pas représentées dans la hiérarchie visuelle Shell. Cette opération est effectuée avec la méthode Routing.RegisterRoute :

Routing.RegisterRoute("monkeydetails", typeof(MonkeyDetailPage));
Routing.RegisterRoute("beardetails", typeof(BearDetailPage));
Routing.RegisterRoute("catdetails", typeof(CatDetailPage));
Routing.RegisterRoute("dogdetails", typeof(DogDetailPage));
Routing.RegisterRoute("elephantdetails", typeof(ElephantDetailPage));

Cet exemple inscrit des pages de détails qui ne sont pas définies dans la sous-classe Shell en tant qu’itinéraires. Il est ensuite possible d’accéder à ces pages de détails à l’aide de la navigation basée sur l’URI, n’importe où dans l’application. Les itinéraires pour ces pages sont appelés itinéraires globaux.

Avertissement

Une ArgumentException est levée si la méthode Routing.RegisterRoute tente d’enregistrer la même route dans au moins deux types différents.

Les pages peuvent également être inscrites sur des hiérarchies d’itinéraires différentes, si nécessaire :

Routing.RegisterRoute("monkeys/details", typeof(MonkeyDetailPage));
Routing.RegisterRoute("bears/details", typeof(BearDetailPage));
Routing.RegisterRoute("cats/details", typeof(CatDetailPage));
Routing.RegisterRoute("dogs/details", typeof(DogDetailPage));
Routing.RegisterRoute("elephants/details", typeof(ElephantDetailPage));

Cet exemple active la navigation contextuelle dans les pages, dans laquelle l’accès à l’itinéraire details depuis la page pour l’itinéraire monkeys affiche l’élément MonkeyDetailPage. De même, l’accès à l’itinéraire details depuis la page pour l’itinéraire elephants affiche l’élément ElephantDetailPage. Pour plus d’informations, consultez Navigation contextuelle.

Remarque

Les pages dont les itinéraires ont été inscrits avec la méthode Routing.RegisterRoute peuvent être désinscrites avec la méthode Routing.UnRegisterRoute, si nécessaire.

Effectuer la navigation

Pour effectuer la navigation, vous devez d’abord obtenir une référence à la sous-classe Shell. Cette référence peut être obtenue via la Shell.Current propriété. La navigation peut ensuite être effectuée en appelant la méthode GoToAsync sur l’objet Shell. Cette méthode permet d’accéder à un élément ShellNavigationState puis retourne un élément Task qui se termine à la fin de l’animation de navigation. L’objet ShellNavigationState est construit par la méthode GoToAsync, à partir d’un élément string ou Uri, et sa propriété Location est définie sur l’argument string ou Uri.

Important

Lorsque vous accédez à un itinéraire depuis la hiérarchie visuelle Shell, aucune pile de navigation n’est créée. Cependant, lorsque vous accédez à une page qui ne figure pas dans la hiérarchie visuelle Shell, une pile de navigation est créée.

Vous pouvez récupérer l’état de navigation actuel de l’objet Shell à l’aide de la propriété Shell.Current.CurrentState qui inclut l’URI de l’itinéraire affiché dans la propriété Location.

Itinéraires absolus

La navigation peut être effectuée en spécifiant un URI absolu valide en tant qu’argument pour la méthode GoToAsync :

await Shell.Current.GoToAsync("//animals/monkeys");

Cet exemple accède à la page pour l’itinéraire monkeys, avec l’itinéraire défini sur un objet ShellContent. L’objet ShellContent qui représente l’itinéraire monkeys est un enfant d’un objet FlyoutItem, dont l’itinéraire est animals.

Itinéraires relatifs

La navigation peut également être effectuée en spécifiant un URI relatif valide en tant qu’argument pour la méthode GoToAsync. Le système d’acheminement tente de faire correspondre l’URI à un objet ShellContent. Par conséquent, si tous les itinéraires d’une application sont uniques, la navigation peut être effectuée en spécifiant uniquement le nom d’itinéraire unique en tant qu’URI relatif.

Les formats d’itinéraire relatif suivants sont pris en charge :

Format Description
route L’itinéraire spécifié est recherché dans la hiérarchie des itinéraires, à partir de la position actuelle vers le haut. La page correspondante est envoyée (push) à la pile de navigation.
/route L’itinéraire spécifié est recherché dans la hiérarchie des itinéraires, à partir de la position actuelle vers le bas. La page correspondante est envoyée (push) à la pile de navigation.
//route L’itinéraire spécifié est recherché dans la hiérarchie des itinéraires, à partir de la position actuelle vers le haut. La page correspondante remplace la pile de navigation.
///route L’itinéraire spécifié est recherché dans la hiérarchie des itinéraires,à partir de la position actuelle vers le bas. La page correspondante remplace la pile de navigation.

L’exemple suivant navigue vers la page de l’itinéraire monkeydetails :

await Shell.Current.GoToAsync("monkeydetails");

Dans cet exemple, l’itinéraire monkeyDetails est recherché vers le haut dans la hiérarchie jusqu’à ce que la page correspondante soit trouvée. Une fois la page trouvée, elle est envoyée (push) à la pile de navigation.

Navigation contextuelle

Les itinéraires relatifs permettent une navigation contextuelle. Par exemple, considérez la hiérarchie d’acheminement suivante :

monkeys
  details
bears
  details

Lorsque la page inscrite pour l’itinéraire monkeys s’affiche, l’accès à l’itinéraire details affichera la page inscrite pour l’itinéraire monkeys/details. De même, lorsque la page inscrite pour l’itinéraire bears s’affiche, l’accès à l’itinéraire details affichera la page inscrite pour l’itinéraire bears/details. Pour plus d’informations sur la façon d’inscrire les itinéraires dans cet exemple, consultez Inscrire les itinéraires de pages.

Navigation vers l’arrière

La navigation vers l’arrière peut être effectuée en spécifiant « .. » comme argument de la méthode GoToAsync :

await Shell.Current.GoToAsync("..");

Vous pouvez également combiner la navigation vers l’arrière avec un itinéraire en utilisant « .. » :

await Shell.Current.GoToAsync("../route");

Dans cet exemple, la navigation vers l’arrière est effectuée, puis la navigation vers l’itinéraire spécifié est effectuée.

Important

La navigation vers l’arrière et dans un itinéraire spécifié n’est possible que si la navigation vers l’arrière vous place à l’emplacement actuel dans la hiérarchie d’itinéraires vous permettant d’accéder à l’itinéraire spécifié.

De même, il est possible de naviguer vers l’arrière plusieurs fois, puis d’accéder à un itinéraire spécifié :

await Shell.Current.GoToAsync("../../route");

Dans cet exemple, la navigation vers l’arrière est effectuée deux fois, puis la navigation vers l’itinéraire spécifié est effectuée.

Il est également possible de passer des données via des propriétés de requête lors de la navigation vers l’arrière :

await Shell.Current.GoToAsync($"..?parameterToPassBack={parameterValueToPassBack}");

Dans cet exemple, la navigation vers l’arrière est effectuée, puis la valeur du paramètre de requête est passée au paramètre de requête de la page précédente.

Remarque

Vous pouvez ajouter des paramètres de requête à n’importe quelle demande de navigation vers l’arrière.

Pour plus d’informations sur le passage de données lors de la navigation, consultez Passer des données.

Itinéraires non valides

Les formats d’itinéraires suivants ne sont pas valides :

Format Explication
//page ou ///page Actuellement, les itinéraires globaux ne peuvent pas représenter la seule page de la pile de navigation. Par conséquent, l’acheminement absolu pour les itinéraires globaux n’est pas pris en charge.

L’utilisation de ces formats d’itinéraire entraîne la levée d’une Exception.

Avertissement

La tentative d’accéder à un itinéraire inexistant lève une exception ArgumentException.

Débogage de la navigation

Certaines des classes Shell comportent l’élément DebuggerDisplayAttribute, qui spécifie comment le débogueur affiche une classe ou un champ. Cela peut faciliter le débogage des demandes de navigation en affichant les données relatives à la demande de navigation. Par exemple, la capture d’écran suivante montre les propriétés CurrentItem et CurrentState de l’objet Shell.Current :

Capture d’écran du débogueur.

Dans cet exemple, la propriété CurrentItem de type FlyoutItem affiche le titre et l’itinéraire de l’objet FlyoutItem. De même, la propriété CurrentState de type ShellNavigationState affiche l’URI de l’itinéraire affiché dans l’application Shell.

La classe Tab définit une propriété Stack de type IReadOnlyList<Page> qui représente la pile de navigation actuelle dans Tab. La classe fournit également les méthodes de navigation remplaçables suivantes :

  • GetNavigationStack, retourne IReadOnlyList<Page>, la pile de navigation actuelle.
  • OnInsertPageBefore, appelée lorsque INavigation.InsertPageBefore est appelée.
  • OnPopAsync, retourne Task<Page> et est appelée lorsque INavigation.PopAsync est appelée.
  • OnPopToRootAsync, retourne Task et est appelée lorsque INavigation.OnPopToRootAsync est appelée.
  • OnPushAsync, retourne Task et est appelée lorsque INavigation.PushAsync est appelée.
  • OnRemovePage, appelée lorsque INavigation.RemovePage est appelée.

L’exemple suivant montre comment remplacer la méthode OnRemovePage :

public class MyTab : Tab
{
    protected override void OnRemovePage(Page page)
    {
        base.OnRemovePage(page);

        // Custom logic
    }
}

Dans cet exemple, les objets MyTab doivent être consommés dans votre hiérarchie visuelle Shell au lieu des objets Tab.

La classe Shell définit l’événement Navigating, qui est déclenché lorsque la navigation est sur le point d’être effectuée à la suite d’une navigation programmatique ou d’une interaction utilisateur. L’objet ShellNavigatingEventArgs qui accompagne l’événement Navigating fournit les propriétés suivantes :

Propriété Type Description
Current ShellNavigationState URI de la page actuelle.
Source ShellNavigationSource Le type de navigation qui s’est produit.
Target ShellNavigationState URI représentant la destination de la navigation.
CanCancel bool Valeur indiquant s’il est possible d’annuler la navigation.
Cancelled bool Valeur indiquant si la navigation a été annulée.

De plus, la classe ShellNavigatingEventArgs fournit une méthode Cancel qui peut être utilisée pour annuler la navigation ainsi qu’une méthode GetDeferral retournant un jeton ShellNavigatingDeferral qui peut servir à terminer la navigation. Pour plus d’informations sur le report de la navigation, consultez Report de navigation.

La classe Shell définit également l’événement Navigated qui est déclenché une fois la navigation terminée. L’objet ShellNavigatedEventArgs qui accompagne l’événement Navigated fournit les propriétés suivantes :

Propriété Type Description
Current ShellNavigationState URI de la page actuelle.
Previous ShellNavigationState URI de la page précédente.
Source ShellNavigationSource Le type de navigation qui s’est produit.

Important

La méthode OnNavigating est appelée lorsque l’événement Navigating se déclenche. De même, la méthode OnNavigated est appelée lorsque l’événement Navigated se déclenche. Vous pouvez remplacer les deux méthodes dans votre sous-classe Shell pour intercepter les demandes de navigation.

Les classes ShellNavigatedEventArgs et ShellNavigatingEventArgs comportent des propriétés Source de type ShellNavigationSource. Cette énumération fournit les valeurs suivantes :

  • Unknown
  • Push
  • Pop
  • PopToRoot
  • Insert
  • Remove
  • ShellItemChanged
  • ShellSectionChanged
  • ShellContentChanged

Il est donc possible d’intercepter la navigation dans un remplacement OnNavigating et d’effectuer des actions en fonction de la source de navigation. Par exemple, le code suivant montre comment annuler la navigation en amont si les données sur la page ne sont pas enregistrées :

protected override void OnNavigating(ShellNavigatingEventArgs args)
{
    base.OnNavigating(args);

    // Cancel any back navigation.
    if (args.Source == ShellNavigationSource.Pop)
    {
        args.Cancel();
    }
}

Vous pouvez intercepter la navigation Shell et la terminer ou l’annuler en fonction du choix de l’utilisateur. Pour ce faire, remplacez la méthode OnNavigating dans votre sous-classe Shell et appelez la méthode GetDeferral sur l’objet ShellNavigatingEventArgs. Cette méthode retourne un jeton ShellNavigatingDeferral doté d’une méthode Complete que vous pouvez utiliser pour terminer la demande de navigation :

public MyShell : Shell
{
    // ...
    protected override async void OnNavigating(ShellNavigatingEventArgs args)
    {
        base.OnNavigating(args);

        ShellNavigatingDeferral token = args.GetDeferral();

        var result = await DisplayActionSheet("Navigate?", "Cancel", "Yes", "No");
        if (result != "Yes")
        {
            args.Cancel();
        }
        token.Complete();
    }    
}

Dans cet exemple, une feuille d’action est affichée pour inviter l’utilisateur à effectuer la demande de navigation ou à l’annuler. Pour annuler la navigation, appelez la méthode Cancel sur l’objet ShellNavigatingEventArgs. Pour terminer la navigation, appelez la méthode Complete sur le jeton ShellNavigatingDeferral récupéré par la méthode GetDeferral sur l’objet ShellNavigatingEventArgs.

Avertissement

La méthode GoToAsync lève une InvalidOperationException si un utilisateur tente de naviguer alors qu’un report de navigation est en attente.

Passer des données

Les données primitives peuvent être passées en tant que paramètres de requête basés sur une chaîne lors de l’exécution d’une navigation par programmation basée sur un URI. Pour ce faire, ajoutez ? après une route, suivi d’un ID de paramètre de requête = et d’une valeur :

async void OnCollectionViewSelectionChanged(object sender, SelectionChangedEventArgs e)
{
    string elephantName = (e.CurrentSelection.FirstOrDefault() as Animal).Name;
    await Shell.Current.GoToAsync($"elephantdetails?name={elephantName}");
}

Cet exemple récupère l’éléphant actuellement sélectionné dans CollectionView et navigue vers l’itinéraire elephantdetails en passant elephantName en tant que paramètre de requête.

Passer des données de navigation basées sur un objet à usage multiple

Vous pouvez passer des données de navigation basées sur un objet à usage multiple avec une surcharge GoToAsync qui spécifie un argument IDictionary<string, object> :

async void OnCollectionViewSelectionChanged(object sender, SelectionChangedEventArgs e)
{
    Animal animal = e.CurrentSelection.FirstOrDefault() as Animal;
    var navigationParameter = new Dictionary<string, object>
    {
        { "Bear", animal }
    };
    await Shell.Current.GoToAsync($"beardetails", navigationParameter);
}

Cet exemple récupère l’ours actuellement sélectionné dans CollectionView en tant que Animal. L’objet Animal est ajouté à un Dictionary avec la clé Bear. La navigation vers l’itinéraire beardetails est ensuite effectuée, Dictionary étant passé en tant que paramètre de navigation.

Toutes les données passées en tant qu’argument IDictionary<string, object> sont conservées en mémoire pendant la durée de vie de la page et ne sont pas libérées tant que la page n’est pas supprimée de la pile de navigation. Cela peut poser problème, comme le montre le scénario suivant :

  1. Page1 navigue vers Page2 à l’aide de la méthode GoToAsync, en passant un objet appelé MyData. Page2 reçoit ensuite MyData en tant que paramètre de requête.
  2. Page2 navigue vers Page3 à l’aide de la méthode GoToAsync, sans passer de données.
  3. Page3 navigue vers l’arrière avec la méthode GoToAsync. Page2 reçoit ensuite à nouveau MyData en tant que paramètre de requête.

Cette approche convient à de nombreux scénarios, mais si ce n’est pas la cas, effacez l’argument IDictionary<string, object> avec la méthode Clear après sa première réception par une page.

Passer des données de navigation basées sur un objet à usage unique

Vous pouvez passer des données de navigation basées sur un objet à usage unique avec une surcharge GoToAsync qui spécifie un argument ShellNavigationQueryParameters. Un objet ShellNavigationQueryParameters est destiné aux données de navigation à usage unique qui sont effacées une fois la navigation effectuée. L’exemple suivant montre comment naviguer tout en passant des données à usage unique :

async void OnCollectionViewSelectionChanged(object sender, SelectionChangedEventArgs e)
{
    Animal animal = e.CurrentSelection.FirstOrDefault() as Animal;
    var navigationParameter = new ShellNavigationQueryParameters
    {
        { "Bear", animal }
    };
    await Shell.Current.GoToAsync($"beardetails", navigationParameter);
}

Cet exemple récupère l’ours actuellement sélectionné dans CollectionView en tant que Animal ajouté à l’objet ShellNavigationQueryParameters. La navigation vers l’itinéraire beardetails est ensuite effectuée, l’objet ShellNavigationQueryParameters étant passé en tant que paramètre de navigation. Une fois la navigation effectuée, les données de l’objet ShellNavigationQueryParameters sont effacées.

Recevoir des données de navigation

Il existe deux approches pour recevoir des données de navigation :

  1. Vous pouvez décorer la classe qui représente la page à laquelle vous accédez, ou la classe du BindingContext de la page, avec un QueryPropertyAttribute pour chaque paramètre de requête. Pour plus d’informations, consultez Traiter les données de navigation à l’aide d’attributs de propriété de requête.
  2. La classe qui représente la page à laquelle vous accédez, ou la classe du BindingContext de la page, peut implémenter l’interfaceIQueryAttributable. Pour plus d’informations, consultez Traiter les données de navigation à l’aide d’une méthode unique.

Traiter les données de navigation à l’aide d’attributs de propriété de requête

Vous pouvez recevoir des données de navigation en décorant la classe de réception avec un QueryPropertyAttribute pour chaque paramètre de requête basé sur une chaîne, paramètre de navigation basé sur un objet ou objet ShellNavigationQueryParameters :

[QueryProperty(nameof(Bear), "Bear")]
public partial class BearDetailPage : ContentPage
{
    Animal bear;
    public Animal Bear
    {
        get => bear;
        set
        {
            bear = value;
            OnPropertyChanged();
        }
    }

    public BearDetailPage()
    {
        InitializeComponent();
        BindingContext = this;
    }
}

Dans cet exemple, le premier argument de QueryPropertyAttribute spécifie le nom de la propriété qui reçoit les données, le deuxième argument spécifiant l’identifiant du paramètre. Par conséquent, dans l’exemple ci-dessus, QueryPropertyAttribute spécifie que la propriété Bear reçoit les données passées dans le paramètre de navigation Bear dans l’appel de méthode GoToAsync.

Important

Les valeurs des paramètres de requête basés sur une chaîne reçues via QueryPropertyAttribute sont automatiquement décodées de l’URL.

Avertissement

La réception de données de navigation à l’aide de l’élément QueryPropertyAttribute n’est pas sécurisée et ne doit pas être utilisée avec le découpage complet ou NativeAOT. Au lieu de cela, vous devez implémenter l’interface IQueryAttributable sur les types qui doivent accepter les paramètres de requête. Pour plus d’informations, consultez Traiter les données de navigation à l’aide d’une méthode unique, découper une application .NET MAUI et un déploiement AOT natif.

Traiter les données de navigation à l’aide d’une méthode unique

Vous pouvez recevoir des données de navigation en implémentant l’interface IQueryAttributable sur la classe de réception. L’interface IQueryAttributable spécifie que la classe d’implémentation doit implémenter la méthode ApplyQueryAttributes. Cette méthode a un argument query de type IDictionary<string, object> qui contient toutes les données passées pendant la navigation. Chaque clé du dictionnaire est un ID de paramètre de requête, dont la valeur correspond à l’objet qui représente les données. L’avantage de cette approche est la possibilité de traiter les données de navigation à l’aide d’une seule méthode, ce qui peut s’avérer utile lorsque plusieurs éléments de données de navigation doivent être traités dans leur ensemble.

L’exemple suivant montre une classe de modèle de vue qui implémente l’interface IQueryAttributable :

public class MonkeyDetailViewModel : IQueryAttributable, INotifyPropertyChanged
{
    public Animal Monkey { get; private set; }

    public void ApplyQueryAttributes(IDictionary<string, object> query)
    {
        Monkey = query["Monkey"] as Animal;
        OnPropertyChanged("Monkey");
    }
    ...
}

Dans cet exemple, la méthode ApplyQueryAttributes récupère l’objet qui correspond à la clé Monkey dans le dictionnaire query, qui a été passé en tant qu’argument à l’appel de méthode GoToAsync.

Important

Les valeurs des paramètres de requête basés sur une chaîne reçues via l’interface IQueryAttributable ne sont pas automatiquement décodées de l’URL.

Passer et traiter plusieurs éléments de données

Vous pouvez passer plusieurs paramètres de requête basés sur une chaîne en les connectant avec &. Par exemple, le code suivant passe deux éléments de données :

async void OnCollectionViewSelectionChanged(object sender, SelectionChangedEventArgs e)
{
    string elephantName = (e.CurrentSelection.FirstOrDefault() as Animal).Name;
    string elephantLocation = (e.CurrentSelection.FirstOrDefault() as Animal).Location;
    await Shell.Current.GoToAsync($"elephantdetails?name={elephantName}&location={elephantLocation}");
}

Cet exemple de code récupère l’éléphant actuellement sélectionné dans CollectionView et navigue vers l’itinéraire elephantdetails en passant elephantName et elephantLocation en tant que paramètres de requête.

Pour recevoir plusieurs éléments de données, vous pouvez décorer la classe qui représente la page à laquelle vous accédez, ou la classe du BindingContext de la page, avec un QueryPropertyAttribute pour chaque paramètre de requête basé sur une chaîne :

[QueryProperty(nameof(Name), "name")]
[QueryProperty(nameof(Location), "location")]
public partial class ElephantDetailPage : ContentPage
{
    public string Name
    {
        set
        {
            // Custom logic
        }
    }

    public string Location
    {
        set
        {
            // Custom logic
        }
    }
    ...    
}

Dans cet exemple, la classe est décorée avec un QueryPropertyAttribute pour chaque paramètre de requête. Le premier QueryPropertyAttribute spécifie que la propriété Name reçoit les données passées dans le paramètre de requête name, tandis que le second QueryPropertyAttribute spécifie que la propriété Location reçoit les données passées dans le paramètre de requête location. Dans les deux cas, les valeurs des paramètres de requête sont spécifiées dans l’URI dans l’appel de méthode GoToAsync.

Avertissement

La réception de données de navigation à l’aide de l’élément QueryPropertyAttribute n’est pas sécurisée et ne doit pas être utilisée avec le découpage complet ou NativeAOT. Au lieu de cela, vous devez implémenter l’interface IQueryAttributable sur les types qui doivent accepter les paramètres de requête. Pour plus d’informations, consultez Trim a .NET MAUI app and Native AOT deployment.

Vous pouvez également traiter les données de navigation avec une méthode unique en implémentant l’interface IQueryAttributable sur la classe qui représente la page à laquelle vous accédez ou la classe du BindingContext de la page :

public class ElephantDetailViewModel : IQueryAttributable, INotifyPropertyChanged
{
    public Animal Elephant { get; private set; }

    public void ApplyQueryAttributes(IDictionary<string, object> query)
    {
        string name = HttpUtility.UrlDecode(query["name"].ToString());
        string location = HttpUtility.UrlDecode(query["location"].ToString());
        ...        
    }
    ...
}

Dans cet exemple, la méthode ApplyQueryAttributes récupère la valeur des paramètres de requête name et location à partir de l’URI dans l’appel de méthode GoToAsync.

Remarque

Vous pouvez passer simultanément les paramètres de requête basés sur une chaîne et les paramètres de navigation basés sur un objet lors de l’exécution d’une navigation basée sur un itinéraire.

Comportement du bouton Précédent

Vous pouvez définir l’apparence et le comportement du bouton Précédent en définissant la propriété jointe BackButtonBehavior sur un objet BackButtonBehavior. La classe BackButtonBehavior définit les propriétés suivantes :

  • Command, de type ICommand : exécuté lorsque l’utilisateur appuie sur le bouton Précédent.
  • CommandParameter, de type object : paramètre passé à la commande Command.
  • IconOverride, de type ImageSource : icône utilisée pour le bouton Précédent.
  • IsEnabled, de type boolean : indique si le bouton Précédent est activé. La valeur par défaut est true.
  • IsVisible, de type boolean, indique si le bouton Précédent est visible. La valeur par défaut est true.
  • TextOverride, de type string : texte utilisé pour le bouton Précédent.

Toutes ces propriétés s’appuient sur des objets BindableProperty, ce qui signifie qu’elles peuvent être des cibles de liaisons de données. Chaque BindableProperty a un mode de liaison OneTime, ce qui signifie que les données passent de la source à la cible, mais uniquement lorsque le BindingContext change.

Toutes ces propriétés s’appuient sur des objets BindableProperty, ce qui signifie qu’elles peuvent être des cibles de liaisons de données. Les objets Command, CommandParameter, IconOveride et TextOverideBindableProperty ont des modes de liaison OneTime, ce qui signifie que les données passent de la source à la cible, mais uniquement lorsque le BindingContext change. Les objets IsEnabled et IsVisibleBindableProperty ont des modes de liaison OneWay, ce qui signifie que les données passent de la source à la cible.

Le code suivant montre un exemple de redéfinition de l’apparence et du comportement du bouton Précédent :

<ContentPage ...>    
    <Shell.BackButtonBehavior>
        <BackButtonBehavior Command="{Binding BackCommand}"
                            IconOverride="back.png" />   
    </Shell.BackButtonBehavior>
    ...
</ContentPage>

La propriété Command est définie sur un élément ICommand à exécuter lorsque le bouton Précédent est enfoncé, et la propriété IconOverride est définie sur l’icône utilisée pour le bouton Précédent :

Capture d’écran du remplacement de l’icône du bouton Précédent du Shell.