ASP.Net MVC 3不显眼的客户端validation不适用于下拉列表

我有一个简单的下拉列表,列表中的第一项有一个空值。 如果我没有在列表中选择任何内容,则客户端validation会忽略它。 我使用注释属性在模型上根据需要设置了该字段。

@Html.DropDownListFor(model => Model.CCPayment.State, UnitedStatesStates.StateSelectList) [Required(ErrorMessage = "State is Required.")] public string State { get { return _state; } set { _state = value; } } 

有任何想法吗? 我错过了什么吗?

它看起来像一个合法的错误,这是我在搜索中找到的最佳解决方法:

http://forums.asp.net/t/1649193.aspx

简而言之。 您将问题的来源DropDownListFor包装在自定义Html扩展中,并手动检索不显眼的客户端validation规则,如下所示:

 IDictionary validationAttributes = htmlHelper. GetUnobtrusiveValidationAttributes( ExpressionHelper.GetExpressionText(expression), metadata ); 

然后将validationAttributes字典与传递到自定义助手中的任何其他html属性组合,然后将其传递给DropDownListFor

我正在使用的完整代码(我也有一个标签,你可以随意分离):

 public static IHtmlString DropDownListWithLabelFor(this HtmlHelper helper, Expression> expression, string label, IEnumerable items, string blankOption, object htmlAttributes = null) { var l = new TagBuilder("label"); var br = new TagBuilder("br"); var metadata = ModelMetadata.FromLambdaExpression(expression, helper.ViewData); var mergedAttributes = helper.GetUnobtrusiveValidationAttributes(ExpressionHelper.GetExpressionText(expression), metadata); if (htmlAttributes != null) { foreach (PropertyDescriptor descriptor in TypeDescriptor.GetProperties(htmlAttributes)) { object value = descriptor.GetValue(htmlAttributes); mergedAttributes.Add(descriptor.Name, value); } } l.InnerHtml = label + br.ToString(TagRenderMode.SelfClosing) + helper.DropDownListFor(expression, items, blankOption, mergedAttributes); return MvcHtmlString.Create(l.ToString(TagRenderMode.Normal)); } 

您提供的信息太少,以便我们能够查明问题。 您可能忘记在视图中包含适当的不显眼的validation脚本但是谁知道? 您尚未显示您的观点。

这是一个完整的工作示例:

模型:

 public class MyViewModel { [Required(ErrorMessage = "State is Required.")] public string State { get; set; } public IEnumerable States { get { return Enumerable.Range(1, 5).Select(x => new SelectListItem { Value = x.ToString(), Text = "state " + x }); } } } 

控制器:

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

视图:

 @model AppName.Models.MyViewModel @{ ViewBag.Title = "Home Page"; }   @using (Html.BeginForm()) { @Html.LabelFor(x => x.State) @Html.DropDownListFor( x => x.State, new SelectList(Model.States, "Value", "Text"), "-- Please select a state --" ) @Html.ValidationMessageFor(x => x.State)  } 

请注意我们如何在DropDownListFor帮助器中提供默认值作为最后一个参数。 这将在开头插入一个带有空值和自定义文本的选项,如果用户没有选择某个状态,则所需的validation器应该启动。

我将@ class =“required”添加到属性中,比如某些人在codeplex http://aspnet.codeplex.com/workitem/7629的线程上说的,它对我来说很好用=)

这是我发现的最简单的方法,只需在视图内的DropDownListFor HtmlAttributes中添加data-val-*-*属性。 以下方法也适用于RemoteValidation,如果您不需要远程validation,只需删除包含data-val-remote-*的元素:

  @Html.DropDownListFor(m => m.yourlistID, (IEnumerable)ViewBag.YourListID, String.Empty, new Dictionary() { { "data-val", "true" }, { "data-val-remote-url", "/Validation/yourremoteval" }, { "data-val-remote-type", "POST" }, { "data-val-remote-additionalfield", "youradditionalfieldtovalidate" } }) 

我希望它可能有所帮助。 最好的祝福!

如果问题是当您选择“空白”选项时,您没有看到validation消息说该字段是必需的,这可能是因为Html Helper如何为“空白”选项生成选项标记。 问题是空值属性。

  

我使用这个单行解决方法来删除value属性,它就像一个魅力!

$('option[value=""]').removeAttr("value");

所有这一切都是从具有空值属性的任何’option’元素中删除value属性。