Я хочу связать видимость средств управления с инверсией значения булево свойства. У меня есть свойство CanDownload, если это верно затем, что я хочу скрыть текстовое поле и наоборот. Как я могу достигнуть этого?
Спасибо
Такого рода вопросы задают так часто, а ответы так похожи. Я подумал, что пришло время дать один ответ на все (хорошо, может «большинство») из bool, чтобы вопросы о преобразовании ценности. Я написал это здесь .
Код довольно прост, поэтому я тоже вставлю его сюда: -
public class BoolToValueConverter<T> : IValueConverter
{
public T FalseValue { get; set; }
public T TrueValue { get; set; }
public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
if (value == null)
return FalseValue;
else
return (bool)value ? TrueValue : FalseValue;
}
public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
return value != null ? value.Equals(TrueValue) : false;
}
}
Теперь вы можете создать преобразователь в видимость с однострочным текстом: -
public class BoolToVisibilityConverter : BoolToValueConverter<Visibility> { }
Затем вы можете создать преобразователь экземпляра в ресурсе, например это: -
<local:BoolToVisibilityConverter x:Key="InverseVisibility" TrueValue="Collapsed" FalseValue="Visible" />
Обратите внимание на то, что TrueValue
и FalseValue
заменены местами из более естественного порядка, давая вам инвертированную логику, которую вы хотели. Благодаря этому в Resources
в вашем UserControl
или даже в App.xaml теперь вы можете использовать его для привязки к свойству CanDownload
в TextBox
Свойство видимости
: -
<TextBox Visibility="{Binding CanDownload, Converter={StaticResource InverseVisibility}}" />
Я использую BoolToVisibilityConverter, который позволяет вам передавать «Inverse» в качестве ConverterParameter, чтобы инвертировать преобразование и отображать, только если свойство имеет значение false.
public class BoolToVisibilityConverter : IValueConverter
{
/// <exception cref="ArgumentException">TargetType must be Visibility</exception>
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
if(!(value is bool))
throw new ArgumentException("Source must be of type bool");
if(targetType != typeof(Visibility))
throw new ArgumentException("TargetType must be Visibility");
bool v = (bool) value;
if(parameter is string && parameter.ToString() == "Inverse")
v = !v;
if (v)
return Visibility.Visible;
else
return Visibility.Collapsed;
}
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
Мне удалось решить эту проблему для недавнего проекта, используя преобразователь типа bool в видимость:
public class BoolToVisibilityConverter : IValueConverter
{
#region IValueConverter Members
public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
if (value.GetType().Equals(typeof(bool)))
{
if ((bool)value == true)
return Visibility.Visible;
else
return Visibility.Collapsed;
}
else
return Visibility.Visible;
}
public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
if (value.GetType().Equals(typeof(Visibility)))
{
if ((Visibility)value == Visibility.Collapsed)
return false;
else
return true;
}
else
return false;
}
#endregion
}
Я думаю, что, возможно, я мог бы заменить эту строку:
if (value.GetType().Equals(typeof(Visibility)))
на что-то более простое, например:
if (value is Visibility)
то же самое с bool GetType, но идею вы поняли.
Конечно, в вашем конвертере вы можете изменить значения видимости в зависимости от ваших потребностей в видимости. Надеюсь, это немного поможет.