> For the complete documentation index, see [llms.txt](https://avaloniachina.gitbook.io/avalonia/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://avaloniachina.gitbook.io/avalonia/docs/data-binding/converting-binding-values.md).

# 转换绑定值

### 否定值 <a href="#negating-values" id="negating-values"></a>

您经常需要对绑定的值取反。常见的用法有显示/隐藏控件或启用/禁用控件。您可以通过在绑定值前面加上运算符`!`来取反。

例如，您可能希望在禁用一个控件时显示另一个控件。

```markup
<StackPanel>
  <TextBox Name="input" IsEnabled="{Binding AllowInput}"/>
  <TextBlock IsVisible="{Binding !AllowInput}">Sorry, no can do!</TextBlock>
</StackPanel>
```

当绑定到非布尔值时，取反也有效。首先，使用`Convert.ToBoolean`将值转换为布尔值，并对结果取反。由于整数值`0`被视为`false`，而所有其他整数值都被视为`true`，因此当集合为空时，可以使用此方式显示消息：

```markup
<Panel>
  <ListBox Items="{Binding Items}"/>
  <TextBlock IsVisible="{Binding !Items.Count}">No results found</TextBlock>
</Panel>
```

双感叹号可用于将非布尔值转换为布尔值。例如，要在集合为空时隐藏控件：

```markup
<Panel>
  <ListBox Items="{Binding Items}" IsVisible="{Binding !!Items.Count}"/>
</Panel>
```

### 绑定转换器 <a href="#binding-converters" id="binding-converters"></a>

对于更高级的转换，和其他XAML框架一样，Avalonia支持[`IValueConverter`](https://docs.microsoft.com/en-gb/dotnet/api/system.windows.data.ivalueconverter?view=netframework-4.7.1)

> 注意：`IValueConverter`接口在.NET标准2.0中不可用，因此我们在`Avalonia.Data.Converters`命名空间中提供了自己的接口。

用法与其他XAML框架相同：

```markup
<Window xmlns="https://github.com/avaloniaui"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="clr-namespace:ExampleApp;assembly=ExampleApp">

  <Window.Resources>
    <local:MyConverter x:Key="myConverter"/>
  </Window.Resources>

  <TextBlock Text="{Binding Value, Converter={StaticResource myConverter}}"/>
</Window>
```

### 内置转换器 <a href="#built-in-converters" id="built-in-converters"></a>

Avalonia为常见场景提供了许多内置值转换器：

| 转换器                                 | 描述                               |
| ----------------------------------- | -------------------------------- |
| `StringConverters.IsNullOrEmpty`    | 如果输入的字符串为null或empty，则返回`true`    |
| `StringConverters.IsNotNullOrEmpty` | 如果输入的字符串不为null或empty，则返回`true`   |
| `ObjectConverters.IsNull`           | 如果输入为null，则返回`true`              |
| `ObjectConverters.IsNotNull`        | 如果输入为null，则返回`false`             |
| `BoolConverters.And`                | 一种多值转换器，如果所有输入均为true，则返回`true`。  |
| `BoolConverters.Or`                 | 一种多值转换器，如果其中任意输入为true，则返回`true`。 |

您可以在此处查看默认转换器列表： [Avalonia.Data.Converters 命名空间](https://docs.avaloniaui.net/api/untitled/avalonia-ui-framework-23/avalonia-ui-framework-24#classtypes).

### 示例

如果绑定文本为null或empty，则隐藏`TextBlock`：

```markup
<TextBlock Text="{Binding MyText}"
           IsVisible="{Binding MyText, Converter={x:Static StringConverters.IsNotNullOrEmpty}}"/>
```

如果绑定内容为null或empty，则隐藏`ContentControl`：

```markup
<ContentControl Content="{Binding MyContent}"
                IsVisible="{Binding MyContent, Converter={x:Static ObjectConverters.IsNotNull}}"/>
```

> 从现在开始，假设转换器已导入，如上一节“绑定转换器”所示

根据不同参数将文本转换为特定大小写格式

```markup
<TextBlock Text="{Binding TheContent, 
    Converter={StaticResource textCaseConverter},
    ConverterParameter=lower}" />
```

```csharp
public class TextCaseConverter : IValueConverter
{
    public static readonly TextCaseConverter Instance = new();

    public object? Convert( object? value, Type targetType, object? parameter, CultureInfo culture )
    {
        if (value is string sourceText && parameter is string targetCase
            && targetType.IsAssignableTo(typeof(string)))
        {
            switch (targetCase)
            {
                case "upper":
                case "SQL":
                    return sourceText.ToUpper();
                case "lower":
                    return sourceText.ToLower();
                case "title": // 首字母大写
                    var txtinfo = new System.Globalization.CultureInfo("en-US",false).TextInfo;
                    return txtinfo.ToTitleCase(sourceText);
                default:
                    // 无效参数，在这里返回异常
                    break;
            }
        }
        // 用于错误类型的转换器
        return new BindingNotification(new InvalidCastException(), BindingErrorType.Error);
    }

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

在上下文中将绑定对象转换为不同的目标类型

```markup
<Image Width="42" 
       Source="{Binding Animal, Converter={StaticResource animalConverter}}"/>
<TextBlock 
       Text="{Binding Animal, Converter={StaticResource animalConverter}}" />
```

```csharp
public class AnimalConverter : IValueConverter
{
    public static readonly AnimalConverter Instance = new();

    public object? Convert( object? value, Type targetType, object? parameter, CultureInfo culture )
    {
        if (value is Animal animal)
        {
            if (targetType.IsAssignableTo(typeof(IImage)))
            {
                img = @"icons/generic-animal-placeholder.png"
                switch (animal)
                {
                    case Dog d:
                      img = d.IsGoodBoy ? @"icons/dog-happy.png" : @"icons/dog.png";
                      break;
                    case Cat:
                      img = @"icons/cat.png";
                      break;
                    // 等等
                }
                // 请看 https://docs.avaloniaui.net/docs/controls/image
                return BitmapAssetValueConverter.Instance
                    .Convert(img, typeof(Bitmap), parameter, culture);
            }
            else if (targetType.IsAssignableTo(typeof(string)))
            {
                return !string.IsNullOrEmpty(animal.NickName) ? 
                    $"{animal.Name} \"{animal.NickName}\"" : animal.Name;
            }
        }
        // 用于错误类型的转换器
        return new BindingNotification(new InvalidCastException(), BindingErrorType.Error);
        
    }

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

### 范例

[ValueConverter Sample](https://github.com/AvaloniaUI/Avalonia.Samples/tree/main/src/Avalonia.Samples/MVVM/ValueConversionSample)


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://avaloniachina.gitbook.io/avalonia/docs/data-binding/converting-binding-values.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
