2010-06-23 1 views
3

Je suis un démarreur dans WPF, et il y a quelque chose que je n'arrive pas à comprendre.Liaison de données d'élément WPF pour IsEnabled (mais pour false)

J'ai un CheckBox que je voudrais désactiver lorsqu'un RadioButton n'est pas sélectionné. Ma syntaxe actuelle est:

<CheckBox IsEnabled="{Binding ElementName=rbBoth, Path=IsChecked}">Show all</CheckBox> 

Donc, fondamentalement, je veux IsEnabled prendre la valeur opposée à l'expression de liaison je fournir actuellement.

Comment est-ce que je peux faire ceci? Merci.

Répondre

18

Vous devez utiliser ce qu'on appelle un convertisseur de valeur (une classe qui implémente IValueConverter.) Un exemple très basique d'une telle classe est montré ci-dessous. (Surveillez détourage ...)

public class NegateConverter : IValueConverter 
{ 

    public object Convert(object value, Type targetType, object parameter, CultureInfo culture) 
    { 
     if (value is bool) { 
      return !(bool)value; 
     } 
     return value; 
    } 

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture) 
    { 
     if (value is bool) { 
      return !(bool)value; 
     } 
     return value; 
    } 

} 

ensuite l'inclure dans votre XAML vous feriez quelque chose comme:

<UserControl xmlns:local="clr-namespace:MyNamespace"> 
    <UserControl.Resources> 
     <local:NegateConverter x:Key="negate" /> 
    </UserControl.Resources> 

    ... 
    <CheckBox IsEnabled="{Binding IsChecked, ElementName=rbBoth, Converter={StaticResource negate}}" 
       Content="Show all" /> 

</UserControl> 
+0

Ouais ... Je pensais à ce sujet, mais je tente de voir s'il y a une approche plus directe. – SiN

+2

À mesure que vous utilisez de plus en plus WPF, vous constaterez que vous créez un ensemble de convertisseurs plutôt sophistiqué et que leur conception est généralement très réutilisable. En fait, j'ai un NegateConverter mais c'est beaucoup plus robuste que mon exemple. Il nie les nombres, les booléens, la visibilité, l'épaisseur, etc. Un seul d'environ une douzaine de convertisseurs que j'utilise fréquemment. – Josh

+0

Josh: Comment annuler une épaisseur? – Gabe

1

Votre syntaxe actuelle sert déjà à vos besoins. Cela désactivera la case à cocher si le bouton radio n'est pas coché.

Si vous voulez vraiment inverser le scénario, tout ce dont vous avez besoin est un convertisseur. Jetez un oeil à ce sample.

0

Que diriez-vous celui-ci:

Créer un convertisseur pour booléens:

class BooleanValueInverter : IValueConverter 
{ 
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture) 
    { 
     if (!(parameter is IValueConverter)) 
     { 
      if (value is bool) 
       return !(bool)value; 
      else 
       return DependencyProperty.UnsetValue; 
     } 
     else 
     { 
      IValueConverter converter = (IValueConverter)parameter; 
      if (value is bool) 
      { 
       bool input = !(bool)value; 
       return converter.Convert(input, targetType, null, culture); 
      } 
      else 
      { 
       return DependencyProperty.UnsetValue; 
      } 
     } 
    } 

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture) 
    { 
     throw new NotImplementedException(); 
    } 
} 

dans l'importation de XAML l'espace de noms où la classe onduleur est mis en œuvre:

xmlns:util="clr-namespace:MyApp.Utilities" 

Dans la section des ressources ajouter référence la classe d'inverseur:

<util:BooleanValueInverter x:Key="Inverter" /> 

Et puis il suffit d'utiliser simplement comme ceci:

<TextBox Text="{Binding Path=TextProperty}" IsEnabled="{Binding SomeBoolPropertyToInvert, Converter={StaticResource Inverter}}"/> 
0
<CheckBox> 
        <CheckBox.Style> 
         <Style TargetType="CheckBox"> 
          <Setter Property="Visibility" Value="Visible" /> 
          <Style.Triggers> 
           <DataTrigger Binding="{Binding IsShowName }" Value="true"> 
            <Setter Property="Visibility" Value="Collapsed" /> 
           </DataTrigger> 
          </Style.Triggers> 
         </Style> 
        </CheckBox.Style> 
    </CheckBox>