EditorFor HTML助手与淘汰赛
问题描述:
我认为这将是非常有用的扩展版 EditorFor HTML助手,它会自动写出Knockout JS的值数据绑定。EditorFor HTML助手与淘汰赛
这将用于客户端视图模型和服务器端视图模型相同的地方 - 我已经通过使用ko映射并通过AJAX获取视图模型来自动生成客户端视图模型。
有没有其他人尝试过这样的事情,还是有任何项目包括类似于我在这里想的东西?
这样做的好处是,重构时不会有数据绑定值被遗漏的危险。
答
我们已经沿着这些方向做了一些事情,它远非完美,我们在自定义扩展中有更多的东西,但我提取了本质。
using System.Web.Mvc.Html;
namespace System.Web.Mvc
{
public static class EditorForExtensions
{
public static MvcHtmlString TextBoxForViewModel<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TProperty>> expression)
{
ModelMetadata metadata = ModelMetadata.FromLambdaExpression(expression, htmlHelper.ViewData);
var htmlAttributes = HtmlAttributesForKnockout(metadata);
return htmlHelper.TextBoxFor(expression, htmlAttributes);
}
private static Dictionary<string, object> HtmlAttributesForKnockout(ModelMetadata metadata)
{
var htmlAttributes = new Dictionary<string, object>();
var knockoutParameter = String.Format("value: {0}", metadata.PropertyName);
htmlAttributes.Add("data-bind", knockoutParameter);
return htmlAttributes;
}
}
}
这可以被使用,如:
@Html.TextBoxForViewModel(m => m.Name)
答
诚征全国htmlAttributes超载添加到乍得的回答上面的任何人都希望将它放在和它的工作。所有其他的助手都可以很容易地从这些例子中构建。 (谢谢乍得,你的扩展帮助我轻松过渡到使用淘汰赛!)
using System.Collections.Generic;
using System.Linq.Expressions;
using System.Web.Mvc.Html;
namespace System.Web.Mvc {
public static class KnockoutExtensions {
public static MvcHtmlString KnockoutTextBoxFor<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TProperty>> expression) {
var metadata = ModelMetadata.FromLambdaExpression(expression, htmlHelper.ViewData);
var htmlAttributes = HtmlAttributesForKnockout(metadata);
return htmlHelper.TextBoxFor(expression, htmlAttributes);
}
public static MvcHtmlString KnockoutTextBoxFor<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TProperty>> expression, object attributes) {
// convert passed anonymous object (attributes) into IDictionary<string,object> to pass into attribute parser
var attrs = HtmlHelper.AnonymousObjectToHtmlAttributes(attributes) as IDictionary<string, object>;
var metadata = ModelMetadata.FromLambdaExpression(expression, htmlHelper.ViewData);
var htmlAttributes = HtmlAttributesForKnockout(metadata, attrs);
return htmlHelper.TextBoxFor(expression, htmlAttributes);
}
private static Dictionary<string, object> HtmlAttributesForKnockout(ModelMetadata metadata, IEnumerable<KeyValuePair<string, object>> attributes = null) {
var htmlAttributes = new Dictionary<string, object>();
var knockoutParameter = String.Format("value: {0}", metadata.PropertyName);
htmlAttributes.Add("data-bind", knockoutParameter);
if (attributes != null) foreach (var attr in attributes) htmlAttributes.Add(attr.Key, attr.Value);
return htmlAttributes;
}
}
}
你知道关于http://knockoutmvc.com/吗?虽然我听说过它的坏事http://stackoverflow.com/questions/11618042/is-there-a-reason-i-would-use-knockout-mvc-instead-of-knockout-js。然而,你可能会从它偷一些扩展:) – 2013-03-23 23:14:19
我会看看,谢谢 – 2013-03-23 23:32:33
我在MVC3开始了一个类似的项目,但是当我们听说MVC4中带有Knockout集成的单页面应用程序模板时,我们停止对此工作。不幸的是,这并没有实现,我们从未回到项目。现在,我相信该功能正在返回(或已经返回)在SP2中。 – 2013-03-24 12:37:59