J'ai trouvé un moyen très simple et propre de le faire avec les déclencheurs d'événements du SDK Blend. Propre MVVM, réutilisable et sans code-behind.
Vous avez probablement déjà quelque chose comme ça :
<Style x:Key="MyListStyle" TargetType="{x:Type ListViewItem}">
Incluez maintenant un ControlTemplate pour le ListViewItem comme ceci si vous n'en utilisez pas déjà un :
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListViewItem}">
<GridViewRowPresenter Content="{TemplateBinding Content}"
Columns="{TemplateBinding GridView.ColumnCollection}" />
</ControlTemplate>
</Setter.Value>
</Setter>
Le GridViewRowPresenter sera la racine visuelle de tous les éléments "intérieurs" constituant un élément de ligne de liste. Nous pourrions maintenant y insérer un déclencheur pour rechercher les événements routés MouseDoubleClick et appeler une commande via InvokeCommandAction comme ceci :
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListViewItem}">
<GridViewRowPresenter Content="{TemplateBinding Content}"
Columns="{TemplateBinding GridView.ColumnCollection}">
<i:Interaction.Triggers>
<i:EventTrigger EventName="MouseDoubleClick">
<i:InvokeCommandAction Command="{Binding DoubleClickCommand}" />
</i:EventTrigger>
</i:Interaction.Triggers>
</GridViewRowPresenter>
</ControlTemplate>
</Setter.Value>
</Setter>
Si vous avez des éléments visuels "au-dessus" du GridRowPresenter (probablement en commençant par une grille), vous pouvez également y placer le déclencheur.
Malheureusement, les événements MouseDoubleClick ne sont pas générés par tous les éléments visuels (ils le sont par les contrôles, mais pas par les FrameworkElements, par exemple). Une solution de contournement consiste à dériver une classe de EventTrigger et à rechercher les MouseButtonEventArgs dont le nombre de clics est égal à 2. Cela permet de filtrer efficacement tous les événements qui ne sont pas des boutons de souris et tous les événements MouseButtonEvents dont le nombre de clics != 2.
class DoubleClickEventTrigger : EventTrigger
{
protected override void OnEvent(EventArgs eventArgs)
{
var e = eventArgs as MouseButtonEventArgs;
if (e == null)
{
return;
}
if (e.ClickCount == 2)
{
base.OnEvent(eventArgs);
}
}
}
Maintenant nous pouvons écrire ceci ('h' est le Namespace de la classe d'aide ci-dessus) :
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListViewItem}">
<GridViewRowPresenter Content="{TemplateBinding Content}"
Columns="{TemplateBinding GridView.ColumnCollection}">
<i:Interaction.Triggers>
<h:DoubleClickEventTrigger EventName="MouseDown">
<i:InvokeCommandAction Command="{Binding DoubleClickCommand}" />
</h:DoubleClickEventTrigger>
</i:Interaction.Triggers>
</GridViewRowPresenter>
</ControlTemplate>
</Setter.Value>
</Setter>