【发布时间】:2017-08-02 16:43:07
【问题描述】:
当使用 html 助手 CheckBoxFor() 时,可以这样做:
@Html.CheckBoxFor(model => model.active)
这将导致像这样的html代码:
<input class="check-box" id="active" name="active" type="checkbox" value="true" />
<input name="active" type="hidden" value="false" />
我的问题是,我使用的 html/css 模板在复选框字段之后需要一个特定的标签才能工作。 (复选框上的某些 css/jquery 效果需要它)。所以我需要修改 CheckBoxFor() 来生成它:
<input class="check-box" id="active" name="active" type="checkbox" value="true" />
<i class="no-rounded"></i>
<input name="active" type="hidden" value="false" />
我尝试过创建这样的自定义扩展方法:
public static MvcHtmlString CustomCheckboxFor<TModel>(this HtmlHelper<TModel> helper, Expression<Func<TModel, bool>> expression)
{
var data = ModelMetadata.FromLambdaExpression(expression, helper.ViewData);
string propertyName = data.PropertyName;
string s = "";
s += "<input class=\"check-box\" id=\"" + propertyName + "\" name=\"" + propertyName+ "\" type=\"checkbox\" value=\"true\" />";
s += "<i class=\"no-rounded\"></i>";
s += "<input name=\"" + propertyName + "\" type=\"hidden\" value=\"false\" />";
return MvcHtmlString.Create(s.ToString());
并调用它
@Html.CustomCheckboxFor(model => model.active)
这正在绘制复选框,并且 css/jquery 效果正在工作, 但例如在创建或编辑视图时,它没有绑定到模型上的属性(如果属性为真,它应该加载选中复选框的表单,但它不会)
我该怎么做?
更新: 好的,我取得了一些进展,它现在可以工作了,但我敢打赌一定有更好、更优雅的方式来做到这一点......我所做的是让 .net 助手完成为复选框和生成 html 代码的工作隐藏字段。然后我得到了那个字符串,只需在两个字段之间插入所需的标签,然后返回:
public static MvcHtmlString UnifyCheckboxFor<TModel>(this HtmlHelper<TModel> helper, Expression<Func<TModel, bool>> expression)
{
string s = helper.CheckBoxFor(expression).ToString();
string part1 = s.Substring(0,s.IndexOf(">")+1);
string part2 = s.Substring(s.IndexOf(">")+1);
string str = part1 + "<i class=\"no-rounded\"></i>" + part2;
return MvcHtmlString.Create(str.ToString());
}
UPDATE2:@Joshua Duxbury 在 cmets 中提供的信息:如果创建自定义助手,框架不会尝试绑定它,所以我们必须自己对助手进行绑定。因此,初始代码只需添加该逻辑即可:
public static MvcHtmlString CustomCheckboxFor<TModel>(this HtmlHelper<TModel> helper, Expression<Func<TModel, bool>> expression)
{
var data = ModelMetadata.FromLambdaExpression(expression, helper.ViewData);
string propertyName = data.PropertyName;
string s = "";
s += "<input class=\"check-box\" id=\"" + propertyName + "\" name=\"" + propertyName+ "\" type=\"checkbox\" value=\"true\" " + ((data.Model.Equals(true)) ? "checked=\"checked\"" : "") +"/>";
s += "<i class=\"no-rounded\"></i>";
s += "<input name=\"" + propertyName + "\" type=\"hidden\" value=\"false\" />";
return MvcHtmlString.Create(s.ToString());
}
【问题讨论】:
-
你在输入标签上的硬编码
value="true",不应该根据model属性来设置吗? -
如果我了解复选框在 .net mvc 中是如何工作的(我可能是错的),复选框的值应该始终为真,而隐藏的值应该始终为假......(这个是因为 html 复选框只有在提交表单时才会被发送回服务器(如果它们被选中)。这样,当未选中复选框时,隐藏字段仍将发送回服务器,值为 false...
-
是的,我虽然只是通过使复选框的名称与属性的名称相同,.net 会绑定它们......但似乎不是这样,哈哈。
-
不,如果您制作了自定义 HTML 助手,它不会根据名称绑定复选框的值。您需要设置该值。
-
@Joshua Duxbury 好的,这似乎是正确的答案......现在我正在检查模型中的属性是否为真,如果是,请在编写复选框 html 时编写“checked=checked”部分代码。谢谢老兄。
标签: c# asp.net-mvc html-helper