web-dev-qa-db-fra.com

WPF Radiobutton (two) (liaison à la valeur booléenne)

J'ai une propriété de type booléen présentée avec une case à cocher.

Je veux changer cela en deux radiobuttons qui se lient sur la même propriété présentant la valeur true/false.

Comment cela peut-il être fait?

38
no9
<RadioButton GroupName="Group1" 
             IsChecked="{Binding PropertyValue}" Content="Yes" />
<RadioButton GroupName="Group1"  Content="No" 
             IsChecked="{Binding PropertyValue, 
                         Converter={StaticResource BoolInverterConverter}}" />
public class BoolInverterConverter : IValueConverter
{
    #region IValueConverter Members

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

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

    #endregion
}
71
Ragunathan

Vous pouvez utiliser un convertisseur de valeur qui rétablit la valeur booléenne:

Avec ce convertisseur, liez une propriété Checkbox.IsChecked à la valeur booléenne sans le convertisseur et une propriété CheckBox.IsChecked avec le convertisseur. Cela devrait faire l'affaire.

Voici le code pour un tel convertisseur. Je l'ai copié de ici et j'ai ajouté quelques lignes de code. Vous y trouverez plus d'informations sur.

public class BoolToOppositeBoolConverter : IValueConverter {
    public object Convert(object value, Type targetType, object parameter,System.Globalization.CultureInfo culture) {
        if (targetType != typeof(bool)) {
            throw new InvalidOperationException("The target must be a boolean");
        }
        if (null == value) {
            return null;
        }
                    return !(bool)value;
    }

    public object ConvertBack(object value, Type targetType, object parameter,System.Globalization.CultureInfo culture) {
        if (targetType != typeof(bool)) {
            throw new InvalidOperationException("The target must be a boolean");
        }
        if (null == value) {
            return null;
        }
        return !(bool)value;
    }
} 

Pour l'utiliser, déclarez-le dans la section resource.

 <local:BoolToOppositeBoolConverter x:Key="BoolToOppositeBoolConverter_ValueConverter"/>

Et l’utiliser dans la liaison en tant que ressource statique:

<CheckBox IsChecked="{Binding YourProperty}" />
<CheckBox IsChecked="{Binding YourProperty,Converter={StaticResource BoolToOppositeBoolConverter_ValueConverter}}" />

Veuillez noter que le convertisseur n'est qu'un exemple simple. Implémentez-le proprement si vous voulez l'utiliser dans un code productif. Je ne l'ai pas testé. Faites un commentaire si cela ne fonctionne pas.

9
HCL

L’approche de liaison standard a l’effet secondaire fâcheux de déclencher le paramètre de liaison comme étant "non sélectionné" chaque fois que l’UI est chargée. Donc, si vous avez du code pour gérer les clics de l'utilisateur dans le setter pour votre bool, il fera des choses étranges comme enflammer le setter sur "false" même si vous l'avez lié à un "vrai" bool.

J'ai contourné cela avec un convertisseur utilisé spécifiquement pour les boutons radio:

public class BoolRadioConverter : IValueConverter
{
    public bool Inverse { get; set; }

    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        bool boolValue = (bool) value;

        return this.Inverse ? !boolValue : boolValue;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        bool boolValue = (bool)value;

        if (!boolValue)
        {
            // We only care when the user clicks a radio button to select it.
            return null;
        }

        return !this.Inverse;
    }
}

Dans vos ressources:

<converters:BoolRadioConverter x:Key="BoolRadioConverter" />
<converters:BoolRadioConverter x:Key="InverseBoolRadioConverter" Inverse="True" />

Dans votre xaml:

<RadioButton
    Content="True option"
    GroupName="radioGroup1"
    IsChecked="{Binding MyProperty,
                        Converter={StaticResource BoolRadioConverter}}" />
<RadioButton
    Content="False option"
    GroupName="radioGroup2"
    IsChecked="{Binding MyProperty,
                        Converter={StaticResource InverseBoolRadioConverter}}" />
7
RandomEngy

Vous pouvez y parvenir sans convertisseur si vous définissez la même valeur sur la propriété GroupName de deux boutons radio (vous ne pouvez donc en cocher qu'un seul à la fois). Ensuite, définissez IsChecked d'un bouton radio sur "True" et liez IsChecked d'un autre à votre Boolean. Le fait de changer de bouton radio changera la valeur booléenne. Cependant, changer la valeur booléenne en False ne vérifiera pas l'autre bouton radio.

Merci, Vlad 

3
votrubac

Voici la solution pour lier des boutons radio à n'importe quel type (énumération, booléen, chaîne de caractères, entier, etc.) avec le code exemple:

http://www.codeproject.com/Tips/720497/Binding-Radio-Buttons-to-a-Single-Property

1
votrubac

Version simplifiée de ragunathan 's answer .

public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) =>
    Convert(value);

public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) =>
    Convert(value);

private object Convert(object value) => 
    value is bool ? !(bool)value : value;
0
oddRaven