catching Description with Enumdropdownlistfor Asp.net mvc5

Asked

Viewed 1,099 times

4

How I get Description using the html helper Enumdropdownlistfor from Asp.net MVC 5 ?

I have my enumerator

public num Dias {
      [Description("Segunda dia de trabalho")]
      Segunda = 1,
      [Description("Terçadia de trabalho")]
      Terca = 2
}

When I use the html helper from Asp.net mvc5

 @Html.EnumDropDownListFor(x => x.Dias);

It returns the values : "Second, Third", I would like to return the values of Description in my select

  • Don’t get it!? can you give an example?

  • I updated Maria, I think it’s better now

  • Now it’s @Rod

3 answers

8

An alternative I found is to use Annotation

[Display(Name = "Valor")]

In it the Html Helper itself recognizes the values, not having to do anything more than that

  • 1

    Excellent solution... :)

  • That response should have been marked as a solution.

  • Thank you for sharing, excellent solution, simple and practical.

3


I rewrote the extensive Static method.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Web;
namespace System.Web.Mvc
{
    public static class MethodsExtensivos
    {
        public static System.Web.Mvc.MvcHtmlString EnumDropDownListDescriptionFor<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TProperty>> expression, string label = null, object htmlAttributes = null)            
        {
            TModel model = htmlHelper.ViewData.Model;
            TProperty property = default(TProperty);
            if (model != null)
            {
                Func<TModel, TProperty> func = expression.Compile();
                property = func(model);
            }
            TagBuilder select = new TagBuilder("select");            
            if (htmlAttributes != null)
            {
                System.Reflection.PropertyInfo[] properties = htmlAttributes.GetType().GetProperties();
                foreach (System.Reflection.PropertyInfo prop in properties)
                {
                    select.MergeAttribute(prop.Name, (String)prop.GetValue(htmlAttributes, null));
                }
            }            
            Type type = typeof(TProperty);            
            String[] Names = type.GetEnumNames();
            if (label != null)
            {
                TagBuilder option = new TagBuilder("option");
                option.MergeAttribute("value", "0");
                option.InnerHtml = label;
                select.InnerHtml += option.ToString();
            }            
            foreach(string Name in Names) {
                System.Reflection.MemberInfo info = type.GetMember(Name).FirstOrDefault();
                TagBuilder option = new TagBuilder("option");
                if (property != null && property.ToString().Equals(Name))
                {
                    option.MergeAttribute("selected", "selected");
                }
                option.MergeAttribute("value", ((int)Enum.Parse(typeof(TProperty), Name)).ToString());
                var texto = info.CustomAttributes
                        .Select(x => x.ConstructorArguments.Select(a => a.Value))
                        .FirstOrDefault();
                if (texto != null)
                {
                    option.SetInnerText(texto.FirstOrDefault().ToString());
                }
                else
                {
                    option.SetInnerText(Name);
                }
                select.InnerHtml += option.ToString();
            }
            if (!select.Attributes.Where(x => x.Key.ToLower().Equals("id")).Any())
            {
                select.MergeAttribute("id", type.Name);

            }
            if (!select.Attributes.Where(x => x.Key.ToLower().Equals("name")).Any())
            {
                select.MergeAttribute("name", type.Name);
            }
            return MvcHtmlString.Create(select.ToString());
        }            
    }
}

Programming this code:

@Html.EnumDropDownListDescriptionFor(a => a.Dias)
@Html.EnumDropDownListDescriptionFor(a => a.Dias, "Escolha do Dia da Semana")
@Html.EnumDropDownListDescriptionFor(a => a.Dias, "Escolha do Dia da Semana", new { id="select1", name="select1", css="style1" })

Upshot:

inserir a descrição da imagem aqui

<select id="Dias" name="Dias">
  <option value="10">Segunda dia de trabalho</option>
  <option selected="selected" value="20">Ter&#231;a dia de trabalho</option>
</select>
<select id="Dias" name="Dias">
  <option value="0">Escolha do Dia da Semana</option>
  <option value="10">Segunda dia de trabalho</option>
  <option selected="selected" value="20">Ter&#231;a dia de trabalho</option>
</select>
<select css="style1" id="select1" name="select1">
  <option value="0">Escolha do Dia da Semana</option>
  <option value="10">Segunda dia de trabalho</option>
  <option selected="selected" value="20">Ter&#231;a dia de trabalho</option>
</select>
  • Good solution. I suggest removing the chunk that assigns value to the label, because usually enums are zero-index, and a value="0" would be the first option. Remove this line: option.Mergeattribute("value", "0");

1

I use this Xtension method:

public static string GetEnumDescription(this 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();
}

That allows you to recover the values to then popular the dropdown this way:

var listaParaDropDown = from EMeuEnum in Enum.GetValues(typeof(EMeuEnum ))
                        select new { Id = e, Nome = e.GetEnumDescription() };

Fill in the dropdown from that list.

Browser other questions tagged

You are not signed in. Login or sign up in order to post.