Voilà un certain temps que je n’avais plus parlé des markup extensions… J’y reviens à l’occasion de la sortie de Visual Studio 11 Developer Preview, qui introduit un certain nombre de nouveautés dans WPF. La nouveauté dont je vais parler n’est sans doute pas la plus spectaculaire, mais elle vient combler un manque des versions précédentes : le support des markup extensions pour les évènements. Jusqu’ici, il était possible d’utiliser une markup extension en XAML pour affecter une valeur à une propriété, mais on ne pouvait pas faire la même chose pour s’abonner à un évènement.
Note : Ce billet est la suite de celui sur une markup extension qui met à jour sa cible, et réutilise le même code de départ. Vous avez peut-être remarqué que l’utilisation d’une markup extension personnalisée dans un template donnait parfois des résultats inattendus… Nous allons voir dans ce billet comment faire une markup extension qui se comporte correctement dans un template. Illustration du problème Reprenons l’exemple du précédent billet : une markup extension qui renvoie l’état de la connectivité réseau, et met à jour la propriété cible quand le réseau est connecté ou déconnecté :
Si vous avez lu mes précédents billets sur le sujet, vous savez que je suis un grand fan des markup extensions… Cependant, celles-ci ont une limitation qui peut s’avérer assez gênante : elles ne sont évaluées qu’une seule fois. Il serait pourtant utile de pouvoir les réévaluer pour mettre à jour la propriété cible, comme pour un binding… Cela peut être utile dans différents cas, notamment :
si la valeur de la markup extension peut changer en réponse à un évènement
Mise à jour : Comme l’a très justement indiqué Jérémy en commentaire, la propriété IsAsync du Binding permet de faire à peu près la même chose beaucoup plus simplement… Bien que ma méthode puisse servir pour certains besoins spécifiques, dans la plupart des cas la propriété IsAsync est probablement le meilleur choix ! Je laisse le billet malgré tout, ne serait-ce que pour la classe SwitchBinding qui me semble assez utile… J’ai eu récemment besoin, dans une application basée sur le pattern MVVM, d’afficher une propriété dont la valeur était assez longue à obtenir (récupérer par une requête HTTP).
Si vous développez des applications WPF en suivant le design pattern Model-View-ViewModel, vous vous êtes peut-être déjà trouvé confronté au problème suivant : comment, en XAML, lier un raccourci clavier ou une action de la souris à une commande du ViewModel ? Idéalement, on aimerait pouvoir faire comme ça :
<UserControl.InputBindings> <KeyBinding Modifiers="Control" Key="E" Command="{Binding EditCommand}"/> </UserControl.InputBindings> Malheureusement, ce code ne fonctionne pas, pour deux raisons :
La propriété Command n’est pas une DependencyProperty, on ne peut donc pas faire de binding dessus Les InputBindings ne font pas partie de l’arbre logique ou visuel du contrôle, ils n’héritent donc pas du DataContext Une solution, bien sûr, serait de passer par le code-behind pour créer les InputBindings, mais en général, dans une application développée selon le pattern MVVM, on préfère éviter d’écrire du code-behind.
Voilà, c’est fait, j’ai créé mon blog sur .NET… j’ai mis le temps, mais j’ai fini par y venir ;-) Je me présente rapidement : Thomas Levesque, 27 ans, ingénieur de formation. Je suis passionné depuis toujours par l’informatique, et plus particulièrement par la technologie .NET, que je suis de très près depuis ses débuts. Comme je suis du genre curieux, je passe pas mal de temps à fouiner dans les docs MSDN et sur le net pour m’auto-former sur les dernières nouveautés du framework.