如何将枚举的值放入选择列表

假设我有一个这样的枚举(仅作为一个示例) :

public enum Direction{
Horizontal = 0,
Vertical = 1,
Diagonal = 2
}

如何编写一个例程将这些值输入到系统中。韦伯。MVC.考虑到枚举的内容将来可能会发生变化,选择列表?我希望将每个枚举名称作为选项文本,将其值作为值文本,如下所示:

<select>
<option value="0">Horizontal</option>
<option value="1">Vertical</option>
<option value="2">Diagonal</option>
</select>

这是我目前能想到的最好的办法:

 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”。韦伯。MVC.ListItem’。通过此调试还可以看到 Enum。GetValue ()返回“水平,垂直”等,而不是我所期望的0,1,这让我想知道 Enum 之间的区别是什么。GetName ()和 Enum。GetValue ().

97992 次浏览

To get the value of an enum you need to cast the enum to its underlying type:

Value = ((int)i).ToString();

It's been awhile since I've had to do this, but I think this should work.

var directions = from Direction d in Enum.GetValues(typeof(Direction))
select new { ID = (int)d, Name = d.ToString() };
return new SelectList(directions , "ID", "Name", someSelectedValue);

maybe not an exact answer to the question, but in CRUD scenarios i usually implements something like this:

private void PopulateViewdata4Selectlists(ImportJob job)
{
ViewData["Fetcher"] = from ImportFetcher d in Enum.GetValues(typeof(ImportFetcher))
select new SelectListItem
{
Value = ((int)d).ToString(),
Text = d.ToString(),
Selected = job.Fetcher == d
};
}

PopulateViewdata4Selectlists is called before View("Create") and View("Edit"), then and in the View:

<%= Html.DropDownList("Fetcher") %>

and that's all..

This is what I have just made and personally I think its sexy:

 public static IEnumerable<SelectListItem> GetEnumSelectList<T>()
{
return (Enum.GetValues(typeof(T)).Cast<T>().Select(
enu => new SelectListItem() { Text = enu.ToString(), Value = enu.ToString() })).ToList();
}

I am going to do some translation stuff eventually so the Value = enu.ToString() will do a call out to something somewhere.

Or:

foreach (string item in Enum.GetNames(typeof(MyEnum)))
{
myDropDownList.Items.Add(new ListItem(item, ((int)((MyEnum)Enum.Parse(typeof(MyEnum), item))).ToString()));
}

I wanted to do something very similar to Dann's solution, but I needed the Value to be an int and the text to be the string representation of the Enum. This is what I came up with:

public static IEnumerable<SelectListItem> GetEnumSelectList<T>()
{
return (Enum.GetValues(typeof(T)).Cast<int>().Select(e => new SelectListItem() { Text = Enum.GetName(typeof(T), e), Value = e.ToString() })).ToList();
}
    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);
}
}
return
Enum
.GetNames(typeof(ReceptionNumberType))
.Where(i => (ReceptionNumberType)(Enum.Parse(typeof(ReceptionNumberType), i.ToString())) < ReceptionNumberType.MCI)
.Select(i => new
{
description = i,
value = (Enum.Parse(typeof(ReceptionNumberType), i.ToString()))
});

There is a new feature in ASP.NET MVC 5.1 for this.

http://www.asp.net/mvc/overview/releases/mvc51-release-notes#Enum

@Html.EnumDropDownListFor(model => model.Direction)

I have more classes and methods for various reasons:

Enum to collection of items

public static class EnumHelper
{
public static List<ItemDto> EnumToCollection<T>()
{
return (Enum.GetValues(typeof(T)).Cast<int>().Select(
e => new ItemViewModel
{
IntKey = e,
Value = Enum.GetName(typeof(T), e)
})).ToList();
}
}

Creating selectlist in Controller

int selectedValue = 1; // resolved from anywhere
ViewBag.Currency = new SelectList(EnumHelper.EnumToCollection<Currency>(), "Key", "Value", selectedValue);

MyView.cshtml

@Html.DropDownListFor(x => x.Currency, null, htmlAttributes: new { @class = "form-control" })

In ASP.NET Core MVC this is done with tag helpers.

<select asp-items="Html.GetEnumSelectList<Direction>()"></select>

I had many enum Selectlists and, after much hunting and sifting, found that making a generic helper worked best for me. It returns the index or descriptor as the Selectlist value, and the Description as the Selectlist text:

Enum:

public enum Your_Enum
{
[Description("Description 1")]
item_one,
[Description("Description 2")]
item_two
}

Helper:

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();
}
}

Usage: Set parameter to 'true' for indices as value:

var descriptorsAsValue = Selectlists.EnumSelectlist<Your_Enum>();
var indicesAsValue = Selectlists.EnumSelectlist<Your_Enum>(true);