Multibinding不在TextBox.Text上工作

时间:2012-05-08 16:00:42

标签: wpf xaml multibinding

我有一个不能在TextBox.Text上运行的MultiBinding。我有相同的代码正确绑定到Extended WPF Toolkit的IntegerUpDown的值。

它通过一个IMultiValueConverter获取绑定的POCO和它所属的列表框(它显示列表框中项目的顺序)

以下是代码:

<!--works-->
<wpf:IntegerUpDown ValueChanged="orderChanged" x:Name="tripOrder">
    <wpf:IntegerUpDown.Value>
        <MultiBinding Converter="{StaticResource listBoxIndexConverter}" Mode="OneWay">
            <Binding />
            <Binding ElementName="listTrips" />
        </MultiBinding>
    </wpf:IntegerUpDown.Value>
</wpf:IntegerUpDown>
<!--doesn't work-->
<TextBox x:Name="tripOrder2">
    <TextBox.Text>
        <MultiBinding Converter="{StaticResource listBoxIndexConverter}" Mode="OneWay">
            <Binding />
            <Binding ElementName="listTrips" />
        </MultiBinding>
    </TextBox.Text>
</TextBox>

结果如下:

result

我不相信它是相关的,但以防万一,这是执行转换的类:

    public class ListBoxIndexConverter : IMultiValueConverter
    {

    #region IMultiValueConverter Members

    public object Convert(object[] values, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        var trip = values[0] as TripBase;

        if (trip == null)
        {
            return null;
        }

        var lb = values[1] as CheckListBox;
        if (lb == null)
        {
            return null;
        }

        //make it 1 based
        return lb.Items.IndexOf(trip) + 1;
    }

    public object[] ConvertBack(object value, Type[] targetTypes, object parameter, System.Globalization.CultureInfo culture)
    {
        throw new NotImplementedException();
    }

    #endregion
}

2 个答案:

答案 0 :(得分:2)

转换器应返回属性所需的类型。原因是在常规使用属性(即没有Binding)时,属性可能具有从一种类型(或更多)转换为属性所需类型的类型转换器。例如,当你写:

<ColumnDefinition Width="Auto"/>

有一个将字符串“Auto”转换为:

的转换器
new GridLength(1, GridUnitType.Auto)

使用绑定时,绕过此机制,因为转换器应返回正确的类型。

所以,要解决您的问题,请在转换器返回时:

return (lb.Items.IndexOf(trip) + 1).ToString();

这应修复TextBox

现在,对于IntegerUpDown。听起来它实际上期望收到int并返回一个字符串会破坏它。所以,再次改变转换器的返回值:

if (targetType == typeof(int))
{
    return lb.Items.IndexOf(trip) + 1;
}
else if (targetType == typeof(string))
{
    return (lb.Items.IndexOf(trip) + 1).ToString();
}
else
{
    throw new NotImplementedException(String.Format("Can not convert to type {0}", targetType.ToString()));
}

答案 1 :(得分:0)

绑定不起作用,因为当列表框的选定值更改时listTrips不会更改。更改的内容是listTrips.SelectedItem,因此您应该绑定它:

<Binding Path="SelectedItem" ElementName="listTrips"/>

实际上,我想知道为什么它适用于第一个例子。