【问题标题】:Silverlight 3 - binding enum to combobox from DomainServiceContextSilverlight 3 - 从 DomainServiceContext 将枚举绑定到组合框
【发布时间】:2010-12-06 19:01:20
【问题描述】:

我刚开始玩 Silverlight,绑定 Combobox 之类的简单事情让我抓狂。我现在阅读了很多文章,但没有一篇文章真正解决了我所追求的或为 Silverlight 2 制作的问题,并且似乎不起作用。

假设我有一个实体对象“用户”,它有一个“用户状态”字段。在数据库中 UserStatus 字段定义为字节,在代码中定义为:

public enum UserStatus : byte
{
    Active = 1,
    Locked = 2,
    Suspended = 3,
}

当 ADO.NET 实体框架创建用户实体时,它将 UserStatus 字段保留为字节。因此,为了解决这个问题,我偶然发现了 IValueConverter 并实现了以下内容:

public class EnumConverter : IValueConverter
{
    #region IValueConverter Members

    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        switch (parameter.ToString())
        {
            case "UserStatus":
                return ((UserStatus)value).ToString();;
        }

        return "?";
    }

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

    #endregion
}

现在,我还需要为 Combobox 提供一个 ItemSource,所以我实现了这个:

internal static class EnumValueCache
{
    private static readonly IDictionary<Type, object[]> Cache = new Dictionary<Type, object[]>();

    public static object[] GetValues(Type type)
    {
        if (!type.IsEnum)
            throw new ArgumentException("Type '" + type.Name + "' is not an enum");

        object[] values;
        if (!Cache.TryGetValue(type, out values))
        {
            values = type.GetFields()
                .Where(f => f.IsLiteral)
                .Select(f => f.GetValue(null))
                .ToArray();
            Cache[type] = values;
        }
        return values;
    }
}

public class EnumValuesConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        if (value == null)
            return null;

        switch (parameter.ToString())
        {
            case "UserStatus":
                return EnumValueCache.GetValues(typeof(UserStatus));
        }

        return null;
    }

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

最后,这就是我将它添加到我的 XAML 的方式:

                            <ComboBox ItemsSource="{Binding UserStatus, Mode=TwoWay, Converter={StaticResource EnumValuesConverter}, ConverterParameter='UserStatus'}" 
                                  SelectedItem="{Binding UserStatus, Mode=TwoWay, Converter={StaticResource EnumConverter}, ConverterParameter='UserStatus'}" />

现在发生的情况是 ItemsSource 已正确绑定,并且我在下拉列表中看到了所有选项,但是 SelectedItem 未设置。 即使我尝试手动将 SelectedItem 设置为 =“1”或“Active”,它们都不起作用。 谁能帮助我并告诉我出了什么问题,为什么我似乎无法设置 SelectedItem?

谢谢,

汤姆

【问题讨论】:

    标签: silverlight data-binding xaml silverlight-3.0 combobox


    【解决方案1】:

    我发现你的代码有两个问题。

    首先,在silverlight 3 中,ComboBox 通过object.Equals 方法将SelectedItem 中的对象与ItemsSource 中的对象集相匹配。但是,您的 GetValues 方法返回一个 Boxed 枚举值数组。而您的 EnumConverter 返回一个字符串。因此,您要求 Silverlight 将字节与字符串进行比较,它们永远不会相等。

    其次,如果您要双向绑定 SelectedItem,则需要在 ConvertBack 方法中放置一些代码(顺便说一句,不需要双向绑定 ItemsSource)。

    【讨论】:

    • 废话,你说的当然是对的,谢谢安东尼。只需调用 f.GetValue(null).ToString() 即可修复它。顺便提一句。 thx 我知道用于 TwoWay 绑定的未实现的 ConvertBack,只是想首先让绑定的第一部分正确:)
    猜你喜欢
    • 2011-08-04
    • 2018-11-12
    • 2020-02-07
    • 1970-01-01
    • 1970-01-01
    • 2016-02-06
    • 1970-01-01
    • 1970-01-01
    • 2015-08-20
    相关资源
    最近更新 更多