Пользовательский сервер проверки и сторона клиента для выпадающего списка, заполненного типом перечисления - PullRequest
0 голосов
/ 24 марта 2012

Допустим, у вас есть следующее перечисление:

public enum ColorsEnum
{
    Undefined,
    Blue,
    Red,
    Green
}

И такая модель:

public class Foo
{
    public ColorsEnum PreferedColor { get; set; }
}

С таким видом:

@model WebUI.Models.Foo

@using (Html.BeginForm())
{
    @Html.LabelFor(m => m.PreferedColor)
    @Html.DropDownListForEnum(m => m.PreferedColor)
    <input type="submit">
}

Вот помощник для DropdownListForEnum:

    public static IHtmlString DropDownListForEnum<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper,
                                                                     Expression<Func<TModel, TProperty>> expression)
    {
        var metaData = ModelMetadata.FromLambdaExpression(expression, htmlHelper.ViewData);
        if (metaData.ModelType.IsEnum)
        {
            var names = Enum.GetNames(metaData.ModelType);
            var translatedNames = GetTranslatedNames(metaData.ModelType);

            var query = from p in names
                        select new SelectListItem
                                   {
                                       Text = translatedNames.ContainsKey(p) ? translatedNames[p] : p,
                                       Value = p,
                                       Selected = false
                                   };

            return htmlHelper.DropDownList(metaData.PropertyName, query.ToList());
        }
        else
        {
            throw new ApplicationException(
                "The DropDownListForEnum helper function must be used with an enum property");
        }
    }

Мой вопрос: как вы проводите проверку (на стороне клиента и сервера), чтобы убедиться, что пользователь выбрал правильный цвет? Неопределенный цвет должен быть отклонен процессом проверки.

Спасибо.

Ответы [ 2 ]

0 голосов
/ 25 марта 2012

Я бы использовал перечислимое значение NULL и атрибут Required в модели представления:

public class MyViewModel
{
    [Required]
    public ColorsEnum? PreferedColor { get; set; }
}

Таким образом, вы можете удалить значение Undefined из определения перечисления:

public enum ColorsEnum
{
    Blue,
    Red,
    Green
}

, а затем немного измените ваш помощник:

public static class HtmlExtensions
{
    public static IHtmlString DropDownListForEnum<TModel, TProperty>(
        this HtmlHelper<TModel> htmlHelper,
        Expression<Func<TModel, TProperty>> expression
    )
    {
        var metaData = ModelMetadata.FromLambdaExpression(expression, htmlHelper.ViewData);
        var enumType = Nullable.GetUnderlyingType(metaData.ModelType);
        if (enumType == null || !enumType.IsEnum)
        {
            throw new ApplicationException(
                "The DropDownListForEnum helper function must be used with a nullable enum property"
            );
        }

        var names = Enum.GetNames(enumType);
        var translatedNames = GetTranslatedNames(metaData.ModelType);

        var query = 
            from p in names
            select new SelectListItem
            {
                Text = translatedNames.ContainsKey(p) ? translatedNames[p] : p,
                Value = p,
                Selected = false
            };
        return htmlHelper.DropDownList(
            metaData.PropertyName, 
            query.ToList(), 
            "-- Select a color --"
        );
    }
}

, а затем просто протестируйте контроллер:

public class HomeController : Controller
{
    public ActionResult Index()
    {
        return View(new MyViewModel());
    }

    [HttpPost]
    public ActionResult Index(MyViewModel model)
    {
        return View(model);
    }
}

и соответствующий вид:

@model MyViewModel

<script src="@Url.Content("~/Scripts/jquery.validate.js")" type="text/javascript"></script>
<script src="@Url.Content("~/Scripts/jquery.validate.unobtrusive.js")" type="text/javascript"></script>

@using (Html.BeginForm())
{
    @Html.LabelFor(m => m.PreferedColor)
    @Html.DropDownListForEnum(m => m.PreferedColor)
    <input type="submit" />
}
0 голосов
/ 24 марта 2012

Если первое значение каждого перечисления, которое вы планируете использовать с DropDownListForEnum, всегда является параметром «по умолчанию», который должен быть отклонен валидатором, вы можете рассмотреть возможность использования параметра optionLabel DropDownList.

Извлеките первый элемент из query и передайте эту строку в качестве третьего параметра в DropDownList.

return htmlHelper.DropDownList(metaData.PropertyName, query.ToList(),
    /* some string containing default value extracted from your enum */);

Таким образом, все DDL, созданные с использованием DropDownListForEnum, будут использовать первое значение перечисления в качестве значения «по умолчанию», и все, что вам нужно будет сделать для проверки, это добавить аннотацию данных [Required] к PreferredColor .

Кроме того, вы можете удалить опцию Default из вашего перечисления и позволить вашему HtmlHelper (или создать новый) принять третий параметр, строку, содержащую optionLabel, которую вы передадите в DropDownList.

В любом случае, идея состоит в том, чтобы использовать optionLabel, поскольку валидатор сделает всю работу за вас.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...