using System; using System.Collections; using System.Collections.Generic; using System.Linq; using System.Reflection; namespace BS.Shared.Core { public static class DisplayEnum { public static readonly DisplayEnum Auszahlungsintervall = new DisplayEnum(); public static readonly DisplayEnum Zahlungstyp = new DisplayEnum(); public static IDisplayEnum GetDisplayEnum(Type type) { var fields = typeof(DisplayEnum).GetFields(BindingFlags.Public | BindingFlags.Static); if (type.IsGenericType && !type.IsGenericTypeDefinition) { // handle Nullable<> var genericTypeDef = type.GetGenericTypeDefinition(); if (genericTypeDef == typeof(Nullable<>)) { type = type.GetGenericArguments()[0]; } } foreach (var field in fields) { if (field.FieldType == type) { return (IDisplayEnum)field.GetValue(null); } IList genericArguments = field.FieldType.GetGenericArguments(); if (genericArguments.Contains(type)) { return (IDisplayEnum)field.GetValue(null); } } return null; } } public interface IDisplayEnum { IList Values { get; } IList SortedValues { get; } IEnumValue this[object enumObj] { get; } } public class DisplayEnum : IDisplayEnum where T : struct, IComparable, IFormattable, IConvertible { private readonly object lockObj = new object(); private readonly ISet excludedValues; private IList> enumValues; public DisplayEnum(params T[] excludedValues) { this.excludedValues = new HashSet(excludedValues); } public IEnumerable> Values { get { if (enumValues == null) { Initialize(); } return enumValues; } } public IEnumerable> SortedValues { get { if (enumValues == null) { Initialize(); } var sortedValues = new List>(enumValues); sortedValues.Sort(); return sortedValues; } } public IList> ExcludedValues { get; private set; } private void Initialize() { lock (lockObj) { if (enumValues == null) { enumValues = new List>(); ExcludedValues = new List>(); foreach (T enumValue in Enum.GetValues(typeof(T))) { var value = CreateEnumValue(enumValue); if (!excludedValues.Contains(enumValue)) { enumValues.Add(value); } else { ExcludedValues.Add(value); } } } } } protected virtual EnumValue CreateEnumValue(T enumValue) { var value = new EnumValue(enumValue, EnumTranslations.AllTranslations[(Enum)(object)enumValue]); return value; } public EnumValue this[T enumObj] { get { var result = Values.FirstOrDefault(value => value.Enum.Equals(enumObj)); return result ?? ExcludedValues.FirstOrDefault(value => value.Enum.Equals(enumObj)); } } public EnumValue this[T? enumObj] => enumObj != null ? this[enumObj.Value] : null; #region IDisplayEnum Implementation IList IDisplayEnum.Values => Values.Cast().ToList(); IList IDisplayEnum.SortedValues => SortedValues.Cast().ToList(); IEnumValue IDisplayEnum.this[object enumObj] { get { if (enumObj is T obj) { return this[obj]; } return null; } } #endregion } }