Click here to Skip to main content
65,938 articles
CodeProject is changing. Read more.
Articles
(untagged)

Dealing with Enum in MVC 5.1

0.00/5 (No votes)
23 May 2014 1  
Learn how to deal with enum dropdown list in Asp.Net MVC 5.1

Introduction

Enum

If you are reading this post, I bet you at least once went in #stackoverflow with the hope to find out a solution of the problem that you were stuck with. Other day, while I was surfing #stackoverflow, I have noticed that a good number of developers often faced difficulty while dealing with enum in Asp.Net MVC, their fair amount of code is just not enough to make their enum turn into dropdown list. And this problem was there for years. Obviously, genius developers did not seat idle. They figure out different approaches to deal with this issue and most often these approaches is not fairly simple to follow.

With the release of MVC 5.1 in Feb 27, 2014 there finally came enum support it View. The old school approach still applicable and useable and plenty of such resources could be found on the web but it is not recommended as the new way is much simpler. I am not going to discuss the old way rather I will focus the new way of achieving our purpose.

Software Requirements

You will be in need of any of the following -

  • Visual Studio 2012: Download ASP.NET and Web Tools 2013.1 for Visual Studio 2012.
  • Visual Studio 2013: Download Visual Studio 2013 Update 1. This update is needed for editing ASP.NET MVC 5.1 Razor Views.

Now, you have the tools, lets get started by creating an Asp.Net Web Application. To demonstrate the enum support we will build a simple student registration form where we expect that a dropdown box will show the Gender, Country from where people can select their desired information. Initially, for the demonstration purpose I have created the following architecture. You can download the entire source file from here.

EnumDemo_Project Hierarchy
Gender enum is fairly simple, it consists with Male and Female and it is defined as
public enum Gender
{
     Male,
     Female
}

5 countries are added in the enum list. The Country enum is defined as

    public enum Country
    {
        Australia,
        Bangladesh,
        England,
        France,
        Usa
    }

The student entity [POCO (Plain Old C# object) class] looks like this

    public class Student
    {
        public int Id { get; set; }
        public String Name { get; set; }
        public Gender Gender { get; set; }
        public Country Country { get; set; }
    }

Right now, If we just rely on scaffolding to do the hard work for you and generate some view then you will end up like this

If you never deal with enum before this view probably freaks you out, you probably found yourself saying -

" hey wait a minute, scaffolding is not working! its not rendering the view properly "

Right now you probably want to inspect the scaffolding generated code for the view and here it is-

    <div class="form-group">
            @Html.LabelFor(model => model.Gender, new { @class = "control-label col-md-2" })
            <div class="col-md-10">
                @Html.EditorFor(model => model.Gender)
                @Html.ValidationMessageFor(model => model.Gender)
            </div>
        

        <div class="form-group">
            @Html.LabelFor(model => model.Country, new { @class = "control-label col-md-2" })
            <div class="col-md-10">
                @Html.EditorFor(model => model.Country)
                @Html.ValidationMessageFor(model => model.Country)
            </div>
        </div>

And everything seems fairly fine. right? There you have the editor extension EditorFor() on the right position and data was also passed properly. Then whats wrong? Well, actually EditorFor() does not know how to render an Enum, so it uses its default settings and render a textbox for the enum.

Don't freak out! We will deal with this issue within a minute. But first update Microsoft ASP.NET MVC from NuGet. Do it otherwise you would not find the extension method that we are going to use to solve our problem.

Managing NuGet Packages Managing NuGet Packages[/caption] Once you are done change the markup as follows -
     @*@Html.EditorFor(model => model.Gender)*@

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

Here, we are using the new EnumDropDownListFor() extension method. Implementation is same as EditorFor() extension. HURRAH! just one line of code saves our live.

EnumDemo_4

Now, lets extend the scenario bit. What if we want to show special character/symbol spaces in the enumdropdowlist. We know Enum does not support spaces/special characters so what we can do is to use Display Attribute. Here in the following scenario we are using [Display(Name="United States")] to show "United States" instead of showing "Usa".

   public enum Country
    {
        Australia,
        Bangladesh,
        England,
        France,
        [Display(Name="United States")]
        Usa
    }
and here is the view. You can see its showing "United States" in the EnumDropDownList.

EnumDemo_5

Note: At this point if you just create a new student selecting the values from EnumDropDownList , when you revisit to see what you have just saved you will find that instead of displaying "United States" , its showing "Usa" in the list. If you don't get my point yet have a look on the following image.

And that something what we probably don't want to display. To deal with we can use some kind of templating mechanism.

We are going to provide the enum template, and its important that we put it in the right folder since we want all Enums to use this by default. Here is the locaition /Shared/DisplayTemplates where we are going to create the partial view for display scenario and make sure to name it as enum.cshtml . File hierarchy is shown in the following image -

EnumDemo_8

Inside Enum.cshtml copy the following code there and you are done !

@model Enum

@if (EnumHelper.IsValidForEnumHelper(ViewData.ModelMetadata))
{
    // Display Enum using same names (from [Display] attributes) as in editors
    string displayName = null;
    foreach (SelectListItem item in EnumHelper.GetSelectList(ViewData.ModelMetadata, (Enum)Model))
    {
        if (item.Selected)
        {
            displayName = item.Text ?? item.Value;
        }
    }

    // Handle the unexpected case that nothing is selected
    if (String.IsNullOrEmpty(displayName))
    {
        if (Model == null)
        {
            displayName = String.Empty;
        }
        else
        {
            displayName = Model.ToString();
        }
    }

    @Html.DisplayTextFor(model => displayName)
}
else
{
    // This Enum type is not supported.  Fall back to the text.
    @Html.DisplayTextFor(model => model)
}

Run the application once again and you will find your long desired solution on the screen :)

If you can remember, we made some changes in the code that was generated by scaffholding. If you are dealing with a large application where almost each view deals with Enum values then probably it would be hard and time consuming to make changes on several places and such scenario I prefer to write down a EditorTemplates so that the scaffholding generated code can run smoothly without any kind of modification.

Here is the locaition /Shared/EditorTemplates where we are going to create the partial view for display scenario and make sure to name it as enum.cshtml . File hierarchy is shown in the following image -

EnumDemo_9

Inside Enum.cshtml copy the following code and you are good to go with the scaffholding generated code.

@model Enum

@if (EnumHelper.IsValidForEnumHelper(ViewData.ModelMetadata))
{
    @Html.EnumDropDownListFor(model => model, htmlAttributes: new { @class = "form-control" })
}
else
{
    @Html.TextBoxFor(model => model, htmlAttributes: new { @class = "form-control" })
}

Thats really everything that you should know to deal with Enum in MVC5. Hope you find this post helpful :) .

Additional Resource:


License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here