1

This is my ViewModel:

public class EntityViewModel
{
    [Required(ErrorMessage = "Title is required")]
    [StringLength(255)]
    [DisplayName("Title")]
    public string Title { get; set; }
    [Required(ErrorMessage = "Description is required")]
    [DisplayName("Description")]
    public string Description { get; set; }
    [Required]
    public DateTime StartTime { get; set; }
    [Required]
    public DateTime EndTime { get; set; }

    [Required]
    public Decimal InstantSellingPrice { get; set; }
    public Nullable<Decimal> ShippingPrice { get; set; }
    public Int64 Views { get; set; }

    public Int32 UserId { get; set; }

    public int RegionId { get; set; }

    public short SelectCategoryId { get; set; }
    public SelectList Categories { get; set; }

    public IEnumerable<HttpPostedFileBase> Files { get; set; }

    public Condition? Condition { get; set; }
}

public enum Condition
{
    New=1,
    Used=2
}

This is my Create Action in my Controller:

public ActionResult Create()
{
    ViewBag.DropDownList = ReUzze.Helpers.EnumHelper.SelectListFor<Condition>();

    var model = new ReUzze.Models.EntityViewModel
    {
        Categories = new SelectList(this.UnitOfWork.CategoryRepository.Get(), "Id", "Name")
    };
    return View(model);
  }

In my Create View:

<div class="form-group">
    @Html.LabelFor(model => model.Condition)
    @Html.DropDownListFor(model => model.Condition, ViewBag.DropDownList as SelectList, null)
</div>   

I am using the Enumhelper that you can find here.

But now I always get this error in my Create View on this rule:

@Html.DropDownListFor(model => model.Condition, ViewBag.DropDownList as SelectList, null)

The error:

Error 1 The call is ambiguous between the following methods or properties: 'System.Web.Mvc.Html.SelectExtensions.DropDownListFor(System.Web.Mvc.HtmlHelper, System.Linq.Expressions.Expression>, System.Collections.Generic.IEnumerable, string)' and 'System.Web.Mvc.Html.SelectExtensions.DropDownListFor(System.Web.Mvc.HtmlHelper, System.Linq.Expressions.Expression>, System.Collections.Generic.IEnumerable, System.Collections.Generic.IDictionary)' c:\Users\Niels\Documents\Visual Studio 2012\Projects\ReUzze\ReUzze\Views\Entity\Create.cshtml 57 30 ReUzze

3 Answers 3

1

I use code like this usually.

public static class Enums {

    public static IList<SelectListItem> SelectListOf<TEnum>(bool empty = false)
    {
        var type = typeof(TEnum);
        if (type.IsEnum)
        {
            var list = Enum.GetValues(type)
                .Cast<TEnum>()
                .OrderBy(x => x)
                .Select(x => new SelectListItem { Text = GetDescription(x), Value = x.ToString() })
                .ToList();

            if (empty)
            {
                list.Insert(0, new SelectListItem());
            }

            return list;

        }

        return new List<SelectListItem>();
    }

    private static string GetDescription(object enumerator)
    {
        try
        {
            //get the enumerator type
            Type type = enumerator.GetType();

            //get the member info
            MemberInfo[] memberInfo = type.GetMember(enumerator.ToString());

            //if there is member information
            if (memberInfo != null && memberInfo.Length > 0)
            {
                //we default to the first member info, as it's for the specific enum value
                object[] attributes = memberInfo[0].GetCustomAttributes(typeof(DescriptionAttribute), false);

                //return the description if it's found
                if (attributes != null && attributes.Length > 0)
                    return ((DescriptionAttribute)attributes[0]).Description;
            }

            //if there's no description, return the string value of the enum
            return enumerator.ToString();
        }
        catch (Exception e)
        {
            return string.Empty;
        }
    }

}

Then you can use it like this:

Conditions = Enums.SelectListOf<Condition>();
Sign up to request clarification or add additional context in comments.

2 Comments

Could you give a little bit more info? Because I don't understand this.. Do I use this in my Model?
Yes you would use it in the constructor of your viewmodel or you could use it directly in your view.
1

Check out my blog post on this very subject.

http://jnye.co/Posts/4/creating-a-dropdown-list-from-an-enum-in-mvc-and-c%23

Here is an enum helper I use that turns an enum into a select list. Note: If the enum has a description (using the DescriptionAttribute) it will use that as its display text

public static class EnumHelper
{
    // Get the value of the description attribute if the   
    // enum has one, otherwise use the value.  
    public static string GetDescription<TEnum>(this TEnum value)
    {
        var fi = value.GetType().GetField(value.ToString());

        if (fi != null)
        {
            var attributes = (DescriptionAttribute[])fi.GetCustomAttributes(typeof(DescriptionAttribute), false);

            if (attributes.Length > 0)
            {
                return attributes[0].Description;
            }
        }

        return value.ToString();
    }

    /// <summary>
    /// Build a select list for an enum
    /// </summary>
    public static SelectList SelectListFor<T>() where T : struct
    {
        Type t = typeof(T);
        return !t.IsEnum ? null
                         : new SelectList(BuildSelectListItems(t), "Value", "Text");
    }

    /// <summary>
    /// Build a select list for an enum with a particular value selected 
    /// </summary>
    public static SelectList SelectListFor<T>(T selected) where T : struct
    {
        Type t = typeof(T);
        return !t.IsEnum ? null
                         : new SelectList(BuildSelectListItems(t), "Value", "Text", selected.ToString());
    }

    private static IEnumerable<SelectListItem> BuildSelectListItems(Type t)
    {
        return Enum.GetValues(t)
                   .Cast<Enum>()
                   .Select(e => new SelectListItem { Value = e.ToString(), Text = e.GetDescription() });
    }
}

Once you have this helper class in place you can do the following.

In your controller:

//If you don't have an enum value use the type
ViewBag.DropDownList = EnumHelper.SelectListFor<MyEnum>();

//If you do have an enum value use the value (the value will be marked as selected)    
ViewBag.DropDownList = EnumHelper.SelectListFor(MyEnum.MyEnumValue);

In your View:

@Html.DropDownList("DropDownList")
@* OR *@
@Html.DropDownListFor(m => m.Property, ViewBag.DropDownList as SelectList, null)

5 Comments

Thanks, how is the Propery defined in the Model?
Yeah, 'Property' is the property of the viewmodel you are creating a drop down list for. It also provides the selected value
Like this: public int ConditionId { get; set; } ?? When I do this I get a huge error
Updated my begin post for more clarity.
remove the last null parameter from the DropDownListFor or replace is with the string of the value you want selected
0

if you want a quick workaround just for this one view you can do something like this. Although Khalid's approach is recommended.

 <select id = 'myenumdropdown' class='something'>

    @foreach(var item in Enum.GetValues(typeof('yourenumtype')))
    {
      <option value=item.ToHashCode()>item.ToString()</option>
    }

 </select>

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.