枚举绑定到 ComboBox






4.90/5 (16投票s)
这个技巧提供了一种将枚举值绑定到 ComboBox 的简单方法,可以在不同的应用程序中重用。
引言
任何实际应用都希望将枚举值绑定到 ComboBox
。 因此,拥有一个执行此逻辑的通用代码始终更好。
Using the Code
我有一个辅助类,它公开了一个属性来获取枚举类型,以便我可以解析枚举值。
public static Type GetEnum(DependencyObject obj)
{
return (Type)obj.GetValue(EnumProperty);
}
public static void SetEnum(DependencyObject obj, string value)
{
obj.SetValue(EnumProperty, value);
}
// Using a DependencyProperty as the backing store for Enum.
// This enables animation, styling, binding, etc...
public static readonly DependencyProperty EnumProperty =
DependencyProperty.RegisterAttached("Enum", typeof(Type),
typeof(EnumHelper), new PropertyMetadata(null, OnEnumChanged));
获取枚举的值并将其设置为 ComboBox ItemsSource
。
private static void OnEnumChanged(DependencyObject sender,
DependencyPropertyChangedEventArgs e)
{
var control = sender as ItemsControl;
if (control != null)
{
if (e.NewValue != null)
{
var _enum = Enum.GetValues(e.NewValue as Type);
control.ItemsSource = _enum;
}
}
}
现在,如果我们在 XAML 中设置枚举值,ComboBox
将绑定到枚举值。
public enum Designation
{
SoftwareEngineer,
TeamLead,
ProductManager
}
<ComboBox x:Name="Designation" Margin="5" Grid.Row="5"
SelectedItem="{Binding Designation, Mode=TwoWay}"
local:EnumHelper.Enum="{x:Type local:Designation}">
</ComboBox>
查看项目名称。 它们间隔不好。 应该显示为“产品经理”,而不是“ProductManager”。 为此,我们将使用枚举值的 Display
属性。 此外,我们还可以使用 Description
属性让用户看到更多详细信息。
我修改了我的枚举,使其如下所示
public enum Designation
{
[Display(Name="Software Engineer")]
[Description("Software engineer responsible for core development.")]
SoftwareEngineer,
[Display(Name = "Team Lead")]
[Description("Team lead responsible for leading a small team of 5 to 10 members.")]
TeamLead,
[Display(Name = "Product Manager")]
[Description("Product manager responsible for core management.")]
ProductManager
}
我们的辅助类还应该公开另一个属性来获取属性值并在需要时进行设置。 例如,在这种情况下,我将显示描述作为工具提示,并将其显示为文本。
public static bool GetMoreDetails(DependencyObject obj)
{
return (bool)obj.GetValue(MoreDetailsProperty);
}
public static void SetMoreDetails(DependencyObject obj, bool value)
{
obj.SetValue(MoreDetailsProperty, value);
}
// Using a DependencyProperty as the backing store for MoreDetails.
// This enables animation, styling, binding, etc...
public static readonly DependencyProperty MoreDetailsProperty =
DependencyProperty.RegisterAttached("MoreDetails",
typeof(bool), typeof(EnumHelper), new PropertyMetadata(false, OnMoreDetailsChanged));
我们获取属性值并将其设置在适当的位置。 我们希望用户在任何 DataTemplate
中设置此属性,以便我们可以将基础枚举对象作为 DataContext
获取。
var array = fieldInfo.GetCustomAttributes(false);
if (array.Length == 0)
{
if (control is TextBlock)
{
((TextBlock)control).Text = enumobject.ToString();
}
else if (control is ContentControl)
{
((ContentControl)control).Content = enumobject;
}
return;
}
foreach (var o in array)
{
if (o is DescriptionAttribute)
{
control.ToolTip = ((DescriptionAttribute) o).Description;
}
else if (o is DisplayAttribute)
{
if (control is TextBlock)
{
((TextBlock) control).Text = ((DisplayAttribute) o).Name;
}
else if (control is ContentControl)
{
((ContentControl)control).Content = ((DisplayAttribute)o).Name;
}
}
}
让我们向 ComboBox
添加一个 DataTemplate
<DataTemplate>
<TextBlock local:EnumHelper.MoreDetails="True"/>
</DataTemplate>