Files
MsAddIns/QuickModeling/Markup/EnumSourceExtension.cs
2026-02-28 21:01:57 +08:00

97 lines
3.3 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Reflection;
using System.Windows;
using System.Windows.Controls.Primitives;
using System.Windows.Markup;
namespace QuickModeling.Markup
{
/// <summary>
/// 枚举类作为数据源
/// </summary>
public class EnumSourceExtension : MarkupExtension
{
private Type enumType;
public bool BindToDescription { get; set; } = false;
public Type EnumType
{
get { return enumType; }
set
{
if (value != enumType)
{
if (null != value)
{
var enumType = Nullable.GetUnderlyingType(value) ?? value;
if (!enumType.IsEnum)
{
throw new ArgumentException("类型必须是枚举类型");
}
}
enumType = value;
}
}
}
/// <summary>
/// 在ResouceDictionary中声明
/// </summary>
/// <example><c>local:EnumSourceExtension x:Key="EnumBindingSource" EnumType="{x:Type local:Sex}"</c></example>
public EnumSourceExtension()
{
}
/// <summary>
/// 用Markup语法
/// </summary>
/// <param name="enumType"></param>
/// <remarks>若需要绑定Description则需设置BindToDescription为True同时只能用SelectedValue来绑定源属性</remarks>
/// <example><c>ItemsSource="{Binding Source={local:EnumSource {x:Type local:ExampleEnum}}}"</c></example>
/// <example><c>ItemsSource="{local:EnumSource EnumType=local:ExampleEnum}" SelectedItem="{Binding ExampleEnum}"</c></example>
public EnumSourceExtension(Type enumType) { EnumType = enumType; }
public override object ProvideValue(IServiceProvider serviceProvider)
{
var pvt = (IProvideValueTarget)serviceProvider.GetService(typeof(IProvideValueTarget));
if (pvt == null) { return null; }
//如果为空,则返回运行时绑定的类。
if (pvt.TargetObject is not FrameworkElement) { return this; }
var enumValues = Enum.GetValues(enumType);
if (BindToDescription)
{
var items = new List<object>();
foreach (var enumValue in enumValues)
{
var item = new
{
Value = enumValue,
Description = GetDescription(enumValue)
};
items.Add(item);
}
if (pvt.TargetObject is Selector selector)
{
selector.DisplayMemberPath = "Description";
selector.SelectedValuePath = "Value";
}
return items;
}
return enumValues;
}
private static string GetDescription(object enumValue)
{
var fieldInfo = enumValue.GetType().GetField(enumValue.ToString());
var descriptionAttribute = fieldInfo.GetCustomAttribute<DescriptionAttribute>();
return descriptionAttribute?.Description ?? enumValue.ToString();
}
}
}