web-dev-qa-db-fra.com

Comment puis-je utiliser des types d'énumération en XAML?

J'apprends WPF et j'ai rencontré le problème suivant:

J'ai un type enum dans un autre espace de noms que mon XAML:

 public enum NodeType
    {
        Type_SYSTEM = 1,              // System
        Type_DB = 2,                  // Database
        Type_ROOT = 512,              // Root folder
        Type_FOLDER = 1024,           // Folder
    }

dans mon XAML, je voudrais déclencher une image avec un entier

<Image.Style>
    <Style TargetType="{x:Type Image}">
        <Style.Triggers>
            <DataTrigger Binding="{Binding Type}" Value="{NodeType: }">
                <Setter Property="Source" Value="/Images/DB.PNG"/>
            </DataTrigger>
            <DataTrigger Binding="{Binding Type}" Value="128">
                <Setter Property="Source" Value="/Images/SERVER.PNG"/>
            </DataTrigger>
        </Style.Triggers>
    </Style>
</Image.Style>

Existe-t-il un moyen d'obtenir une valeur entière et de la comparer avec un type d'énumération directement dans le code XAML?

Mon énumération est dans l'espace de noms AnotherNamespace.Types

<DataTrigger Binding="{Binding IntegerType}" Value="MyEnumType.Type_DB">
                                        <Setter Property="Source" Value="/Images/SERVER.PNG"/> 
33
davymartu

J'avais une question similaire ici , et mon résultat final a été de créer un générique IValueConverter qui a passé la valeur enum que je voulais faire correspondre en tant que ConverterParameter, et il renvoie true ou false selon que la valeur liée correspond à (int) valeur de l'énumération.

Le résultat final ressemble à ceci:

Code XAML:

<DataTrigger Value="True"
             Binding="{Binding SomeIntValue, 
                 Converter={StaticResource IsIntEqualEnumConverter},
                 ConverterParameter={x:Static local:NodeType.Type_DB}}">

Convertisseur

public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
    if (parameter == null || value == null) return false;

    if (parameter.GetType().IsEnum && value is int)
    {
        return (int)parameter == (int)value;
    } 
    return false;
}
50
Rachel

Il vous suffit de vous assurer que votre espace de noms est pris en compte dans votre en-tête XAML, puis vous pouvez référencer les DP personnalisés et les valeurs d'énumération directement dans votre balisage.

Par exemple, j'utilise ce code pour faire exactement cela:

<DataTemplate.Triggers>
  <MultiDataTrigger>
    <MultiDataTrigger.Conditions>
      <Condition Binding="{Binding IsMouseOver, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type ListBoxItem}}}" Value="True" />
      <Condition Binding="{Binding Type}" Value="{x:Static loc:AppProfileItemType.Custom}" />
    </MultiDataTrigger.Conditions>
    <MultiDataTrigger.Setters>
      <Setter TargetName="PART_Delete" Property="Visibility" Value="{x:Static Visibility.Visible}" />
    </MultiDataTrigger.Setters>
  </MultiDataTrigger>
</DataTemplate.Triggers>

Notez que vous ne pouvez pas accéder aux DataTriggers dans un style, vous devez plutôt créer un DataTemplate ou ControlTemplate pour cela (cependant, .NET 4 ajoute la possibilité de définir des déclencheurs dans les styles). Vous pouvez remplacer le ControlTemplate d'un style comme ceci:

<Style x:Key="MyCustomButtonStyle" TargetType="Button">
  <Setter Property="Template">
    <Setter.Value>
      <ControlTemplate TargetType="Button">
        <ContentPresenter />
        <ControlTemplate.Triggers>
          <!-- Put your DataTriggers here -->
        </ControlTemplate.Triggers>
      </ControlTemplate>
    </Setter.Value>
  </Setter>
</Style>

Pour les DataTemplates que vous souhaitez avoir des liaisons à un objet, vous pouvez simplement utiliser un ContentPresenter et définir son contenu sur l'objet que vous souhaitez afficher avec une définition DataTemplate à utiliser pour l'affichage de l'objet. Il y a toujours un moyen d'utiliser DataTriggers, ce n'est pas toujours direct ou aussi simple que d'utiliser un style.

10
tpartee