How to get the values of an enum into a SelectList
假设我有一个这样的枚举(举个例子):
1 2 3 4 5 | public enum Direction{ Horizontal = 0, Vertical = 1, Diagonal = 2 } |
如果枚举的内容将来可能发生更改,我如何编写一个将这些值放入System.Web.MVC.SelectList的例程?我想获取每个枚举名称作为选项文本,其值作为值文本,如下所示:
1 2 3 4 5 | <select> <option value="0">Horizontal</option> <option value="1">Vertical</option> <option value="2">Diagonal</option> </select> |
这是迄今为止我能想到的最好的方法:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | public static SelectList GetDirectionSelectList() { Array values = Enum.GetValues(typeof(Direction)); List<ListItem> items = new List<ListItem>(values.Length); foreach (var i in values) { items.Add(new ListItem { Text = Enum.GetName(typeof(Direction), i), Value = i.ToString() }); } return new SelectList(items); } |
但是,这始终将选项文本呈现为"system.web.mvc.listem"。通过这个调试,我还可以看到Enum.GetValues()返回的是"水平、垂直"等,而不是如我所料的0、1,这让我想知道Enum.GetName()和Enum.GetValue()之间的区别是什么。
我已经有一段时间没有这样做了,但我认为这应该有效。
1 2 3 |
在ASP.NET MVC 5.1中有一个新功能。
http://www.asp.net/mvc/overview/releases/mvc51发行说明枚举
1 | @Html.EnumDropDownListFor(model => model.Direction) |
这就是我刚刚做的,我个人认为它很性感:
1 2 3 4 5 |
我最终要做一些翻译工作,这样值=enu.toString()将在某个地方执行对某个内容的调用。
要获取枚举的值,需要将枚举强制转换为其基础类型:
1 | Value = ((int)i).ToString(); |
我想做一些与Dann的解决方案非常相似的事情,但我需要值是int,文本是枚举的字符串表示。这就是我想到的:
1 2 3 4 |
在ASP.NET核心MVC中,这是通过标记助手完成的。
1 | <select asp-items="Html.GetEnumSelectList<Direction>()"></select> |
1 2 3 4 5 6 7 8 9 |
或:
1 2 3 4 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | public static SelectList ToSelectList<TEnum>(this TEnum enumObj) where TEnum : struct { if (!typeof(TEnum).IsEnum) throw new ArgumentException("An Enumeration type is required.","enumObj"); var values = from TEnum e in Enum.GetValues(typeof(TEnum)) select new { ID = (int)Enum.Parse(typeof(TEnum), e.ToString()), Name = e.ToString() }; //var values = from TEnum e in Enum.GetValues(typeof(TEnum)) select new { ID = e, Name = e.ToString() }; return new SelectList(values,"ID","Name", enumObj); } public static SelectList ToSelectList<TEnum>(this TEnum enumObj, string selectedValue) where TEnum : struct { if (!typeof(TEnum).IsEnum) throw new ArgumentException("An Enumeration type is required.","enumObj"); var values = from TEnum e in Enum.GetValues(typeof(TEnum)) select new { ID = (int)Enum.Parse(typeof(TEnum), e.ToString()), Name = e.ToString() }; //var values = from TEnum e in Enum.GetValues(typeof(TEnum)) select new { ID = e, Name = e.ToString() }; if (string.IsNullOrWhiteSpace(selectedValue)) { return new SelectList(values,"ID","Name", enumObj); } else { return new SelectList(values,"ID","Name", selectedValue); } } |
可能不是问题的确切答案,但在CRUD场景中,我通常实现如下功能:
1 2 3 4 5 6 7 8 9 10 |
在视图("创建")和视图("编辑")之前调用
1 | <%= Html.DropDownList("Fetcher") %> |
就这些……
由于各种原因,我有更多的类和方法:
枚举到项集合
1 2 3 4 5 6 7 8 9 10 11 12 |
在控制器中创建selectlist
1 2 | int selectedValue = 1; // resolved from anywhere ViewBag.Currency = new SelectList(EnumHelper.EnumToCollection<Currency>(),"Key","Value", selectedValue); |
MyVIEW.CSHML
1 |
我有很多枚举选择列表,经过大量的搜索和筛选,我发现让一个通用的助手对我来说最有用。它将索引或描述符返回为selectlist值,将描述返回为selectlist文本:
枚举:
1 2 3 4 5 6 7 | public enum Your_Enum { [Description("Description 1")] item_one, [Description("Description 2")] item_two } |
帮手:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | public static class Selectlists { public static SelectList EnumSelectlist<TEnum>(bool indexed = false) where TEnum : struct { return new SelectList(Enum.GetValues(typeof(TEnum)).Cast<TEnum>().Select(item => new SelectListItem { Text = GetEnumDescription(item as Enum), Value = indexed ? Convert.ToInt32(item).ToString() : item.ToString() }).ToList(),"Value","Text"); } // NOTE: returns Descriptor if there is no Description private static string GetEnumDescription(Enum value) { FieldInfo fi = value.GetType().GetField(value.ToString()); DescriptionAttribute[] attributes = (DescriptionAttribute[])fi.GetCustomAttributes(typeof(DescriptionAttribute), false); if (attributes != null && attributes.Length > 0) return attributes[0].Description; else return value.ToString(); } } |
用途:将索引的参数设置为"true"作为值:
16