如何在 {x:bind} 中投射依赖项 属性?

How do I cast a dependency property in {x:bind}?

{X:bind}documentation 提到可以在 属性 路径中进行转换(提到 {x:Bind obj.(TextBox.Text)})作为示例。在下面的简单示例中,我看不到这应该如何工作。我尝试了括号中类型名称的各种组合,但没有成功。

一个常见的用例是组合框的双向绑定,在这里我会将 SelectedValue 属性 从通用对象类型转换为更具体的类型。

示例 xaml 页面 MainPage.xaml:

<Page
    x:Class="XBindTest4.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:XBindTest4"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    mc:Ignorable="d" >

    <StackPanel>
        <ComboBox ItemsSource="{x:Bind SampleList, Mode=OneWay}" 
                  SelectedValue="{x:Bind SampleData, Mode=TwoWay}"/>
    </StackPanel>

</Page>

MainPage.xaml.cs 背后的代码:

using System.Collections.ObjectModel;
using Windows.UI.Xaml.Controls;

namespace XBindTest4 {

    public class SampleClass {
    }

    public sealed partial class MainPage : Page {

        public ObservableCollection<SampleClass> SampleList = new ObservableCollection<SampleClass>(new[] {
            new SampleClass(),
            new SampleClass()
            });

        public SampleClass SampleData { get; set; }

        public MainPage() {
            this.InitializeComponent();
        }
    }
}

目前,现有的语法不可能做到这一点。这很糟糕,因为它向绑定表达式添加了不必要的重复代码:要在这种情况下使用 {x:Bind},必须指定转换器,即使它什么都不做。

...
SelectedValue="{x:Bind SampleData, Mode=TwoWay, Converter={StaticResource NoOpConverter}}
...

如果使用转换器,则将适当的转换插入到生成的文件中 MainPage.g.cs:

this.dataRoot.SampleData = (global::XBindTest4.SampleClass)this.LookupConverter("NoOpConverter").ConvertBack((this.obj2).SelectedValue, typeof(global::XBindTest4.SampleClass), null, null);

其他来源:

NoOpConverter.cs:

using System;
using Windows.UI.Xaml.Data;

namespace XBindTest4 {

    public class NoOpConverter : IValueConverter {
        public object Convert(object value, Type targetType, object parameter, string language)
            => value;

        public object ConvertBack(object value, Type targetType, object parameter, string language)
            => value;

    }
}

App.xaml中注册转换器:

<Application
    x:Class="XBindTest4.App"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:XBindTest4"
    RequestedTheme="Light">

    <Application.Resources>
        <ResourceDictionary>
            <local:NoOpConverter x:Key="NoOpConverter"/>
        </ResourceDictionary>
    </Application.Resources>

</Application>

MainPage.xaml.cs:

<Page
    x:Class="XBindTest4.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:XBindTest4"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    mc:Ignorable="d" >

    <StackPanel>
        <ComboBox ItemsSource="{x:Bind SampleList, Mode=OneWay}" 
                  SelectedValue="{x:Bind SampleData, Mode=TwoWay, Converter={StaticResource NoOpConverter}}"/>
    </StackPanel>
</Page>