web-dev-qa-db-fra.com

utilisation du convertisseur booléen en couleur en XAML

Je travaille sur l'application WPF, j'ai lié mon bloc de texte à mon bouton. Je veux mettre le premier plan de mon bloc de texte à la couleur noire lorsque le bouton associé est activé est vrai. Je veux le faire en utilisant un convertisseur. Mais ça ne marche pas. ne donnant également aucune erreur. J'ai déclaré la classe suivante dans mon dossier "Modèles".

public class BrushColorConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        if ((bool)value)
        {
            {
                return System.Windows.Media.Colors.Black;
            }
        }
        return System.Windows.Media.Colors.LightGreen;
    }

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

Activer le bouton, les propriétés des propriétés modifiables du viewmodel (par exemple en utilisant RaiseCanExecuteChanged) ())

les éléments liés au bloc de texte en XAML sont:

   <Window.Resources>
            <local:BrushColorConverter x:Key="BConverter"></local:BrushColorConverter>
   </Window.Resources>
<Button>(!..all button properties..!)</Button>
    <TextBlock x:Name="AnswerText"                                           
               Text="Answer"                                          
               Foreground="{Binding ElementName=AnswerButton,Path=IsEnabled, Converter={StaticResource BConverter}}"
               TextWrapping="Wrap"/>
30
deathrace

utilisez return new SolidColorBrush (Colors.Black);

41
user1101511

La réponse ci-dessus vous montre comment utiliser correctement un convertisseur. Cependant, avez-vous vraiment besoin d'utiliser un convertisseur? Cela peut être fait en XAML uniquement en utilisant Triggers:

XAML

        <StackPanel>

            <Button IsEnabled="{Binding ElementName=isEnabledCheckBox, Path=IsChecked}">
                <TextBlock Text="Answer" TextWrapping="Wrap">
                    <TextBlock.Style>
                        <Style TargetType="{x:Type TextBlock}">
                            <Style.Triggers>
                                <DataTrigger Binding="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type Button}}, Path=IsEnabled}" Value="True">
                                    <Setter Property="Foreground" Value="Green"/>
                                </DataTrigger>
                            </Style.Triggers>
                        </Style>
                    </TextBlock.Style>
                </TextBlock>
            </Button>

            <Button IsEnabled="{Binding ElementName=isEnabledCheckBox, Path=IsChecked}">
                <TextBlock Text="Answer" TextWrapping="Wrap">
                    <TextBlock.Style>
                        <Style TargetType="{x:Type TextBlock}">
                            <Style.Triggers>
                                <Trigger Property="IsEnabled" Value="True">
                                    <Setter Property="Foreground" Value="Green"/>
                                </Trigger>
                            </Style.Triggers>
                        </Style>
                    </TextBlock.Style>
                </TextBlock>
            </Button>

            <CheckBox x:Name="isEnabledCheckBox" Content="Toggle IsEnable on Buttons above" />

        </StackPanel>

Dans l'exemple ci-dessus, le premier TextBlock se lie à la propriété IsEnabled de son parent à l'aide d'un DataTrigger et définit le Foreground sur une certaine couleur s'il est vrai.

Cependant, c'est exagéré - la propriété IsEnabled est propagée automatiquement aux enfants par WPF. Autrement dit, si vous définissez IsEnabled sur false sur votre Button, votre TextBlock verra sa propriété IsEnabled mise à jour automatiquement sur false. Ceci est démontré dans le deuxième TextBlock qui utilise une propriété Trigger pour vérifier sa propre propriété IsEnabled par rapport à la valeur true (puisque sa propriété IsEnabled sera le même que celui de son parent). Ce serait l'approche préférée.

J'espère que cela t'aides!

16
F Ruffell

Pour rendre ce convertisseur général, vous pouvez utiliser un ConverterParameter pour spécifier les couleurs à insérer lorsque value est vrai ou faux. L'opacité peut également être intéressante. Je fournis ici le convertisseur I en prenant le paramètre [ColorNameIfTrue; ColorNameIfFalse; OpacityNumber].

Étant donné que la méthode SolidColorBrush() mentionnée par @ user1101511 fait partie de la bibliothèque System.Windows.Media, Elle utilise le type Color de cette même bibliothèque. Ce type n'a pas de méthode Color.FromName(), comme la classe System.Drawing.Color.

J'ai donc créé une méthode d'aide appelée ColorFromName(string name). Je spécifie "LimeGreen" Comme couleur de remplacement si l'interpertation de ConverterParameter échoue. Dans mon cas, je veux que la sortie soit "Transparent" Lorsque value est faux.

using System;
using System.Globalization;
using System.Windows.Data;
using System.Windows.Media;

namespace MyConverters
{
    [ValueConversion(typeof(bool), typeof(SolidColorBrush))]
    class BoolToColorBrushConverter : IValueConverter
    {
        #region Implementation of IValueConverter

        /// <summary>
        /// 
        /// </summary>
        /// <param name="value">Bolean value controlling wether to apply color change</param>
        /// <param name="targetType"></param>
        /// <param name="parameter">A CSV string on the format [ColorNameIfTrue;ColorNameIfFalse;OpacityNumber] may be provided for customization, default is [LimeGreen;Transperent;1.0].</param>
        /// <param name="culture"></param>
        /// <returns>A SolidColorBrush in the supplied or default colors depending on the state of value.</returns>
        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        SolidColorBrush color;
        // Setting default values
        var colorIfTrue = Colors.LimeGreen;
        var colorIfFalse = Colors.Transparent;
        double opacity = 1;
        // Parsing converter parameter
        if (parameter != null)
        {
            // Parameter format: [ColorNameIfTrue;ColorNameIfFalse;OpacityNumber]
            var parameterstring = parameter.ToString();
            if (!string.IsNullOrEmpty(parameterstring))
            {
                var parameters = parameterstring.Split(';');
                var count = parameters.Length;
                if (count > 0 && !string.IsNullOrEmpty(parameters[0]))
                {
                    colorIfTrue = ColorFromName(parameters[0]);
                }
                if (count > 1 && !string.IsNullOrEmpty(parameters[1]))
                {
                    colorIfFalse = ColorFromName(parameters[1]);
                }
                if (count > 2 && !string.IsNullOrEmpty(parameters[2]))
                {
                    double dblTemp;
                    if (double.TryParse(parameters[2], NumberStyles.AllowDecimalPoint, CultureInfo.InvariantCulture.NumberFormat, out dblTemp))
                        opacity = dblTemp;
                }
            }
        }
        // Creating Color Brush
        if ((bool) value)
        {
            color = new SolidColorBrush(colorIfTrue);
            color.Opacity = opacity;
        }
        else
        {
            color = new SolidColorBrush(colorIfFalse);
            color.Opacity = opacity;
        }
        return color;
    }


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

    #endregion

    public static Color ColorFromName(string colorName)
    {
        System.Drawing.Color systemColor = System.Drawing.Color.FromName(colorName);
        return Color.FromArgb(systemColor.A, systemColor.R, systemColor.G, systemColor.B);
    }
}

Depuis xaml, le convertisseur ci-dessus peut être utilisé comme ceci:

Background="{Binding MyBooleanValue, Converter={StaticResource BoolToColorBrushConverter}, ConverterParameter=LimeGreen;Transperent;0.2, Mode=OneWay}"
7
Håkon Seljåsen